From a4702753c7da76a6434c9458f11ffce426be6e75 Mon Sep 17 00:00:00 2001 From: nds Date: Fri, 13 Mar 2015 11:29:19 +0300 Subject: [PATCH] Multi-selection widget to be used in the extrusion feature. --- .../FeaturesPlugin_Extrusion.cpp | 28 ++-- src/FeaturesPlugin/FeaturesPlugin_Extrusion.h | 11 ++ src/FeaturesPlugin/extrusion_widget.xml | 13 +- src/ModuleBase/CMakeLists.txt | 2 + .../ModuleBase_WidgetMultiSelector.cpp | 126 ++++++++++-------- .../ModuleBase_WidgetMultiSelector.h | 19 ++- .../ModuleBase_WidgetShapeSelector.cpp | 102 ++------------ .../ModuleBase_WidgetShapeSelector.h | 23 +--- src/ModuleBase/ModuleBase_WidgetValidated.cpp | 86 ++++++++++++ src/ModuleBase/ModuleBase_WidgetValidated.h | 58 ++++++++ src/PartSet/CMakeLists.txt | 2 + src/PartSet/PartSet_FilterSketchEntity.cpp | 43 ++++++ src/PartSet/PartSet_FilterSketchEntity.h | 33 +++++ src/PartSet/PartSet_Module.cpp | 3 + src/PartSet/PartSet_WidgetShapeSelector.cpp | 23 +--- 15 files changed, 359 insertions(+), 213 deletions(-) create mode 100644 src/ModuleBase/ModuleBase_WidgetValidated.cpp create mode 100644 src/ModuleBase/ModuleBase_WidgetValidated.h create mode 100644 src/PartSet/PartSet_FilterSketchEntity.cpp create mode 100644 src/PartSet/PartSet_FilterSketchEntity.h diff --git a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp index 265ba6576..d3473fa85 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp +++ b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.cpp @@ -12,6 +12,7 @@ #include #include #include +#include #include #include @@ -27,15 +28,20 @@ FeaturesPlugin_Extrusion::FeaturesPlugin_Extrusion() void FeaturesPlugin_Extrusion::initAttributes() { - data()->addAttribute(FeaturesPlugin_Extrusion::FACE_ID(), ModelAPI_AttributeSelection::type()); + data()->addAttribute(FeaturesPlugin_Extrusion::LIST_ID(), ModelAPI_AttributeSelectionList::type()); data()->addAttribute(FeaturesPlugin_Extrusion::SIZE_ID(), ModelAPI_AttributeDouble::type()); data()->addAttribute(FeaturesPlugin_Extrusion::REVERSE_ID(), ModelAPI_AttributeBoolean::type()); } void FeaturesPlugin_Extrusion::execute() { - std::shared_ptr aFaceRef = std::dynamic_pointer_cast< - ModelAPI_AttributeSelection>(data()->attribute(FeaturesPlugin_Extrusion::FACE_ID())); + std::shared_ptr aFaceRefs = std::dynamic_pointer_cast< + ModelAPI_AttributeSelectionList>(data()->attribute(FeaturesPlugin_Extrusion::LIST_ID())); + if (aFaceRefs.get() == NULL || aFaceRefs->size() == 0) { + clearResult(); + return; + } + std::shared_ptr aFaceRef = aFaceRefs->value(0); if (!aFaceRef) return; @@ -46,11 +52,8 @@ void FeaturesPlugin_Extrusion::execute() std::shared_ptr aContext; ResultPtr aContextRes = aFaceRef->context(); - if (aContextRes) { - if (aContextRes->groupName() == ModelAPI_ResultBody::group()) - aContext = std::dynamic_pointer_cast(aContextRes)->shape(); - else if (aContextRes->groupName() == ModelAPI_ResultConstruction::group()) - aContext = std::dynamic_pointer_cast(aContextRes)->shape(); + if (aContextRes && aContextRes->groupName() == ModelAPI_ResultConstruction::group()) { + aContext = std::dynamic_pointer_cast(aContextRes)->shape(); } if (!aContext) { static const std::string aContextError = "The selection context is bad"; @@ -131,3 +134,12 @@ void FeaturesPlugin_Extrusion::LoadNamingDS(GeomAlgoAPI_Extrusion& theFeature, } } + +//============================================================================ +void FeaturesPlugin_Extrusion::clearResult() +{ + std::shared_ptr aResultBody = document()->createBody(data()); + std::shared_ptr anEmptyShape(new GeomAPI_Shape); + aResultBody->store(anEmptyShape); + setResult(aResultBody); +} \ No newline at end of file diff --git a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.h b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.h index bbc636c92..87f33180d 100644 --- a/src/FeaturesPlugin/FeaturesPlugin_Extrusion.h +++ b/src/FeaturesPlugin/FeaturesPlugin_Extrusion.h @@ -36,6 +36,14 @@ class FeaturesPlugin_Extrusion : public ModelAPI_Feature static const std::string MY_FACE_ID("extrusion_face"); return MY_FACE_ID; } + /// attribute name of references sketch entities list, it should contain a sketch result or + /// a pair a sketch result to sketch face + inline static const std::string& LIST_ID() + { + static const std::string MY_GROUP_LIST_ID("group_list"); + return MY_GROUP_LIST_ID; + } + /// attribute name of extrusion size inline static const std::string& SIZE_ID() { @@ -69,6 +77,9 @@ private: void LoadNamingDS(GeomAlgoAPI_Extrusion& theFeature, std::shared_ptr theResultBody, std::shared_ptr theBasis, std::shared_ptr theContext); + + /// Set an empty shape to the result of extrusion + void clearResult(); }; #endif diff --git a/src/FeaturesPlugin/extrusion_widget.xml b/src/FeaturesPlugin/extrusion_widget.xml index 6f2ea7d18..9e3857742 100644 --- a/src/FeaturesPlugin/extrusion_widget.xml +++ b/src/FeaturesPlugin/extrusion_widget.xml @@ -1,15 +1,14 @@ - + tooltip="Select a sketch face" + type_choice="Faces"> - + + getProperty("type_choice"); + QString aTypesStr = aPropertyTypes.c_str(); QStringList aShapeTypes = aTypesStr.split(' '); + myTypeCombo->addItems(aShapeTypes); aMainLay->addWidget(myTypeCombo, 0, 1); + // if the xml definition contains one type, the controls to select a type should not be shown + if (aShapeTypes.size() == 1) { + aTypeLabel->setVisible(false); + myTypeCombo->setVisible(false); + } QLabel* aListLabel = new QLabel(tr("Selected objects:"), this); - aMainLay->addWidget(aListLabel, 1, 0, 1, -1); + aMainLay->addWidget(aListLabel, 1, 0); + // if the xml definition contains one type, an information label should be shown near to the latest + if (aShapeTypes.size() == 1) { + QString aLabelText = QString::fromStdString(theData->widgetLabel()); + QString aLabelIcon = QString::fromStdString(theData->widgetIcon()); + QLabel* aSelectedLabel = new QLabel(aLabelText, this); + if (!aLabelIcon.isEmpty()) + aSelectedLabel->setPixmap(QPixmap(aLabelIcon)); + aMainLay->addWidget(aSelectedLabel, 1, 1); + aMainLay->setColumnStretch(2, 1); + } myListControl = new QListWidget(this); aMainLay->addWidget(myListControl, 2, 0, 2, -1); @@ -72,13 +90,32 @@ ModuleBase_WidgetMultiSelector::ModuleBase_WidgetMultiSelector(QWidget* theParen myListControl->addAction(myCopyAction); myListControl->setContextMenuPolicy(Qt::ActionsContextMenu); connect(myListControl, SIGNAL(itemSelectionChanged()), SLOT(onListSelection())); - - activateSelection(true); } ModuleBase_WidgetMultiSelector::~ModuleBase_WidgetMultiSelector() { - activateSelection(false); + myIsActive = false; + activateShapeSelection(); +} + +//******************************************************************** +void ModuleBase_WidgetMultiSelector::activateCustom() +{ + ModuleBase_IViewer* aViewer = myWorkshop->viewer(); + connect(myWorkshop, SIGNAL(selectionChanged()), + this, SLOT(onSelectionChanged()), + Qt::UniqueConnection); + + myIsActive = true; + activateShapeSelection(); +} + +//******************************************************************** +void ModuleBase_WidgetMultiSelector::deactivate() +{ + disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); + myIsActive = false; + activateShapeSelection(); } //******************************************************************** @@ -150,23 +187,6 @@ bool ModuleBase_WidgetMultiSelector::eventFilter(QObject* theObj, QEvent* theEve return ModuleBase_ModelWidget::eventFilter(theObj, theEvent); } -//******************************************************************** -void ModuleBase_WidgetMultiSelector::activateSelection(bool toActivate) -{ - myIsActive = toActivate; - if (myIsActive) { - connect(myWorkshop, SIGNAL(selectionChanged()), - this, SLOT(onSelectionChanged()), - Qt::UniqueConnection); - activateShapeSelection(); - } else { - disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); - myWorkshop->deactivateSubShapesSelection(); - - myWorkshop->viewer()->removeSelectionFilter(myEdgesTypeFilter); - } -} - //******************************************************************** void ModuleBase_WidgetMultiSelector::onSelectionTypeChanged() { @@ -213,23 +233,6 @@ void ModuleBase_WidgetMultiSelector::onSelectionChanged() emit valuesChanged(); } -//******************************************************************** -void ModuleBase_WidgetMultiSelector::filterShapes(const NCollection_List& theShapesToFilter, - NCollection_List& theResult) -{ - if(myTypeCombo->count() == 0 || theShapesToFilter.IsEmpty()) - return; - TopAbs_ShapeEnum aReferenceType = - ModuleBase_WidgetShapeSelector::shapeType(myTypeCombo->currentText()); - NCollection_List::Iterator anIter(theShapesToFilter); - for (; anIter.More(); anIter.Next()) { - TopoDS_Shape aShape = anIter.Value(); - if (aShape.IsNull() || aShape.ShapeType() != aReferenceType) - continue; - theResult.Append(aShape); - } -} - //******************************************************************** void ModuleBase_WidgetMultiSelector::setCurrentShapeType(const TopAbs_ShapeEnum theShapeType) { @@ -239,11 +242,13 @@ void ModuleBase_WidgetMultiSelector::setCurrentShapeType(const TopAbs_ShapeEnum aShapeTypeName = myTypeCombo->itemText(idx); TopAbs_ShapeEnum aRefType = ModuleBase_WidgetShapeSelector::shapeType(aShapeTypeName); if(aRefType == theShapeType && idx != myTypeCombo->currentIndex()) { - activateSelection(false); + myIsActive = false; + activateShapeSelection(); bool isBlocked = myTypeCombo->blockSignals(true); myTypeCombo->setCurrentIndex(idx); + myIsActive = true; myTypeCombo->blockSignals(isBlocked); - activateSelection(true); + activateShapeSelection(); break; } } @@ -251,21 +256,30 @@ void ModuleBase_WidgetMultiSelector::setCurrentShapeType(const TopAbs_ShapeEnum void ModuleBase_WidgetMultiSelector::activateShapeSelection() { - QString aNewType = myTypeCombo->currentText(); - QIntList aList; - aList.append(ModuleBase_WidgetShapeSelector::shapeType(aNewType)); - myWorkshop->activateSubShapesSelection(aList); - - // it is necessary to filter the selected edges to be non-degenerated - // it is not possible to build naming name for such edges - if (aNewType == "Edges") { - myEdgesTypeFilter = new ModuleBase_FilterNoDegeneratedEdge(); - ModuleBase_IViewer* aViewer = myWorkshop->viewer(); - aViewer->addSelectionFilter(myEdgesTypeFilter); - } - else { - myWorkshop->viewer()->removeSelectionFilter(myEdgesTypeFilter); + ModuleBase_IViewer* aViewer = myWorkshop->viewer(); + + if (myIsActive) { + QString aNewType = myTypeCombo->currentText(); + QIntList aList; + aList.append(ModuleBase_WidgetShapeSelector::shapeType(aNewType)); + myWorkshop->activateSubShapesSelection(aList); + + // it is necessary to filter the selected edges to be non-degenerated + // it is not possible to build naming name for such edges + if (aNewType == "Edges") { + myEdgesTypeFilter = new ModuleBase_FilterNoDegeneratedEdge(); + aViewer->addSelectionFilter(myEdgesTypeFilter); + } + else { + aViewer->removeSelectionFilter(myEdgesTypeFilter); + } + + } else { + myWorkshop->deactivateSubShapesSelection(); + aViewer->removeSelectionFilter(myEdgesTypeFilter); } + + activateFilters(myWorkshop, myIsActive); } //******************************************************************** diff --git a/src/ModuleBase/ModuleBase_WidgetMultiSelector.h b/src/ModuleBase/ModuleBase_WidgetMultiSelector.h index 660fe0698..bdb1a46ed 100644 --- a/src/ModuleBase/ModuleBase_WidgetMultiSelector.h +++ b/src/ModuleBase/ModuleBase_WidgetMultiSelector.h @@ -11,7 +11,7 @@ #define MODULEBASE_WIDGETMULTISELECTOR_H_ #include -#include +#include #include #include @@ -47,7 +47,7 @@ class QAction; * - tooltip - a tooltip for the widget * - type_choice - list of expected shape types. */ -class MODULEBASE_EXPORT ModuleBase_WidgetMultiSelector : public ModuleBase_ModelWidget +class MODULEBASE_EXPORT ModuleBase_WidgetMultiSelector : public ModuleBase_WidgetValidated { Q_OBJECT public: @@ -70,10 +70,10 @@ class MODULEBASE_EXPORT ModuleBase_WidgetMultiSelector : public ModuleBase_Model virtual bool eventFilter(QObject* , QEvent* ); - public slots: - /// Activate or deactivate selection - void activateSelection(bool toActivate); + /// The methiod called when widget is deactivated + virtual void deactivate(); + public slots: /// Slot is called on selection type changed void onSelectionTypeChanged(); @@ -88,16 +88,13 @@ protected slots: void onListSelection(); protected: + /// The methiod called when widget is activated + virtual void activateCustom(); + /// Saves the internal parameters to the given feature /// \return True in success virtual bool storeValueCustom() const; - /// Provide filtering of selected shapes - /// \param theShapesToFilter source list of shapes - /// \param theResult result list of shapes - void filterShapes(const NCollection_List& theShapesToFilter, - NCollection_List& theResult); - /// Set current shape type for selection void setCurrentShapeType(const TopAbs_ShapeEnum theShapeType); diff --git a/src/ModuleBase/ModuleBase_WidgetShapeSelector.cpp b/src/ModuleBase/ModuleBase_WidgetShapeSelector.cpp index 5514a06e3..3d376aace 100644 --- a/src/ModuleBase/ModuleBase_WidgetShapeSelector.cpp +++ b/src/ModuleBase/ModuleBase_WidgetShapeSelector.cpp @@ -93,7 +93,7 @@ ModuleBase_WidgetShapeSelector::ModuleBase_WidgetShapeSelector(QWidget* theParen ModuleBase_IWorkshop* theWorkshop, const Config_WidgetAPI* theData, const std::string& theParentId) - : ModuleBase_ModelWidget(theParent, theData, theParentId), + : ModuleBase_WidgetValidated(theParent, theData, theParentId), myWorkshop(theWorkshop), myIsActive(false) { QFormLayout* aLayout = new QFormLayout(this); @@ -116,9 +116,6 @@ ModuleBase_WidgetShapeSelector::ModuleBase_WidgetShapeSelector(QWidget* theParen std::string aTypes = theData->getProperty("shape_types"); myShapeTypes = QString(aTypes.c_str()).split(' ', QString::SkipEmptyParts); - - std::string aObjTypes = theData->getProperty("object_types"); - myObjectTypes = QString(aObjTypes.c_str()).split(' ', QString::SkipEmptyParts); } //******************************************************************** @@ -266,10 +263,6 @@ bool ModuleBase_WidgetShapeSelector::setSelection(ModuleBase_ViewerPrs theValue) if (!aShape) return false; - /// Check that object has acceptable type - if (!acceptObjectType(aObject)) - return false; - // Get sub-shapes from local selection if (!theValue.shape().IsNull()) { aShape = std::shared_ptr(new GeomAPI_Shape()); @@ -286,7 +279,7 @@ bool ModuleBase_WidgetShapeSelector::setSelection(ModuleBase_ViewerPrs theValue) Handle(SelectMgr_EntityOwner) anOwner = theValue.owner(); if (!anOwner.IsNull()) { SelectMgr_ListOfFilter aFilters; - selectionFilters(aFilters); + selectionFilters(myWorkshop, aFilters); SelectMgr_ListIteratorOfListOfFilter aIt(aFilters); for (; aIt.More(); aIt.Next()) { const Handle(SelectMgr_Filter)& aFilter = aIt.Value(); @@ -354,26 +347,6 @@ bool ModuleBase_WidgetShapeSelector::acceptSubShape(std::shared_ptr(theObject); - return (aConstr != NULL); - } // ToDo: Process other types of objects - } - // Object type is defined but not found - return false; -} - - //******************************************************************** void ModuleBase_WidgetShapeSelector::updateSelectionName() { @@ -406,62 +379,18 @@ void ModuleBase_WidgetShapeSelector::activateSelection(bool toActivate) return; myIsActive = toActivate; updateSelectionName(); - ModuleBase_IViewer* aViewer = myWorkshop->viewer(); if (myIsActive) { - connect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); QIntList aList; foreach (QString aType, myShapeTypes) { aList.append(shapeType(aType)); } myWorkshop->activateSubShapesSelection(aList); } else { - disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); myWorkshop->deactivateSubShapesSelection(); } - // the initial code is moved here in order to clear filters, it is possible, that it is excessive and - // is performed outside - if (myIsActive && !myObjectTypes.isEmpty()) { - aViewer->clearSelectionFilters(); - } - SelectMgr_ListOfFilter aFilters; - selectionFilters(aFilters); - SelectMgr_ListIteratorOfListOfFilter aIt(aFilters); - for (; aIt.More(); aIt.Next()) { - const Handle(SelectMgr_Filter)& aSelFilter = aIt.Value(); - if (myIsActive) - aViewer->addSelectionFilter(aSelFilter); - else - aViewer->removeSelectionFilter(aSelFilter); - } - // the internal filter should be removed by the widget deactivation, it is done historically - if (!myIsActive && !myObjTypeFilter.IsNull()) { - myObjTypeFilter.Nullify(); - } -} - -//******************************************************************** -void ModuleBase_WidgetShapeSelector::selectionFilters(SelectMgr_ListOfFilter& theFilters) -{ - if (!myObjectTypes.isEmpty() && myObjTypeFilter.IsNull()) { - myObjTypeFilter = new ModuleBase_ObjectTypesFilter(myWorkshop, myObjectTypes); - } - if (!myObjTypeFilter.IsNull()) - theFilters.Append(myObjTypeFilter); - - // apply filters loaded from the XML definition of the widget - ModuleBase_FilterFactory* aFactory = myWorkshop->selectionFilters(); - SelectMgr_ListOfFilter aFilters; - aFactory->filters(parentID(), attributeID(), aFilters); - SelectMgr_ListIteratorOfListOfFilter aIt(aFilters); - for (; aIt.More(); aIt.Next()) { - Handle(SelectMgr_Filter) aSelFilter = aIt.Value(); - if (aSelFilter.IsNull()) - continue; - - theFilters.Append(aSelFilter); - } + activateFilters(myWorkshop, myIsActive); } //******************************************************************** @@ -484,6 +413,7 @@ void ModuleBase_WidgetShapeSelector::raisePanel() const //******************************************************************** void ModuleBase_WidgetShapeSelector::activateCustom() { + connect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); activateSelection(true); } @@ -491,36 +421,24 @@ void ModuleBase_WidgetShapeSelector::activateCustom() void ModuleBase_WidgetShapeSelector::deactivate() { activateSelection(false); + disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); } //******************************************************************** bool ModuleBase_WidgetShapeSelector::isValid(ObjectPtr theObj, std::shared_ptr theShape) { + bool isValid = ModuleBase_WidgetValidated::isValid(theObj, theShape); + if (!isValid) + return false; + SessionPtr aMgr = ModelAPI_Session::get(); ModelAPI_ValidatorsFactory* aFactory = aMgr->validators(); std::list aValidators; std::list > anArguments; aFactory->validators(parentID(), attributeID(), aValidators, anArguments); - // Check the type of selected object - std::list::iterator aValidator = aValidators.begin(); - bool isValid = true; - for (; aValidator != aValidators.end(); aValidator++) { - const ModelAPI_ResultValidator* aResValidator = - dynamic_cast(*aValidator); - if (aResValidator) { - isValid = false; - if (aResValidator->isValid(theObj)) { - isValid = true; - break; - } - } - } - if (!isValid) - return false; - // Check the acceptability of the object as attribute - aValidator = aValidators.begin(); + std::list::iterator aValidator = aValidators.begin(); std::list >::iterator aArgs = anArguments.begin(); for (; aValidator != aValidators.end(); aValidator++, aArgs++) { const ModelAPI_RefAttrValidator* aAttrValidator = diff --git a/src/ModuleBase/ModuleBase_WidgetShapeSelector.h b/src/ModuleBase/ModuleBase_WidgetShapeSelector.h index 98a1e4c34..f4be3ab69 100644 --- a/src/ModuleBase/ModuleBase_WidgetShapeSelector.h +++ b/src/ModuleBase/ModuleBase_WidgetShapeSelector.h @@ -8,14 +8,13 @@ #define ModuleBase_WidgetShapeSelector_H #include "ModuleBase.h" -#include "ModuleBase_ModelWidget.h" +#include "ModuleBase_WidgetValidated.h" #include "ModuleBase_ViewerFilters.h" #include #include #include -#include #include @@ -52,7 +51,7 @@ class ModuleBase_IWorkshop; * which corresponds to ModelAPI_ResultConstruction object type * - concealment - hide or not hide selected object after operation */ -class MODULEBASE_EXPORT ModuleBase_WidgetShapeSelector : public ModuleBase_ModelWidget +class MODULEBASE_EXPORT ModuleBase_WidgetShapeSelector : public ModuleBase_WidgetValidated { Q_OBJECT public: @@ -124,12 +123,6 @@ Q_OBJECT /// \param theShape a shape virtual bool acceptSubShape(std::shared_ptr theShape) const; - /// Returns true if selected object corresponds to requested Object type - /// Thid method is used in any selection mode - /// \param theObject an object - virtual bool acceptObjectType(const ObjectPtr theObject) const; - - // Set the given object as a value of the widget /// \param theObj an object /// \param theShape a shape @@ -143,12 +136,6 @@ Q_OBJECT /// Clear attribute void clearAttribute(); - /// Fills the given list with all widget filters. It can be used by activation widget for the viewer - /// or by checking the selection parameter in addition to check validity of the selection argument - /// It creates an object type filter if it has not been created yet and save it in the class field - /// \param theFilters a list of filter - void selectionFilters(SelectMgr_ListOfFilter& theFilters); - //----------- Class members ------------- protected: /// Label of the widget @@ -169,14 +156,8 @@ Q_OBJECT /// List of accepting shapes types QStringList myShapeTypes; - /// List of accepting object types - QStringList myObjectTypes; - /// Active/inactive flag bool myIsActive; - - /// Filter by objects types - Handle(ModuleBase_ObjectTypesFilter) myObjTypeFilter; }; #endif diff --git a/src/ModuleBase/ModuleBase_WidgetValidated.cpp b/src/ModuleBase/ModuleBase_WidgetValidated.cpp new file mode 100644 index 000000000..a6f05af60 --- /dev/null +++ b/src/ModuleBase/ModuleBase_WidgetValidated.cpp @@ -0,0 +1,86 @@ +// Copyright (C) 2014-20xx CEA/DEN, EDF R&D + +#include +#include +#include +#include + +#include +#include +#include + +#include + +ModuleBase_WidgetValidated::ModuleBase_WidgetValidated(QWidget* theParent, + const Config_WidgetAPI* theData, + const std::string& theParentId) + : ModuleBase_ModelWidget(theParent, theData, theParentId) +{ +} + +ModuleBase_WidgetValidated::~ModuleBase_WidgetValidated() +{ +} + +//******************************************************************** +bool ModuleBase_WidgetValidated::isValid(ObjectPtr theObj, GeomShapePtr theShape) const +{ + SessionPtr aMgr = ModelAPI_Session::get(); + ModelAPI_ValidatorsFactory* aFactory = aMgr->validators(); + std::list aValidators; + std::list > anArguments; + aFactory->validators(parentID(), attributeID(), aValidators, anArguments); + + // Check the type of selected object + std::list::iterator aValidator = aValidators.begin(); + bool isValid = true; + for (; aValidator != aValidators.end(); aValidator++) { + const ModelAPI_ResultValidator* aResValidator = + dynamic_cast(*aValidator); + if (aResValidator) { + isValid = false; + if (aResValidator->isValid(theObj)) { + isValid = true; + break; + } + } + } + return isValid; +} + +void ModuleBase_WidgetValidated::activateFilters(ModuleBase_IWorkshop* theWorkshop, + const bool toActivate) const +{ + ModuleBase_IViewer* aViewer = theWorkshop->viewer(); + + // apply filters loaded from the XML definition of the widget + ModuleBase_FilterFactory* aFactory = theWorkshop->selectionFilters(); + SelectMgr_ListOfFilter aFactoryFilters; + aFactory->filters(parentID(), attributeID(), aFactoryFilters); + SelectMgr_ListIteratorOfListOfFilter aFactoryIt(aFactoryFilters); + for (; aFactoryIt.More(); aFactoryIt.Next()) { + Handle(SelectMgr_Filter) aSelFilter = aFactoryIt.Value(); + if (aSelFilter.IsNull()) + continue; + if (toActivate) + aViewer->addSelectionFilter(aSelFilter); + else + aViewer->removeSelectionFilter(aSelFilter); + } +} + +void ModuleBase_WidgetValidated::selectionFilters(ModuleBase_IWorkshop* theWorkshop, + SelectMgr_ListOfFilter& theFilters) const +{ + ModuleBase_FilterFactory* aFactory = theWorkshop->selectionFilters(); + SelectMgr_ListOfFilter aFilters; + aFactory->filters(parentID(), attributeID(), aFilters); + SelectMgr_ListIteratorOfListOfFilter aIt(aFilters); + for (; aIt.More(); aIt.Next()) { + Handle(SelectMgr_Filter) aSelFilter = aIt.Value(); + if (aSelFilter.IsNull()) + continue; + + theFilters.Append(aSelFilter); + } +} diff --git a/src/ModuleBase/ModuleBase_WidgetValidated.h b/src/ModuleBase/ModuleBase_WidgetValidated.h new file mode 100644 index 000000000..014668e12 --- /dev/null +++ b/src/ModuleBase/ModuleBase_WidgetValidated.h @@ -0,0 +1,58 @@ +// Copyright (C) 2014-20xx CEA/DEN, EDF R&D + +// File: ModuleBase_WidgetValidated.h +// Created: 12 Mar 2015 +// Author: Natalia ERMOLAEVA + + +#ifndef MODULEBASE_WIDGETVALIDATED_H_ +#define MODULEBASE_WIDGETVALIDATED_H_ + +#include +#include + +#include +#include + +#include + +class QWidget; +class ModuleBase_IWorkshop; +class Config_WidgetAPI; + +/** +* \ingroup GUI +* Implementation of widget with validators and filters processing. +*/ +class MODULEBASE_EXPORT ModuleBase_WidgetValidated : public ModuleBase_ModelWidget +{ + Q_OBJECT + public: + /// Constructor + /// \param theParent the parent object + /// \param theData the widget configuation. The attribute of the model widget is obtained from + /// \param theParentId is Id of a parent of the current attribute + ModuleBase_WidgetValidated(QWidget* theParent, + const Config_WidgetAPI* theData, + const std::string& theParentId); + virtual ~ModuleBase_WidgetValidated(); + +protected: + /// Check the selected with validators if installed + /// \param theObj the object for checking + /// \param theShape the shape for checking + virtual bool isValid(ObjectPtr theObj, GeomShapePtr theShape) const; + + /// It obtains selection filters from the workshop and activates them in the active viewer + /// \param theWorkshop an active workshop + /// \param toActivate a flag about activation or deactivation the filters + virtual void activateFilters(ModuleBase_IWorkshop* theWorkshop, const bool toActivate) const; + + /// Fills the given list with all widget filters. + /// \param theWorkshop an active workshop + /// \param theFilters a list of filters + void selectionFilters(ModuleBase_IWorkshop* theWorkshop, + SelectMgr_ListOfFilter& theFilters) const; +}; + +#endif /* MODULEBASE_WIDGETVALIDATED_H_ */ diff --git a/src/PartSet/CMakeLists.txt b/src/PartSet/CMakeLists.txt index 60388bb2b..326fb1c61 100644 --- a/src/PartSet/CMakeLists.txt +++ b/src/PartSet/CMakeLists.txt @@ -16,6 +16,7 @@ SET(PROJECT_HEADERS PartSet_WidgetPoint2dDistance.h PartSet_WidgetShapeSelector.h PartSet_Filters.h + PartSet_FilterSketchEntity.h PartSet_SketcherMgr.h ) @@ -29,6 +30,7 @@ SET(PROJECT_SOURCES PartSet_WidgetPoint2dDistance.cpp PartSet_WidgetShapeSelector.cpp PartSet_Filters.cpp + PartSet_FilterSketchEntity.cpp PartSet_SketcherMgr.cpp ) diff --git a/src/PartSet/PartSet_FilterSketchEntity.cpp b/src/PartSet/PartSet_FilterSketchEntity.cpp new file mode 100644 index 000000000..04b5f4f3e --- /dev/null +++ b/src/PartSet/PartSet_FilterSketchEntity.cpp @@ -0,0 +1,43 @@ +// Copyright (C) 2014-20xx CEA/DEN, EDF R&D + +// File: PartSet_FilterSketchEntity.cpp +// Created: 13 Mar 2015 +// Author: Natalia ERMOLAEVA + +#include "PartSet_FilterSketchEntity.h" + +#include + +#include +#include + +#include + +#include +#include + + +IMPLEMENT_STANDARD_HANDLE(PartSet_FilterSketchEntity, ModuleBase_ShapeDocumentFilter); +IMPLEMENT_STANDARD_RTTIEXT(PartSet_FilterSketchEntity, ModuleBase_ShapeDocumentFilter); + +Standard_Boolean PartSet_FilterSketchEntity::IsOk(const Handle(SelectMgr_EntityOwner)& theOwner) const +{ + if (ModuleBase_ShapeDocumentFilter::IsOk(theOwner)) { + if (theOwner->HasSelectable()) { + Handle(AIS_InteractiveObject) aAisObj = + Handle(AIS_InteractiveObject)::DownCast(theOwner->Selectable()); + if (!aAisObj.IsNull()) { + std::shared_ptr aAISObj = AISObjectPtr(new GeomAPI_AISObject()); + aAISObj->setImpl(new Handle(AIS_InteractiveObject)(aAisObj)); + ObjectPtr aObj = myWorkshop->findPresentedObject(aAISObj); + if (aObj) { + FeaturePtr aFeature = ModelAPI_Feature::feature(aObj); + + if (aFeature->getKind() == SketchPlugin_Sketch::ID()) + return Standard_True; + } + } + } + } + return Standard_False; +} diff --git a/src/PartSet/PartSet_FilterSketchEntity.h b/src/PartSet/PartSet_FilterSketchEntity.h new file mode 100644 index 000000000..62849e6f8 --- /dev/null +++ b/src/PartSet/PartSet_FilterSketchEntity.h @@ -0,0 +1,33 @@ +// Copyright (C) 2014-20xx CEA/DEN, EDF R&D + +// File: PartSet_FilterSketchEntity.h +// Created: 13 Mar 2015 +// Author: Natalia ERMOLAEVA + +#ifndef PartSet_FilterSketchEntity_H +#define PartSet_FilterSketchEntity_H + +#include + +/** +* \class PartSet_FilterSketchEntity +* \ingroup Modules +* A class which filters groups object in addition to documents (see issue #310) +*/ +DEFINE_STANDARD_HANDLE(PartSet_FilterSketchEntity, ModuleBase_ShapeDocumentFilter); +class PartSet_FilterSketchEntity: public ModuleBase_ShapeDocumentFilter +{ +public: + /// Constructor + /// \param theWorkshop a pointer to workshop + PartSet_FilterSketchEntity(ModuleBase_IWorkshop* theWorkshop) + : ModuleBase_ShapeDocumentFilter(theWorkshop) {} + + /// Returns True if selected presentation can be selected + /// \param theOwner an owner of the persentation + Standard_EXPORT virtual Standard_Boolean IsOk(const Handle(SelectMgr_EntityOwner)& theOwner) const; + + DEFINE_STANDARD_RTTI(PartSet_FilterSketchEntity) +}; + +#endif \ No newline at end of file diff --git a/src/PartSet/PartSet_Module.cpp b/src/PartSet/PartSet_Module.cpp index 08191e8d3..ebc5db732 100644 --- a/src/PartSet/PartSet_Module.cpp +++ b/src/PartSet/PartSet_Module.cpp @@ -21,6 +21,7 @@ #include #include #include +#include #include #include @@ -139,6 +140,8 @@ void PartSet_Module::registerFilters() Handle(SelectMgr_Filter) aSelectFilter = new ModuleBase_FilterNoConsructionSubShapes(workshop()); aFactory->registerFilter("NoConstructionSubShapesFilter", new ModuleBase_FilterCustom(aSelectFilter)); + aSelectFilter = new PartSet_FilterSketchEntity(workshop()); + aFactory->registerFilter("SketchEntityFilter", new ModuleBase_FilterCustom(aSelectFilter)); } void PartSet_Module::registerProperties() diff --git a/src/PartSet/PartSet_WidgetShapeSelector.cpp b/src/PartSet/PartSet_WidgetShapeSelector.cpp index bd9e1ce81..d51be0d51 100644 --- a/src/PartSet/PartSet_WidgetShapeSelector.cpp +++ b/src/PartSet/PartSet_WidgetShapeSelector.cpp @@ -65,6 +65,10 @@ bool PartSet_WidgetShapeSelector::storeValueCustom() const //******************************************************************** bool PartSet_WidgetShapeSelector::isValid(ObjectPtr theObj, std::shared_ptr theShape) { + bool isValid = ModuleBase_WidgetValidated::isValid(theObj, theShape); + if (!isValid) + return false; + // the method is redefined to analize the selected shape in validators SessionPtr aMgr = ModelAPI_Session::get(); ModelAPI_ValidatorsFactory* aFactory = aMgr->validators(); @@ -72,23 +76,6 @@ bool PartSet_WidgetShapeSelector::isValid(ObjectPtr theObj, std::shared_ptr > anArguments; aFactory->validators(parentID(), attributeID(), aValidators, anArguments); - // Check the type of selected object - std::list::iterator aValidator = aValidators.begin(); - bool isValid = true; - for (; aValidator != aValidators.end(); aValidator++) { - const ModelAPI_ResultValidator* aResValidator = - dynamic_cast(*aValidator); - if (aResValidator) { - isValid = false; - if (aResValidator->isValid(theObj)) { - isValid = true; - break; - } - } - } - if (!isValid) - return false; - // Check the acceptability of the object and shape as validator attribute AttributePtr aPntAttr; DataPtr aData = myFeature->data(); @@ -102,7 +89,7 @@ bool PartSet_WidgetShapeSelector::isValid(ObjectPtr theObj, std::shared_ptr::iterator aValidator = aValidators.begin(); std::list >::iterator aArgs = anArguments.begin(); for (; aValidator != aValidators.end(); aValidator++, aArgs++) { const ModelAPI_RefAttrValidator* aAttrValidator = -- 2.39.2