X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;ds=sidebyside;f=src%2FModuleBase%2FModuleBase_WidgetMultiSelector.cpp;h=755d74c59217940d963bcbfe16987332b829acb5;hb=f9be1b7f715b7c630906cfde5a1c4ed25e1a1e63;hp=9d74cc2fb48bb08f67d546bcf00611bf0389cf2b;hpb=368eb86f8835d384a102ad84410a6c825c597a8c;p=modules%2Fshaper.git diff --git a/src/ModuleBase/ModuleBase_WidgetMultiSelector.cpp b/src/ModuleBase/ModuleBase_WidgetMultiSelector.cpp index 9d74cc2fb..755d74c59 100644 --- a/src/ModuleBase/ModuleBase_WidgetMultiSelector.cpp +++ b/src/ModuleBase/ModuleBase_WidgetMultiSelector.cpp @@ -13,6 +13,9 @@ #include #include #include +#include + +#include #include #include @@ -38,7 +41,7 @@ ModuleBase_WidgetMultiSelector::ModuleBase_WidgetMultiSelector(QWidget* theParen const Config_WidgetAPI* theData, const std::string& theParentId) : ModuleBase_WidgetValidated(theParent, theData, theParentId), - myWorkshop(theWorkshop), myIsActive(false) + myWorkshop(theWorkshop) { QGridLayout* aMainLay = new QGridLayout(this); ModuleBase_Tools::adjustMargins(aMainLay); @@ -49,19 +52,26 @@ ModuleBase_WidgetMultiSelector::ModuleBase_WidgetMultiSelector(QWidget* theParen myTypeCombo = new QComboBox(this); // There is no sence to paramerize list of types while we can not parametrize selection mode + myShapeValidator = new GeomValidators_ShapeType(); + std::string aPropertyTypes = theData->getProperty("type_choice"); QString aTypesStr = aPropertyTypes.c_str(); QStringList aShapeTypes = aTypesStr.split(' '); + //myIsUseChoice = theData->getBooleanAttribute("use_choice", true); + 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) { + if (aShapeTypes.size() == 1/* || !myIsUseChoice*/) { aTypeLabel->setVisible(false); myTypeCombo->setVisible(false); } - QLabel* aListLabel = new QLabel(tr("Selected objects:"), this); +// Modification for specification of 1.3.0 + std::string aLabelText = "";//theData->getProperty("label"); + QLabel* aListLabel = new QLabel(!aLabelText.empty() ? aLabelText.c_str() + : tr("Selected objects:"), this); 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) { @@ -93,8 +103,13 @@ ModuleBase_WidgetMultiSelector::ModuleBase_WidgetMultiSelector(QWidget* theParen ModuleBase_WidgetMultiSelector::~ModuleBase_WidgetMultiSelector() { - myIsActive = false; - activateShapeSelection(); + delete myShapeValidator; +} + +//TODO: nds stabilization hotfix +void ModuleBase_WidgetMultiSelector::disconnectSignals() +{ + disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); } //******************************************************************** @@ -105,16 +120,20 @@ void ModuleBase_WidgetMultiSelector::activateCustom() this, SLOT(onSelectionChanged()), Qt::UniqueConnection); - myIsActive = true; - activateShapeSelection(); + activateShapeSelection(true); + + // Restore selection in the viewer by the attribute selection list + myWorkshop->setSelected(getAttributeSelection()); + + activateFilters(myWorkshop, true); } //******************************************************************** void ModuleBase_WidgetMultiSelector::deactivate() { disconnect(myWorkshop, SIGNAL(selectionChanged()), this, SLOT(onSelectionChanged())); - myIsActive = false; - activateShapeSelection(); + activateShapeSelection(false); + activateFilters(myWorkshop, false); } //******************************************************************** @@ -131,7 +150,7 @@ bool ModuleBase_WidgetMultiSelector::storeValueCustom() const if (aSelectionListAttr) { // Store shapes type TopAbs_ShapeEnum aCurrentType = - ModuleBase_WidgetShapeSelector::shapeType(myTypeCombo->currentText()); + ModuleBase_Tools::shapeType(myTypeCombo->currentText()); aSelectionListAttr->setSelectionType(myTypeCombo->currentText().toStdString()); } return true; @@ -149,8 +168,8 @@ bool ModuleBase_WidgetMultiSelector::restoreValue() if (aSelectionListAttr) { // Restore shape type - setCurrentShapeType( - ModuleBase_WidgetShapeSelector::shapeType(aSelectionListAttr->selectionType().c_str())); + if (!aSelectionListAttr->selectionType().empty()) + setCurrentShapeType(ModuleBase_Tools::shapeType(aSelectionListAttr->selectionType().c_str())); updateSelectionList(aSelectionListAttr); return true; } @@ -196,20 +215,99 @@ void ModuleBase_WidgetMultiSelector::restoreAttributeValue(bool/* theValid*/) } //******************************************************************** -bool ModuleBase_WidgetMultiSelector::setSelection(const Handle_SelectMgr_EntityOwner& theOwner) +void ModuleBase_WidgetMultiSelector::customValidators( + std::list& theValidators, + std::list >& theArguments) const +{ + return; + std::list anArguments; + + theValidators.push_back(myShapeValidator); + if (true/*myIsUseChoice*/) { + QString aType = myTypeCombo->currentText(); + anArguments.push_back(validatorType(aType)); + } + else { + for(int i = 0, aCount = myTypeCombo->count(); i < aCount; i++) { + anArguments.push_back(validatorType(myTypeCombo->itemText(i))); + } + } + theArguments.push_back(anArguments); +} + +//******************************************************************** +bool ModuleBase_WidgetMultiSelector::acceptSubShape(const TopoDS_Shape& theShape) const { - ModuleBase_ViewerPrs aPrs; - ModuleBase_ISelection* aSelection = myWorkshop->selection(); - aSelection->fillPresentation(aPrs, theOwner); + bool aValid = true; + if (theShape.IsNull()) { + aValid = true; // do not check the shape type if the shape is empty + // extrusion uses a sketch object selectected in Object browser + } + else { + aValid = false; + TopAbs_ShapeEnum aShapeType = theShape.ShapeType(); + if (myTypeCombo->count() > 1) { + TopAbs_ShapeEnum aType = ModuleBase_Tools::shapeType(myTypeCombo->currentText()); + aValid = aShapeType == aType; + } + else { + for(int i = 0, aCount = myTypeCombo->count(); i < aCount && !aValid; i++) { + TopAbs_ShapeEnum aType = ModuleBase_Tools::shapeType(myTypeCombo->itemText(i)); + aValid = aShapeType == aType; + } + } + } + return aValid; +} - const TopoDS_Shape& aTDSShape = aPrs.shape(); - if (aTDSShape.IsNull()) +//******************************************************************** +bool ModuleBase_WidgetMultiSelector::setSelection(const QList& theValues, + int& thePosition) +{ + if (thePosition < 0) return false; - GeomShapePtr aShape = std::shared_ptr(new GeomAPI_Shape()); - aShape->setImpl(new TopoDS_Shape(aTDSShape)); - ObjectPtr anObject = aSelection->getSelectableObject(theOwner); - ResultPtr aResult = std::dynamic_pointer_cast(anObject); + QList::const_iterator anIt = theValues.begin(), aLast = theValues.end(); + bool isDone = false; + for (int i = thePosition; i < theValues.size(); i++) { + ModuleBase_ViewerPrs aValue = theValues[i]; + bool aProcessed = false; + if (isValidSelection(aValue)) { + aProcessed = setSelectionCustom(aValue); + } + // if there is at least one set, the result is true + isDone = isDone || aProcessed; + // when an object, which do not satisfy the validating process, stop set selection + if (!aProcessed) + break; + else + thePosition++; + } + if (isDone) { + updateObject(myFeature); + // this emit is necessary to call store/restore method an restore type of selection + emit valuesChanged(); + } + return isDone; +} + +//******************************************************************** +bool ModuleBase_WidgetMultiSelector::setSelectionCustom(const ModuleBase_ViewerPrs& thePrs) +{ + TopoDS_Shape aShape = thePrs.shape(); + if (!acceptSubShape(aShape)) + return false; + + ResultPtr aResult; + if (!thePrs.owner().IsNull()) { + ObjectPtr anObject = myWorkshop->selection()->getSelectableObject(thePrs.owner()); + aResult = std::dynamic_pointer_cast(anObject); + } + else { + aResult = std::dynamic_pointer_cast(thePrs.object()); + } + + if (myFeature) { // We can not select a result of our feature const std::list& aResList = myFeature->results(); @@ -230,11 +328,21 @@ bool ModuleBase_WidgetMultiSelector::setSelection(const Handle_SelectMgr_EntityO DataPtr aData = myFeature->data(); AttributeSelectionListPtr aSelectionListAttr = std::dynamic_pointer_cast(aData->attribute(attributeID())); - if (aShape->isEqual(aResult->shape())) - aSelectionListAttr->append(aResult, GeomShapePtr()); - else - aSelectionListAttr->append(aResult, aShape); + const TopoDS_Shape& aTDSShape = thePrs.shape(); + // if only result is selected, an empty shape is set to the model + if (aTDSShape.IsNull()) { + aSelectionListAttr->append(aResult, GeomShapePtr()); + } + else { + GeomShapePtr aShape(new GeomAPI_Shape()); + aShape->setImpl(new TopoDS_Shape(aTDSShape)); + // We can not select a result of our feature + if (aShape->isEqual(aResult->shape())) + aSelectionListAttr->append(aResult, GeomShapePtr()); + else + aSelectionListAttr->append(aResult, aShape); + } return true; } @@ -257,17 +365,19 @@ bool ModuleBase_WidgetMultiSelector::eventFilter(QObject* theObj, QEvent* theEve //******************************************************************** void ModuleBase_WidgetMultiSelector::onSelectionTypeChanged() { - activateShapeSelection(); - QObjectPtrList anEmptyList; + activateShapeSelection(true); + activateFilters(myWorkshop, true); + QList anEmptyList; + // This method will call Selection changed event which will call onSelectionChanged + // To clear mySelection, myListControl and storeValue() + // So, we don't need to call it myWorkshop->setSelected(anEmptyList); - // Clear mySelection, myListControl and storeValue() - onSelectionChanged(); } //******************************************************************** void ModuleBase_WidgetMultiSelector::onSelectionChanged() { - QList aSelected = myWorkshop->selection()->getSelected(); + QList aSelected = getSelectedEntitiesOrObjects(myWorkshop->selection()); DataPtr aData = myFeature->data(); AttributeSelectionListPtr aSelectionListAttr = @@ -276,17 +386,20 @@ void ModuleBase_WidgetMultiSelector::onSelectionChanged() aSelectionListAttr->clear(); if (aSelected.size() > 0) { foreach (ModuleBase_ViewerPrs aPrs, aSelected) { - Handle(SelectMgr_EntityOwner) anOwner = aPrs.owner(); - if (isValid(anOwner)) { - setSelection(anOwner); + if (isValidSelection(aPrs)) { + setSelectionCustom(aPrs); } } } + emit valuesChanged(); // the updateObject method should be called to flush the updated sigal. The workshop listens it, // calls validators for the feature and, as a result, updates the Apply button state. updateObject(myFeature); - emit valuesChanged(); + // Set focus to List control in order to make possible + // to use Tab key for transfer the focus to next widgets + myListControl->setCurrentRow(myListControl->model()->rowCount() - 1); + myListControl->setFocus(); } //******************************************************************** @@ -296,34 +409,65 @@ void ModuleBase_WidgetMultiSelector::setCurrentShapeType(const TopAbs_ShapeEnum for (int idx = 0; idx < myTypeCombo->count(); ++idx) { aShapeTypeName = myTypeCombo->itemText(idx); - TopAbs_ShapeEnum aRefType = ModuleBase_WidgetShapeSelector::shapeType(aShapeTypeName); + TopAbs_ShapeEnum aRefType = ModuleBase_Tools::shapeType(aShapeTypeName); if(aRefType == theShapeType && idx != myTypeCombo->currentIndex()) { - myIsActive = false; - activateShapeSelection(); + activateShapeSelection(false); + activateFilters(myWorkshop, false); bool isBlocked = myTypeCombo->blockSignals(true); myTypeCombo->setCurrentIndex(idx); - myIsActive = true; myTypeCombo->blockSignals(isBlocked); - activateShapeSelection(); + + activateShapeSelection(true); + activateFilters(myWorkshop, true); break; } } } -void ModuleBase_WidgetMultiSelector::activateShapeSelection() +void ModuleBase_WidgetMultiSelector::activateShapeSelection(const bool isActivated) { ModuleBase_IViewer* aViewer = myWorkshop->viewer(); - if (myIsActive) { + if (isActivated) { QString aNewType = myTypeCombo->currentText(); QIntList aList; - aList.append(ModuleBase_WidgetShapeSelector::shapeType(aNewType)); + if (true /*myIsUseChoice*/) { + aList.append(ModuleBase_Tools::shapeType(aNewType)); + } + else { + for(int i = 0, aCount = myTypeCombo->count(); i < aCount; i++) + aList.append(ModuleBase_Tools::shapeType(myTypeCombo->itemText(i))); + } myWorkshop->activateSubShapesSelection(aList); } else { myWorkshop->deactivateSubShapesSelection(); } +} - activateFilters(myWorkshop, myIsActive); +QList ModuleBase_WidgetMultiSelector::getAttributeSelection() const +{ + QList aSelected; + // Restore selection in the viewer by the attribute selection list + if(myFeature) { + DataPtr aData = myFeature->data(); + AttributeSelectionListPtr aListAttr = + std::dynamic_pointer_cast(aData->attribute(attributeID())); + if (aListAttr) { + for (int i = 0; i < aListAttr->size(); i++) { + AttributeSelectionPtr anAttr = aListAttr->value(i); + ResultPtr anObject = anAttr->context(); + if (anObject.get()) { + TopoDS_Shape aShape; + std::shared_ptr aShapePtr = anAttr->value(); + if (aShapePtr.get()) { + aShape = aShapePtr->impl(); + } + aSelected.append(ModuleBase_ViewerPrs(anObject, aShape, NULL)); + } + } + } + } + return aSelected; } //******************************************************************** @@ -334,6 +478,25 @@ void ModuleBase_WidgetMultiSelector::updateSelectionList(AttributeSelectionListP AttributeSelectionPtr aAttr = theList->value(i); myListControl->addItem(aAttr->namingName().c_str()); } + // We have to call repaint because sometimes the List control is not updated + myListControl->repaint(); +} + +//******************************************************************** +std::string ModuleBase_WidgetMultiSelector::validatorType(const QString& theType) const +{ + std::string aType; + + if (theType == "Vertices") + aType = "vertex"; + else if (theType == "Edges") + aType = "edge"; + else if (theType == "Faces") + aType = "face"; + else if (theType == "Solids") + aType = "solid"; + + return aType; } //********************************************************************