0031642: Visualization - crash in Graphic3d_Structure::SetVisual() on redisplaying...
[occt.git] / src / TopOpeBRepBuild / TopOpeBRepBuild_Area3dBuilder.cxx
CommitLineData
b311480e 1// Created on: 1995-12-21
2// Created by: Jean Yves LEBEY
3// Copyright (c) 1995-1999 Matra Datavision
973c2be1 4// Copyright (c) 1999-2014 OPEN CASCADE SAS
b311480e 5//
973c2be1 6// This file is part of Open CASCADE Technology software library.
b311480e 7//
d5f74e42 8// This library is free software; you can redistribute it and/or modify it under
9// the terms of the GNU Lesser General Public License version 2.1 as published
973c2be1 10// by the Free Software Foundation, with special exception defined in the file
11// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12// distribution for complete text of the license and disclaimer of any warranty.
b311480e 13//
973c2be1 14// Alternatively, this file may be used under the terms of Open CASCADE
15// commercial license or contractual agreement.
7fd59977 16
7fd59977 17
42cf5bc1 18#include <TopOpeBRepBuild_Area3dBuilder.hxx>
7fd59977 19#include <TopOpeBRepBuild_Loop.hxx>
42cf5bc1 20#include <TopOpeBRepBuild_LoopClassifier.hxx>
21#include <TopOpeBRepBuild_LoopSet.hxx>
7fd59977 22
23//=======================================================================
24//function : TopOpeBRepBuild_Area3dBuilder
25//purpose :
26//=======================================================================
7fd59977 27TopOpeBRepBuild_Area3dBuilder::TopOpeBRepBuild_Area3dBuilder()
28{
29}
30
31//=======================================================================
32//function : TopOpeBRepBuild_Area3dBuilder
33//purpose :
34//=======================================================================
35
36TopOpeBRepBuild_Area3dBuilder::TopOpeBRepBuild_Area3dBuilder
37(TopOpeBRepBuild_LoopSet& LS, TopOpeBRepBuild_LoopClassifier& LC,
38 const Standard_Boolean ForceClass)
39{
40 InitAreaBuilder(LS,LC,ForceClass);
41}
42
43//=======================================================================
44//function : InitAreaBuilder
45//purpose :
46//=======================================================================
47
48void TopOpeBRepBuild_Area3dBuilder::InitAreaBuilder
49(TopOpeBRepBuild_LoopSet& LS,
50 TopOpeBRepBuild_LoopClassifier& LC,
51 const Standard_Boolean ForceClass)
52{
53 TopAbs_State state;
54 Standard_Boolean Loopinside;
55 Standard_Boolean loopoutside;
56
57 TopOpeBRepBuild_ListIteratorOfListOfListOfLoop AreaIter;
58 TopOpeBRepBuild_ListIteratorOfListOfLoop LoopIter;
59 // boundaryloops : list of boundary loops out of the areas.
60 TopOpeBRepBuild_ListOfLoop boundaryloops;
61
62 myArea.Clear(); // Clear the list of Area to be built
63
64 for (LS.InitLoop(); LS.MoreLoop(); LS.NextLoop()) {
65
66 // process a new loop : L is the new current Loop
67 const Handle(TopOpeBRepBuild_Loop)& L = LS.Loop();
68 Standard_Boolean boundaryL = L->IsShape();
69
70 // L = shape et ForceClass : on traite L comme un block
71 // L = shape et !ForceClass : on traite L comme un pur shape
72 // L = !shape : on traite L comme un block
73 Standard_Boolean traitercommeblock = (!boundaryL) || ForceClass;
74 if ( ! traitercommeblock ) {
75
76 // the loop L is a boundary loop :
77 // - try to insert it in an existing area, such as L is inside all
78 // the block loops. Only block loops of the area are compared.
79 // - if L could not be inserted, store it in list of boundary loops.
80
81 Loopinside = Standard_False;
82 for (AreaIter.Initialize(myArea); AreaIter.More(); AreaIter.Next()) {
83 TopOpeBRepBuild_ListOfLoop& aArea = AreaIter.Value();
84 if ( aArea.IsEmpty() ) continue;
85 state = CompareLoopWithListOfLoop(LC,L,aArea,TopOpeBRepBuild_BLOCK );
86 if (state == TopAbs_UNKNOWN) Atomize(state,TopAbs_IN);
87 Loopinside = ( state == TopAbs_IN);
88 if ( Loopinside ) break;
89 } // end of Area scan
90
91 if ( Loopinside ) {
92 TopOpeBRepBuild_ListOfLoop& aArea = AreaIter.Value();
93 ADD_Loop_TO_LISTOFLoop(L,aArea,(void*)("IN, to current area"));
94 }
95 else if ( ! Loopinside ) {
96 ADD_Loop_TO_LISTOFLoop(L,boundaryloops,(void*)("! IN, to boundaryloops"));
97 }
98
99 } // end of boundary loop
100
101 else {
102 // the loop L is a block loop
103 // if L is IN theArea :
104 // - stop area scan, insert L in theArea.
105 // - remove from the area all the loops outside L
106 // - make a new area with them, unless they are all boundary
107 // - if they are all boundary put them back in boundaryLoops
108 // else :
109 // - create a new area with L.
110 // - insert boundary loops that are IN the new area
111 // (and remove them from 'boundaryloops')
112
113 Loopinside = Standard_False;
114 for (AreaIter.Initialize(myArea); AreaIter.More(); AreaIter.Next() ) {
115 TopOpeBRepBuild_ListOfLoop& aArea = AreaIter.Value();
116 if ( aArea.IsEmpty() ) continue;
117 state = CompareLoopWithListOfLoop(LC,L,aArea,TopOpeBRepBuild_ANYLOOP);
118 if (state == TopAbs_UNKNOWN) Atomize(state,TopAbs_IN);
119 Loopinside = (state == TopAbs_IN);
120 if ( Loopinside ) break;
121 } // end of Area scan
122
123 if ( Loopinside) {
124 TopOpeBRepBuild_ListOfLoop& aArea = AreaIter.Value();
125 Standard_Boolean allShape = Standard_True;
126 TopOpeBRepBuild_ListOfLoop removedLoops;
127 LoopIter.Initialize(aArea);
128 while (LoopIter.More()) {
129 const Handle(TopOpeBRepBuild_Loop)& LLI1 = LoopIter.Value();
130 state = LC.Compare(LLI1,L);
131 if (state == TopAbs_UNKNOWN) Atomize(state,TopAbs_IN); // not OUT
132 loopoutside = ( state == TopAbs_OUT );
133 if ( loopoutside ) {
134 const Handle(TopOpeBRepBuild_Loop)& curL = LoopIter.Value();
135 // remove the loop from the area
136 ADD_Loop_TO_LISTOFLoop
137 (curL,removedLoops,(void*)("loopoutside = 1, area = removedLoops"));
138
139 allShape = allShape && curL->IsShape();
140 REM_Loop_FROM_LISTOFLoop
141 (LoopIter,AreaIter.Value(),(void*)("loop of cur. area, cur. area"));
142 }
143 else {
144 LoopIter.Next();
145 }
146 }
147 // insert the loop in the area
148 ADD_Loop_TO_LISTOFLoop(L,aArea,(void*)("area = current"));
149 if ( ! removedLoops.IsEmpty() ) {
150 if ( allShape ) {
151 ADD_LISTOFLoop_TO_LISTOFLoop
152 (removedLoops,boundaryloops,(void*)(
153 "allShape = 1"),(void*)("removedLoops"),(void*)("boundaryloops"));
154 }
155 else {
156 // make a new area with the removed loops
157 TopOpeBRepBuild_ListOfLoop thelist;
158 myArea.Append(thelist);
159 ADD_LISTOFLoop_TO_LISTOFLoop
160 (removedLoops,myArea.Last(),
161 (void*)("allShape = 0"),(void*)("removedLoops"),(void*)("new area"));
162 }
163 }
164 } // Loopinside == True
165
166 else {
167 Standard_Integer ashapeinside,ablockinside;
168 TopOpeBRepBuild_ListOfLoop thelist1;
169 myArea.Append( thelist1);
170 TopOpeBRepBuild_ListOfLoop& newArea0 = myArea.Last();
171 ADD_Loop_TO_LISTOFLoop(L,newArea0,(void*)("new area"));
172
173 LoopIter.Initialize(boundaryloops);
174 while ( LoopIter.More() ) {
175 ashapeinside = ablockinside = Standard_False;
176 const Handle(TopOpeBRepBuild_Loop)& LLI2 = LoopIter.Value();
177 state = LC.Compare(LLI2,L);
178 if (state == TopAbs_UNKNOWN) Atomize(state,TopAbs_IN);
179 ashapeinside = (state == TopAbs_IN);
180 if (ashapeinside) {
181 const Handle(TopOpeBRepBuild_Loop)& LLI3 = LoopIter.Value();
182 state = LC.Compare(L,LLI3);
183 if (state == TopAbs_UNKNOWN) Atomize(state,TopAbs_IN);
184 ablockinside = (state == TopAbs_IN);
185 }
186 if ( ashapeinside && ablockinside ) {
187 const Handle(TopOpeBRepBuild_Loop)& curL = LoopIter.Value();
188 ADD_Loop_TO_LISTOFLoop
189 (curL,newArea0,(void*)("ashapeinside && ablockinside, new area"));
190
191 REM_Loop_FROM_LISTOFLoop
192 (LoopIter,boundaryloops,(void*)("loop of boundaryloops, boundaryloops"));
193 }
194 else {
195 LoopIter.Next();
196 }
197 } // end of boundaryloops scan
198 } // Loopinside == False
199 } // end of block loop
200 } // end of LoopSet LS scan
201
202 InitArea();
203}
204
205
206
207
208
209
210
211
212