1 // Copyright (C) 2017-2021 CEA/DEN, EDF R&D
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
20 #include "FeaturesPlugin_ImportResult.h"
22 #include <ModelAPI_AttributeSelectionList.h>
23 #include <ModelAPI_AttributeRefList.h>
24 #include <ModelAPI_ResultBody.h>
25 #include <ModelAPI_ResultGroup.h>
26 #include <ModelAPI_Session.h>
27 #include <ModelAPI_ResultPart.h>
28 #include <ModelAPI_Tools.h>
29 #include <Events_InfoMessage.h>
30 #include <GeomAPI_ShapeExplorer.h>
32 void FeaturesPlugin_ImportResult::initAttributes()
34 data()->addAttribute(OBJECTS(), ModelAPI_AttributeSelectionList::typeId());
36 AttributePtr aFeaturesAttribute =
37 data()->addAttribute(FEATURES_ID(),
38 ModelAPI_AttributeRefList::typeId());
39 aFeaturesAttribute->setIsArgument(false);
41 ModelAPI_Session::get()->validators()->registerNotObligatory(
42 getKind(), FEATURES_ID());
45 void FeaturesPlugin_ImportResult::execute()
47 // Process groups/fields
48 std::shared_ptr<ModelAPI_AttributeRefList> aRefListOfGroups =
49 std::dynamic_pointer_cast<ModelAPI_AttributeRefList>(data()->attribute(FEATURES_ID()));
51 // Remove previous groups/fields stored in RefList
52 //std::list<ObjectPtr> anGroupList = aRefListOfGroups->list();
53 //std::list<ObjectPtr>::iterator anGroupIt = anGroupList.begin();
54 const std::list<ObjectPtr>& anGroupList = aRefListOfGroups->list();
55 std::list<ObjectPtr>::const_iterator anGroupIt = anGroupList.begin();
56 for (; anGroupIt != anGroupList.end(); ++anGroupIt) {
57 std::shared_ptr<ModelAPI_Feature> aFeature = ModelAPI_Feature::feature(*anGroupIt);
59 document()->removeFeature(aFeature);
62 aRefListOfGroups->clear();
64 std::set<ResultPtr> aGlobalResultsCashed; // cash to speed up searching in all results selected
65 std::list<ResultGroupPtr> aGroups;
67 std::list<ResultPtr> aResults;
69 AttributeSelectionListPtr aList = selectionList(OBJECTS());
71 for (int aSelIndex = 0; aSelIndex < aList->size(); aSelIndex++)
73 AttributeSelectionPtr aSel = aList->value(aSelIndex);
75 ResultPtr aContext = aSel->context();
77 aResults.push_back (aContext);
80 FeaturePtr aFeature = aSel->contextFeature();
83 const std::list<ResultPtr>& aResList = aFeature->results();
84 aResults.assign (aResList.begin(), aResList.end());
89 std::list<ResultPtr>::iterator aResIter = aResults.begin();
90 for(; aResIter != aResults.end(); aResIter++)
92 GeomShapePtr aShape = (*aResIter)->shape();
93 if (!aShape.get() || aShape->isNull())
96 std::shared_ptr<ModelAPI_ResultBody> aResultBody = document()->createBody(data(), aResultIndex);
97 aResultBody->store(aShape);
98 aResultBody->loadFirstLevel(aShape, "ImportResult");
99 setResult(aResultBody, aResultIndex++);
101 std::set<ResultPtr> allResultsCashed; // cash to speed up searching in all results selected
102 std::list<ResultPtr> aLocalResults;
103 aLocalResults.push_back (*aResIter);
105 std::list<DocumentPtr> aDocuments; /// documents of Parts
106 aDocuments.push_back ((*aResIter)->document());
107 std::list<DocumentPtr>::iterator aDoc = aDocuments.begin();
108 for(; aDoc != aDocuments.end(); aDoc++)
111 int aGroupCount = (*aDoc)->size(ModelAPI_ResultGroup::group());
112 for (int aGroupIndex = 0; aGroupIndex < aGroupCount; ++aGroupIndex)
114 ResultGroupPtr aResultGroup =
115 std::dynamic_pointer_cast<ModelAPI_ResultGroup>((*aDoc)->object(ModelAPI_ResultGroup::group(), aGroupIndex));
117 if (!aResultGroup.get() || !aResultGroup->shape().get())
120 FeaturePtr aGroupFeature = (*aDoc)->feature(aResultGroup);
122 AttributeSelectionListPtr aSelectionList =
123 aGroupFeature->selectionList("group_list");
125 if (!ModelAPI_Tools::isInResults(aSelectionList,
127 allResultsCashed))// skip group not used in result
130 aGlobalResultsCashed.insert (allResultsCashed.begin(), allResultsCashed.end());
132 //Check: may be this group already exists in the list
133 bool anIsFound = false;
134 std::list<ResultGroupPtr>::iterator anIter = aGroups.begin();
135 for (; anIter != aGroups.end(); anIter++)
137 if (*anIter == aResultGroup)
144 aGroups.push_back (aResultGroup);
149 std::list<ResultGroupPtr>::iterator anIter = aGroups.begin();
150 for (; anIter != aGroups.end(); anIter++)
152 DocumentPtr aDoc = (*anIter)->document();
154 FeaturePtr aGroupFeature = aDoc->feature(*anIter);
156 AttributeSelectionListPtr aSelectionList =
157 aGroupFeature->selectionList("group_list");
159 std::shared_ptr<ModelAPI_Feature> aNewGroupFeature = addFeature("Group");
160 aNewGroupFeature->data()->setName(aGroupFeature->name());
162 AttributeSelectionListPtr aNewSelectionList = aNewGroupFeature->selectionList("group_list");
163 aNewSelectionList->setSelectionType (aSelectionList->selectionType());
164 GeomAPI_Shape::ShapeType aTypeOfShape = GeomAPI_Shape::shapeTypeByStr (aSelectionList->selectionType());
166 for (int aLocalSelIndex = 0; aLocalSelIndex < aSelectionList->size(); aLocalSelIndex++) {
168 AttributeSelectionPtr aLocalSel = aSelectionList->value(aLocalSelIndex);
169 ResultPtr aLocalContext = aLocalSel->context();
170 ResultGroupPtr aLocalGroup = std::dynamic_pointer_cast<ModelAPI_ResultGroup> (aLocalContext);
171 if (aLocalGroup.get())
173 GeomShapePtr aLocalShape = aGroupFeature->firstResult()->shape();
174 GeomAPI_ShapeExplorer anExplo (aLocalShape, aTypeOfShape);
175 for (; anExplo.more(); anExplo.next())
177 GeomShapePtr anExploredShape = anExplo.current();
178 std::set<ResultPtr>::iterator aResultIter = aGlobalResultsCashed.begin();
179 for (; aResultIter != aGlobalResultsCashed.end(); aResultIter++)
181 GeomShapePtr aCashedShape = (*aResultIter)->shape();
182 if (aCashedShape->isSubShape(anExploredShape))
183 aNewSelectionList->append((*aResultIter), anExploredShape);
190 GeomShapePtr aLocalShape = aLocalSel->value();
192 if (aLocalContext.get() && aGlobalResultsCashed.count(aLocalContext))
193 aNewSelectionList->append(aLocalContext, aLocalShape);
198 removeResults(aResultIndex);
201 bool FeaturesPlugin_ValidatorImportResults::isValid(const AttributePtr& theAttribute,
202 const std::list<std::string>&, Events_InfoMessage& theError) const
204 AttributeSelectionListPtr aList =
205 std::dynamic_pointer_cast<ModelAPI_AttributeSelectionList>(theAttribute);
206 if (aList->size() == 0) {
208 theError = "Please select sources.";
212 // store documents in the Part-fesatures in order to check
213 // the selection is located in the previous documents
214 std::map<DocumentPtr, int> aDocIndices;
215 DocumentPtr aRoot = ModelAPI_Session::get()->moduleDocument();
216 int aNum = aRoot->size(ModelAPI_Feature::group());
217 for (int a = 0; a < aNum; a++) {
218 FeaturePtr aFeat = std::dynamic_pointer_cast<ModelAPI_Feature>(
219 aRoot->object(ModelAPI_Feature::group(), a));
220 if (aFeat.get() && aFeat->data() && aFeat->data()->isValid() && aFeat->getKind() == "Part" &&
221 aFeat->results().size()) {
222 ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(aFeat->firstResult());
223 if (aPart.get() && aPart->partDoc()) {
224 aDocIndices[aPart->partDoc()] = a;
228 int aThisIndex = aDocIndices[aList->owner()->document()];
229 for (int aSelIndex = 0; aSelIndex < aList->size(); aSelIndex++) {
230 AttributeSelectionPtr aSel = aList->value(aSelIndex);
231 ResultPtr aContext = aSel->context();
232 if (!aContext.get()) {
234 theError = "Empty context.";
238 GeomShapePtr aShape = aSel->value();
239 if (aShape.get() && !aShape->isNull() && !aShape->isSame(aContext->shape())) {
241 theError = "Import results does not support selection of sub-shapes";
245 ResultBodyPtr aBody = std::dynamic_pointer_cast<ModelAPI_ResultBody>(aContext);
248 theError = "Only results may be selected.";
252 if (!aBody->shape()) {
254 theError = "Result is empty.";
258 int aBodyIndex = aDocIndices[aBody->document()];
259 if (aBodyIndex >= aThisIndex) {
260 theError = "The selected result must be located in earlier part.";
267 //============================================================================
268 std::shared_ptr<ModelAPI_Feature> FeaturesPlugin_ImportResult::addFeature(
271 std::shared_ptr<ModelAPI_Feature> aNew = document()->addFeature(theID, false);
273 data()->reflist(FEATURES_ID())->append(aNew);
274 // set as current also after it becomes sub to set correctly enabled for other subs
275 //document()->setCurrentFeature(aNew, false);
279 //=================================================================================================
280 int FeaturesPlugin_ImportResult::numberOfSubs(bool /*forTree*/) const
282 return data()->reflist(FEATURES_ID())->size(true);
285 //=================================================================================================
286 std::shared_ptr<ModelAPI_Feature> FeaturesPlugin_ImportResult::subFeature(const int theIndex,
289 ObjectPtr anObj = data()->reflist(FEATURES_ID())->object(theIndex, false);
290 FeaturePtr aRes = std::dynamic_pointer_cast<ModelAPI_Feature>(anObj);
294 //=================================================================================================
295 int FeaturesPlugin_ImportResult::subFeatureId(const int theIndex) const
297 std::shared_ptr<ModelAPI_AttributeRefList> aRefList = std::dynamic_pointer_cast<
298 ModelAPI_AttributeRefList>(data()->attribute(FEATURES_ID()));
299 std::list<ObjectPtr> aFeatures = aRefList->list();
300 std::list<ObjectPtr>::const_iterator anIt = aFeatures.begin();
301 int aResultIndex = 1; // number of the counted (created) features, started from 1
302 int aFeatureIndex = -1; // number of the not-empty features in the list
303 for (; anIt != aFeatures.end(); anIt++) {
306 if (aFeatureIndex == theIndex)
313 //=================================================================================================
314 bool FeaturesPlugin_ImportResult::isSub(ObjectPtr theObject) const
316 // check is this feature of result
317 FeaturePtr aFeature = ModelAPI_Feature::feature(theObject);
319 return data()->reflist(FEATURES_ID())->isInList(aFeature);
323 //=================================================================================================
324 void FeaturesPlugin_ImportResult::removeFeature(
325 std::shared_ptr<ModelAPI_Feature> theFeature)
327 if (!data()->isValid())
329 AttributeRefListPtr aList = reflist(FEATURES_ID());
330 aList->remove(theFeature);