]> SALOME platform Git repositories - modules/shaper.git/blobdiff - src/Model/Model_Update.cpp
Salome HOME
Make Data not null, but invalid after the feature remove
[modules/shaper.git] / src / Model / Model_Update.cpp
index 50d73e311f387c2eb1397214d80b95df2aca868a..17f344c28ec1efebaaf735712eb95aee27871092 100644 (file)
@@ -110,11 +110,13 @@ void Model_Update::processEvent(const std::shared_ptr<Events_Message>& theMessag
     isOperationChanged = true;
   }
   if (isOperationChanged) {
-    // remove all macros before clearing all created
+    // remove all macros before clearing all created and execute all not-previewed
     std::set<ObjectPtr>::iterator aCreatedIter = myJustCreated.begin();
-    for(; aCreatedIter != myJustCreated.end(); aCreatedIter++) {
-      FeaturePtr aFeature = 
-        std::dynamic_pointer_cast<ModelAPI_Feature>(*aCreatedIter);
+    std::set<ObjectPtr>::iterator anUpdatedIter = myJustUpdated.begin();
+    for(; aCreatedIter != myJustCreated.end() || anUpdatedIter != myJustUpdated.end();
+      aCreatedIter == myJustCreated.end() ? anUpdatedIter++ : aCreatedIter++) {
+      FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(*
+        (aCreatedIter == myJustCreated.end() ? anUpdatedIter : aCreatedIter));
       if (aFeature.get()) {
         // execute not-previewed feature on "apply"
         if (!aFeature->isPreviewNeeded() && (myJustCreated.find(aFeature) != myJustCreated.end() ||
@@ -143,7 +145,7 @@ void Model_Update::processOperation(const bool theTotalUpdate, const bool theFin
     for(aFIter = myJustCreated.begin(); aFIter != myJustCreated.end(); aFIter++)
     {
       FeaturePtr aF = std::dynamic_pointer_cast<ModelAPI_Feature>(*aFIter);
-      if (aF && aF->data().get() && aF->getKind() == "Extrusion") {
+      if (aF && aF->data()->isValid() && aF->getKind() == "Extrusion") {
         AttributeSelectionListPtr aBase = aF->selectionList("base");
         if (aBase.get()) {
           for(int a = aBase->size() - 1; a >= 0; a--) {
@@ -197,6 +199,7 @@ void Model_Update::updateInDoc(std::shared_ptr<ModelAPI_Document> theDoc)
         // number of subs can be changed in execution: like fillet
         for(int a = 0; a < aComposite->numberOfSubs(); a++) {
           FeaturePtr aSub = aComposite->subFeature(a);
+          updateArguments(aSub);
           updateFeature(aSub);
           alreadyProcessed.insert(aSub);
         }
@@ -257,7 +260,9 @@ void Model_Update::updateArguments(FeaturePtr theFeature) {
 
   bool aJustUpdated = false;
   ModelAPI_ExecState aState = theFeature->data()->execState();
-  // check the parameters: values can be changed
+  if (aState == ModelAPI_StateInvalidArgument) // a chance to be corrected
+    aState = ModelAPI_StateMustBeUpdated;
+  // check the parameters state
   std::list<AttributePtr> aDoubles = 
     theFeature->data()->attributes(ModelAPI_AttributeDouble::typeId()); 
   std::list<AttributePtr>::iterator aDoubleIter = aDoubles.begin();
@@ -265,13 +270,7 @@ void Model_Update::updateArguments(FeaturePtr theFeature) {
     AttributeDoublePtr aDouble = 
       std::dynamic_pointer_cast<ModelAPI_AttributeDouble>(*aDoubleIter);
     if (aDouble.get() && !aDouble->text().empty()) {
-      double aNewVal;
-      if (ModelAPI_Tools::findVariable(aDouble->text(), aNewVal)) {
-        if (aNewVal != aDouble->value()) {
-          aDouble->setValue(aNewVal);
-          aJustUpdated = true;
-        }
-      } else {
+      if (aDouble->expressionInvalid()) {
         aState = ModelAPI_StateInvalidArgument;
       }
     }
@@ -333,7 +332,8 @@ void Model_Update::updateFeature(FeaturePtr theFeature)
   // check all features this feature depended on (recursive call of updateFeature)
   static ModelAPI_ValidatorsFactory* aFactory = ModelAPI_Session::get()->validators();
 
-  if (theFeature->isDisabled()) // nothing to do with disabled feature
+  if (theFeature->isDisabled() ||  // nothing to do with disabled feature
+      theFeature->data()->execState() == ModelAPI_StateInvalidArgument)
     return;
   bool aJustUpdated = false;
 
@@ -375,31 +375,37 @@ void Model_Update::updateFeature(FeaturePtr theFeature)
     //std::cout<<"Update feature "<<theFeature->getKind()<<" must be updated = "<<aMustbeUpdated<<std::endl;
     // execute feature if it must be updated
     if (aJustUpdated) {
-      if ((std::dynamic_pointer_cast<Model_Document>(theFeature->document())->executeFeatures() ||
-          !theFeature->isPersistentResult()) && theFeature->isPreviewNeeded()) {
-        if (aFactory->validate(theFeature)) {
-          if (myIsAutomatic || !theFeature->isPersistentResult() /* execute quick, not persistent results */
-              || (isUpdated(theFeature) && 
-               theFeature == theFeature->document()->currentFeature(false))) // currently edited
-          {
-            if (aState == ModelAPI_StateDone || aState == ModelAPI_StateMustBeUpdated) {
-              executeFeature(theFeature);
-            }
-          } else { // must be updatet, but not updated yet
-            theFeature->data()->execState(ModelAPI_StateMustBeUpdated);
-            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++) {
-              std::shared_ptr<ModelAPI_Result> aRes = *aRIter;
-              aRes->data()->execState(ModelAPI_StateMustBeUpdated);
+      if (theFeature->isPreviewNeeded()) {
+        if (std::dynamic_pointer_cast<Model_Document>(theFeature->document())->executeFeatures() ||
+            !theFeature->isPersistentResult()) {
+          if (aFactory->validate(theFeature)) {
+            if (myIsAutomatic || !theFeature->isPersistentResult() /* execute quick, not persistent results */
+                || (isUpdated(theFeature) && 
+                     (theFeature == theFeature->document()->currentFeature(false) || 
+                      theFeature->document()->currentFeature(false)->isMacro()))) // currently edited
+            {
+              if (aState == ModelAPI_StateDone || aState == ModelAPI_StateMustBeUpdated) {
+                executeFeature(theFeature);
+              }
+            } else { // must be updatet, but not updated yet
+              theFeature->data()->execState(ModelAPI_StateMustBeUpdated);
+              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++) {
+                std::shared_ptr<ModelAPI_Result> aRes = *aRIter;
+                aRes->data()->execState(ModelAPI_StateMustBeUpdated);
+              }
             }
+          } else {
+            theFeature->eraseResults();
+            redisplayWithResults(theFeature, ModelAPI_StateInvalidArgument); // result also must be updated
           }
-        } else {
-          theFeature->eraseResults();
-          redisplayWithResults(theFeature, ModelAPI_StateInvalidArgument); // result also must be updated
+        } else { // for automatically updated features (on abort, etc) it is necessary to redisplay anyway
+          redisplayWithResults(theFeature, ModelAPI_StateNothing);
         }
-      } else { // for automatically updated features (on abort, etc) it is necessary to redisplay anyway
-        redisplayWithResults(theFeature, ModelAPI_StateNothing);
+      } else { // preview is not needed => make state Done
+        if (theFeature->data()->execState() == ModelAPI_StateMustBeUpdated)
+          theFeature->data()->execState(ModelAPI_StateDone);
       }
     }
   }