Salome HOME
Merge branch 'Dev_1.1.0' of newgeom:newgeom into Dev_1.1.0
[modules/shaper.git] / src / FeaturesPlugin / FeaturesPlugin_Placement.cpp
1 // Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
2
3 // File:        FeaturesPlugin_Placement.cpp
4 // Created:     2 Dec 2014
5 // Author:      Artem ZHIDKOV
6
7 #include "FeaturesPlugin_Placement.h"
8
9 #include <ModelAPI_ResultConstruction.h>
10 #include <ModelAPI_ResultBody.h>
11 #include <ModelAPI_AttributeSelection.h>
12 #include <ModelAPI_AttributeBoolean.h>
13
14 #include <GeomAPI_Edge.h>
15 #include <GeomAPI_Face.h>
16 #include <GeomAPI_Pln.h>
17 #include <GeomAlgoAPI_Placement.h>
18
19 #define _MODIFIEDF_TAG 1
20 #define _MODIFIEDE_TAG 2
21 #define _MODIFIEDV_TAG 3
22 #define _FACE 4
23 FeaturesPlugin_Placement::FeaturesPlugin_Placement()
24 {
25 }
26
27 void FeaturesPlugin_Placement::initAttributes()
28 {
29   data()->addAttribute(FeaturesPlugin_Placement::BASE_OBJECT_ID(), ModelAPI_AttributeSelection::type());
30   data()->addAttribute(FeaturesPlugin_Placement::ATTRACT_OBJECT_ID(), ModelAPI_AttributeSelection::type());
31   data()->addAttribute(FeaturesPlugin_Placement::REVERSE_ID(), ModelAPI_AttributeBoolean::type());
32   data()->addAttribute(FeaturesPlugin_Placement::CENTERING_ID(), ModelAPI_AttributeBoolean::type());
33 }
34
35 void FeaturesPlugin_Placement::execute()
36 {
37   // Verify the base face
38   std::shared_ptr<ModelAPI_AttributeSelection> anObjRef = std::dynamic_pointer_cast<
39     ModelAPI_AttributeSelection>(data()->attribute(FeaturesPlugin_Placement::BASE_OBJECT_ID()));
40   if (!anObjRef)
41     return;
42
43   std::shared_ptr<GeomAPI_Shape> aBaseShape = 
44     std::dynamic_pointer_cast<GeomAPI_Shape>(anObjRef->value());
45   if (!aBaseShape)
46     return;
47
48   std::shared_ptr<GeomAPI_Shape> aBaseObject;
49   ResultPtr aContextRes = anObjRef->context();
50   if (aContextRes) {
51     if (aContextRes->groupName() == ModelAPI_ResultBody::group())
52       aBaseObject = std::dynamic_pointer_cast<ModelAPI_ResultBody>(aContextRes)->shape();
53     else if (aContextRes->groupName() == ModelAPI_ResultConstruction::group())
54       aBaseObject = std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(aContextRes)->shape();
55   }
56   if (!aBaseObject) {
57     static const std::string aContextError = "The selection context is bad";
58     setError(aContextError);
59     return;
60   }
61
62   // Verify the attractive face
63   anObjRef = std::dynamic_pointer_cast<ModelAPI_AttributeSelection>(
64       data()->attribute(FeaturesPlugin_Placement::ATTRACT_OBJECT_ID()));
65
66   std::shared_ptr<GeomAPI_Shape> aSlaveShape = 
67     std::dynamic_pointer_cast<GeomAPI_Shape>(anObjRef->value());
68   if (!aSlaveShape)
69     return;
70
71   std::shared_ptr<GeomAPI_Shape> aSlaveObject;
72   aContextRes = anObjRef->context();
73   if (aContextRes) {
74     if (aContextRes->groupName() == ModelAPI_ResultBody::group())
75       aSlaveObject = std::dynamic_pointer_cast<ModelAPI_ResultBody>(aContextRes)->shape();
76     else if (aContextRes->groupName() == ModelAPI_ResultConstruction::group())
77       aSlaveObject = std::dynamic_pointer_cast<ModelAPI_ResultConstruction>(aContextRes)->shape();
78   }
79   if (!aSlaveObject) {
80     static const std::string aContextError = "The selection context is bad";
81     setError(aContextError);
82     return;
83   }
84
85   // Verify planarity of faces and linearity of edges
86   std::shared_ptr<GeomAPI_Shape> aShapes[2] = {aBaseShape, aSlaveShape};
87   for (int i = 0; i < 2; i++) {
88     if (aShapes[i]->isFace()) {
89       std::shared_ptr<GeomAPI_Face> aFace(new GeomAPI_Face(aShapes[i]));
90       if (!aFace->isPlanar()) {
91         static const std::string aPlanarityError = "One of selected faces is not planar";
92         setError(aPlanarityError);
93         return;
94       }
95     }
96     else if (aShapes[i]->isEdge()) {
97       std::shared_ptr<GeomAPI_Edge> anEdge(new GeomAPI_Edge(aShapes[i]));
98       if (!anEdge->isLine()) {
99         static const std::string aLinearityError = "One of selected endges is not linear";
100         setError(aLinearityError);
101         return;
102       }
103     }
104   }
105
106   // Flags of the Placement
107   AttributeBooleanPtr aBoolAttr = std::dynamic_pointer_cast<ModelAPI_AttributeBoolean>(
108       data()->attribute(FeaturesPlugin_Placement::REVERSE_ID()));
109   bool isReverse = aBoolAttr->value();
110   aBoolAttr = std::dynamic_pointer_cast<ModelAPI_AttributeBoolean>(
111       data()->attribute(FeaturesPlugin_Placement::CENTERING_ID()));
112   bool isCentering = aBoolAttr->value();
113
114   std::shared_ptr<ModelAPI_ResultBody> aResultBody = document()->createBody(data());
115   GeomAlgoAPI_Placement aFeature(aSlaveObject, aBaseObject, aSlaveShape, aBaseShape, isReverse, isCentering);
116   if(!aFeature.isDone()) {
117     static const std::string aFeatureError = "Placement algorithm failed";
118     setError(aFeatureError);
119     return;
120   }
121
122   // Check if shape is valid
123   if (aFeature.shape()->isNull()) {
124     static const std::string aShapeError = "Resulting shape is Null";
125     setError(aShapeError);
126     return;
127   }
128   if(!aFeature.isValid()) {
129     std::string aFeatureError = "Warning: resulting shape is not valid";
130     setError(aFeatureError);
131     return;
132   }  
133   //LoadNamingDS
134   LoadNamingDS(aFeature, aResultBody, aSlaveObject);
135
136   setResult(aResultBody);
137 }
138
139 //============================================================================
140 void FeaturesPlugin_Placement::LoadNamingDS(
141     GeomAlgoAPI_Placement& theFeature,
142     std::shared_ptr<ModelAPI_ResultBody> theResultBody,
143     std::shared_ptr<GeomAPI_Shape> theSlaveObject)
144 {
145   //load result
146   theResultBody->storeModified(theSlaveObject, theFeature.shape()); // the initial Slave, the resulting Slave
147
148   GeomAPI_DataMapOfShapeShape* aSubShapes = new GeomAPI_DataMapOfShapeShape();
149   theFeature.mapOfShapes(*aSubShapes);
150   
151     // put modifed faces in DF
152   std::string aModName = "Modified";
153   theResultBody->loadAndOrientModifiedShapes(theFeature.makeShape(), theSlaveObject, _FACE, _MODIFIEDF_TAG, aModName, *aSubShapes); 
154
155 }