* Add tab "General" in Preferences window.
* Add algorithm to update displaying elements depending of settings.
* Update opening file algorithm to activating parts depending of settings.
* Update activating part algorithm to display elements depending of settings.
* Update activating part algorithm to display elements depending of sub elements.
* Update the documentation.
SHAPER preferences contains the following tabs:
+- :ref:`general_preferences`;
- :ref:`visualization_preferences`;
- :ref:`plugins_preferences`;
- :ref:`shortcuts_preferences`;
- :ref:`sketch_preferences`.
- :ref:`viewer_preferences`.
-Visualization tab is activated by default when **Preferences** dialog box is opened in the active SHAPER module.
+General tab is activated by default when **Preferences** dialog box is opened in the active SHAPER module.
Other tabs are activated by click on tab header.
+.. _general_preferences:
+
+General tab
+^^^^^^^^^^^
+
+This tab defines what parts to be activated and what elements to be visible after opening a study or a script.
+
+.. figure:: /images/general_preferences.png
+ :align: center
+
+ **Preferences**: General tab
+
+**Input fields**:
+
+- **Activate** relates to activation of part when opening a HDF document. Its could be one of the following:
+
+ - "Last part" - activate last part in the document (**default value**);
+ - "All parts" - activate all parts within the document;
+ - "No activation" - do not activate any part.
+
+- **Display** in "Opening a study". It specifies the shapes, which should be visualized when activating a part. It could be one of the following:
+
+ - "As stored in HDF" - display only the shapes visible before the document is saved (**default value**);
+ - "Last item in each folder" - show only the last result in each folder of the part: Constructions, Results, Groups, Fields;
+ - "All items" - show all shapes from each folder;
+ - "No visualization" - do not display any shape.
+
+- **Display** in "Launching a python script". It specifies the shapes, which should be visualized when loading a script using "File -> Load Script..." menu. It could be one of the following:
+
+ - "Last item in each folder" - show only the last result in each folder of the part: Constructions, Results, Groups, Fields;
+ - "All items" - show all shapes from each folder(**default value**);
+ - "No visualization" - do not display any shape.
+
.. _visualization_preferences:
Visualization tab
Locale
ModelAPI
ModelGeomAlgo
+ ModuleBase
)
ADD_DEFINITIONS(-DMODELHIGHAPI_EXPORTS -DWNT)
${PROJECT_SOURCE_DIR}/src/Locale
${PROJECT_SOURCE_DIR}/src/ModelAPI
${PROJECT_SOURCE_DIR}/src/ModelGeomAlgo
+ ${PROJECT_SOURCE_DIR}/src/ModuleBase
${PROJECT_SOURCE_DIR}/src/PartSetPlugin
${OpenCASCADE_INCLUDE_DIR}
)
Events_Loop* aLoop = Events_Loop::loop();
aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED));
aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
- //aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
+ aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
//aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_DELETED));
}
#include <ModelAPI_ResultConstruction.h>
#include <ModelAPI_Events.h>
+#include <ModuleBase_Tools.h>
+
#include <cmath>
#include <sstream>
aNbTransactions = aNbUndo;
++aTransactionID;
}
+ static std::string anOperationPrefix(ModuleBase_Tools::translate("", "Operation").toStdString());
std::ostringstream aTransactionName;
- aTransactionName << "Operation_" << aTransactionID;
+ aTransactionName << anOperationPrefix << "_" << aTransactionID;
ModelAPI_Session::get()->startOperation(aTransactionName.str());
}
const QString ModuleBase_Preferences::VIEWER_SECTION = "Viewer";
const QString ModuleBase_Preferences::MENU_SECTION = "Menu";
+const QString ModuleBase_Preferences::GENERAL_SECTION = "General";
SUIT_ResourceMgr* ModuleBase_Preferences::myResourceMgr = 0;
void ModuleBase_Preferences::createEditContent(ModuleBase_IPrefMgr* thePref, int thePage)
{
thePref->prefMgr()->setItemIcon(thePage, QIcon(":pictures/module.png"));
+ createGeneralTab(thePref, thePage);
createCustomPage(thePref, thePage);
}
}
}
+void ModuleBase_Preferences::createGeneralTab(ModuleBase_IPrefMgr* thePref, int thePageId)
+{
+ int generalTab = thePref->addPreference(QObject::tr("General"), thePageId,
+ SUIT_PreferenceMgr::Auto, QString(), QString());
+ thePref->setItemProperty("columns", 2, generalTab);
+
+ QStringList actItemList;
+ actItemList << QObject::tr("Last part")
+ << QObject::tr("All parts")
+ << QObject::tr("No activation");
+
+ QList<QVariant> actIdList;
+ actIdList << 0 << 1 << 2;
+
+ // Group related to opening a study
+ int group = thePref->addPreference(QObject::tr("Opening a study"), generalTab,
+ SUIT_PreferenceMgr::Auto, QString(), QString());
+
+ int actId = thePref->addPreference(QObject::tr("Activate"), group, SUIT_PreferenceMgr::Selector,
+ ModuleBase_Preferences::GENERAL_SECTION,
+ "part_activation_study");
+ thePref->setItemProperty("strings", actItemList, actId);
+ thePref->setItemProperty("indexes", actIdList, actId);
+
+ QStringList visuItemList;
+ visuItemList << QObject::tr("As stored in HDF")
+ << QObject::tr("Last item in each folder")
+ << QObject::tr("All items")
+ << QObject::tr("No visualization");
+
+ QList<QVariant> visuIdList;
+ visuIdList << 0 << 1 << 2 << 3;
+
+ int visuId = thePref->addPreference(QObject::tr("Display"), group, SUIT_PreferenceMgr::Selector,
+ ModuleBase_Preferences::GENERAL_SECTION,
+ "part_visualization_study");
+ thePref->setItemProperty("strings", visuItemList, visuId);
+ thePref->setItemProperty("indexes", visuIdList, visuId);
+
+ // Group related to running a python script
+ group = thePref->addPreference(QObject::tr("Launching a python script"), generalTab,
+ SUIT_PreferenceMgr::Auto, QString(), QString());
+
+ visuItemList.clear();
+ visuItemList << QObject::tr("Last item in each folder")
+ << QObject::tr("All items")
+ << QObject::tr("No visualization");
+
+ visuIdList.clear();
+ visuIdList << 0 << 1 << 2;
+
+ visuId = thePref->addPreference(QObject::tr("Display"), group, SUIT_PreferenceMgr::Selector,
+ ModuleBase_Preferences::GENERAL_SECTION,
+ "part_visualization_script");
+ thePref->setItemProperty("strings", visuItemList, visuId);
+ thePref->setItemProperty("indexes", visuIdList, visuId);
+}
+
void ModuleBase_Preferences::createCustomPage(ModuleBase_IPrefMgr* thePref, int thePageId)
{
SUIT_ResourceMgr* aResMgr = ModuleBase_Preferences::resourceMgr();
/// Name of preferences of menu section
static const QString MENU_SECTION;
+ /// Name of preferences of general section
+ static const QString GENERAL_SECTION;
+
/// Shows a dialog box to edit preferences
/// \param theModified a list of modified preferences
static bool editPreferences(ModuleBase_Prefs& theModified);
/// Set default values to the Config_PropManager properties
static void resetConfig();
+ /// Creates a content for General tab, which defines behavior of loading parts and displaying shapes
+ static void createGeneralTab(ModuleBase_IPrefMgr* thePref, int thePageId);
+
/// Creates content of preferences editing widget
static void createCustomPage(ModuleBase_IPrefMgr* thePref, int thePageId);
#include <ModuleBase_ParamIntSpinBox.h>
#include <ModuleBase_ParamSpinBox.h>
+#include <ModuleBase_Preferences.h>
#include <ModuleBase_WidgetFactory.h>
#include <ModuleBase_IWorkshop.h>
#include <ModuleBase_IModule.h>
#include <ModelAPI_AttributeSelectionList.h>
#include <ModelAPI_AttributeRefList.h>
#include <ModelAPI_AttributeRefAttrList.h>
+#include <ModelAPI_ResultGroup.h>
#include <ModelAPI_ResultPart.h>
#include <ModelAPI_ResultConstruction.h>
#include <ModelAPI_AttributeString.h>
#include <ModelGeomAlgo_Point2D.h>
+#ifdef HAVE_SALOME
+#include <SUIT_Application.h>
+#include <SUIT_ResourceMgr.h>
+#include <SUIT_Session.h>
+#endif
+
#include <StdSelect_BRepOwner.hxx>
#include <TopoDS_Iterator.hxx>
#include <AIS_InteractiveContext.hxx>
//******************************************************************
+ //! Waits for REDISPLAY message and set the Visible flag to the entities
+ //! according to Preferences choice.
+ class ModuleBase_RedisplayListener : public Events_Listener
+ {
+ public:
+ static std::shared_ptr<ModuleBase_RedisplayListener> instance()
+ {
+ static std::shared_ptr<ModuleBase_RedisplayListener>
+ anInstance(new ModuleBase_RedisplayListener);
+ return anInstance;
+ }
+
+ void processEvent(const std::shared_ptr<Events_Message>& theMessage)
+ {
+ if (theMessage->eventID() == Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY))
+ {
+#if HAVE_SALOME
+ // If the python script is being loaded now, the preferences should be used
+ // to display the required object
+ SUIT_Application * app = SUIT_Session::session()->activeApplication();
+ QVariant aVar = app->property("IsLoadedScript");
+ if (!aVar.isNull() && aVar.toBool()) {
+ DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
+ int aSize = aRootDoc->size(ModelAPI_ResultPart::group());
+ if (aSize > 0) {
+ ObjectPtr anPartObject = aRootDoc->object(ModelAPI_ResultPart::group(), aSize - 1);
+ ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(anPartObject);
+ ModuleBase_Tools::setDisplaying(aPart, true);
+ }
+ }
+#endif
+ }
+ }
+
+ private:
+ ModuleBase_RedisplayListener()
+ {
+ Events_Loop::loop()->registerListener(this,
+ Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
+ }
+ };
+
+ static std::shared_ptr<ModuleBase_RedisplayListener>
+ RL = ModuleBase_RedisplayListener::instance();
+
//******************************************************************
void adjustMargins(QWidget* theWidget)
}
+// Set displaying status to every element on group
+static void setDisplayingByLoop(DocumentPtr theDoc, int theSize,
+ std::string theGroup, bool theDisplayFromScript)
+{
+ int aDisplayingId = -1;
+ if (theDisplayFromScript) {
+ aDisplayingId = ModuleBase_Preferences::resourceMgr()->integerValue("General",
+ "part_visualization_script", -1);
+ // Increase ID to prevert using "As stored in HDF"
+ ++aDisplayingId;
+ }
+ else {
+ aDisplayingId = ModuleBase_Preferences::resourceMgr()->integerValue("General",
+ "part_visualization_study", -1);
+
+ // if chosen "As stored in HDF" then don't change displaying
+ if (aDisplayingId == 0)
+ return;
+ }
+
+ for (int anIndex = theSize - 1; anIndex >= 0; --anIndex) {
+ ObjectPtr anObject = theDoc->object(theGroup, anIndex);
+ anObject->setDisplayed((aDisplayingId == 1 && anIndex == theSize - 1) || aDisplayingId == 2);
+ }
+}
+
+void setDisplaying(ResultPartPtr thePart, bool theDisplayFromScript)
+{
+ DocumentPtr aDoc = thePart->partDoc();
+ int aConstructionSize = aDoc->size(ModelAPI_ResultConstruction::group());
+ int aGroupSize = aDoc->size(ModelAPI_ResultGroup::group());
+ int aFieldSize = aDoc->size(ModelAPI_ResultField::group());
+ int aResultSize = aDoc->size(ModelAPI_ResultBody::group());
+ setDisplayingByLoop(aDoc, aConstructionSize,
+ ModelAPI_ResultConstruction::group(), theDisplayFromScript);
+ setDisplayingByLoop(aDoc, aGroupSize, ModelAPI_ResultGroup::group(), theDisplayFromScript);
+ setDisplayingByLoop(aDoc, aFieldSize, ModelAPI_ResultField::group(), theDisplayFromScript);
+ setDisplayingByLoop(aDoc, aResultSize, ModelAPI_ResultBody::group(), theDisplayFromScript);
+}
+
} // namespace ModuleBase_Tools
/// Returns pixel ratio of a screen where main window is displayed
qreal MODULEBASE_EXPORT currentPixelRatio();
+
+/// Set displaying status for elements from part depending on the settings
+/// \param thePart a pointer of part
+void MODULEBASE_EXPORT setDisplaying(std::shared_ptr<ModelAPI_ResultPart> thePart,
+ bool theDisplayFromScript = false);
}
#endif
<source>Replace</source>
<translation>Remplacer</translation>
</message>
- <message>
- <source>Trihedron arrows constant size</source>
- <translation>Flèche trièdre de taille constante</translation>
- </message>
+ <message>
+ <source>Trihedron arrows constant size</source>
+ <translation>Flèche trièdre de taille constante</translation>
+ </message>
<message>
<source>Keep trihedron arrows view size constant</source>
<translation>Maintenir la taille de la vue des flèches trièdres constante</translation>
</message>
+ <message>
+ <source>General</source>
+ <translation>Général</translation>
+ </message>
+ <message>
+ <source>Opening a study</source>
+ <translation>Ouverture d'une étude</translation>
+ </message>
+ <message>
+ <source>Launching a python script</source>
+ <translation>Lancement d'un script python</translation>
+ </message>
+ <message>
+ <source>Activate</source>
+ <translation>Activation</translation>
+ </message>
+ <message>
+ <source>Display</source>
+ <translation>Visualisation</translation>
+ </message>
+ <message>
+ <source>Last part</source>
+ <translation>Dernière pièce</translation>
+ </message>
+ <message>
+ <source>All parts</source>
+ <translation>Toutes les pièces</translation>
+ </message>
+ <message>
+ <source>No activation</source>
+ <translation>Aucune</translation>
+ </message>
+ <message>
+ <source>As stored in HDF</source>
+ <translation>Comme dans le HDF</translation>
+ </message>
+ <message>
+ <source>Last item in each folder</source>
+ <translation>Le dernier élément de chaque dossier</translation>
+ </message>
+ <message>
+ <source>All items</source>
+ <translation>Tous les éléments</translation>
+ </message>
+ <message>
+ <source>No visualization</source>
+ <translation>Aucune visualisation</translation>
+ </message>
</context>
</TS>
#include <XGUI_DataModel.h>
#include <XGUI_OperationMgr.h>
#include <XGUI_ObjectsBrowser.h>
+#include <XGUI_Tools.h>
#include <XGUI_ViewerProxy.h>
#include <Events_Loop.h>
void PartSet_MenuMgr::activatePart(ResultPartPtr thePart) const
{
bool isFirstLoad = !thePart->partDoc().get();
+ ModuleBase_Tools::blockUpdateViewer(true);
thePart->activate();
if (isFirstLoad) {
XGUI_Workshop* aWorkshop = myModule->getWorkshop();
XGUI_ObjectsBrowser* aObjBrowser = aWorkshop->objectBrowser();
+ ModuleBase_Tools::setDisplaying(thePart);
+ Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_TO_REDISPLAY));
+ aObjBrowser->onSelectionChanged();
DocumentPtr aDoc = thePart->partDoc();
std::list<bool> aStates;
aDoc->restoreNodesState(aStates);
aObjBrowser->setStateForDoc(aDoc, aStates);
}
+ ModuleBase_Tools::blockUpdateViewer(false);
}
void PartSet_MenuMgr::onActivateAllParts()
<parameter name="PartSet" value="%SHAPER_ROOT_DIR%/share/salome/resources/shaper"/>
<parameter name="XGUI" value="%SHAPER_ROOT_DIR%/share/salome/resources/shaper"/>
</section>
+ <section name="General">
+ <!-- Common settings of part's activation and visualization -->
+ <parameter name="part_activation_study" value="0"/>
+ <parameter name="part_visualization_study" value="0"/>
+ <parameter name="part_visualization_script" value="1"/>
+ </section>
<section name="Viewer" >
<!-- Viewer preferences -->
<parameter name="face-selection" value="true" />
<parameter name="language" value="en"/>
<parameter name="locale" value="true"/>
</section>
+ <section name="General">
+ <!-- Common settings of part's activation and visualization -->
+ <parameter name="part_activation_study" value="0"/>
+ <parameter name="part_visualization_study" value="0"/>
+ <parameter name="part_visualization_script" value="1"/>
+ </section>
<section name="Viewer" >
<!-- Viewer preferences -->
<parameter name="background" value="bt=2;fn=;tm=0;ts=false;c1=#cddbff;c2=#698fff;gt=1;gr=" />
}
#endif
+ int anActivationId =
+ ModuleBase_Preferences::resourceMgr()->integerValue("General", "part_activation_study", -1);
+ int aSize = aRootDoc->size(ModelAPI_ResultPart::group());
+
+ if (anActivationId == 0 && aSize > 0) {
+ ObjectPtr anObject = aRootDoc->object(ModelAPI_ResultPart::group(), aSize - 1);
+ ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(anObject);
+ if (aPart.get()) {
+ aPart->activate();
+ ModuleBase_Tools::setDisplaying(aPart);
+ }
+ }
+ else if (anActivationId == 1) {
+ for (int anIndex = 0; anIndex < aSize; ++anIndex) {
+ ObjectPtr anObject = aRootDoc->object(ModelAPI_ResultPart::group(), anIndex);
+ ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(anObject);
+ if (aPart.get()) {
+ aPart->activate();
+ ModuleBase_Tools::setDisplaying(aPart);
+
+ if (anIndex < aSize - 1) {
+ SessionPtr aMgr = ModelAPI_Session::get();
+ aMgr->startOperation("Activation");
+ aMgr->setActiveDocument(aMgr->moduleDocument());
+ aMgr->finishOperation();
+ updateCommandStatus();
+ viewer()->update();
+ }
+ }
+ }
+ }
QApplication::restoreOverrideCursor();
}
#include <ModuleBase_Tools.h>
#include <ModuleBase_WidgetSelector.h>
+#ifdef HAVE_SALOME
+#include <SUIT_Application.h>
+#include <SUIT_Session.h>
+#endif
+
#include "XGUI_ActionsMgr.h"
#include "XGUI_Displayer.h"
#include "XGUI_ErrorMgr.h"
#include "XGUI_OperationMgr.h"
#include "XGUI_ModuleConnector.h"
#include "XGUI_PropertyPanel.h"
-
#include "XGUI_QtEvents.h"
#include "XGUI_SalomeConnector.h"
#include "XGUI_SelectionMgr.h"
}
}
}
+
// this processing should be moved in another place in order to do not cause problems in
// flush messages chain
//if (aHiddenObjects.size() > 0)
void XGUI_WorkshopListener::
onFeatureCreatedMsg(const std::shared_ptr<ModelAPI_ObjectUpdatedMessage>& theMsg)
{
+ SUIT_Application * app = SUIT_Session::session()->activeApplication();
+
+ QVariant aVar = app->property("IsLoadedScript");
+
std::set<ObjectPtr> anObjects = theMsg->objects();
std::set<ObjectPtr>::const_iterator aIt;
#ifdef DEBUG_FEATURE_CREATED
//bool aHasPart = false;
bool aDisplayed = false;
- for (aIt = anObjects.begin(); aIt != anObjects.end(); ++aIt) {
- ObjectPtr anObject = *aIt;
+ if (aVar.isNull() || !aVar.toBool()) {
+ for (aIt = anObjects.begin(); aIt != anObjects.end(); ++aIt) {
+ ObjectPtr anObject = *aIt;
#ifdef DEBUG_RESULT_COMPSOLID
- ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(anObject);
- if (aRes.get()) {
- ResultCompSolidPtr aCompSolidRes = std::dynamic_pointer_cast<ModelAPI_ResultCompSolid>(aRes);
- if (aCompSolidRes.get()) {
- qDebug(QString("COMPSOLID, numberOfSubs = %1")
- .arg(aCompSolidRes->numberOfSubs()).toStdString().c_str());
+ ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(anObject);
+ if (aRes.get()) {
+ ResultCompSolidPtr aCompSolidRes = std::dynamic_pointer_cast<ModelAPI_ResultCompSolid>(aRes);
+ if (aCompSolidRes.get()) {
+ qDebug(QString("COMPSOLID, numberOfSubs = %1")
+ .arg(aCompSolidRes->numberOfSubs()).toStdString().c_str());
+ }
+ if (ModelAPI_Tools::compSolidOwner(aRes))
+ qDebug("COMPSOLID sub-object");
}
- if (ModelAPI_Tools::compSolidOwner(aRes))
- qDebug("COMPSOLID sub-object");
- }
#endif
- // the validity of the data should be checked here in order to avoid display of the objects,
- // which were created, then deleted, but flush for the creation event happens after that
- // we should not display disabled objects
- bool aHide = !anObject->data()->isValid() ||
- anObject->isDisabled() ||
- !anObject->isDisplayed();
- if (!aHide) { // check that this is not hidden result
- ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(anObject);
- aHide = aRes && aRes->isConcealed();
- // Hide the presentation with an empty shape. But isDisplayed state of the object should not
- // be changed to the object becomes visible when the shape becomes not empty
- if (!aHide && aRes.get())
- aHide = !aRes->shape().get() || aRes->shape()->isNull();
- }
- if (!aHide) {
- // setDisplayed has to be called in order to synchronize internal state of the object
- // with list of displayed objects
- if (myWorkshop->module()->canDisplayObject(anObject)) {
- anObject->setDisplayed(true);
- aDisplayed = displayObject(anObject);
- } else
- anObject->setDisplayed(false);
+
+ ResultBodyPtr aRes = std::dynamic_pointer_cast<ModelAPI_ResultBody>(anObject);
+
+ if (aRes.get() && aRes->numberOfSubs() > 0)
+ for (int anIndex = 0; anIndex < aRes->numberOfSubs(); ++anIndex)
+ setDisplayed(aRes->subResult(anIndex), aDisplayed);
+ else
+ setDisplayed(anObject, aDisplayed);
}
}
-
MAYBE_UNUSED bool isCustomized = customizeFeature(anObjects, aDisplayed);
//if (myObjectBrowser)
{
return myWorkshop;
}
+
+
+void XGUI_WorkshopListener::setDisplayed(ObjectPtr theObject, bool& theDisplayed)
+{
+ // the validity of the data should be checked here in order to avoid display of the objects,
+ // which were created, then deleted, but flush for the creation event happens after that
+ // we should not display disabled objects
+ bool aHide = !theObject->data()->isValid() ||
+ theObject->isDisabled() ||
+ !theObject->isDisplayed();
+ if (!aHide) { // check that this is not hidden result
+ ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(theObject);
+ aHide = aRes && aRes->isConcealed();
+ // Hide the presentation with an empty shape. But isDisplayed state of the object should not
+ // be changed to the object becomes visible when the shape becomes not empty
+ if (!aHide && aRes.get())
+ aHide = !aRes->shape().get() || aRes->shape()->isNull();
+ }
+ if (!aHide) {
+ // setDisplayed has to be called in order to synchronize internal state of the object
+ // with list of displayed objects
+ if (myWorkshop->module()->canDisplayObject(theObject)) {
+ theObject->setDisplayed(true);
+ theDisplayed = displayObject(theObject);
+ }
+ else
+ theObject->setDisplayed(false);
+ }
+}
XGUI_Workshop* workshop() const;
private:
+
+ void setDisplayed(ObjectPtr theObject, bool& theDisplayed);
+
XGUI_Workshop* myWorkshop; // the current workshop
bool myUpdatePrefs;