Salome HOME
Debug of Selector and correction of unit-tests
[modules/shaper.git] / src / Selector / Selector_Selector.cpp
1   // Copyright (C) 2014-2017  CEA/DEN, EDF R&D
2 //
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.
7 //
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.
12 //
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
16 //
17 // See http://www.salome-platform.org/ or
18 // email : webmaster.salome@opencascade.com<mailto:webmaster.salome@opencascade.com>
19 //
20
21 #include <Selector_Selector.h>
22
23 #include <Selector_NameGenerator.h>
24 #include <Selector_Algo.h>
25
26 #include <TopTools_MapOfShape.hxx>
27 #include <TopExp_Explorer.hxx>
28 #include <TopoDS_Builder.hxx>
29 #include <TopoDS_Compound.hxx>
30 #include <TNaming_NamedShape.hxx>
31
32 Selector_Selector::Selector_Selector(TDF_Label theLab, TDF_Label theBaseDocLab) :
33   myLab(theLab), myBaseDocumentLab(theBaseDocLab), myAlgo(NULL)
34 {}
35
36 Selector_Selector::~Selector_Selector()
37 {
38   if (myAlgo)
39     delete myAlgo;
40 }
41
42 bool Selector_Selector::select(const TopoDS_Shape theContext, const TopoDS_Shape theValue,
43   const bool theGeometricalNaming)
44 {
45   if (theValue.IsNull() || theContext.IsNull())
46     return false;
47
48   myAlgo = Selector_Algo::select(theContext, theValue, myLab, myBaseDocumentLab,
49     theGeometricalNaming, true, true);
50
51   return myAlgo != NULL;
52 }
53
54 bool Selector_Selector::store(const TopoDS_Shape theContext)
55 {
56   myAlgo->store();
57   return myAlgo->solve(theContext); // to update the selection shape on the label
58 }
59
60 bool Selector_Selector::restore(const TopoDS_Shape theContext)
61 {
62   myAlgo = Selector_Algo::restoreByLab(myLab, myBaseDocumentLab);
63   if (myAlgo) {
64     return myAlgo->solve(theContext); // to update the selection shape on the label
65   }
66   return false;
67 }
68
69 TopoDS_Shape Selector_Selector::value()
70 {
71   Handle(TNaming_NamedShape) aNS;
72   if (myLab.FindAttribute(TNaming_NamedShape::GetID(), aNS))
73     return aNS->Get();
74   return TopoDS_Shape(); // empty, error shape
75 }
76
77 std::string Selector_Selector::name(Selector_NameGenerator* theNameGenerator) {
78   return myAlgo->name(theNameGenerator);
79 }
80
81 TDF_Label Selector_Selector::restoreByName(
82   std::string theName, const TopAbs_ShapeEnum theShapeType,
83   Selector_NameGenerator* theNameGenerator, const bool theGeometricalNaming)
84 {
85   TDF_Label aResult;
86   myAlgo = Selector_Algo::restoreByName(
87     myLab, myBaseDocumentLab, theName, theShapeType, theNameGenerator, aResult);
88   if (myAlgo) {
89     if (theGeometricalNaming)
90       myAlgo->setGeometricalNaming();
91     return aResult;
92   }
93   return TDF_Label();
94 }
95
96 void Selector_Selector::combineGeometrical(const TopoDS_Shape theContext)
97 {
98   TopoDS_Shape aValue = value();
99   if (aValue.IsNull() || aValue.ShapeType() == TopAbs_COMPOUND)
100     return;
101
102   Selector_Algo* aNewAlgo = Selector_Algo::relesectWithAllGeometry(myAlgo, theContext);
103   if (aNewAlgo) {
104     aNewAlgo->store();
105     aNewAlgo->solve(theContext);
106     delete myAlgo;
107     myAlgo = aNewAlgo;
108   } else {
109     // if can not select, select the compound in a custom way
110     TopTools_MapOfShape aMap;
111     TopoDS_ListOfShape aList;
112     for(TopExp_Explorer anExp(theContext, aValue.ShapeType()); anExp.More(); anExp.Next()) {
113       if (aMap.Add(anExp.Current())) {
114         if (myAlgo->sameGeometry(aValue, anExp.Current()))
115           aList.Append(anExp.Current());
116       }
117     }
118     if (aList.Size() > 1) {
119       TopoDS_Builder aBuilder;
120       TopoDS_Compound aCompound;
121       aBuilder.MakeCompound(aCompound);
122       for(TopoDS_ListIteratorOfListOfShape aListIter(aList); aListIter.More(); aListIter.Next()) {
123         aBuilder.Add(aCompound, aListIter.Value());
124       }
125       Selector_Algo* aNewAlgo = Selector_Algo::relesectWithAllGeometry(myAlgo, theContext);
126       if (aNewAlgo) {
127         aNewAlgo->store();
128         aNewAlgo->solve(theContext);
129         delete myAlgo;
130         myAlgo = aNewAlgo;
131       }
132     }
133   }
134 }
135
136 bool Selector_Selector::solve(const TopoDS_Shape theContext)
137 {
138   return myAlgo->solve(theContext);
139 }