Salome HOME
Issue #1343 validators update
[modules/shaper.git] / src / FeaturesPlugin / FeaturesPlugin_Validators.cpp
index 40c1197db3424471f59a58c588cd88633dc88dbf..0c0e893ba24e1eed4fa20274f3baf6e204a439b6 100644 (file)
@@ -9,9 +9,12 @@
 #include <ModelAPI_Attribute.h>
 #include <ModelAPI_AttributeSelectionList.h>
 #include <ModelAPI_AttributeString.h>
+#include <ModelAPI_ResultConstruction.h>
+
+#include <GeomValidators_ShapeType.h>
 
 //=================================================================================================
-bool FeaturesPlugin_PipeLocationsValidator::isValid(const std::shared_ptr<ModelAPI_Feature>& theFeature,
+bool FeaturesPlugin_ValidatorPipeLocations::isValid(const std::shared_ptr<ModelAPI_Feature>& theFeature,
                                                     const std::list<std::string>& theArguments,
                                                     std::string& theError) const
 {
@@ -19,7 +22,6 @@ bool FeaturesPlugin_PipeLocationsValidator::isValid(const std::shared_ptr<ModelA
   static const std::string aBaseObjectsID = "base_objects";
   static const std::string aLocationsID = "locations_objects";
 
-
   if(theFeature->getKind() != "Pipe") {
     theError = "Feature \"" + theFeature->getKind() + "\" does not supported by this validator.";
     return false;
@@ -56,10 +58,249 @@ bool FeaturesPlugin_PipeLocationsValidator::isValid(const std::shared_ptr<ModelA
 }
 
 //=================================================================================================
-bool FeaturesPlugin_PipeLocationsValidator::isNotObligatory(std::string theFeature, std::string theAttribute)
+bool FeaturesPlugin_ValidatorPipeLocations::isNotObligatory(std::string theFeature, std::string theAttribute)
+{
+  return false;
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorBaseForGeneration::isValid(const AttributePtr& theAttribute,
+                                                        const std::list<std::string>& theArguments,
+                                                        std::string& theError) const
+{
+  if(theArguments.empty()) {
+    theError = "Validator parameters is empty.";
+    return false;
+  }
+
+  // Checking attribute.
+  if(!isValidAttribute(theAttribute, theArguments, theError)) {
+    if(theError.empty()) {
+      theError = "Attribute contains unacceptable shape.";
+    }
+    return false;
+  }
+
+  return true;
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorBaseForGeneration::isValidAttribute(const AttributePtr& theAttribute,
+                                                                 const std::list<std::string>& theArguments,
+                                                                 std::string& theError) const
+{
+  if(!theAttribute.get()) {
+    theError = "Empty attribute.";
+    return false;
+  }
+
+  std::string anAttributeType = theAttribute->attributeType();
+  if(anAttributeType == ModelAPI_AttributeSelectionList::typeId()) {
+    AttributeSelectionListPtr aListAttr = std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(theAttribute);
+    for(int anIndex = 0; anIndex < aListAttr->size(); ++anIndex) {
+      // If at least one attribute is invalid, the result is false.
+      if(!isValidAttribute(aListAttr->value(anIndex), theArguments, theError)) {
+        return false;
+      }
+    }
+  } else if(anAttributeType == ModelAPI_AttributeSelection::typeId()) {
+    // Getting context.
+    AttributeSelectionPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeSelection>(theAttribute);
+    ResultPtr aContext = anAttr->context();
+    if(!aContext.get()) {
+      theError = "Attribute have empty context.";
+      return false;
+    }
+
+    GeomShapePtr aShape = anAttr->value();
+    GeomShapePtr aContextShape = aContext->shape();
+    if(!aShape.get()) {
+      aShape = aContextShape;
+    }
+    if(!aShape.get()) {
+      theError = "Empty shape selected";
+      return false;
+    }
+
+    ResultConstructionPtr aConstruction = std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(aContext);
+    if(aConstruction.get()) {
+      // Construciotn selected. Check that is is not infinite.
+      if(aConstruction->isInfinite()) {
+        theError = "Infinite constructions is not allowed as base.";
+        return false;
+      }
+
+      if(aShape->isEqual(aContextShape)) {
+        // Whole construction selected. Check that it have faces.
+        if(aConstruction->facesNum() > 0) {
+          return true;
+        }
+      } else {
+        // Shape on construction selected. Check that it is a face or wire.
+        if(aShape->shapeType() == GeomAPI_Shape::WIRE || aShape->shapeType() == GeomAPI_Shape::FACE) {
+          return true;
+        }
+      }
+    }
+
+    if(!aShape->isEqual(aContextShape)) {
+      // Local selection on body does not allowed.
+      theError = "Selected shape is in the local selection. Only global selection is allowed.";
+      return false;
+    }
+
+    // Check that object is a shape with allowed type.
+    GeomValidators_ShapeType aShapeTypeValidator;
+    if(!aShapeTypeValidator.isValid(anAttr, theArguments, theError)) {
+      theError = "Selected shape has unacceptable type. Acceptable types are: faces or wires on sketch, \
+                  whole sketch(if it has at least one face), and whole objects with shape types: ";
+      std::list<std::string>::const_iterator anIt = theArguments.cbegin();
+      theError += *anIt;
+      for(++anIt; anIt != theArguments.cend(); ++anIt) {
+        theError += ", " + *anIt;
+      }
+      return false;
+    }
+
+  } else {
+    theError = "Following attribute does not supported: " + anAttributeType + ".";
+    return false;
+  }
+
+  return true;
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorCompositeLauncher::isValid(const AttributePtr& theAttribute,
+                                                        const std::list<std::string>& theArguments,
+                                                        std::string& theError) const
+{
+  FeaturesPlugin_ValidatorBaseForGeneration aBaseValidator;
+
+  if(aBaseValidator.isValid(theAttribute, theArguments, theError)) {
+    return true;
+  }
+
+  // Check that face selected.
+  GeomValidators_ShapeType aShapeType;
+  std::list<std::string> anArguments;
+  anArguments.push_back("face");
+  if(aShapeType.isValid(theAttribute, anArguments, theError)) {
+    return true;
+  }
+
+  theError = "Selected shape is not suitable for this operation";
+
+  return false;
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorCanBeEmpty::isValid(const std::shared_ptr<ModelAPI_Feature>& theFeature,
+                                                 const std::list<std::string>& theArguments,
+                                                 std::string& theError) const
 {
-  if(theFeature == "Pipe" && theAttribute == "locations") {
+  if(theArguments.size() != 5 && theArguments.size() != 6) {
+    theError = "Validator should be used with 6 parameters for extrusion and with 5 for revolution.";
+    return false;
+  }
+
+  std::list<std::string>::const_iterator anArgsIt = theArguments.begin(), aLast = theArguments.end();
+
+  std::string aSelectedMethod;
+  if(theFeature->string(*anArgsIt)) {
+    aSelectedMethod = theFeature->string(*anArgsIt)->value();
+  }
+  ++anArgsIt;
+  std::string aCreationMethod = *anArgsIt;
+  ++anArgsIt;
+
+  AttributePtr aCheckAttribute = theFeature->attribute(*anArgsIt);
+  ++anArgsIt;
+
+  if(isShapesCanBeEmpty(aCheckAttribute, theError)) {
     return true;
   }
+
+  if(aSelectedMethod == aCreationMethod) {
+    ++anArgsIt;
+    ++anArgsIt;
+  }
+
+  for(; anArgsIt != theArguments.cend(); ++anArgsIt) {
+    AttributeSelectionPtr aSelAttr = theFeature->selection(*anArgsIt);
+    if(!aSelAttr.get()) {
+      theError = "Could not get selection attribute \"" + *anArgsIt + "\".";
+      return false;
+    }
+
+    GeomShapePtr aShape = aSelAttr->value();
+    if(!aShape.get()) {
+      ResultPtr aContext = aSelAttr->context();
+      if(!aContext.get()) {
+        theError = "Selection attribute \"" + *anArgsIt + "\" can not be empty.";
+        return false;
+      }
+
+      aShape = aContext->shape();
+    }
+
+    if(!aShape.get()) {
+      theError = "Selection attribute \"" + *anArgsIt + "\" can not be empty.";
+      return false;
+    }
+  }
+
+  return true;
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorCanBeEmpty::isNotObligatory(std::string theFeature, std::string theAttribute)
+{
   return false;
-}
\ No newline at end of file
+}
+
+//=================================================================================================
+bool FeaturesPlugin_ValidatorCanBeEmpty::isShapesCanBeEmpty(const AttributePtr& theAttribute,
+                                                            std::string& theError) const
+{
+  if(!theAttribute.get()) {
+    return true;
+  }
+
+  std::string anAttributeType = theAttribute->attributeType();
+  if(anAttributeType == ModelAPI_AttributeSelectionList::typeId()) {
+    AttributeSelectionListPtr aListAttr = std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(theAttribute);
+    for(int anIndex = 0; anIndex < aListAttr->size(); ++anIndex) {
+      // If at least one attribute is invalid, the result is false.
+      if(!isShapesCanBeEmpty(aListAttr->value(anIndex), theError)) {
+        return false;
+      }
+    }
+  } else if(anAttributeType == ModelAPI_AttributeSelection::typeId()) {
+    // Getting context.
+    AttributeSelectionPtr anAttr = std::dynamic_pointer_cast<ModelAPI_AttributeSelection>(theAttribute);
+    ResultPtr aContext = anAttr->context();
+    if(!aContext.get()) {
+      return false;
+    }
+
+    GeomShapePtr aShape = anAttr->value();
+    GeomShapePtr aContextShape = aContext->shape();
+    if(!aShape.get()) {
+      aShape = aContextShape;
+    }
+    if(!aShape.get()) {
+      return false;
+    }
+
+    if(aShape->shapeType() == GeomAPI_Shape::VERTEX ||
+       aShape->shapeType() == GeomAPI_Shape::EDGE ||
+       !aShape->isPlanar()) {
+      return false;
+    }
+  } else {
+    return false;
+  }
+
+  return true;
+}