33ba8565 |
1 | // Created by: Eugeny MALTCHIKOV |
2 | // Copyright (c) 2017 OPEN CASCADE SAS |
3 | // |
4 | // This file is part of Open CASCADE Technology software library. |
5 | // |
6 | // This library is free software; you can redistribute it and/or modify it under |
7 | // the terms of the GNU Lesser General Public License version 2.1 as published |
8 | // by the Free Software Foundation, with special exception defined in the file |
9 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
10 | // distribution for complete text of the license and disclaimer of any warranty. |
11 | // |
12 | // Alternatively, this file may be used under the terms of Open CASCADE |
13 | // commercial license or contractual agreement. |
14 | |
15 | |
16 | #include <BOPAlgo_PaveFiller.hxx> |
17 | #include <BOPAlgo_Alerts.hxx> |
18 | |
19 | #include <BOPDS_DS.hxx> |
20 | #include <BOPDS_MapOfCommonBlock.hxx> |
21 | |
22 | #include <BRep_Builder.hxx> |
23 | |
24 | #include <TopoDS_Compound.hxx> |
25 | |
26 | //======================================================================= |
27 | //function : CheckSelfInterference |
28 | //purpose : |
29 | //======================================================================= |
30 | void BOPAlgo_PaveFiller::CheckSelfInterference() |
31 | { |
32 | if (myArguments.Extent() == 1) { |
33 | // Self-interference mode |
34 | return; |
35 | } |
36 | // |
37 | BRep_Builder aBB; |
38 | // |
39 | Standard_Integer i, aNbR = myDS->NbRanges(); |
40 | for (i = 0; i < aNbR; ++i) { |
41 | const BOPDS_IndexRange& aR = myDS->Range(i); |
42 | // |
43 | // Map of connections of interfering shapes |
44 | NCollection_IndexedDataMap<TopoDS_Shape, |
1155d05a |
45 | TopTools_IndexedMapOfShape, |
33ba8565 |
46 | TopTools_ShapeMapHasher> aMCSI; |
47 | BOPDS_MapOfCommonBlock aMCBFence; |
48 | // |
49 | Standard_Integer j = aR.First(), aRLast = aR.Last(); |
50 | for (; j <= aRLast; ++j) { |
51 | const BOPDS_ShapeInfo& aSI = myDS->ShapeInfo(j); |
52 | if (!aSI.HasReference()) { |
53 | // No pave blocks and no face info |
54 | continue; |
55 | } |
56 | // |
57 | const TopoDS_Shape& aS = aSI.Shape(); |
58 | // |
59 | if (aSI.ShapeType() == TopAbs_EDGE) { |
60 | if (aSI.HasFlag()) { |
61 | continue; |
62 | } |
63 | // |
64 | // Analyze the shared vertices and common blocks |
65 | // |
1155d05a |
66 | TColStd_MapOfInteger aMSubS; |
67 | TColStd_ListIteratorOfListOfInteger aItLI(aSI.SubShapes()); |
33ba8565 |
68 | for (; aItLI.More(); aItLI.Next()) { |
69 | Standard_Integer nV = aItLI.Value(); |
70 | myDS->HasShapeSD(nV, nV); |
71 | aMSubS.Add(nV); |
72 | } |
73 | // |
74 | const BOPDS_ListOfPaveBlock& aLPB = myDS->PaveBlocks(j); |
75 | Standard_Boolean bAnalyzeV = aLPB.Extent() > 1; |
76 | // |
77 | BOPDS_ListIteratorOfListOfPaveBlock aIt(aLPB); |
78 | for (; aIt.More(); aIt.Next()) { |
79 | const Handle(BOPDS_PaveBlock)& aPB = aIt.Value(); |
80 | // |
81 | // Check the vertices |
82 | if (bAnalyzeV) { |
83 | Standard_Integer nV[2]; |
84 | aPB->Indices(nV[0], nV[1]); |
85 | for (Standard_Integer k = 0; k < 2; ++k) { |
86 | if (!aR.Contains(nV[k]) && !aMSubS.Contains(nV[k])) { |
87 | // Add connection |
88 | const TopoDS_Shape& aV = myDS->Shape(nV[k]); |
1155d05a |
89 | TopTools_IndexedMapOfShape* pMSOr = aMCSI.ChangeSeek(aV); |
33ba8565 |
90 | if (!pMSOr) { |
1155d05a |
91 | pMSOr = &aMCSI(aMCSI.Add(aV, TopTools_IndexedMapOfShape())); |
33ba8565 |
92 | } |
93 | pMSOr->Add(aS); |
94 | } |
95 | } |
96 | } |
97 | // |
98 | // Check common blocks |
99 | if (myDS->IsCommonBlock(aPB)) { |
100 | const Handle(BOPDS_CommonBlock)& aCB = myDS->CommonBlock(aPB); |
101 | if (aMCBFence.Add(aCB)) { |
102 | const BOPDS_ListOfPaveBlock& aLPBCB = aCB->PaveBlocks(); |
103 | // |
1155d05a |
104 | TColStd_ListOfInteger aLE; |
33ba8565 |
105 | BOPDS_ListIteratorOfListOfPaveBlock aItCB(aLPBCB); |
106 | for (; aItCB.More(); aItCB.Next()) { |
107 | const Handle(BOPDS_PaveBlock)& aPBCB = aItCB.Value(); |
108 | Standard_Integer nEOr = aPBCB->OriginalEdge(); |
109 | if (aR.Contains(nEOr)) { |
110 | aLE.Append(nEOr); |
111 | } |
112 | } |
113 | // |
114 | if (aLE.Extent() > 1) { |
ad8b073e |
115 | // Add the acquired self-interference warning: |
116 | // The same common block contains several edges from one argument |
33ba8565 |
117 | TopoDS_Compound aWC; |
118 | aBB.MakeCompound(aWC); |
119 | // |
1155d05a |
120 | TColStd_ListIteratorOfListOfInteger aItLE(aLE); |
33ba8565 |
121 | for (; aItLE.More(); aItLE.Next()) { |
122 | const TopoDS_Shape& aE1 = myDS->Shape(aItLE.Value()); |
123 | aBB.Add(aWC, aE1); |
124 | } |
125 | // |
ad8b073e |
126 | AddWarning (new BOPAlgo_AlertAcquiredSelfIntersection (aWC)); |
33ba8565 |
127 | } |
128 | } |
129 | } |
130 | } |
131 | } |
132 | else if(aSI.ShapeType() == TopAbs_FACE) { |
133 | // Analyze IN and Section vertices and edges of the faces |
134 | const BOPDS_FaceInfo& aFI = myDS->FaceInfo(j); |
135 | // |
136 | for (Standard_Integer k = 0; k < 2; ++k) { |
1155d05a |
137 | const TColStd_MapOfInteger& aMVF = !k ? aFI.VerticesIn() : aFI.VerticesSc(); |
138 | TColStd_MapIteratorOfMapOfInteger aItM(aMVF); |
33ba8565 |
139 | for (; aItM.More(); aItM.Next()) { |
140 | const TopoDS_Shape& aV = myDS->Shape(aItM.Value()); |
141 | // add connection |
1155d05a |
142 | TopTools_IndexedMapOfShape* pMSOr = aMCSI.ChangeSeek(aV); |
33ba8565 |
143 | if (!pMSOr) { |
1155d05a |
144 | pMSOr = &aMCSI(aMCSI.Add(aV, TopTools_IndexedMapOfShape())); |
33ba8565 |
145 | } |
146 | pMSOr->Add(aS); |
147 | } |
148 | } |
149 | // |
150 | for (Standard_Integer k = 0; k < 2; ++k) { |
151 | const BOPDS_IndexedMapOfPaveBlock& aMPBF = !k ? aFI.PaveBlocksIn() : aFI.PaveBlocksSc(); |
152 | Standard_Integer iPB, aNbPB = aMPBF.Extent(); |
153 | for (iPB = 1; iPB <= aNbPB; ++iPB) { |
154 | const Handle(BOPDS_PaveBlock)& aPB = aMPBF(iPB); |
155 | const TopoDS_Shape& aE = myDS->Shape(aPB->Edge()); |
156 | // add connection |
1155d05a |
157 | TopTools_IndexedMapOfShape* pMSOr = aMCSI.ChangeSeek(aE); |
33ba8565 |
158 | if (!pMSOr) { |
1155d05a |
159 | pMSOr = &aMCSI(aMCSI.Add(aE, TopTools_IndexedMapOfShape())); |
33ba8565 |
160 | } |
161 | pMSOr->Add(aS); |
162 | } |
163 | } |
164 | } |
165 | } |
166 | // |
167 | // Analyze connections |
168 | Standard_Integer aNbC = aMCSI.Extent(); |
169 | for (j = 1; j <= aNbC; ++j) { |
1155d05a |
170 | const TopTools_IndexedMapOfShape& aMCS = aMCSI(j); |
33ba8565 |
171 | if (aMCS.Extent() > 1) { |
ad8b073e |
172 | // Add acquired self-interference warning: |
173 | // Several faces from one argument contain the same vertex or edge |
33ba8565 |
174 | TopoDS_Compound aWC; |
175 | aBB.MakeCompound(aWC); |
176 | // |
177 | Standard_Integer iS, aNbS = aMCS.Extent(); |
178 | for (iS = 1; iS <= aNbS; ++iS) { |
179 | const TopoDS_Shape& aSx = aMCS(iS); |
180 | aBB.Add(aWC, aSx); |
181 | } |
ad8b073e |
182 | AddWarning (new BOPAlgo_AlertAcquiredSelfIntersection (aWC)); |
33ba8565 |
183 | } |
184 | } |
185 | } |
186 | } |