X-Git-Url: http://git.salome-platform.org/gitweb/?a=blobdiff_plain;ds=sidebyside;f=src%2FPartSet%2FPartSet_WidgetPoint2d.cpp;h=004fd0d3c9db6694d18e9cfee901e59db9e87570;hb=3b1b1527a60ec9d92b332e3df9056c5a16c22ff9;hp=9e380d4319bd1727ccfea37a2a66de7a2e09e3d7;hpb=5a164a3520051f4c52642e8bd0baf38c5ed4c4b5;p=modules%2Fshaper.git diff --git a/src/PartSet/PartSet_WidgetPoint2d.cpp b/src/PartSet/PartSet_WidgetPoint2d.cpp index 9e380d431..004fd0d3c 100644 --- a/src/PartSet/PartSet_WidgetPoint2d.cpp +++ b/src/PartSet/PartSet_WidgetPoint2d.cpp @@ -8,6 +8,10 @@ #include #include +#include +#include +#include + #include #include #include @@ -19,6 +23,7 @@ #include #include +#include #include #include @@ -53,9 +58,10 @@ static QStringList MyFeaturesForCoincedence; PartSet_WidgetPoint2D::PartSet_WidgetPoint2D(QWidget* theParent, ModuleBase_IWorkshop* theWorkshop, - const Config_WidgetAPI* theData, - const std::string& theParentId) - : ModuleBase_ModelWidget(theParent, theData, theParentId), myWorkshop(theWorkshop) + const Config_WidgetAPI* theData) +: ModuleBase_ModelWidget(theParent, theData), myWorkshop(theWorkshop), + myValueIsCashed(false), myIsFeatureVisibleInCash(true), + myXValueInCash(0), myYValueInCash(0) { if (MyFeaturesForCoincedence.isEmpty()) { MyFeaturesForCoincedence << SketchPlugin_Line::ID().c_str() @@ -118,14 +124,21 @@ bool PartSet_WidgetPoint2D::resetCustom() aDone = false; } else { - bool isOk; - double aDefValue = QString::fromStdString(getDefaultValue()).toDouble(&isOk); - // it is important to block the spin box control in order to do not through out the - // locking of the validating state. - ModuleBase_Tools::setSpinValue(myXSpin, isOk ? aDefValue : 0.0); - ModuleBase_Tools::setSpinValue(myYSpin, isOk ? aDefValue : 0.0); - storeValueCustom(); - aDone = true; + if (myValueIsCashed) { + // if the restored value should be hidden, aDone = true to set + // reset state for the widget in the parent + aDone = restoreCurentValue(); + } + else { + bool isOk; + double aDefValue = QString::fromStdString(getDefaultValue()).toDouble(&isOk); + // it is important to block the spin box control in order to do not through out the + // locking of the validating state. + ModuleBase_Tools::setSpinValue(myXSpin, isOk ? aDefValue : 0.0); + ModuleBase_Tools::setSpinValue(myYSpin, isOk ? aDefValue : 0.0); + storeValueCustom(); + aDone = true; + } } return aDone; } @@ -142,11 +155,12 @@ bool PartSet_WidgetPoint2D::setSelection(QList& theValues, return isDone; ModuleBase_ViewerPrs aValue = theValues.takeFirst(); - TopoDS_Shape aShape = aValue.shape(); - if (!aShape.IsNull()) { + GeomShapePtr aShape = aValue.shape(); + if (aShape.get() && !aShape->isNull()) { Handle(V3d_View) aView = myWorkshop->viewer()->activeView(); double aX, aY; - if (getPoint2d(aView, aShape, aX, aY)) { + const TopoDS_Shape& aTDShape = aShape->impl(); + if (getPoint2d(aView, aTDShape, aX, aY)) { isDone = setPoint(aX, aY); PartSet_Tools::setConstraints(mySketch, feature(), attributeID(), aX, aY); } @@ -256,6 +270,43 @@ bool PartSet_WidgetPoint2D::restoreValueCustom() return true; } +void PartSet_WidgetPoint2D::storeCurentValue() +{ + // do not use cash if a variable is used + if (myXSpin->hasVariable() || myYSpin->hasVariable()) + return; + + myValueIsCashed = true; + myIsFeatureVisibleInCash = XGUI_Displayer::isVisible( + XGUI_Tools::workshop(myWorkshop)->displayer(), myFeature); + myXValueInCash = myXSpin->value(); + myYValueInCash = myYSpin->value(); +} + +bool PartSet_WidgetPoint2D::restoreCurentValue() +{ + bool aRestoredAndHidden = true; + + bool isVisible = myIsFeatureVisibleInCash; + // fill the control widgets by the cashed value + + myValueIsCashed = false; + myIsFeatureVisibleInCash = true; + ModuleBase_Tools::setSpinValue(myXSpin, myXValueInCash); + ModuleBase_Tools::setSpinValue(myYSpin, myYValueInCash); + + // store value to the model + storeValueCustom(); + if (isVisible) { + setValueState(Stored); + aRestoredAndHidden = false; + } + else + aRestoredAndHidden = true; + + return aRestoredAndHidden; +} + QList PartSet_WidgetPoint2D::getControls() const { QList aControls; @@ -277,6 +328,12 @@ void PartSet_WidgetPoint2D::activateCustom() aModes << TopAbs_VERTEX; aModes << TopAbs_EDGE; myWorkshop->activateSubShapesSelection(aModes); + + if (!isEditingMode()) { + FeaturePtr aFeature = feature(); + if (aFeature.get() && aFeature->getKind() == SketchPlugin_Point::ID()) + storeValue(); + } } bool PartSet_WidgetPoint2D::canBeActivatedByMove() @@ -327,24 +384,44 @@ bool PartSet_WidgetPoint2D::getPoint2d(const Handle(V3d_View)& theView, return false; } -void PartSet_WidgetPoint2D::setConstraintWith(const ObjectPtr& theObject) +bool PartSet_WidgetPoint2D::setConstraintWith(const ObjectPtr& theObject) { + std::shared_ptr aFeaturePoint; + if (feature()->isMacro()) { + AttributePtr aThisAttr = feature()->data()->attribute(attributeID()); + std::shared_ptr anAttrPoint = + std::dynamic_pointer_cast(aThisAttr); + if (anAttrPoint.get()) { + // the macro feature will be removed after the operation is stopped, so we need to build + // coicidence to possible sub-features + aFeaturePoint = PartSet_Tools::findFirstEqualPointInArgumentFeatures(feature(), + anAttrPoint->pnt()); + } + } + else { + AttributePtr aThisAttr = feature()->data()->attribute(attributeID()); + aFeaturePoint = std::dynamic_pointer_cast(aThisAttr); + } + if (!aFeaturePoint.get()) + return false; + // Create point-edge coincedence FeaturePtr aFeature = mySketch->addFeature(SketchPlugin_ConstraintCoincidence::ID()); std::shared_ptr aData = aFeature->data(); std::shared_ptr aRef1 = std::dynamic_pointer_cast< ModelAPI_AttributeRefAttr>(aData->attribute(SketchPlugin_Constraint::ENTITY_A())); - AttributePtr aThisAttr = feature()->data()->attribute(attributeID()); - std::shared_ptr aThisPoint = - std::dynamic_pointer_cast(aThisAttr); - aRef1->setAttr(aThisPoint); + + aRef1->setAttr(aFeaturePoint); std::shared_ptr aRef2 = std::dynamic_pointer_cast< ModelAPI_AttributeRefAttr>(aData->attribute(SketchPlugin_Constraint::ENTITY_B())); aRef2->setObject(theObject); - aFeature->execute(); + // we need to flush created signal in order to coincidence is processed by solver + Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED)); + + return true; } void PartSet_WidgetPoint2D::onMouseRelease(ModuleBase_IViewWindow* theWnd, QMouseEvent* theEvent) @@ -370,11 +447,11 @@ void PartSet_WidgetPoint2D::onMouseRelease(ModuleBase_IViewWindow* theWnd, QMous aSPFeature = std::dynamic_pointer_cast(aSelectedFeature); if ((!aSPFeature && !aShape.IsNull()) || (aSPFeature.get() && aSPFeature->isExternal())) { + ResultPtr aFixedObject; anExternal = true; - ResultPtr aFixedObject = PartSet_Tools::findFixedObjectByExternal(aShape, aObject, mySketch); + aFixedObject = PartSet_Tools::findFixedObjectByExternal(aShape, aObject, mySketch); if (!aFixedObject.get()) aFixedObject = PartSet_Tools::createFixedObjectByExternal(aShape, aObject, mySketch); - double aX, aY; if (getPoint2d(aView, aShape, aX, aY) && isFeatureContainsPoint(myFeature, aX, aY)) { // do not create a constraint to the point, which already used by the feature @@ -394,12 +471,12 @@ void PartSet_WidgetPoint2D::onMouseRelease(ModuleBase_IViewWindow* theWnd, QMous if (aShape.ShapeType() == TopAbs_VERTEX) { FeaturePtr aFixedFeature = ModelAPI_Feature::feature(aFixedObject); if (aFixedFeature.get() && aFixedFeature->getKind() == SketchPlugin_Point::ID()) { - anOrphanPoint = isOrphanPoint(aFixedFeature, mySketch, aX, aY, true); + anOrphanPoint = isOrphanPoint(aFixedFeature, mySketch, aX, aY); } } } - - setConstraintWith(aFixedObject); + if (aFixedObject.get()) + setConstraintWith(aFixedObject); // fignal updated should be flushed in order to visualize possible created external objects // e.g. selection of trihedron axis when input end arc point updateObject(feature()); @@ -423,15 +500,26 @@ void PartSet_WidgetPoint2D::onMouseRelease(ModuleBase_IViewWindow* theWnd, QMous // do not set a coincidence constraint in the attribute if the feature contains a point // with the same coordinates. It is important for line creation in order to do not set // the same constraints for the same points, oterwise the result line has zero length. + bool isAuxiliaryFeature = false; if (getPoint2d(aView, aShape, aX, aY)) { setPoint(aX, aY); + feature()->execute(); PartSet_Tools::setConstraints(mySketch, feature(), attributeID(), aX, aY); } else if (aShape.ShapeType() == TopAbs_EDGE) { - if (MyFeaturesForCoincedence.contains(myFeature->getKind().c_str())) { - setConstraintWith(aObject); - setValueState(Stored); // in case of edge selection, Apply state should also be updated + if (!setConstraintWith(aObject)) { + gp_Pnt aPoint = PartSet_Tools::convertClickToPoint(theEvent->pos(), theWnd->v3dView()); + PartSet_Tools::convertTo2D(aPoint, mySketch, aView, aX, aY); + setPoint(aX, aY); } + setValueState(Stored); // in case of edge selection, Apply state should also be updated + + FeaturePtr anObjectFeature = ModelAPI_Feature::feature(aObject); + std::string anAuxiliaryAttribute = SketchPlugin_SketchEntity::AUXILIARY_ID(); + AttributeBooleanPtr anAuxiliaryAttr = std::dynamic_pointer_cast( + anObjectFeature->data()->attribute(anAuxiliaryAttribute)); + if (anAuxiliaryAttr.get()) + isAuxiliaryFeature = anAuxiliaryAttr->value(); } // it is important to perform updateObject() in order to the current value is // processed by Sketch Solver. Test case: line is created from a previous point @@ -440,7 +528,7 @@ void PartSet_WidgetPoint2D::onMouseRelease(ModuleBase_IViewWindow* theWnd, QMous // points of the line becomes less than the tolerance. Validator of the line returns // false, the line will be aborted, but sketch stays valid. updateObject(feature()); - if (!anOrphanPoint && !anExternal) + if (!anOrphanPoint && !anExternal && !isAuxiliaryFeature) emit vertexSelected(); emit focusOutWidget(this); } @@ -486,6 +574,8 @@ void PartSet_WidgetPoint2D::onMouseMove(ModuleBase_IViewWindow* theWnd, QMouseEv double aX, anY; PartSet_Tools::convertTo2D(aPoint, mySketch, theWnd->v3dView(), aX, anY); + if (myState != ModifiedInViewer) + storeCurentValue(); // we need to block the value state change bool isBlocked = blockValueState(true); setPoint(aX, anY); @@ -561,7 +651,7 @@ bool PartSet_WidgetPoint2D::useSelectedShapes() const bool PartSet_WidgetPoint2D::isOrphanPoint(const FeaturePtr& theFeature, const CompositeFeaturePtr& theSketch, - double theX, double theY, const bool theSearchInResults) + double theX, double theY) { bool anOrphanPoint = false; if (theFeature.get()) { @@ -592,14 +682,15 @@ bool PartSet_WidgetPoint2D::isOrphanPoint(const FeaturePtr& theFeature, std::shared_ptr aPoint = aPointAttr->pnt(); // we need to find coincidence features in results also, because external object(point) // uses refs to me in another feature. - FeaturePtr aCoincidence = PartSet_Tools::findFirstCoincidence(theFeature, aPoint, theSearchInResults); + FeaturePtr aCoincidence = PartSet_Tools::findFirstCoincidence(theFeature, aPoint); anOrphanPoint = true; // if there is at least one concident line to the point, the point is not an orphant if (aCoincidence.get()) { QList aCoinsideLines; - PartSet_Tools::findCoincidences(aCoincidence, aCoinsideLines, + QList aCoins; + PartSet_Tools::findCoincidences(aCoincidence, aCoinsideLines, aCoins, SketchPlugin_ConstraintCoincidence::ENTITY_A()); - PartSet_Tools::findCoincidences(aCoincidence, aCoinsideLines, + PartSet_Tools::findCoincidences(aCoincidence, aCoinsideLines, aCoins, SketchPlugin_ConstraintCoincidence::ENTITY_B()); QList::const_iterator anIt = aCoinsideLines.begin(), aLast = aCoinsideLines.end();