MESSAGE(STATUS "FWOS " ${CAS_FWOSPlugin})
FIND_LIBRARY(CAS_PTKernel PTKernel )
-FIND_LIBRARY(CAS_TKAdvTools TKAdvTools )
FIND_LIBRARY(CAS_TKBin TKBin )
FIND_LIBRARY(CAS_TKBinL TKBinL )
FIND_LIBRARY(CAS_TKBinTObj TKBinTObj )
REQUIRED_VARS CAS_INCLUDE_DIRS
CAS_FWOSPlugin
CAS_PTKernel
- CAS_TKAdvTools
CAS_TKBin
CAS_TKBinL
CAS_TKBinTObj
ADD_SUBDIRECTORY (src/GeomApp)
ADD_SUBDIRECTORY (src/ExchangePlugin)
ADD_SUBDIRECTORY (src/GeomValidators)
+ADD_SUBDIRECTORY (src/ConnectorPlugin)
+
IF(${HAVE_SALOME})
ADD_SUBDIRECTORY (src/NewGeom)
@SET NEW_GEOM_CONFIG_FILE=%ROOT_DIR%\install\plugins
@SET PATH=%ROOT_DIR%\install\plugins;%ROOT_DIR%\install\bin;%PATH%
-@SET PYTHONPATH=%ROOT_DIR%\install\swig;%PYTHONPATH%
+@SET PYTHONPATH=%ROOT_DIR%\install\swig;%ROOT_DIR%\install\plugins;%PYTHONPATH%
@SET LightAppConfig=%ROOT_DIR%\install\share\salome\resources\newgeom;%GUI_ROOT_DIR%\share\salome\resources\gui
@SET NewGeomResources=%ROOT_DIR%\install\resources
#------ NewGEOM ------
export NEWGEOM_ROOT_DIR=${ROOT_DIR}/install
export PATH=${NEWGEOM_ROOT_DIR}/bin:${NEWGEOM_ROOT_DIR}/plugins:${PATH}
-export PYTHONPATH=${NEWGEOM_ROOT_DIR}/swig:${PYTHONPATH}
+export PYTHONPATH=${NEWGEOM_ROOT_DIR}/swig:${NEWGEOM_ROOT_DIR}/plugins:${PYTHONPATH}
export LD_LIBRARY_PATH=${NEWGEOM_ROOT_DIR}/bin:${NEWGEOM_ROOT_DIR}/swig:${NEWGEOM_ROOT_DIR}/plugins:${LD_LIBRARY_PATH}
export NEW_GEOM_CONFIG_FILE=${NEWGEOM_ROOT_DIR}/plugins
export NewGeomResources=${NEWGEOM_ROOT_DIR}/resources
+
@REM -------------------------
@REM QT
@SET QTDIR=%PDIR%\qt-4.8.4
-@ECHO -- Creating qt.conf...
+@ECHO -- Creating qt.conf... in %QTDIR%
@ECHO [Paths] > %QTDIR%/bin/qt.conf
@ECHO Prefix = %QTDIR:\=/% >> %QTDIR%/bin/qt.conf
@SET PATH=%QTDIR%\bin;%PATH%
@SET NEW_GEOM_CONFIG_FILE=%ROOT_DIR%\install\plugins
@SET PATH=%ROOT_DIR%\install\plugins;%ROOT_DIR%\install\bin;%PATH%
-@SET PYTHONPATH=%ROOT_DIR%\install\swig;%PYTHONPATH%
+@SET PYTHONPATH=%ROOT_DIR%\install\swig;%ROOT_DIR%\install\plugins;%PYTHONPATH%
@REM -------------------------
@REM PTHREAD
INCLUDE(Common)
INCLUDE(XMLProcessing)
-INCLUDE_DIRECTORIES (${PROJECT_SOURCE_DIR}/src/Events)
+INCLUDE_DIRECTORIES (${PROJECT_SOURCE_DIR}/src/Events
+ ${PYTHON_INCLUDE_DIRS})
SET(PROJECT_HEADERS
Config_def.h
SET(PROJECT_LIBRARIES
Events
${LIBXML2_LIBRARIES}
+ ${PYTHON_LIBRARIES}
)
SOURCE_GROUP ("Resource Files" FILES ${XML_RESOURCES})
\r
bool isElementNode(xmlNodePtr theNode)\r
{\r
+ if (!theNode)\r
+ return false;\r
return theNode->type == XML_ELEMENT_NODE;\r
}\r
\r
/*
* Hardcoded xml entities of plugins.xml
*/
+
+const static char* PLUGIN_FILE = "plugins.xml";
const static char* NODE_PLUGIN = "plugin";
const static char* NODE_PLUGINS = "plugins";
const static char* PLUGINS_MODULE = "module";
const static char* PLUGIN_CONFIG = "configuration";
const static char* PLUGIN_LIBRARY = "library";
+const static char* PLUGIN_SCRIPT = "script";
#endif /* CONFIG_KEYWORDS_H_ */
#include <libxml/parser.h>
#include <libxml/tree.h>
+// Have to be included before std headers
+#include <Python.h>
+
//Necessary for cerr
#include <iostream>
#include <dlfcn.h>
#endif
+std::map<std::string, Config_ModuleReader::PluginType> Config_ModuleReader::myPluginTypes;
+
Config_ModuleReader::Config_ModuleReader(const char* theEventGenerated)
- : Config_XMLReader("plugins.xml"),
+ : Config_XMLReader(PLUGIN_FILE),
myEventGenerated(theEventGenerated)
{
}
if (isNode(theNode, NODE_PLUGIN, NULL)) {
std::string aPluginConf = getProperty(theNode, PLUGIN_CONFIG);
std::string aPluginLibrary = getProperty(theNode, PLUGIN_LIBRARY);
- std::list<std::string> aFeatures = importPlugin(aPluginLibrary, aPluginConf);
+ std::string aPluginScript = getProperty(theNode, PLUGIN_SCRIPT);
+ std::string aPluginName = addPlugin(aPluginLibrary, aPluginScript, aPluginConf);
+
+ std::list<std::string> aFeatures = importPlugin(aPluginName, aPluginConf);
std::list<std::string>::iterator it = aFeatures.begin();
for (; it != aFeatures.end(); it++) {
myFeaturesInFiles[*it] = aPluginConf;
}
std::list<std::string> Config_ModuleReader::importPlugin(const std::string& thePluginLibrary,
- const std::string& thePluginFile)
+ const std::string& thePluginXmlConf)
{
- if (thePluginFile.empty()) { //probably a third party library
+ if (thePluginXmlConf.empty()) { //probably a third party library
loadLibrary(thePluginLibrary);
return std::list<std::string>();
}
- Config_FeatureReader aReader = Config_FeatureReader(thePluginFile, thePluginLibrary,
+ Config_FeatureReader aReader = Config_FeatureReader(thePluginXmlConf,
+ thePluginLibrary,
myEventGenerated);
aReader.readAll();
return aReader.features();
}
+std::string Config_ModuleReader::addPlugin(const std::string& aPluginLibrary,
+ const std::string& aPluginScript,
+ const std::string& aPluginConf)
+{
+ PluginType aType = Config_ModuleReader::Binary;
+ std::string aPluginName;
+ if (!aPluginLibrary.empty()) {
+ aPluginName = aPluginLibrary;
+ if (aPluginConf.empty()) {
+ aType = Config_ModuleReader::Intrenal;
+ }
+ } else if (!aPluginScript.empty()) {
+ aPluginName = aPluginScript;
+ aType = Config_ModuleReader::Python;
+ }
+ if(!aPluginName.empty()) {
+ myPluginTypes[aPluginName] = aType;
+
+ }
+ return aPluginName;
+}
+
+void Config_ModuleReader::loadPlugin(const std::string thePluginName)
+{
+ PluginType aType = Config_ModuleReader::Binary;
+ if(myPluginTypes.find(thePluginName) != myPluginTypes.end()) {
+ aType = myPluginTypes.at(thePluginName);
+ }
+ switch (aType) {
+ case Config_ModuleReader::Python:
+ loadScript(thePluginName);
+ break;
+ case Config_ModuleReader::Binary:
+ case Config_ModuleReader::Intrenal:
+ default:
+ loadLibrary(thePluginName);
+ break;
+ }
+}
+
+void Config_ModuleReader::loadScript(const std::string theFileName)
+{
+ /* aquire python thread */
+ PyGILState_STATE gstate = PyGILState_Ensure();
+ PyObject* module = PyImport_ImportModule(theFileName.c_str());
+
+ if (!module) {
+ std::string anErrorMsg = "An error occured while importing " + theFileName;
+ //Get detailed error message:
+ if (PyErr_Occurred()) {
+ PyObject *ptype, *pvalue, *ptraceback;
+ PyErr_Fetch(&ptype, &pvalue, &ptraceback);
+ std::string aPyError = std::string(PyString_AsString(pvalue));
+ if (!aPyError.empty()) {
+ anErrorMsg += ":\n" + aPyError;
+ }
+ Py_XDECREF(ptype);
+ Py_XDECREF(pvalue);
+ Py_XDECREF(ptraceback);
+ }
+ Events_Error::send(anErrorMsg);
+ }
+
+ /* release python thread */
+ PyGILState_Release(gstate);
+}
+
void Config_ModuleReader::loadLibrary(const std::string theLibName)
{
std::string aFileName = library(theLibName);
#ifdef WIN32
HINSTANCE aModLib = ::LoadLibrary(aFileName.c_str());
- if (!aModLib && theLibName != "DFBrowser") { // don't shor error for internal debugging tool
- std::string errorMsg = "Failed to load " + aFileName;
- std::cerr << errorMsg << std::endl;
- Events_Error::send(errorMsg);
- }
#else
void* aModLib = dlopen( aFileName.c_str(), RTLD_LAZY | RTLD_GLOBAL );
- if ( !aModLib && theLibName != "DFBrowser") { // don't shor error for internal debugging tool
- std::cerr << "Failed to load " << aFileName.c_str() << std::endl;
- }
#endif
+ if(!aModLib && theLibName != "DFBrowser") { // don't show error for internal debugging tool
+ std::string anErrorMsg = "Failed to load " + aFileName;
+ #ifndef WIN32
+ anErrorMsg += ": " + std::string(dlerror());
+ #endif
+ Events_Error::send(anErrorMsg);
+ }
}
class Config_ModuleReader : public Config_XMLReader
{
+ enum PluginType {
+ Binary = 0,
+ Intrenal = 1,
+ Python = 2
+ };
public:
CONFIG_EXPORT Config_ModuleReader(const char* theEventGenerated = 0);
CONFIG_EXPORT std::string getModuleName();
+ CONFIG_EXPORT static void loadPlugin(const std::string thePluginName);
/// loads the library with specific name, appends "lib*.dll" or "*.so" depending on the platform
CONFIG_EXPORT static void loadLibrary(const std::string theLibName);
+ /// loads the python module with specified name
+ CONFIG_EXPORT static void loadScript(const std::string theFileName);
protected:
void processNode(xmlNodePtr aNode);
std::list<std::string> importPlugin(const std::string& thePluginLibrary,
const std::string& thePluginFile);
+ std::string addPlugin(const std::string& aPluginLibrary,
+ const std::string& aPluginScript,
+ const std::string& aPluginConf);
private:
std::map<std::string, std::string> myFeaturesInFiles;
+ static std::map<std::string, PluginType> myPluginTypes;
const char* myEventGenerated;
};
{
if (myCurrentNode && hasChild(myCurrentNode)) {
myCurrentNode = myCurrentNode->children;
- while (!isElementNode(myCurrentNode)) {
+ while (myCurrentNode && !isElementNode(myCurrentNode)) {
myCurrentNode = myCurrentNode->next;
}
- return true;
+ return myCurrentNode != NULL;
}
return false;
}
<plugin library="ConstructionPlugin" configuration="plugin-Construction.xml"/>
<plugin library="FeaturesPlugin" configuration="plugin-Features.xml"/>
<plugin library="ExchangePlugin" configuration="plugin-Exchange.xml"/>
+ <plugin script="ConnectorPlugin" configuration="plugin-Connector.xml"/>
<plugin library="SketchSolver"/>
<plugin library="GeomValidators"/>
- <plugin library="DFBrowser"/>
+ <plugin library="DFBrowser" internal="true"/>
</plugins>
--- /dev/null
+INCLUDE(Common)
+
+SET(PYTHON_FILES
+ ConnectorPlugin.py
+ ConnectorPlugin_ExportFeature.py
+)
+
+SET(XML_RESSOURCES
+ plugin-Connector.xml
+)
+
+ADD_CUSTOM_TARGET(ConnectorPlugin SOURCES ${PYTHON_FILES} ${XML_RESSOURCES})
+
+INSTALL(FILES ${PYTHON_FILES} ${XML_RESSOURCES} DESTINATION plugins)
--- /dev/null
+"""
+Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+"""
+
+import ModelAPI
+
+from ConnectorPlugin_ExportFeature import ExportFeature
+
+
+class ConnectorPlugin(ModelAPI.ModelAPI_Plugin):
+
+ def __init__(self):
+ ModelAPI.ModelAPI_Plugin.__init__(self)
+ pass
+
+ def createFeature(self, theFeatureID):
+ if theFeatureID == ExportFeature.ID():
+ return ExportFeature().__disown__()
+ else:
+ print "ConnectorPlugin: No such feature %s" % theFeatureID
+
+plugin = ConnectorPlugin()
+aSession = ModelAPI.ModelAPI_Session.get()
+print "Module loaded. Session", aSession
+aSession.registerPlugin(plugin)
--- /dev/null
+"""
+Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+"""
+
+import ModelAPI
+import salome
+from salome.geom import geomBuilder
+
+
+class ExportFeature(ModelAPI.ModelAPI_Feature):
+
+ "Feature to create a box by drawing a sketch and extruding it"
+
+ def __init__(self):
+ ModelAPI.ModelAPI_Feature.__init__(self)
+
+ @staticmethod
+ def ID():
+ return "ExportToGEOM"
+
+ def getKind(self):
+ return ExportFeature.ID()
+
+ # This feature is action: has no property pannel and executes immideately
+ def isAction(self):
+ return True
+
+ def initAttributes(self):
+ # This feature has no attributes, but should perfore some actions on initialization
+ aSession = ModelAPI.ModelAPI_Session.get()
+ aPart = aSession.activeDocument()
+ # Get all bodies
+ kResultBodyType = "ResultBody"
+ aPartSize = aPart.size(kResultBodyType)
+ if aPartSize == 0:
+ print "No results in the active document"
+ return
+
+ aResultList = [aPart.object(kResultBodyType, idx) for idx in xrange(aPartSize)]
+ for idx, aResult in enumerate(aResultList):
+ aBodyResult = modelAPI_ResultBody(aResult)
+ if not aBodyResult:
+ continue
+ aShape = aBodyResult.shape()
+ aDump = aShape.getShapeStream()
+ # Load shape to SALOME Geom
+ geompy = geomBuilder.New(salome.myStudy)
+ aBrep = geompy.RestoreShape(aDump)
+ geompy.addToStudy(aBrep, "NewGeomShape_{0}".format(idx))
+
+ def execute(self):
+ # Nothing to execute: all logic would be in the initAttributes
+ pass
+
+# TEST
+"""
+if __name__=='__main__':
+ session = ModelAPI.ModelAPI_Session.get()
+ part = session.activeDocument()
+ session.startOperation()
+ feature = part.addFeature('Box')
+ feature.real('box_width').setValue(10)
+ feature.real('box_length').setValue(10)
+ feature.real('box_height').setValue(10)
+ feature.execute()
+ session.finishOperation()
+"""
--- /dev/null
+#=========================================================================
+# Creation of the circular Sketch, then Extrusion (cylinder),
+# then export to the old GEOM and usage of SMESH for meshing.
+# Based on SALOME 7.4.0 and NewGEOM version: master 18Dec2014.
+#=========================================================================
+from ModelAPI import *
+from GeomDataAPI import *
+from GeomAlgoAPI import *
+from GeomAPI import *
+
+aSession = ModelAPI_Session.get()
+aDocument = aSession.moduleDocument()
+
+# Create a part for extrusion
+aSession.startOperation()
+aPartFeature = aDocument.addFeature("Part")
+aSession.finishOperation()
+
+aPartResult = modelAPI_ResultPart(aPartFeature.firstResult())
+aPart = aPartResult.partDoc()
+
+#=========================================================================
+# Create a sketch circle to extrude
+#=========================================================================
+aSession.startOperation()
+aSketchFeature = modelAPI_CompositeFeature(aPart.addFeature("Sketch"))
+origin = geomDataAPI_Point(aSketchFeature.attribute("Origin"))
+origin.setValue(0, 0, 0)
+dirx = geomDataAPI_Dir(aSketchFeature.attribute("DirX"))
+dirx.setValue(1, 0, 0)
+diry = geomDataAPI_Dir(aSketchFeature.attribute("DirY"))
+diry.setValue(0, 1, 0)
+norm = geomDataAPI_Dir(aSketchFeature.attribute("Norm"))
+norm.setValue(0, 0, 1)
+# Create circle
+aSketchCircle = aSketchFeature.addFeature("SketchCircle")
+anCircleCentr = geomDataAPI_Point2D(aSketchCircle.attribute("CircleCenter"))
+aCircleRadius = aSketchCircle.real("CircleRadius")
+anCircleCentr.setValue(50., 50)
+aCircleRadius.setValue(20.)
+aSession.finishOperation()
+
+#=========================================================================
+# Make extrusion on circle
+#=========================================================================
+# Build shape from sketcher results
+aSketchResult = aSketchFeature.firstResult()
+aSketchEdges = modelAPI_ResultConstruction(aSketchResult).shape()
+origin = geomDataAPI_Point(aSketchFeature.attribute("Origin")).pnt()
+dirX = geomDataAPI_Dir(aSketchFeature.attribute("DirX")).dir()
+dirY = geomDataAPI_Dir(aSketchFeature.attribute("DirY")).dir()
+norm = geomDataAPI_Dir(aSketchFeature.attribute("Norm")).dir()
+aSketchFaces = ShapeList()
+GeomAlgoAPI_SketchBuilder.createFaces(
+ origin, dirX, dirY, norm, aSketchEdges, aSketchFaces)
+
+# Create extrusion
+anExtrusionFt = aPart.addFeature("Extrusion")
+anExtrusionFt.selection("extrusion_face").setValue(
+ aSketchResult, aSketchFaces[0])
+anExtrusionFt.real("extrusion_size").setValue(50)
+anExtrusionFt.boolean("extrusion_reverse").setValue(False)
+anExtrusionFt.execute()
+aSession.finishOperation()
+
+# Check extrusion results
+anExtrusionResult = modelAPI_ResultBody(anExtrusionFt.firstResult())
+
+#==================================================
+# Transfer shape to Geom module of Salome
+#==================================================
+aShape = anExtrusionResult.shape()
+aDump = aShape.getShapeStream()
+
+# Load shape to SALOME Geom
+import salome
+from salome.geom import geomBuilder
+geompy = geomBuilder.New(salome.myStudy)
+aBrep = geompy.RestoreShape(aDump)
+geompy.addToStudy(aBrep, "NewGeomShape")
+
+# Meshing of the Shape
+from salome.smesh import smeshBuilder
+meshpy = smeshBuilder.New(salome.myStudy)
+aMesh = meshpy.Mesh(aBrep)
+Regular_1D = aMesh.Segment()
+Max_Size_1 = Regular_1D.MaxSize(5)
+MEFISTO_2D = aMesh.Triangle(algo=smeshBuilder.MEFISTO)
+isDone = aMesh.Compute()
+assert (isDone)
+meshpy.SetName(aMesh.GetMesh(), 'NewGeomMesh')
+
--- /dev/null
+<plugin>
+ <workbench id="Features" document="Part">
+ <group id="Exchange">
+ <feature
+ id="ExportToGEOM"
+ title="Export to GEOM"
+ tooltip="Exports all data in GEOM compatible format"
+ icon=":pictures/part_ico.png">
+ </feature>
+ </group>
+ </workbench>
+</plugin>
\ No newline at end of file
virtual FeaturePtr createFeature(std::string theFeatureID);
public:
- /// Is needed for python wrapping by swig
ConstructionPlugin_Plugin();
};
std::shared_ptr<Events_Message> aGroup = aMyGroup->second;
myGroups.erase(aMyGroup);
send(aGroup, false);
+
if (!aWasFlushed)
myFlushed.erase(myFlushed.find(theID.myID));
}
virtual FeaturePtr createFeature(std::string theFeatureID);
public:
- /// Is needed for python wrapping by swig
ExchangePlugin_Plugin();
};
virtual FeaturePtr createFeature(std::string theFeatureID);
public:
- /// Is needed for python wrapping by swig
FeaturesPlugin_Plugin();
};
ADD_DEFINITIONS(-DGEOMAPI_EXPORTS ${CAS_DEFINITIONS})
ADD_LIBRARY(GeomAPI SHARED ${PROJECT_SOURCES} ${PROJECT_HEADERS})
-SET(CMAKE_SWIG_FLAGS "")
+SET(CMAKE_SWIG_FLAGS -threads -Wall)
SET_SOURCE_FILES_PROPERTIES(GeomAPI.i PROPERTIES CPLUSPLUS ON)
SET_SOURCE_FILES_PROPERTIES(GeomAPI.i PROPERTIES SWIG_DEFINITIONS "-shadow")
ADD_DEFINITIONS(-DGEOMALGOAPI_EXPORTS ${CAS_DEFINITIONS})
ADD_LIBRARY(GeomAlgoAPI SHARED ${PROJECT_SOURCES} ${PROJECT_HEADERS})
-SET(CMAKE_SWIG_FLAGS "")
+SET(CMAKE_SWIG_FLAGS "-Wall")
SET_SOURCE_FILES_PROPERTIES(GeomAlgoAPI.i PROPERTIES CPLUSPLUS ON)
SET_SOURCE_FILES_PROPERTIES(GeomAlgoAPI.i PROPERTIES SWIG_DEFINITIONS "-shadow")
GeomDataAPI_Point2D.h
)
-SET(CMAKE_SWIG_FLAGS "")
+SET(CMAKE_SWIG_FLAGS "-Wall")
SET_SOURCE_FILES_PROPERTIES(GeomDataAPI.i PROPERTIES CPLUSPLUS ON)
SET_SOURCE_FILES_PROPERTIES(GeomDataAPI.i PROPERTIES SWIG_DEFINITIONS "-shadow")
FeaturePtr Model_Session::createFeature(string theFeatureID)
{
- if (this != myImpl)
+ if (this != myImpl) {
return myImpl->createFeature(theFeatureID);
+ }
// load all information about plugins, features and attributes
LoadPluginsInfo();
myCurrentPluginName = aPlugin.first;
if (myPluginObjs.find(myCurrentPluginName) == myPluginObjs.end()) {
// load plugin library if not yet done
- Config_ModuleReader::loadLibrary(myCurrentPluginName);
+ Config_ModuleReader::loadPlugin(myCurrentPluginName);
}
if (myPluginObjs.find(myCurrentPluginName) != myPluginObjs.end()) {
FeaturePtr aCreated = myPluginObjs[myCurrentPluginName]->createFeature(theFeatureID);
std::set<ObjectPtr>::const_iterator anObjIter = anObjs.cbegin();
for(; anObjIter != anObjs.cend(); anObjIter++) {
myJustCreatedOrUpdated.insert(*anObjIter);
+ // TODO(mpv): check the next line. Came into dev 0.6.1 from BR_PYTHON_PLUGIN
+ // (*anObjIter)->data()->mustBeUpdated(true); // object must be updated because it was changed
}
if (theMessage->eventID() == kMovedEvent)
return; // this event is for solver update, not here
} else { // for automatically updated features (on abort, etc) it is necessary to redisplay anyway
redisplayWithResults(theFeature, ModelAPI_StateNothing);
}
- } else { // returns also true is results were updated: for sketch that refers to sub-features but results of sub-features were changed
+ } else {
+ // returns also true is results were updated: for sketch that
+ // refers to sub-features but results of sub-features were changed
const std::list<std::shared_ptr<ModelAPI_Result> >& aResults = theFeature->results();
std::list<std::shared_ptr<ModelAPI_Result> >::const_iterator aRIter = aResults.begin();
for (; aRIter != aResults.cend(); aRIter++) {
SET(PROJECT_LIBRARIES
Config
)
-
+SET(CMAKE_SWIG_FLAGS -threads -Wall)
ADD_DEFINITIONS(-DMODELAPI_EXPORTS)
+
ADD_LIBRARY(ModelAPI SHARED ${PROJECT_SOURCES} ${PROJECT_HEADERS})
SET_TARGET_PROPERTIES(ModelAPI PROPERTIES LINKER_LANGUAGE CXX)
TARGET_LINK_LIBRARIES(ModelAPI ${PROJECT_LIBRARIES})
../GeomAlgoAPI
)
-SET(CMAKE_SWIG_FLAGS "")
SET_SOURCE_FILES_PROPERTIES(ModelAPI.i PROPERTIES CPLUSPLUS ON)
# "-includeall" is not needed: it starts to follow the standard inludes (like "string") without success
/* ModelAPI.i */
-%module ModelAPI
+%module(directors="1") ModelAPI
+%feature("director:except") {
+ if ($error != NULL) {
+ PyErr_Print();
+ std::cerr << std::endl;
+ throw Swig::DirectorMethodException();
+ }
+}
+
%{
#include "GeomAPI_Interface.h"
#include "GeomAPI_Shape.h"
#include "ModelAPI_Session.h"
#include "ModelAPI_Object.h"
#include "ModelAPI_Feature.h"
+ #include "ModelAPI_Plugin.h"
#include "ModelAPI_CompositeFeature.h"
#include "ModelAPI_Data.h"
#include "ModelAPI_Attribute.h"
%include "std_list.i"
%include "std_shared_ptr.i"
+// directors
+%feature("director") ModelAPI_Plugin;
+%feature("director") ModelAPI_Object;
+%feature("director") ModelAPI_Feature;
+
// shared pointers
// For ModelAPI_ResultConstruction.shape()
%shared_ptr(GeomAPI_Interface)
%shared_ptr(GeomAPI_Shape)
%shared_ptr(ModelAPI_Document)
%shared_ptr(ModelAPI_Session)
+%shared_ptr(ModelAPI_Plugin)
%shared_ptr(ModelAPI_Object)
%shared_ptr(ModelAPI_Feature)
%shared_ptr(ModelAPI_CompositeFeature)
%include "GeomAPI_Shape.h"
%include "ModelAPI_Document.h"
%include "ModelAPI_Session.h"
+%include "ModelAPI_Plugin.h"
%include "ModelAPI_Object.h"
%include "ModelAPI_Feature.h"
%include "ModelAPI_CompositeFeature.h"
%include "ModelAPI_ResultParameters.h"
%include "ModelAPI_Tools.h"
+// std::list -> []
%template(ObjectList) std::list<std::shared_ptr<ModelAPI_Object> >;
%template(ResultList) std::list<std::shared_ptr<ModelAPI_Result> >;
%template(DocumentList) std::list<std::shared_ptr<ModelAPI_Document> >;
+// std::dynamic_pointer_cast
template<class T1, class T2> std::shared_ptr<T1> shared_ptr_cast(std::shared_ptr<T2> theObject);
%template(modelAPI_CompositeFeature) shared_ptr_cast<ModelAPI_CompositeFeature, ModelAPI_Feature>;
%template(modelAPI_Feature) shared_ptr_cast<ModelAPI_Feature, ModelAPI_Object>;
+
+%template(modelAPI_Result) shared_ptr_cast<ModelAPI_Result, ModelAPI_Object>;
%template(modelAPI_ResultConstruction) shared_ptr_cast<ModelAPI_ResultConstruction, ModelAPI_Result>;
%template(modelAPI_ResultBody) shared_ptr_cast<ModelAPI_ResultBody, ModelAPI_Result>;
%template(modelAPI_ResultPart) shared_ptr_cast<ModelAPI_ResultPart, ModelAPI_Result>;
%template(modelAPI_ResultGroup) shared_ptr_cast<ModelAPI_ResultPart, ModelAPI_ResultGroup>;
+
+// Attribute casts
+%template(modelAPI_AttributeDocRef) shared_ptr_cast<ModelAPI_AttributeDocRef, ModelAPI_Attribute>;
+%template(modelAPI_AttributeDouble) shared_ptr_cast<ModelAPI_AttributeDouble, ModelAPI_Attribute>;
+%template(modelAPI_AttributeInteger) shared_ptr_cast<ModelAPI_AttributeInteger, ModelAPI_Attribute>;
+%template(modelAPI_AttributeString) shared_ptr_cast<ModelAPI_AttributeString, ModelAPI_Attribute>;
+%template(modelAPI_AttributeReference) shared_ptr_cast<ModelAPI_AttributeReference, ModelAPI_Attribute>;
+%template(modelAPI_AttributeRefAttr) shared_ptr_cast<ModelAPI_AttributeRefAttr, ModelAPI_Attribute>;
+%template(modelAPI_AttributeBoolean) shared_ptr_cast<ModelAPI_AttributeBoolean, ModelAPI_Attribute>;
+%template(modelAPI_AttributeSelection) shared_ptr_cast<ModelAPI_AttributeSelection, ModelAPI_Attribute>;
+%template(modelAPI_AttributeSelectionList) shared_ptr_cast<ModelAPI_AttributeSelectionList, ModelAPI_Attribute>;
+%template(modelAPI_AttributeRefList) shared_ptr_cast<ModelAPI_AttributeRefList, ModelAPI_Attribute>;
MODELAPI_EXPORT virtual bool isObject() = 0;
/// Defines the reference to the attribute
- MODELAPI_EXPORT virtual void setAttr(std::shared_ptr<ModelAPI_Attribute> theAttr) = 0;
+ MODELAPI_EXPORT virtual void setAttr(AttributePtr theAttr) = 0;
/// Returns attribute referenced from this attribute
- MODELAPI_EXPORT virtual std::shared_ptr<ModelAPI_Attribute> attr() = 0;
+ MODELAPI_EXPORT virtual AttributePtr attr() = 0;
/// Defines the reference to the object
MODELAPI_EXPORT virtual void setObject(ObjectPtr theFeature) = 0;
virtual ~ModelAPI_Plugin()
{
}
-
- protected:
- /// Is needed for python wrapping by swig
- ModelAPI_Plugin()
- {
- }
};
#endif
/// Manager that will be initialized from Model package, one per application
std::shared_ptr<ModelAPI_Session> MY_MANAGER;
-ModelAPI_Session::ModelAPI_Session()
-{
-}
-
void ModelAPI_Session::setSession(std::shared_ptr<ModelAPI_Session> theManager)
{
MY_MANAGER = theManager;
/// Returns the validators factory: the only one instance per application
virtual ModelAPI_ValidatorsFactory* validators() = 0;
- /// Is needed for python wrapping by swig, call Get to get an instance
- ModelAPI_Session();
-
/// To virtually destroy the fields of successors
virtual ~ModelAPI_Session()
{
/// Remove all selection filters from the viewer
virtual void clearSelectionFilters() = 0;
+ /// Update current viewer
+ virtual void update() = 0;
+
signals:
void lastViewClosed();
void tryCloseView(ModuleBase_IViewWindow* theWnd);
virtual ModuleBase_ISelection* selection() const = 0;
/// Activate sub-shapes selection (opens local context)
- /// Types has to be dined according to TopAbs_ShapeEnum
+ /// Types has to be defined according to TopAbs_ShapeEnum
virtual void activateSubShapesSelection(const QIntList& theTypes) = 0;
/// Deactivate sub-shapes selection (closes local context)
aContext->RemoveFilters();
}
}
+
+//***************************************
+void NewGeom_SalomeViewer::update()
+{
+ Handle(AIS_InteractiveContext) aContext = AISContext();
+ if (!aContext.IsNull()) {
+ aContext->UpdateCurrentViewer();
+ }
+}
return mySelector;
}
+ /// Update current viewer
+ virtual void update();
+
+
private slots:
void onMousePress(SUIT_ViewWindow*, QMouseEvent*);
void onMouseRelease(SUIT_ViewWindow*, QMouseEvent*);
PartSet_WidgetPoint2dDistance.h
PartSet_WidgetShapeSelector.h
PartSet_Filters.h
+ PartSet_SketcherMgr.h
)
SET(PROJECT_SOURCES
PartSet_WidgetPoint2dDistance.cpp
PartSet_WidgetShapeSelector.cpp
PartSet_Filters.cpp
+ PartSet_SketcherMgr.cpp
)
SET(PROJECT_RESOURCES
#include <PartSet_WidgetPoint2d.h>
#include <PartSet_WidgetPoint2dDistance.h>
#include <PartSet_WidgetShapeSelector.h>
+#include <PartSet_SketcherMgr.h>
#include <ModuleBase_Operation.h>
#include <ModuleBase_IViewer.h>
#include <XGUI_ModuleConnector.h>
#include <XGUI_Tools.h>
-#include <SketchPlugin_Line.h>
+#include <SketchPlugin_Feature.h>
#include <SketchPlugin_Sketch.h>
-#include <SketchPlugin_Point.h>
-#include <SketchPlugin_Arc.h>
-#include <SketchPlugin_Circle.h>
+#include <SketchPlugin_Line.h>
+//#include <SketchPlugin_Arc.h>
+//#include <SketchPlugin_Circle.h>
#include <SketchPlugin_ConstraintLength.h>
#include <SketchPlugin_ConstraintDistance.h>
#include <SketchPlugin_ConstraintParallel.h>
#include <SketchPlugin_ConstraintPerpendicular.h>
#include <SketchPlugin_ConstraintRadius.h>
-#include <SketchPlugin_ConstraintRigid.h>
+//#include <SketchPlugin_ConstraintRigid.h>
#include <Events_Loop.h>
#include <QDebug>
#endif
-
-/// Returns list of unique objects by sum of objects from List1 and List2
-QList<ObjectPtr> getSumList(const QList<ModuleBase_ViewerPrs>& theList1,
- const QList<ModuleBase_ViewerPrs>& theList2)
-{
- QList<ObjectPtr> aRes;
- foreach (ModuleBase_ViewerPrs aPrs, theList1) {
- if (!aRes.contains(aPrs.object()))
- aRes.append(aPrs.object());
- }
- foreach (ModuleBase_ViewerPrs aPrs, theList2) {
- if (!aRes.contains(aPrs.object()))
- aRes.append(aPrs.object());
- }
- return aRes;
-}
-
/*!Create and return new instance of XGUI_Module*/
extern "C" PARTSET_EXPORT ModuleBase_IModule* createModule(ModuleBase_IWorkshop* theWshop)
{
PartSet_Module::PartSet_Module(ModuleBase_IWorkshop* theWshop)
: ModuleBase_IModule(theWshop),
- myIsDragging(false), myRestartingMode(RM_None), myDragDone(false)
+ myRestartingMode(RM_None)
{
//myWorkshop = dynamic_cast<XGUI_Workshop*>(theWshop);
- ModuleBase_IViewer* aViewer = aViewer = theWshop->viewer();
- connect(aViewer, SIGNAL(mousePress(ModuleBase_IViewWindow*, QMouseEvent*)),
- this, SLOT(onMousePressed(ModuleBase_IViewWindow*, QMouseEvent*)));
-
- connect(aViewer, SIGNAL(mouseRelease(ModuleBase_IViewWindow*, QMouseEvent*)),
- this, SLOT(onMouseReleased(ModuleBase_IViewWindow*, QMouseEvent*)));
-
- connect(aViewer, SIGNAL(mouseMove(ModuleBase_IViewWindow*, QMouseEvent*)),
- this, SLOT(onMouseMoved(ModuleBase_IViewWindow*, QMouseEvent*)));
-
- connect(aViewer, SIGNAL(mouseDoubleClick(ModuleBase_IViewWindow*, QMouseEvent*)),
- this, SLOT(onMouseDoubleClick(ModuleBase_IViewWindow*, QMouseEvent*)));
+ mySketchMgr = new PartSet_SketcherMgr(this);
XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(theWshop);
XGUI_Workshop* aWorkshop = aConnector->workshop();
connect(anOpMgr, SIGNAL(operationActivatedByPreselection()),
this, SLOT(onOperationActivatedByPreselection()));
+ ModuleBase_IViewer* aViewer = theWshop->viewer();
connect(aViewer, SIGNAL(keyRelease(ModuleBase_IViewWindow*, QKeyEvent*)),
this, SLOT(onKeyRelease(ModuleBase_IViewWindow*, QKeyEvent*)));
}
{
if (!myDocumentShapeFilter.IsNull())
myDocumentShapeFilter.Nullify();
- if (!myPlaneFilter.IsNull())
- myPlaneFilter.Nullify();
}
void PartSet_Module::registerValidators()
void PartSet_Module::operationStarted(ModuleBase_Operation* theOperation)
{
if (theOperation->id().toStdString() == SketchPlugin_Sketch::ID()) {
- // Display all sketcher sub-Objects
- myCurrentSketch = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(theOperation->feature());
- XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(workshop());
- XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
-
- for (int i = 0; i < myCurrentSketch->numberOfSubs(); i++) {
- FeaturePtr aFeature = myCurrentSketch->subFeature(i);
- std::list<ResultPtr> aResults = aFeature->results();
- std::list<ResultPtr>::const_iterator aIt;
- for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
- aDisplayer->display((*aIt), false);
- }
- aDisplayer->display(aFeature);
- }
- // Hide sketcher result
- std::list<ResultPtr> aResults = myCurrentSketch->results();
- std::list<ResultPtr>::const_iterator aIt;
- for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
- aDisplayer->erase((*aIt), false);
- }
- aDisplayer->erase(myCurrentSketch);
-
-
- if (myPlaneFilter.IsNull())
- myPlaneFilter = new ModuleBase_ShapeInPlaneFilter();
- myWorkshop->viewer()->addSelectionFilter(myPlaneFilter);
- if (theOperation->isEditOperation()) {
- // If it is editing of sketch then it means that plane is already defined
- std::shared_ptr<GeomAPI_Pln> aPln = PartSet_Tools::sketchPlane(myCurrentSketch);
- myPlaneFilter->setPlane(aPln->impl<gp_Pln>());
- }
+ mySketchMgr->startSketch(theOperation);
}
if (myDocumentShapeFilter.IsNull())
myDocumentShapeFilter = new PartSet_GlobalFilter(myWorkshop);
void PartSet_Module::operationStopped(ModuleBase_Operation* theOperation)
{
if (theOperation->id().toStdString() == SketchPlugin_Sketch::ID()) {
- DataPtr aData = myCurrentSketch->data();
- if ((!aData) || (!aData->isValid())) {
- // The sketch was aborted
- myCurrentSketch = CompositeFeaturePtr();
- return;
- }
- // Hide all sketcher sub-Objects
- XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(workshop());
- XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
- for (int i = 0; i < myCurrentSketch->numberOfSubs(); i++) {
- FeaturePtr aFeature = myCurrentSketch->subFeature(i);
- std::list<ResultPtr> aResults = aFeature->results();
- std::list<ResultPtr>::const_iterator aIt;
- for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
- aDisplayer->erase((*aIt), false);
- }
- aDisplayer->erase(aFeature, false);
- }
- // Display sketcher result
- std::list<ResultPtr> aResults = myCurrentSketch->results();
- std::list<ResultPtr>::const_iterator aIt;
- for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
- aDisplayer->display((*aIt), false);
- }
- aDisplayer->display(myCurrentSketch);
-
- myCurrentSketch = CompositeFeaturePtr();
- myWorkshop->viewer()->removeSelectionFilter(myPlaneFilter);
+ mySketchMgr->stopSketch(theOperation);
}
myWorkshop->viewer()->removeSelectionFilter(myDocumentShapeFilter);
}
-void PartSet_Module::onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>& thePln)
-{
- myPlaneFilter->setPlane(thePln->impl<gp_Pln>());
-}
-
void PartSet_Module::propertyPanelDefined(ModuleBase_Operation* theOperation)
{
std::dynamic_pointer_cast<GeomDataAPI_Point2D>(aData->attribute(SketchPlugin_Line::END_ID()));
if (aPoint) {
aPnt2dWgt->setPoint(aPoint->x(), aPoint->y());
- PartSet_Tools::setConstraints(myCurrentSketch, theOperation->feature(),
+ PartSet_Tools::setConstraints(mySketchMgr->activeSketch(), theOperation->feature(),
aWgt->attributeID(), aPoint->x(), aPoint->y());
theOperation->propertyPanel()->activateNextWidget(aPnt2dWgt);
}
// Start editing constraint
if (theOperation->isEditOperation()) {
std::string aId = theOperation->id().toStdString();
- if (sketchOperationIdList().contains(QString(aId.c_str()))) {
+ if (PartSet_SketcherMgr::sketchOperationIdList().contains(QString(aId.c_str()))) {
if ((aId == SketchPlugin_ConstraintRadius::ID()) ||
(aId == SketchPlugin_ConstraintLength::ID()) ||
(aId == SketchPlugin_ConstraintDistance::ID())) {
ModuleBase_Operation* aOperation = myWorkshop->currentOperation();
bool isSketcherOp = false;
// An edit operation is enable only if the current opeation is the sketch operation
- if (aOperation && myCurrentSketch) {
- if (PartSet_Tools::sketchPlane(myCurrentSketch))
+ if (aOperation && mySketchMgr->activeSketch()) {
+ if (PartSet_Tools::sketchPlane(mySketchMgr->activeSketch()))
isSketcherOp = (aOperation->id().toStdString() == SketchPlugin_Sketch::ID());
}
if (!isSketcherOp)
}
}
-void PartSet_Module::onMousePressed(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
-{
- if (!(theEvent->buttons() & Qt::LeftButton))
- return;
-
- ModuleBase_Operation* aOperation = myWorkshop->currentOperation();
- // Use only for sketch operations
- if (aOperation && myCurrentSketch) {
- if (!PartSet_Tools::sketchPlane(myCurrentSketch))
- return;
-
- bool isSketcher = (aOperation->id().toStdString() == SketchPlugin_Sketch::ID());
- bool isSketchOpe = sketchOperationIdList().contains(aOperation->id());
-
- // Avoid non-sketch operations
- if ((!isSketchOpe) && (!isSketcher))
- return;
-
- bool isEditing = aOperation->isEditOperation();
-
- // Ignore creation sketch operation
- if ((!isSketcher) && (!isEditing))
- return;
-
- if (theEvent->modifiers()) {
- // If user performs multiselection
- if (isSketchOpe && (!isSketcher))
- if (!aOperation->commit())
- aOperation->abort();
- return;
- }
- // Remember highlighted objects for editing
- ModuleBase_ISelection* aSelect = myWorkshop->selection();
- QList<ModuleBase_ViewerPrs> aHighlighted = aSelect->getHighlighted();
- QList<ModuleBase_ViewerPrs> aSelected = aSelect->getSelected();
- myEditingFeatures.clear();
- myEditingAttr.clear();
- if ((aHighlighted.size() == 0) && (aSelected.size() == 0)) {
- if (isSketchOpe && (!isSketcher))
- // commit previous operation
- if (!aOperation->commit())
- aOperation->abort();
- return;
- }
-
- QObjectPtrList aSelObjects = getSumList(aHighlighted, aSelected);
- if ((aHighlighted.size() == 1) && (aSelected.size() == 0)) {
- // Move by selected shape (vertex). Can be used only for single selection
- foreach(ModuleBase_ViewerPrs aPrs, aHighlighted) {
- FeaturePtr aFeature = ModelAPI_Feature::feature(aHighlighted.first().object());
- if (aFeature) {
- myEditingFeatures.append(aFeature);
- TopoDS_Shape aShape = aPrs.shape();
- if (!aShape.IsNull()) {
- if (aShape.ShapeType() == TopAbs_VERTEX) {
- AttributePtr aAttr = PartSet_Tools::findAttributeBy2dPoint(myEditingFeatures.first(),
- aShape, myCurrentSketch);
- if (aAttr)
- myEditingAttr.append(aAttr);
- }
- }
- }
- }
- } else {
- // Provide multi-selection. Can be used only for features
- foreach (ObjectPtr aObj, aSelObjects) {
- FeaturePtr aFeature = ModelAPI_Feature::feature(aObj);
- if (aFeature && (!myEditingFeatures.contains(aFeature)))
- myEditingFeatures.append(aFeature);
- }
-
- }
- // If nothing highlighted - return
- if (myEditingFeatures.size() == 0)
- return;
-
- if (isSketcher) {
- myIsDragging = true;
- get2dPoint(theWnd, theEvent, myCurX, myCurY);
- myDragDone = false;
- myWorkshop->viewer()->enableSelection(false);
- launchEditing();
-
- } else if (isSketchOpe && isEditing) {
- // If selected another object
- aOperation->abort();
-
- myIsDragging = true;
- get2dPoint(theWnd, theEvent, myCurX, myCurY);
- myDragDone = false;
- myWorkshop->viewer()->enableSelection(false);
-
- // This is necessary in order to finalize previous operation
- QApplication::processEvents();
- launchEditing();
- }
- }
-}
-
-
-void PartSet_Module::get2dPoint(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent,
- double& theX, double& theY)
-{
- Handle(V3d_View) aView = theWnd->v3dView();
- gp_Pnt aPoint = PartSet_Tools::convertClickToPoint(theEvent->pos(), aView);
- PartSet_Tools::convertTo2D(aPoint, myCurrentSketch, aView, theX, theY);
-}
-
-
-void PartSet_Module::launchEditing()
-{
- if (myEditingFeatures.size() > 0) {
- FeaturePtr aFeature = myEditingFeatures.first();
- std::shared_ptr<SketchPlugin_Feature> aSPFeature =
- std::dynamic_pointer_cast<SketchPlugin_Feature>(aFeature);
- if (aSPFeature) {
- editFeature(aSPFeature);
- }
- }
-}
-
-void PartSet_Module::onMouseReleased(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
-{
- myWorkshop->viewer()->enableSelection(true);
- if (myIsDragging) {
- myIsDragging = false;
- if (myDragDone) {
- myWorkshop->currentOperation()->commit();
- myEditingFeatures.clear();
- myEditingAttr.clear();
- }
- }
-}
-
-
-void PartSet_Module::onMouseMoved(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
-{
- if (myIsDragging) {
- ModuleBase_Operation* aOperation = myWorkshop->currentOperation();
- if (aOperation->id().toStdString() == SketchPlugin_Sketch::ID())
- return; // No edit operation activated
-
- static Events_ID anEvent = Events_Loop::eventByName(EVENT_OBJECT_MOVED);
- Handle(V3d_View) aView = theWnd->v3dView();
- gp_Pnt aPoint = PartSet_Tools::convertClickToPoint(theEvent->pos(), aView);
- double aX, aY;
- PartSet_Tools::convertTo2D(aPoint, myCurrentSketch, aView, aX, aY);
- double dX = aX - myCurX;
- double dY = aY - myCurY;
-
- if ((aOperation->id().toStdString() == SketchPlugin_Line::ID()) &&
- (myEditingAttr.size() == 1) &&
- myEditingAttr.first()) {
- // probably we have prehighlighted point
- AttributePtr aAttr = myEditingAttr.first();
- std::string aAttrId = aAttr->id();
- ModuleBase_IPropertyPanel* aPanel = aOperation->propertyPanel();
- QList<ModuleBase_ModelWidget*> aWidgets = aPanel->modelWidgets();
- // Find corresponded widget to provide dragging
- foreach (ModuleBase_ModelWidget* aWgt, aWidgets) {
- if (aWgt->attributeID() == aAttrId) {
- PartSet_WidgetPoint2D* aWgt2d = dynamic_cast<PartSet_WidgetPoint2D*>(aWgt);
- if (aWgt2d) {
- aWgt2d->setPoint(aWgt2d->x() + dX, aWgt2d->y() + dY);
- break;
- }
- }
- }
- } else {
- foreach(FeaturePtr aFeature, myEditingFeatures) {
- std::shared_ptr<SketchPlugin_Feature> aSketchFeature =
- std::dynamic_pointer_cast<SketchPlugin_Feature>(aFeature);
- if (aSketchFeature) {
- aSketchFeature->move(dX, dY);
- ModelAPI_EventCreator::get()->sendUpdated(aSketchFeature, anEvent);
- }
- }
// after movement the solver will call the update event: optimization
- Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_MOVED));
- }
- myDragDone = true;
- myCurX = aX;
- myCurY = aY;
- }
-}
-
-void PartSet_Module::onMouseDoubleClick(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
-{
- ModuleBase_Operation* aOperation = myWorkshop->currentOperation();
- if (aOperation && aOperation->isEditOperation()) {
- std::string aId = aOperation->id().toStdString();
- if ((aId == SketchPlugin_ConstraintLength::ID()) ||
- (aId == SketchPlugin_ConstraintDistance::ID()) ||
- (aId == SketchPlugin_ConstraintRadius::ID()))
- {
- // Activate dimension value editing on double click
- ModuleBase_IPropertyPanel* aPanel = aOperation->propertyPanel();
- QList<ModuleBase_ModelWidget*> aWidgets = aPanel->modelWidgets();
- // Find corresponded widget to activate value editing
- foreach (ModuleBase_ModelWidget* aWgt, aWidgets) {
- if (aWgt->attributeID() == "ConstraintValue") {
- aWgt->focusTo();
- return;
- }
- }
- }
- }
-}
void PartSet_Module::onKeyRelease(ModuleBase_IViewWindow* theWnd, QKeyEvent* theEvent)
{
}
}
-QStringList PartSet_Module::sketchOperationIdList() const
-{
- QStringList aIds;
- aIds << SketchPlugin_Line::ID().c_str();
- aIds << SketchPlugin_Point::ID().c_str();
- aIds << SketchPlugin_Arc::ID().c_str();
- aIds << SketchPlugin_Circle::ID().c_str();
- aIds << SketchPlugin_ConstraintLength::ID().c_str();
- aIds << SketchPlugin_ConstraintDistance::ID().c_str();
- aIds << SketchPlugin_ConstraintRigid::ID().c_str();
- aIds << SketchPlugin_ConstraintRadius::ID().c_str();
- aIds << SketchPlugin_ConstraintPerpendicular::ID().c_str();
- aIds << SketchPlugin_ConstraintParallel::ID().c_str();
- return aIds;
-}
-
void PartSet_Module::onVertexSelected(ObjectPtr theObject, const TopoDS_Shape& theShape)
{
ModuleBase_Operation* aOperation = myWorkshop->currentOperation();
PartSet_WidgetSketchLabel* aWgt = new PartSet_WidgetSketchLabel(theParent, theWidgetApi, theParentId);
aWgt->setWorkshop(aWorkshop);
connect(aWgt, SIGNAL(planeSelected(const std::shared_ptr<GeomAPI_Pln>&)),
- this, SLOT(onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>&)));
+ mySketchMgr, SLOT(onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>&)));
theModelWidgets.append(aWgt);
return aWgt->getControl();
} else if (theType == "sketch-2dpoint_selector") {
PartSet_WidgetPoint2D* aWgt = new PartSet_WidgetPoint2D(theParent, theWidgetApi, theParentId);
aWgt->setWorkshop(aWorkshop);
- aWgt->setSketch(myCurrentSketch);
+ aWgt->setSketch(mySketchMgr->activeSketch());
connect(aWgt, SIGNAL(vertexSelected(ObjectPtr, const TopoDS_Shape&)),
this, SLOT(onVertexSelected(ObjectPtr, const TopoDS_Shape&)));
} if (theType == "point2ddistance") {
PartSet_WidgetPoint2dDistance* aWgt = new PartSet_WidgetPoint2dDistance(theParent, theWidgetApi, theParentId);
aWgt->setWorkshop(aWorkshop);
- aWgt->setSketch(myCurrentSketch);
+ aWgt->setSketch(mySketchMgr->activeSketch());
theModelWidgets.append(aWgt);
return aWgt->getControl();
} if (theType == "sketch_shape_selector") {
PartSet_WidgetShapeSelector* aWgt =
new PartSet_WidgetShapeSelector(theParent, workshop(), theWidgetApi, theParentId);
- aWgt->setSketcher(myCurrentSketch);
+ aWgt->setSketcher(mySketchMgr->activeSketch());
theModelWidgets.append(aWgt);
return aWgt->getControl();
} if (theType == "sketch_constraint_shape_selector") {
PartSet_WidgetConstraintShapeSelector* aWgt =
new PartSet_WidgetConstraintShapeSelector(theParent, workshop(), theWidgetApi, theParentId);
- aWgt->setSketcher(myCurrentSketch);
+ aWgt->setSketcher(mySketchMgr->activeSketch());
theModelWidgets.append(aWgt);
return aWgt->getControl();
- }else
+ } else
return 0;
}
#define PartSet_Module_H
#include "PartSet.h"
-#include <PartSet_Filters.h>
+#include "PartSet_Filters.h"
+#include "PartSet_SketcherMgr.h"
#include <ModuleBase_IModule.h>
#include <ModuleBase_Definitions.h>
#include <ModelAPI_Attribute.h>
#include <ModelAPI_CompositeFeature.h>
-#include <StdSelect_FaceFilter.hxx>
+//#include <StdSelect_FaceFilter.hxx>
#include <TopoDS_Shape.hxx>
#include <QMap>
/// Call back forlast tuning of property panel before operation performance
virtual void propertyPanelDefined(ModuleBase_Operation* theOperation);
- QStringList sketchOperationIdList() const;
/// Realizes some functionality by an operation start
/// Displays all sketcher sub-Objects, hides sketcher result, appends selection filters
/// SLOT, that is called by mouse press in the viewer.
/// \param theWnd - the window where the event happens
/// \param theEvent the mouse event
- void onMousePressed(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
+ //void onMousePressed(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
/// SLOT, that is called by mouse release in the viewer.
/// \param theWnd - the window where the event happens
/// \param theEvent the mouse event
- void onMouseReleased(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
+ //void onMouseReleased(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
/// SLOT, that is called by mouse move in the viewer.
/// \param theWnd - the window where the event happens
/// \param theEvent the mouse event
- void onMouseMoved(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
+ //void onMouseMoved(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
/// SLOT, that is called by mouse double click in the viewer.
/// \param theWnd - the window where the event happens
/// \param theEvent the mouse event
- void onMouseDoubleClick(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
+ //void onMouseDoubleClick(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent);
/// SLOT, that is called by key release in the viewer.
/// The mouse moved point is sent to the current operation to be processed.
/// It commits the operation of it is can be committed
void onOperationActivatedByPreselection();
- /// Launches the operation from current highlighting
- void launchEditing();
protected:
/// Register validators for this module
private slots:
void onVertexSelected(ObjectPtr theObject, const TopoDS_Shape& theShape);
- void onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>& thePln);
private:
- /// Converts mouse position to 2d coordinates.
- /// Member myCurrentSketch has to be correctly defined
- void get2dPoint(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent,
- double& theX, double& theY);
/// Breaks sequense of automatically resterted operations
void breakOperationSequence();
QString myLastOperationId;
FeaturePtr myLastFeature;
- bool myIsDragging;
- bool myDragDone;
-
// Automatical restarting mode flag
RestartingMode myRestartingMode;
- double myCurX, myCurY;
- CompositeFeaturePtr myCurrentSketch;
- QList<FeaturePtr> myEditingFeatures;
- QList<AttributePtr> myEditingAttr;
-
- Handle(ModuleBase_ShapeInPlaneFilter) myPlaneFilter;
/// A filter which provides selection within a current document or whole PartSet
Handle(PartSet_GlobalFilter) myDocumentShapeFilter;
+
+ PartSet_SketcherMgr* mySketchMgr;
};
#endif
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: PartSet_SketcherMgr.cpp
+// Created: 19 Dec 2014
+// Author: Vitaly SMETANNIKOV
+
+#include "PartSet_SketcherMgr.h"
+#include "PartSet_Module.h"
+#include "PartSet_WidgetPoint2D.h"
+#include "PartSet_Tools.h"
+
+#include <XGUI_ModuleConnector.h>
+#include <XGUI_Displayer.h>
+#include <XGUI_Workshop.h>
+
+#include <ModuleBase_IViewer.h>
+#include <ModuleBase_IWorkshop.h>
+#include <ModuleBase_IViewWindow.h>
+#include <ModuleBase_Operation.h>
+#include <ModuleBase_ISelection.h>
+#include <ModuleBase_IPropertyPanel.h>
+#include <ModuleBase_Operation.h>
+
+#include <Events_Loop.h>
+
+#include <SketchPlugin_Line.h>
+#include <SketchPlugin_Sketch.h>
+#include <SketchPlugin_Point.h>
+#include <SketchPlugin_Arc.h>
+#include <SketchPlugin_Circle.h>
+#include <SketchPlugin_ConstraintLength.h>
+#include <SketchPlugin_ConstraintDistance.h>
+#include <SketchPlugin_ConstraintParallel.h>
+#include <SketchPlugin_ConstraintPerpendicular.h>
+#include <SketchPlugin_ConstraintRadius.h>
+#include <SketchPlugin_ConstraintRigid.h>
+
+#include <ModelAPI_Events.h>
+
+#include <QMouseEvent>
+#include <QApplication>
+
+
+
+
+/// Returns list of unique objects by sum of objects from List1 and List2
+QList<ObjectPtr> getSumList(const QList<ModuleBase_ViewerPrs>& theList1,
+ const QList<ModuleBase_ViewerPrs>& theList2)
+{
+ QList<ObjectPtr> aRes;
+ foreach (ModuleBase_ViewerPrs aPrs, theList1) {
+ if (!aRes.contains(aPrs.object()))
+ aRes.append(aPrs.object());
+ }
+ foreach (ModuleBase_ViewerPrs aPrs, theList2) {
+ if (!aRes.contains(aPrs.object()))
+ aRes.append(aPrs.object());
+ }
+ return aRes;
+}
+
+
+
+
+PartSet_SketcherMgr::PartSet_SketcherMgr(PartSet_Module* theModule)
+ : QObject(theModule), myModule(theModule), myIsDragging(false), myDragDone(false)
+{
+ ModuleBase_IWorkshop* aWorkshop = myModule->workshop();
+ ModuleBase_IViewer* aViewer = aWorkshop->viewer();
+
+ connect(aViewer, SIGNAL(mousePress(ModuleBase_IViewWindow*, QMouseEvent*)),
+ this, SLOT(onMousePressed(ModuleBase_IViewWindow*, QMouseEvent*)));
+
+ connect(aViewer, SIGNAL(mouseRelease(ModuleBase_IViewWindow*, QMouseEvent*)),
+ this, SLOT(onMouseReleased(ModuleBase_IViewWindow*, QMouseEvent*)));
+
+ connect(aViewer, SIGNAL(mouseMove(ModuleBase_IViewWindow*, QMouseEvent*)),
+ this, SLOT(onMouseMoved(ModuleBase_IViewWindow*, QMouseEvent*)));
+
+ connect(aViewer, SIGNAL(mouseDoubleClick(ModuleBase_IViewWindow*, QMouseEvent*)),
+ this, SLOT(onMouseDoubleClick(ModuleBase_IViewWindow*, QMouseEvent*)));
+}
+
+PartSet_SketcherMgr::~PartSet_SketcherMgr()
+{
+ if (!myPlaneFilter.IsNull())
+ myPlaneFilter.Nullify();
+}
+
+void PartSet_SketcherMgr::onMousePressed(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
+{
+ //
+ if (!(theEvent->buttons() & Qt::LeftButton))
+ return;
+
+ ModuleBase_IWorkshop* aWorkshop = myModule->workshop();
+ ModuleBase_Operation* aOperation = aWorkshop->currentOperation();
+ // Use only for sketch operations
+ if (aOperation && myCurrentSketch) {
+ if (!PartSet_Tools::sketchPlane(myCurrentSketch))
+ return;
+
+ bool isSketcher = (aOperation->id().toStdString() == SketchPlugin_Sketch::ID());
+ bool isSketchOpe = sketchOperationIdList().contains(aOperation->id());
+
+ // Avoid non-sketch operations
+ if ((!isSketchOpe) && (!isSketcher))
+ return;
+
+ bool isEditing = aOperation->isEditOperation();
+
+ // Ignore creation sketch operation
+ if ((!isSketcher) && (!isEditing))
+ return;
+
+ if (theEvent->modifiers()) {
+ // If user performs multiselection
+ if (isSketchOpe /* && (!isSketcher)*/)
+ if (!aOperation->commit())
+ aOperation->abort();
+ return;
+ }
+ // Remember highlighted objects for editing
+ ModuleBase_ISelection* aSelect = aWorkshop->selection();
+ QList<ModuleBase_ViewerPrs> aHighlighted = aSelect->getHighlighted();
+ QList<ModuleBase_ViewerPrs> aSelected = aSelect->getSelected();
+ myEditingFeatures.clear();
+ myEditingAttr.clear();
+ if ((aHighlighted.size() == 0) && (aSelected.size() == 0)) {
+ if (isSketchOpe && (!isSketcher))
+ // commit previous operation
+ if (!aOperation->commit())
+ aOperation->abort();
+ return;
+ }
+
+ QObjectPtrList aSelObjects = getSumList(aHighlighted, aSelected);
+ //foreach (ModuleBase_ViewerPrs aPrs, aHighlighted) {
+ // aSelObjects.append(aPrs.object());
+ //}
+
+ if ((aHighlighted.size() == 1) && (aSelected.size() == 0)) {
+ // Move by selected shape (vertex). Can be used only for single selection
+ foreach(ModuleBase_ViewerPrs aPrs, aHighlighted) {
+ FeaturePtr aFeature = ModelAPI_Feature::feature(aHighlighted.first().object());
+ if (aFeature) {
+ myEditingFeatures.append(aFeature);
+ TopoDS_Shape aShape = aPrs.shape();
+ if (!aShape.IsNull()) {
+ if (aShape.ShapeType() == TopAbs_VERTEX) {
+ AttributePtr aAttr = PartSet_Tools::findAttributeBy2dPoint(myEditingFeatures.first(),
+ aShape, myCurrentSketch);
+ if (aAttr)
+ myEditingAttr.append(aAttr);
+ }
+ }
+ }
+ }
+ } else {
+ // Provide multi-selection. Can be used only for features
+ foreach (ObjectPtr aObj, aSelObjects) {
+ FeaturePtr aFeature = ModelAPI_Feature::feature(aObj);
+ if (aFeature && (!myEditingFeatures.contains(aFeature)))
+ myEditingFeatures.append(aFeature);
+ }
+
+ }
+ // If nothing highlighted - return
+ if (myEditingFeatures.size() == 0)
+ return;
+
+ if (isSketcher) {
+ myIsDragging = true;
+ get2dPoint(theWnd, theEvent, myCurX, myCurY);
+ myDragDone = false;
+ aWorkshop->viewer()->enableMultiselection(false);
+ launchEditing();
+
+ } else if (isSketchOpe && isEditing) {
+ // If selected another object
+ aOperation->abort();
+
+ myIsDragging = true;
+ get2dPoint(theWnd, theEvent, myCurX, myCurY);
+ myDragDone = false;
+ aWorkshop->viewer()->enableMultiselection(false);
+
+ // This is necessary in order to finalize previous operation
+ QApplication::processEvents();
+ launchEditing();
+ }
+ }
+}
+
+void PartSet_SketcherMgr::onMouseReleased(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
+{
+ ModuleBase_IWorkshop* aWorkshop = myModule->workshop();
+ ModuleBase_Operation* aOp = aWorkshop->currentOperation();
+ if (!aOp)
+ return;
+ if (!sketchOperationIdList().contains(aOp->id()))
+ return;
+
+ // Only for sketcher operations
+ ModuleBase_IViewer* aViewer = aWorkshop->viewer();
+ if (myIsDragging) {
+ myIsDragging = false;
+ if (myDragDone) {
+ aViewer->enableMultiselection(true);
+ aOp->commit();
+ myEditingFeatures.clear();
+ myEditingAttr.clear();
+ return;
+ }
+ }
+ if (!aViewer->isMultiSelectionEnabled()) {
+ aViewer->enableMultiselection(true);
+ }
+ aViewer->AISContext()->MoveTo(theEvent->x(), theEvent->y(), theWnd->v3dView());
+ if (theEvent->modifiers() & Qt::ShiftModifier)
+ aViewer->AISContext()->ShiftSelect();
+ else
+ aViewer->AISContext()->Select();
+}
+
+void PartSet_SketcherMgr::onMouseMoved(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
+{
+ if (myIsDragging) {
+ ModuleBase_Operation* aOperation = myModule->workshop()->currentOperation();
+ if (aOperation->id().toStdString() == SketchPlugin_Sketch::ID())
+ return; // No edit operation activated
+
+ static Events_ID anEvent = Events_Loop::eventByName(EVENT_OBJECT_MOVED);
+ Handle(V3d_View) aView = theWnd->v3dView();
+ gp_Pnt aPoint = PartSet_Tools::convertClickToPoint(theEvent->pos(), aView);
+ double aX, aY;
+ PartSet_Tools::convertTo2D(aPoint, myCurrentSketch, aView, aX, aY);
+ double dX = aX - myCurX;
+ double dY = aY - myCurY;
+
+ if ((aOperation->id().toStdString() == SketchPlugin_Line::ID()) &&
+ (myEditingAttr.size() == 1) &&
+ myEditingAttr.first()) {
+ // probably we have prehighlighted point
+ AttributePtr aAttr = myEditingAttr.first();
+ std::string aAttrId = aAttr->id();
+ ModuleBase_IPropertyPanel* aPanel = aOperation->propertyPanel();
+ QList<ModuleBase_ModelWidget*> aWidgets = aPanel->modelWidgets();
+ // Find corresponded widget to provide dragging
+ foreach (ModuleBase_ModelWidget* aWgt, aWidgets) {
+ if (aWgt->attributeID() == aAttrId) {
+ PartSet_WidgetPoint2D* aWgt2d = dynamic_cast<PartSet_WidgetPoint2D*>(aWgt);
+ if (aWgt2d) {
+ aWgt2d->setPoint(aWgt2d->x() + dX, aWgt2d->y() + dY);
+ break;
+ }
+ }
+ }
+ } else {
+ foreach(FeaturePtr aFeature, myEditingFeatures) {
+ std::shared_ptr<SketchPlugin_Feature> aSketchFeature =
+ std::dynamic_pointer_cast<SketchPlugin_Feature>(aFeature);
+ if (aSketchFeature) {
+ aSketchFeature->move(dX, dY);
+ ModelAPI_EventCreator::get()->sendUpdated(aSketchFeature, anEvent);
+ }
+ }
+ Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_MOVED));
+ Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
+ }
+ myDragDone = true;
+ myCurX = aX;
+ myCurY = aY;
+ }
+}
+
+void PartSet_SketcherMgr::onMouseDoubleClick(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent)
+{
+ ModuleBase_Operation* aOperation = myModule->workshop()->currentOperation();
+ if (aOperation && aOperation->isEditOperation()) {
+ std::string aId = aOperation->id().toStdString();
+ if ((aId == SketchPlugin_ConstraintLength::ID()) ||
+ (aId == SketchPlugin_ConstraintDistance::ID()) ||
+ (aId == SketchPlugin_ConstraintRadius::ID()))
+ {
+ // Activate dimension value editing on double click
+ ModuleBase_IPropertyPanel* aPanel = aOperation->propertyPanel();
+ QList<ModuleBase_ModelWidget*> aWidgets = aPanel->modelWidgets();
+ // Find corresponded widget to activate value editing
+ foreach (ModuleBase_ModelWidget* aWgt, aWidgets) {
+ if (aWgt->attributeID() == "ConstraintValue") {
+ aWgt->focusTo();
+ return;
+ }
+ }
+ }
+ }
+}
+
+void PartSet_SketcherMgr::get2dPoint(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent,
+ double& theX, double& theY)
+{
+ Handle(V3d_View) aView = theWnd->v3dView();
+ gp_Pnt aPoint = PartSet_Tools::convertClickToPoint(theEvent->pos(), aView);
+ PartSet_Tools::convertTo2D(aPoint, myCurrentSketch, aView, theX, theY);
+}
+
+void PartSet_SketcherMgr::launchEditing()
+{
+ if (myEditingFeatures.size() > 0) {
+ FeaturePtr aFeature = myEditingFeatures.first();
+ std::shared_ptr<SketchPlugin_Feature> aSPFeature =
+ std::dynamic_pointer_cast<SketchPlugin_Feature>(aFeature);
+ if (aSPFeature) {
+ myModule->editFeature(aSPFeature);
+ }
+ }
+}
+
+
+QStringList PartSet_SketcherMgr::sketchOperationIdList()
+{
+ static QStringList aIds;
+ if (aIds.size() == 0) {
+ aIds << SketchPlugin_Line::ID().c_str();
+ aIds << SketchPlugin_Point::ID().c_str();
+ aIds << SketchPlugin_Arc::ID().c_str();
+ aIds << SketchPlugin_Circle::ID().c_str();
+ aIds << SketchPlugin_ConstraintLength::ID().c_str();
+ aIds << SketchPlugin_ConstraintDistance::ID().c_str();
+ aIds << SketchPlugin_ConstraintRigid::ID().c_str();
+ aIds << SketchPlugin_ConstraintRadius::ID().c_str();
+ aIds << SketchPlugin_ConstraintPerpendicular::ID().c_str();
+ aIds << SketchPlugin_ConstraintParallel::ID().c_str();
+ }
+ return aIds;
+}
+
+void PartSet_SketcherMgr::startSketch(ModuleBase_Operation* theOperation)
+{
+ // Display all sketcher sub-Objects
+ myCurrentSketch = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>(theOperation->feature());
+ XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(myModule->workshop());
+ XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
+
+ // Hide sketcher result
+ std::list<ResultPtr> aResults = myCurrentSketch->results();
+ std::list<ResultPtr>::const_iterator aIt;
+ for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
+ aDisplayer->erase((*aIt), false);
+ }
+ aDisplayer->erase(myCurrentSketch, false);
+
+ // Display sketcher objects
+ for (int i = 0; i < myCurrentSketch->numberOfSubs(); i++) {
+ FeaturePtr aFeature = myCurrentSketch->subFeature(i);
+ std::list<ResultPtr> aResults = aFeature->results();
+ std::list<ResultPtr>::const_iterator aIt;
+ for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
+ aDisplayer->display((*aIt), false);
+ }
+ aDisplayer->display(aFeature, false);
+ }
+
+ if (myPlaneFilter.IsNull())
+ myPlaneFilter = new ModuleBase_ShapeInPlaneFilter();
+
+ myModule->workshop()->viewer()->addSelectionFilter(myPlaneFilter);
+ if (theOperation->isEditOperation()) {
+ // If it is editing of sketch then it means that plane is already defined
+ std::shared_ptr<GeomAPI_Pln> aPln = PartSet_Tools::sketchPlane(myCurrentSketch);
+ myPlaneFilter->setPlane(aPln->impl<gp_Pln>());
+ }
+ aDisplayer->updateViewer();
+}
+
+void PartSet_SketcherMgr::stopSketch(ModuleBase_Operation* theOperation)
+{
+ DataPtr aData = myCurrentSketch->data();
+ if ((!aData) || (!aData->isValid())) {
+ // The sketch was aborted
+ myCurrentSketch = CompositeFeaturePtr();
+ return;
+ }
+ // Hide all sketcher sub-Objects
+ XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(myModule->workshop());
+ XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
+ for (int i = 0; i < myCurrentSketch->numberOfSubs(); i++) {
+ FeaturePtr aFeature = myCurrentSketch->subFeature(i);
+ std::list<ResultPtr> aResults = aFeature->results();
+ std::list<ResultPtr>::const_iterator aIt;
+ for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
+ aDisplayer->erase((*aIt), false);
+ }
+ aDisplayer->erase(aFeature, false);
+ }
+ // Display sketcher result
+ std::list<ResultPtr> aResults = myCurrentSketch->results();
+ std::list<ResultPtr>::const_iterator aIt;
+ for (aIt = aResults.begin(); aIt != aResults.end(); ++aIt) {
+ aDisplayer->display((*aIt), false);
+ }
+ aDisplayer->display(myCurrentSketch);
+
+ myCurrentSketch = CompositeFeaturePtr();
+ myModule->workshop()->viewer()->removeSelectionFilter(myPlaneFilter);
+ aDisplayer->updateViewer();
+}
+
+
+void PartSet_SketcherMgr::onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>& thePln)
+{
+ myPlaneFilter->setPlane(thePln->impl<gp_Pln>());
+}
--- /dev/null
+// Copyright (C) 2014-20xx CEA/DEN, EDF R&D
+
+// File: PartSet_SketcherMgr.h
+// Created: 19 Dec 2014
+// Author: Vitaly SMETANNIKOV
+
+#ifndef PartSet_SketcherMgr_H
+#define PartSet_SketcherMgr_H
+
+#include "PartSet.h"
+
+#include <ModelAPI_Feature.h>
+#include <ModelAPI_Attribute.h>
+#include <ModelAPI_CompositeFeature.h>
+
+#include <ModuleBase_ViewerFilters.h>
+
+#include <GeomAPI_Pln.h>
+
+#include <QObject>
+#include <QList>
+
+class PartSet_Module;
+class ModuleBase_IViewWindow;
+class ModuleBase_Operation;
+class QMouseEvent;
+
+
+/**
+* A class for management of sketch operations
+*/
+class PARTSET_EXPORT PartSet_SketcherMgr : public QObject
+{
+ Q_OBJECT
+public:
+ PartSet_SketcherMgr(PartSet_Module* theModule);
+
+ virtual ~PartSet_SketcherMgr();
+
+ static QStringList sketchOperationIdList();
+
+ /// Launches the operation from current highlighting
+ void launchEditing();
+
+ // Returns current Sketch feature/ Returns NULL if there is no launched sketch operation
+ CompositeFeaturePtr activeSketch() const { return myCurrentSketch; }
+
+ /// Starts sketch operation
+ void startSketch(ModuleBase_Operation* theOperation);
+
+ /// Stops sketch operation
+ void stopSketch(ModuleBase_Operation* theOperation);
+
+public slots:
+ void onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>& thePln);
+
+
+private slots:
+ void onMousePressed(ModuleBase_IViewWindow*, QMouseEvent*);
+ void onMouseReleased(ModuleBase_IViewWindow*, QMouseEvent*);
+ void onMouseMoved(ModuleBase_IViewWindow*, QMouseEvent*);
+ void onMouseDoubleClick(ModuleBase_IViewWindow*, QMouseEvent*);
+
+private:
+ /// Converts mouse position to 2d coordinates.
+ /// Member myCurrentSketch has to be correctly defined
+ void get2dPoint(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent,
+ double& theX, double& theY);
+
+
+private:
+ PartSet_Module* myModule;
+
+ bool myIsDragging;
+ bool myDragDone;
+ double myCurX, myCurY;
+
+ CompositeFeaturePtr myCurrentSketch;
+ QList<FeaturePtr> myEditingFeatures;
+ QList<AttributePtr> myEditingAttr;
+
+ Handle(ModuleBase_ShapeInPlaneFilter) myPlaneFilter;
+};
+
+
+#endif
\ No newline at end of file
#include <Config_PropManager.h>
#include <QLabel>
+#include <QTimer>
#define PLANE_SIZE "200"
#define SKETCH_WIDTH "4"
myTooltip = QString::fromStdString(theData->getProperty("tooltip"));
myLabel->setToolTip("");
myLabel->setIndent(5);
+
+ mySelectionTimer = new QTimer(this);
+ connect(mySelectionTimer, SIGNAL(timeout()), SLOT(setSketchingMode()));
+ mySelectionTimer->setSingleShot(true);
}
PartSet_WidgetSketchLabel::~PartSet_WidgetSketchLabel()
// Clear selection mode and define sketching mode
XGUI_Displayer* aDisp = myWorkshop->displayer();
aDisp->removeSelectionFilter(myFaceFilter);
- aDisp->closeLocalContexts();
+ //aDisp->closeLocalContexts();
emit planeSelected(plane());
setSketchingMode();
{
std::shared_ptr<GeomAPI_Pln> aPlane = plane();
if (aPlane) {
- setSketchingMode();
+ //setSketchingMode();
+ // In order to avoid Opening/Closing of context too often
+ mySelectionTimer->start(20);
} else {
// We have to select a plane before any operation
showPreviewPlanes();
XGUI_Displayer* aDisp = myWorkshop->displayer();
- aDisp->openLocalContext();
- aDisp->activateObjects(QIntList());
+ //aDisp->openLocalContext();
+ //aDisp->activateObjects(QIntList());
if (myFaceFilter.IsNull())
myFaceFilter = new StdSelect_FaceFilter(StdSelect_Plane);
aDisp->addSelectionFilter(myFaceFilter);
void PartSet_WidgetSketchLabel::deactivate()
{
-
+ // Do not set selection mode if the widget was activated for a small moment
+ mySelectionTimer->stop();
XGUI_Displayer* aDisp = myWorkshop->displayer();
aDisp->removeSelectionFilter(myFaceFilter);
//aDisp->removeSelectionFilter(mySketchFilter);
- aDisp->closeLocalContexts();
+ //aDisp->closeLocalContexts();
erasePreviewPlanes();
}
void PartSet_WidgetSketchLabel::setSketchingMode()
{
+ qDebug("### Set sketching mode");
+
XGUI_Displayer* aDisp = myWorkshop->displayer();
- QIntList aModes;
// Clear standard selection modes if they are defined
- aDisp->activateObjects(aModes);
- aDisp->openLocalContext();
-
- // Set filter
- std::shared_ptr<GeomAPI_Pln> aPlane = plane();
- double aA, aB, aC, aD;
- aPlane->coefficients(aA, aB, aC, aD);
- gp_Pln aPln(aA, aB, aC, aD);
- // No selection of external objects
- //mySketchFilter = new ModuleBase_ShapeInPlaneFilter(aPln);
- //aDisp->addSelectionFilter(mySketchFilter);
+ //aDisp->activateObjects(aModes);
+ //aDisp->openLocalContext();
// Get default selection modes
+ QIntList aModes;
aModes.append(AIS_DSM_Text);
aModes.append(AIS_DSM_Line);
aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_VERTEX));
#include <TopoDS_Shape.hxx>
class QLabel;
+class QTimer;
class XGUI_OperationMgr;
class XGUI_Workshop;
-//class PartSet_OperationSketch;
class PARTSET_EXPORT PartSet_WidgetSketchLabel : public ModuleBase_ModelWidget
{
private slots:
void onPlaneSelected();
+ void setSketchingMode();
private:
AISObjectPtr createPreviewPlane(std::shared_ptr<GeomAPI_Pnt> theOrigin,
void erasePreviewPlanes();
void showPreviewPlanes();
- void setSketchingMode();
QLabel* myLabel;
QString myText;
bool myPreviewDisplayed;
Handle(StdSelect_FaceFilter) myFaceFilter;
- //Handle(ModuleBase_ShapeInPlaneFilter) mySketchFilter;
+
+ QTimer* mySelectionTimer;
};
#endif
virtual FeaturePtr createFeature(std::string theFeatureID);
public:
- /// Is needed for python wrapping by swig
SketchPlugin_Plugin();
//! Redefinition of Events_Listener method
virtual void processEvent(const std::shared_ptr<Events_Message>& theMessage);
#include <SelectMgr_ListOfFilter.hxx>
#include <SelectMgr_ListIteratorOfListOfFilter.hxx>
+#include <TColStd_MapOfTransient.hxx>
+#include <TColStd_MapIteratorOfMapOfTransient.hxx>
+
#include <set>
const int MOUSE_SENSITIVITY_IN_PIXEL = 10; ///< defines the local context mouse selection sensitivity
XGUI_Displayer::XGUI_Displayer(XGUI_Workshop* theWorkshop)
- : myUseExternalObjects(false), myWorkshop(theWorkshop)
+ : myWorkshop(theWorkshop)
{
}
Handle(AIS_InteractiveObject) anAISIO = theAIS->impl<Handle(AIS_InteractiveObject)>();
if (!anAISIO.IsNull()) {
myResult2AISObjectMap[theObject] = theAIS;
+
+ closeLocalContexts(false);
aContext->Display(anAISIO, false);
aContext->SetDisplayMode(anAISIO, isShading? Shading : Wireframe, false);
-
+ // Customization of presentation
FeaturePtr aFeature = ModelAPI_Feature::feature(theObject);
if (aFeature.get() != NULL) {
GeomCustomPrsPtr aCustPrs = std::dynamic_pointer_cast<GeomAPI_ICustomPrs>(aFeature);
if (aCustPrs.get() != NULL)
aCustPrs->customisePresentation(theAIS);
}
- if (aContext->HasOpenedContext()) {
- if (myUseExternalObjects) {
- if (myActiveSelectionModes.size() == 0)
- aContext->Activate(anAISIO);
- else {
- foreach(int aMode, myActiveSelectionModes) {
- aContext->Activate(anAISIO, aMode);
- }
- }
- }
- }
+ openLocalContext();
+ aContext->Load(anAISIO, -1, true);
+ activate(theObject);
+ //if (aContext->HasOpenedContext()) {
+ //if (myUseExternalObjects) {
+ //if (myActiveSelectionModes.size() == 0)
+ // aContext->Activate(anAISIO);
+ //else {
+ // foreach(int aMode, myActiveSelectionModes) {
+ // aContext->Activate(anAISIO, aMode);
+ // }
+ //}
+ //}
+ //}
}
if (isUpdateViewer)
updateViewer();
void XGUI_Displayer::activate(ObjectPtr theFeature)
{
- QIntList aModes;
- activate(theFeature, aModes);
+ activate(theFeature, myActiveSelectionModes);
}
void XGUI_Displayer::activate(ObjectPtr theObject, const QIntList& theModes)
AISObjectPtr anObj = myResult2AISObjectMap[theObject];
Handle(AIS_InteractiveObject) anAIS = anObj->impl<Handle(AIS_InteractiveObject)>();
- if (aContext->HasOpenedContext()) {
- aContext->Load(anAIS, -1, true);
- }
+ aContext->Deactivate(anAIS);
+ //if (aContext->HasOpenedContext()) {
+ // aContext->Load(anAIS, -1, true);
+ //}
+ // In order to clear active modes list
if (theModes.size() > 0) {
foreach(int aMode, theModes) {
aContext->Activate(anAIS, aMode);
}
}
+void XGUI_Displayer::activateObjects(const QIntList& theModes)
+{
+ // In order to avoid doblications of selection modes
+ myActiveSelectionModes.clear();
+ foreach (int aMode, theModes) {
+ if (!myActiveSelectionModes.contains(aMode))
+ myActiveSelectionModes.append(aMode);
+ }
+ Handle(AIS_InteractiveContext) aContext = AISContext();
+ // Open local context if there is no one
+ if (!aContext->HasOpenedContext())
+ return;
+
+ //aContext->UseDisplayedObjects();
+ //myUseExternalObjects = true;
+
+ AIS_ListOfInteractive aPrsList;
+ aContext->DisplayedObjects(aPrsList, true);
+ //Deactivate trihedron which can be activated in local selector
+
+ Handle(AIS_Trihedron) aTrihedron;
+ AIS_ListIteratorOfListOfInteractive aLIt(aPrsList);
+ Handle(AIS_InteractiveObject) anAISIO;
+ for(aLIt.Initialize(aPrsList); aLIt.More(); aLIt.Next()){
+ anAISIO = aLIt.Value();
+ aTrihedron = Handle(AIS_Trihedron)::DownCast(anAISIO);
+ if (!aTrihedron.IsNull()) {
+ aContext->Deactivate(aTrihedron);
+ } else {
+ //aContext->Load(anAISIO, -1, true);
+ // In order to clear active modes list
+ aContext->Deactivate(anAISIO);
+ if (myActiveSelectionModes.size() == 0)
+ aContext->Activate(anAISIO);
+ else {
+ foreach(int aMode, myActiveSelectionModes) {
+ aContext->Activate(anAISIO, aMode);
+ }
+ }
+ }
+ }
+}
+
+
+void XGUI_Displayer::deactivateObjects()
+{
+ myActiveSelectionModes.clear();
+ Handle(AIS_InteractiveContext) aContext = AISContext();
+ // Open local context if there is no one
+ if (!aContext->HasOpenedContext())
+ return;
+
+ aContext->NotUseDisplayedObjects();
+ AIS_ListOfInteractive aPrsList;
+ aContext->DisplayedObjects(aPrsList);
+
+ AIS_ListIteratorOfListOfInteractive aLIt;
+ Handle(AIS_Trihedron) aTrihedron;
+ Handle(AIS_InteractiveObject) anAISIO;
+ for(aLIt.Initialize(aPrsList); aLIt.More(); aLIt.Next()){
+ anAISIO = aLIt.Value();
+ aTrihedron = Handle(AIS_Trihedron)::DownCast(anAISIO);
+ if (!aTrihedron.IsNull()) {
+ aContext->Deactivate(aTrihedron);
+ } else {
+ //aContext->Load(anAISIO, -1, true);
+ aContext->Deactivate(anAISIO);
+ //aContext->Activate(anAISIO);
+ }
+ }
+}
+
bool XGUI_Displayer::isActive(ObjectPtr theObject) const
{
Handle(AIS_InteractiveContext) aContext = AISContext();
updateViewer();
}
-void XGUI_Displayer::eraseDeletedResults(const bool isUpdateViewer)
-{
- Handle(AIS_InteractiveContext) aContext = AISContext();
- if (aContext.IsNull())
- return;
-
- QObjectPtrList aRemoved;
- foreach (ObjectPtr aFeature, myResult2AISObjectMap.keys()) {
- if (!aFeature || !aFeature->data() || !aFeature->data()->isValid()) {
- AISObjectPtr anObj = myResult2AISObjectMap[aFeature];
- if (!anObj)
- continue;
- Handle(AIS_InteractiveObject) anAIS = anObj->impl<Handle(AIS_InteractiveObject)>();
- if (!anAIS.IsNull()) {
- aContext->Remove(anAIS, false);
- aRemoved.append(aFeature);
- }
- }
- }
- foreach(ObjectPtr aObj, aRemoved) {
- myResult2AISObjectMap.remove(aObj);
- }
-
- if (isUpdateViewer)
- updateViewer();
-}
+//void XGUI_Displayer::eraseDeletedResults(const bool isUpdateViewer)
+//{
+// Handle(AIS_InteractiveContext) aContext = AISContext();
+// if (aContext.IsNull())
+// return;
+//
+// QObjectPtrList aRemoved;
+// foreach (ObjectPtr aFeature, myResult2AISObjectMap.keys()) {
+// if (!aFeature || !aFeature->data() || !aFeature->data()->isValid()) {
+// AISObjectPtr anObj = myResult2AISObjectMap[aFeature];
+// if (!anObj)
+// continue;
+// Handle(AIS_InteractiveObject) anAIS = anObj->impl<Handle(AIS_InteractiveObject)>();
+// if (!anAIS.IsNull()) {
+// aContext->Remove(anAIS, false);
+// aRemoved.append(aFeature);
+// }
+// }
+// }
+// foreach(ObjectPtr aObj, aRemoved) {
+// myResult2AISObjectMap.remove(aObj);
+// }
+//
+// if (isUpdateViewer)
+// updateViewer();
+//}
void XGUI_Displayer::openLocalContext()
{
aContext->ClearCurrents();
aContext->OpenLocalContext();
- aContext->NotUseDisplayedObjects();
+ //aContext->NotUseDisplayedObjects();
- myUseExternalObjects = false;
+ //myUseExternalObjects = false;
myActiveSelectionModes.clear();
SelectMgr_ListIteratorOfListOfFilter aIt(aFilters);
if (isUpdateViewer)
updateViewer();
- myUseExternalObjects = false;
+ //myUseExternalObjects = false;
myActiveSelectionModes.clear();
// Restore selection
Handle(AIS_InteractiveContext) XGUI_Displayer::AISContext() const
{
- return myWorkshop->viewer()->AISContext();
+ Handle(AIS_InteractiveContext) aContext = myWorkshop->viewer()->AISContext();
+ if ((!aContext.IsNull()) && (!aContext->HasOpenedContext())) {
+ aContext->OpenLocalContext();
+ }
+ return aContext;
}
Handle(SelectMgr_AndFilter) XGUI_Displayer::GetFilter()
if (!anAISIO.IsNull()) {
aContext->Display(anAISIO, isUpdate);
if (aContext->HasOpenedContext()) {
- if (myUseExternalObjects) {
+ //if (myUseExternalObjects) {
if (myActiveSelectionModes.size() == 0)
aContext->Activate(anAISIO);
else {
aContext->Activate(anAISIO, aMode);
}
}
- }
+ //}
}
}
}
}
}
-void XGUI_Displayer::activateObjects(const QIntList& theModes)
-{
- Handle(AIS_InteractiveContext) aContext = AISContext();
- // Open local context if there is no one
- if (!aContext->HasOpenedContext())
- return;
-
- aContext->UseDisplayedObjects();
- myUseExternalObjects = true;
- myActiveSelectionModes = theModes;
-
- //Deactivate trihedron which can be activated in local selector
- AIS_ListOfInteractive aPrsList;
- aContext->DisplayedObjects(aPrsList, true);
-
- Handle(AIS_Trihedron) aTrihedron;
- AIS_ListIteratorOfListOfInteractive aLIt(aPrsList);
- for(; aLIt.More(); aLIt.Next()){
- aTrihedron = Handle(AIS_Trihedron)::DownCast(aLIt.Value());
- if (!aTrihedron.IsNull()) {
- aContext->Deactivate(aTrihedron);
- break;
- }
- }
-
- //Activate all displayed objects with the module modes
- //AIS_ListOfInteractive aPrsList;
- //aContext->DisplayedObjects(aPrsList, true);
-
- //AIS_ListIteratorOfListOfInteractive aLIt(aPrsList);
- Handle(AIS_InteractiveObject) anAISIO;
- for(aLIt.Initialize(aPrsList); aLIt.More(); aLIt.Next()){
- anAISIO = aLIt.Value();
- aTrihedron = Handle(AIS_Trihedron)::DownCast(anAISIO);
- if (!aTrihedron.IsNull())
- continue;
-
- aContext->Load(anAISIO, -1, true);
- if (theModes.size() == 0)
- aContext->Activate(anAISIO);
- else {
- foreach(int aMode, theModes) {
- aContext->Activate(anAISIO, aMode);
- }
- }
- }
-}
-
-
-void XGUI_Displayer::deactivateObjects()
-{
- Handle(AIS_InteractiveContext) aContext = AISContext();
- // Open local context if there is no one
- if (!aContext->HasOpenedContext())
- return;
-
- aContext->NotUseDisplayedObjects();
-}
-
void XGUI_Displayer::setDisplayMode(ObjectPtr theObject, DisplayMode theMode, bool toUpdate)
{
/// Erase AIS interactive objects, which has an empty feature in the internal map
/// \param isUpdateViewer the parameter whether the viewer should be update immediatelly
- void eraseDeletedResults(const bool isUpdateViewer = true);
-
- /// Opens local context. Does nothing if it is already opened.
- void openLocalContext();
+ //void eraseDeletedResults(const bool isUpdateViewer = true);
/// Deactivates selection of sub-shapes
/// \param isUpdateViewer the parameter whether the viewer should be update immediatelly
*/
void redisplay(ObjectPtr theObject, bool isUpdateViewer = true);
+ /// Opens local context. Does nothing if it is already opened.
+ void openLocalContext();
+
protected:
XGUI_Workshop* myWorkshop;
ResultToAISMap myResult2AISObjectMap;
// A flag of initialization of external objects selection
- bool myUseExternalObjects;
+ //bool myUseExternalObjects;
// Selection modes installed for external objects in local context
QIntList myActiveSelectionModes;
};
{
XGUI_Displayer* aDisp = myWorkshop->displayer();
// Close context if it was opened in order to clear stsndard selection modes
- aDisp->closeLocalContexts(false);
- aDisp->openLocalContext();
+ //aDisp->closeLocalContexts(false);
+ //aDisp->openLocalContext();
// Convert shape types to selection types
QIntList aModes;
foreach(int aType, theTypes) {
XGUI_Displayer* aDisp = myWorkshop->displayer();
// The document limitation selection has to be only during operation
//aDisp->removeSelectionFilter(myDocumentShapeFilter);
- aDisp->closeLocalContexts(false);
+ //aDisp->closeLocalContexts(false);
}
AISObjectPtr XGUI_ModuleConnector::findPresentation(const ObjectPtr& theObject) const
{
myWorkshop->displayer()->removeFilters();
}
+
+//***************************************
+void XGUI_ViewerProxy::update()
+{
+ myWorkshop->displayer()->updateViewer();
+}
/// Remove all selection filters from the viewer
virtual void clearSelectionFilters();
+ /// Update current viewer
+ virtual void update();
+
private slots:
void onTryCloseView(AppElements_ViewWindow*);
void onDeleteView(AppElements_ViewWindow*);