b311480e |
1 | // Created on: 1993-11-04 |
2 | // Created by: Jean Marc LACHAUME |
3 | // Copyright (c) 1993-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 | |
17 | #include <HatchGen_Domain.hxx> |
18 | #include <HatchGen_Domains.hxx> |
19 | #include <HatchGen_PointOnElement.hxx> |
20 | #include <HatchGen_PointOnHatching.hxx> |
21 | #include <IntRes2d_IntersectionPoint.hxx> |
22 | #include <IntRes2d_IntersectionSegment.hxx> |
23 | #include <IntRes2d_Transition.hxx> |
24 | #include <Precision.hxx> |
25 | #include <TopAbs.hxx> |
26 | #include <TopTrans_CurveTransition.hxx> |
27 | |
28 | #define RAISE_IF_NOSUCHOBJECT 0 |
29 | #define TRACE_HATCHER 0 |
30 | |
31 | //======================================================================= |
32 | //======================================================================= |
33 | // Category : General use. |
34 | //======================================================================= |
35 | //======================================================================= |
36 | |
37 | //======================================================================= |
38 | // Function : HatchGen_Hatcher |
39 | // Purpose : Constructor. |
40 | //======================================================================= |
41 | |
42 | HatchGen_Hatcher::HatchGen_Hatcher (const TheIntersector& Intersector, |
43 | const Standard_Real Confusion2d, |
44 | const Standard_Real Confusion3d, |
45 | const Standard_Boolean KeepPnt, |
46 | const Standard_Boolean KeepSeg) : |
47 | myIntersector (Intersector) , |
48 | myConfusion2d (Confusion2d) , |
49 | myConfusion3d (Confusion3d) , |
50 | myKeepPoints (KeepPnt) , |
51 | myKeepSegments (KeepSeg) , |
52 | myNbElements (0) , |
53 | myNbHatchings (0) |
54 | { |
55 | } |
56 | |
57 | //======================================================================= |
58 | // Function : Intersector |
59 | // Purpose : Sets the associated intersector. |
60 | //======================================================================= |
61 | |
62 | void HatchGen_Hatcher::Intersector (const TheIntersector& Intersector) |
63 | { |
64 | myIntersector = Intersector ; |
65 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
66 | if (myHatchings.IsBound (IndH)) { |
67 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
68 | Hatching.ClrPoints() ; |
69 | } |
70 | } |
71 | } |
72 | |
73 | |
74 | //======================================================================= |
75 | // Function : Confusion2d |
76 | // Purpose : Sets the 2dconfusion tolerance. |
77 | //======================================================================= |
78 | |
79 | void HatchGen_Hatcher::Confusion2d (const Standard_Real Confusion) |
80 | { |
81 | myConfusion2d = Confusion ; |
82 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
83 | if (myHatchings.IsBound (IndH)) { |
84 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
85 | Hatching.ClrPoints() ; |
86 | } |
87 | } |
88 | } |
89 | |
90 | |
91 | //======================================================================= |
92 | // Function : Confusion3d |
93 | // Purpose : Sets the 3d confusion tolerance. |
94 | //======================================================================= |
95 | |
96 | void HatchGen_Hatcher::Confusion3d (const Standard_Real Confusion) |
97 | { |
98 | myConfusion3d = Confusion ; |
99 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
100 | if (myHatchings.IsBound (IndH)) { |
101 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
102 | Hatching.ClrPoints() ; |
103 | } |
104 | } |
105 | } |
106 | |
107 | //======================================================================= |
108 | // Function : KeepPoints |
109 | // Purpose : Sets the above flag. |
110 | //======================================================================= |
111 | |
112 | void HatchGen_Hatcher::KeepPoints (const Standard_Boolean Keep) |
113 | { |
114 | myKeepPoints = Keep ; |
115 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
116 | if (myHatchings.IsBound (IndH)) { |
117 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
118 | Hatching.ClrDomains() ; |
119 | } |
120 | } |
121 | } |
122 | |
123 | |
124 | //======================================================================= |
125 | // Function : KeepSegments |
126 | // Purpose : Sets the above flag. |
127 | //======================================================================= |
128 | |
129 | void HatchGen_Hatcher::KeepSegments (const Standard_Boolean Keep) |
130 | { |
131 | myKeepSegments = Keep ; |
132 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
133 | if (myHatchings.IsBound (IndH)) { |
134 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
135 | Hatching.ClrDomains() ; |
136 | } |
137 | } |
138 | } |
139 | |
140 | |
141 | |
142 | //======================================================================= |
143 | //======================================================================= |
144 | // Category : Element. |
145 | //======================================================================= |
146 | //======================================================================= |
147 | |
148 | |
149 | //======================================================================= |
150 | // Function : AddElement |
151 | // Purpose : Adds an element to the Hatcher and returns its index. |
152 | //======================================================================= |
153 | |
154 | Standard_Integer HatchGen_Hatcher::AddElement (const TheCurveE& Curve, |
155 | const TopAbs_Orientation Orientation) |
156 | { |
157 | Standard_Integer IndE ; |
158 | for (IndE = 1 ; IndE <= myNbElements && myElements.IsBound(IndE) ; IndE++) ; |
159 | if (IndE > myNbElements) { |
160 | myNbElements++ ; |
161 | IndE = myNbElements ; |
162 | } |
163 | HatchGen_Element Element (Curve, Orientation) ; |
164 | myElements.Bind (IndE, Element) ; |
165 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings; IndH++) { |
166 | if (myHatchings.IsBound(IndH)) { |
167 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
168 | Hatching.ClrPoints () ; |
169 | } |
170 | } |
171 | return IndE ; |
172 | } |
173 | |
174 | //======================================================================= |
175 | // Function : RemElement |
176 | // Purpose : Removes the IndE-th element from the hatcher. |
177 | //======================================================================= |
178 | |
179 | void HatchGen_Hatcher::RemElement (const Standard_Integer IndE) |
180 | { |
181 | #if RAISE_IF_NOSUCHOBJECT |
182 | Standard_NoSuchObject_Raise_if (!myElements.IsBound (IndE), "") ; |
183 | #endif |
184 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
185 | if (myHatchings.IsBound (IndH)) { |
186 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
187 | Standard_Boolean DomainsToClear = Standard_False ; |
188 | for (Standard_Integer IPntH = Hatching.NbPoints() ; IPntH > 0 ; IPntH--) { |
189 | HatchGen_PointOnHatching PntH = Hatching.ChangePoint (IPntH) ; |
190 | for (Standard_Integer IPntE = PntH.NbPoints() ; IPntE > 0 ; IPntE--) { |
191 | if (PntH.Point(IPntE).Index() == IndE) { |
192 | PntH.RemPoint (IPntE) ; |
193 | DomainsToClear = Standard_True ; |
194 | } |
195 | } |
196 | if (PntH.NbPoints() == 0) Hatching.RemPoint (IPntH) ; |
197 | } |
198 | if (DomainsToClear) Hatching.ClrDomains() ; |
199 | } |
200 | } |
201 | myElements.UnBind (IndE) ; |
202 | if (IndE == myNbElements) myNbElements-- ; |
203 | } |
204 | |
205 | //======================================================================= |
206 | // Function : ClrElements |
207 | // Purpose : Removes all the elements from the hatcher. |
208 | //======================================================================= |
209 | |
210 | void HatchGen_Hatcher::ClrElements () |
211 | { |
212 | if (myNbElements != 0) { |
213 | if (myNbHatchings != 0) { |
214 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
215 | if (myHatchings.IsBound(IndH)) { |
216 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
217 | Hatching.ClrPoints() ; |
218 | } |
219 | } |
220 | } |
221 | myElements.Clear() ; |
222 | myNbElements = 0 ; |
223 | } |
224 | } |
225 | |
226 | //======================================================================= |
227 | //======================================================================= |
228 | // Category : Hatching. |
229 | //======================================================================= |
230 | //======================================================================= |
231 | |
232 | |
233 | //======================================================================= |
234 | // Function : AddHatching |
235 | // Purpose : Adds a hatching to the hatcher and returns its index. |
236 | //======================================================================= |
237 | |
238 | Standard_Integer HatchGen_Hatcher::AddHatching (const TheCurveH& Curve) |
239 | { |
240 | Standard_Integer IndH ; |
241 | for (IndH = 1 ; IndH <= myNbHatchings && myHatchings.IsBound(IndH) ; IndH++) ; |
242 | if (IndH > myNbHatchings) { |
243 | myNbHatchings++ ; |
244 | IndH = myNbHatchings ; |
245 | } |
246 | HatchGen_Hatching Hatching (Curve) ; |
247 | myHatchings.Bind (IndH, Hatching) ; |
248 | return IndH ; |
249 | } |
250 | |
251 | //======================================================================= |
252 | // Function : RemHatching |
253 | // Purpose : Removes the IndH-th hatching from the hatcher. |
254 | //======================================================================= |
255 | |
256 | void HatchGen_Hatcher::RemHatching (const Standard_Integer IndH) |
257 | { |
258 | #if RAISE_IF_NOSUCHOBJECT |
259 | Standard_NoSuchObject_Raise_if (!myHatchings.IsBound (IndH), "") ; |
260 | #endif |
261 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
262 | Hatching.ClrPoints() ; |
263 | myHatchings.UnBind (IndH) ; |
264 | if (IndH == myNbHatchings) myNbHatchings-- ; |
265 | } |
266 | |
267 | //======================================================================= |
268 | // Function : ClrHatchings |
269 | // Purpose : Removes all the hatchings from the hatcher. |
270 | //======================================================================= |
271 | |
272 | void HatchGen_Hatcher::ClrHatchings () |
273 | { |
274 | if (myNbHatchings != 0) { |
275 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
276 | if (myHatchings.IsBound(IndH)) { |
277 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
278 | Hatching.ClrPoints() ; |
279 | } |
280 | } |
281 | myHatchings.Clear() ; |
282 | myNbHatchings = 0 ; |
283 | } |
284 | } |
285 | |
286 | |
287 | |
288 | //======================================================================= |
289 | //======================================================================= |
290 | // Category : Computation - Trimming |
291 | //======================================================================= |
292 | //======================================================================= |
293 | |
294 | //======================================================================= |
295 | // Function : Trim |
296 | // Purpose : Trims all the hatchings of the hatcher by all the elements |
297 | // of the hatcher. |
298 | //======================================================================= |
299 | |
300 | void HatchGen_Hatcher::Trim () |
301 | { |
302 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) |
303 | if (myHatchings.IsBound (IndH)) |
304 | Trim (IndH) ; |
305 | } |
306 | |
307 | //======================================================================= |
308 | // Function : Trim |
309 | // Purpose : Adds a hatching to the hatcher and trims it by the elements |
310 | // already given and returns its index. |
311 | //======================================================================= |
312 | |
313 | Standard_Integer HatchGen_Hatcher::Trim (const TheCurveH& Curve) |
314 | { |
315 | Standard_Integer IndH = AddHatching (Curve) ; |
316 | Trim (IndH) ; |
317 | return IndH ; |
318 | } |
319 | |
320 | //======================================================================= |
321 | // Function : Trim |
322 | // Purpose : Trims the IndH-th hatching by the elements already given. |
323 | //======================================================================= |
324 | |
325 | void HatchGen_Hatcher::Trim (const Standard_Integer IndH) |
326 | { |
327 | #if RAISE_IF_NOSUCHOBJECT |
328 | Standard_NoSuchObject_Raise_if (!myHatchings.IsBound (IndH), "") ; |
329 | #endif |
330 | |
331 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
332 | |
333 | Hatching.ClrPoints() ; |
334 | |
335 | Standard_Boolean OK, AllOK ; |
336 | |
337 | AllOK = Standard_True ; |
338 | for (Standard_Integer IndE = 1 ; IndE <= myNbElements ; IndE++) { |
339 | if (myElements.IsBound (IndE)) { |
340 | OK = Trim (IndH, IndE) ; |
341 | AllOK = AllOK && OK ; |
342 | } |
343 | } |
344 | Hatching.TrimDone (Standard_True) ; |
345 | Hatching.TrimFailed (!AllOK) ; |
346 | |
347 | if (AllOK) { |
348 | for (Standard_Integer IPnt = 1 ; IPnt <= Hatching.NbPoints() ; IPnt++) { |
349 | HatchGen_PointOnHatching& PntH = Hatching.ChangePoint(IPnt) ; |
350 | OK = GlobalTransition (PntH) ; |
351 | AllOK = AllOK && OK ; |
352 | } |
353 | Hatching.Status (AllOK ? HatchGen_NoProblem : HatchGen_TransitionFailure) ; |
354 | } |
355 | } |
356 | |
357 | #if TRACE_HATCHER |
358 | |
359 | //======================================================================= |
360 | // Function : IntersectionPointDump |
361 | // Purpose : Dump of the intersection point. |
362 | //======================================================================= |
363 | |
364 | static void IntersectionPointDump (const IntRes2d_IntersectionPoint& Pnt, |
365 | const Standard_Integer Index) |
366 | { |
367 | Standard_Integer SavedPrecision = cout.precision() ; |
368 | cout.precision (15) ; |
369 | cout << "----- IntRes2d:: Point # " << setw(3) << Index << " ---------------" << endl ; |
370 | cout << "-- U: "<<Pnt.Value().X()<<" V: "<<Pnt.Value().Y()<<endl; |
371 | cout << "-- Parameter on first : " << Pnt.ParamOnFirst() << endl ; |
372 | cout << "-- Position on first : " ; |
373 | switch (Pnt.TransitionOfFirst().PositionOnCurve()) { |
374 | case IntRes2d_Head : cout << "HEAD" ; break ; |
375 | case IntRes2d_Middle : cout << "MIDDLE" ; break ; |
376 | case IntRes2d_End : cout << "END" ; break ; |
377 | } |
378 | cout << endl ; |
379 | cout << "-- IntRes2d:: Transition on first : " ; |
380 | switch (Pnt.TransitionOfFirst().TransitionType()) { |
381 | case IntRes2d_In : cout << "IN" ; break ; |
382 | case IntRes2d_Out : cout << "OUT" ; break ; |
383 | case IntRes2d_Touch : cout << "TOUCH" ; break ; |
384 | case IntRes2d_Undecided : cout << "UNDECIDED" ; break ; |
385 | } |
386 | cout << endl ; |
387 | if (Pnt.TransitionOfFirst().TransitionType() == IntRes2d_Touch) { |
388 | cout << "-- IntRes2d:: Situation on first : " ; |
389 | switch (Pnt.TransitionOfFirst().Situation()) { |
390 | case IntRes2d_Inside : cout << "INSIDE" ; break ; |
391 | case IntRes2d_Outside : cout << "OUTSIDE" ; break ; |
392 | case IntRes2d_Unknown : cout << "UNKNOWN" ; break ; |
393 | } |
394 | cout << endl ; |
395 | } |
396 | cout << "--------------------------------------------" << endl ; |
397 | cout << "-- Parameter on second : " << Pnt.ParamOnSecond() << endl ; |
398 | cout << "-- Position on second : " ; |
399 | switch (Pnt.TransitionOfSecond().PositionOnCurve()) { |
400 | case IntRes2d_Head : cout << "HEAD" ; break ; |
401 | case IntRes2d_Middle : cout << "MIDDLE" ; break ; |
402 | case IntRes2d_End : cout << "END" ; break ; |
403 | } |
404 | cout << endl ; |
405 | cout << "-- IntRes2d:: Transition on second : " ; |
406 | switch (Pnt.TransitionOfSecond().TransitionType()) { |
407 | case IntRes2d_In : cout << "IN" ; break ; |
408 | case IntRes2d_Out : cout << "OUT" ; break ; |
409 | case IntRes2d_Touch : cout << "TOUCH" ; break ; |
410 | case IntRes2d_Undecided : cout << "UNDECIDED" ; break ; |
411 | } |
412 | cout << endl ; |
413 | if (Pnt.TransitionOfSecond().TransitionType() == IntRes2d_Touch) { |
414 | cout << "-- IntRes2d:: Situation on second : " ; |
415 | switch (Pnt.TransitionOfSecond().Situation()) { |
416 | case IntRes2d_Inside : cout << "INSIDE" ; break ; |
417 | case IntRes2d_Outside : cout << "OUTSIDE" ; break ; |
418 | case IntRes2d_Unknown : cout << "UNKNOWN" ; break ; |
419 | } |
420 | cout << endl ; |
421 | } |
422 | cout << "--------------------------------------------" << endl ; |
423 | cout.precision (SavedPrecision) ; |
424 | } |
425 | |
426 | #endif |
427 | |
428 | //======================================================================= |
429 | // Function : Trim |
430 | // Purpose : Trims the IndH-th hatching of the hatcher by the IndE th |
431 | // element. |
432 | //======================================================================= |
433 | |
434 | Standard_Boolean HatchGen_Hatcher::Trim (const Standard_Integer IndH, |
435 | const Standard_Integer IndE) |
436 | { |
437 | #if RAISE_IF_NOSUCHOBJECT |
438 | Standard_NoSuchObject_Raise_if (!myHatchings.IsBound (IndH), "") ; |
439 | Standard_NoSuchObject_Raise_if (!myElements.IsBound (IndE), "") ; |
440 | #endif |
441 | |
442 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
443 | HatchGen_Element& Element = myElements.ChangeFind (IndE) ; |
444 | |
445 | TheCurveH hatching = Hatching.ChangeCurve() ; |
446 | TheCurveE element = Element.ChangeCurve() ; |
447 | |
448 | myIntersector.Intersect (hatching, element) ; |
449 | |
450 | #if TRACE_HATCHER |
451 | cout << "--- Hatcher - Trim:: Hatching # " << setw(3); |
452 | cout << IndH << " with Element # " << setw(3); |
453 | cout << IndE << " ----------" << endl ; |
454 | #endif |
455 | |
456 | if (!myIntersector.IsDone()) { |
457 | cout<<" Intersector -> Done = False "; |
458 | return Standard_False ; |
459 | } |
460 | |
461 | #if TRACE_HATCHER |
462 | if (myIntersector.IsEmpty()) { |
463 | cout << "No intersection" << endl ; |
464 | cout << "--------------------------------------------------------------------" << endl ; |
465 | } |
466 | #endif |
467 | |
468 | if (myIntersector.IsEmpty()) return Standard_True ; |
469 | |
470 | #if TRACE_HATCHER |
471 | cout << "Number of intersection points : " << setw(3) << (myIntersector.NbPoints()) << endl ; |
472 | cout << "Number of intersection segments : " << setw(3) << (myIntersector.NbSegments()) << endl ; |
473 | #endif |
474 | |
475 | //----------------------------------------------------------------------- |
476 | // Traitement des points d intersection. |
477 | //----------------------------------------------------------------------- |
478 | |
479 | for (Standard_Integer IPntI = 1 ; IPntI <= myIntersector.NbPoints() ; IPntI++) { |
480 | const IntRes2d_IntersectionPoint& PntI = myIntersector.Point (IPntI) ; |
481 | |
482 | #if TRACE_HATCHER |
483 | IntersectionPointDump (PntI, IPntI) ; |
484 | #endif |
485 | |
486 | HatchGen_PointOnElement PntE (PntI) ; |
487 | PntE.SetIndex (IndE) ; |
488 | |
489 | HatchGen_PointOnHatching PntH (PntI) ; |
490 | PntH.SetIndex (IndH) ; |
491 | PntH.AddPoint (PntE, myConfusion2d) ; |
492 | |
493 | Hatching.AddPoint (PntH, myConfusion2d) ; |
494 | } |
495 | |
496 | //----------------------------------------------------------------------- |
497 | // Traitement des segments d intersection. |
498 | //----------------------------------------------------------------------- |
499 | |
500 | for (Standard_Integer ISeg = 1 ; ISeg <= myIntersector.NbSegments() ; ISeg++) { |
501 | |
502 | const IntRes2d_IntersectionSegment& Seg = myIntersector.Segment (ISeg) ; |
503 | |
504 | #if TRACE_HATCHER |
505 | cout << "----- Segment # " << setw(3) << ISeg << " -------------" << endl ; |
506 | #endif |
507 | |
508 | Standard_Boolean FirstPoint = Seg.HasFirstPoint() ; |
509 | Standard_Boolean LastPoint = Seg.HasLastPoint() ; |
510 | |
511 | //----------------------------------------------------------------------- |
512 | // Les deux points peuvent etre confondus. |
513 | //----------------------------------------------------------------------- |
514 | |
515 | if (FirstPoint && LastPoint) { |
516 | |
517 | const IntRes2d_IntersectionPoint& Pnt1 = Seg.FirstPoint() ; |
518 | const IntRes2d_IntersectionPoint& Pnt2 = Seg.LastPoint() ; |
519 | |
520 | const IntRes2d_Transition& TrsPnt1H = Pnt1.TransitionOfFirst() ; |
521 | const IntRes2d_Transition& TrsPnt1E = Pnt1.TransitionOfSecond() ; |
522 | const IntRes2d_Transition& TrsPnt2H = Pnt2.TransitionOfFirst() ; |
523 | const IntRes2d_Transition& TrsPnt2E = Pnt2.TransitionOfSecond() ; |
524 | |
525 | IntRes2d_TypeTrans TypePnt1H = TrsPnt1H.TransitionType() ; |
526 | IntRes2d_TypeTrans TypePnt1E = TrsPnt1E.TransitionType() ; |
527 | IntRes2d_TypeTrans TypePnt2H = TrsPnt2H.TransitionType() ; |
528 | IntRes2d_TypeTrans TypePnt2E = TrsPnt2E.TransitionType() ; |
529 | |
530 | //----------------------------------------------------------------------- |
531 | // Les deux points peuvent etre confondus au regard de la precision du |
532 | // `hatcher'. |
533 | //----------------------------------------------------------------------- |
534 | |
535 | Standard_Boolean Conf2d = Abs (Pnt1.ParamOnFirst() - Pnt2.ParamOnFirst()) <= myConfusion2d ; |
536 | |
537 | //----------------------------------------------------------------------- |
538 | // Les deux points peuvent etre `confondus' au regard des intersections. |
539 | //----------------------------------------------------------------------- |
540 | |
541 | Standard_Boolean Conf3d = Standard_False ; |
542 | |
543 | if (!Conf2d) { |
544 | Conf3d = Standard_True ; |
545 | if (Conf3d) Conf3d = TypePnt1H != IntRes2d_Touch && TypePnt1H != IntRes2d_Undecided ; |
546 | if (Conf3d) Conf3d = TypePnt1E != IntRes2d_Touch && TypePnt1E != IntRes2d_Undecided ; |
547 | if (Conf3d) Conf3d = TypePnt2H != IntRes2d_Touch && TypePnt2H != IntRes2d_Undecided ; |
548 | if (Conf3d) Conf3d = TypePnt2E != IntRes2d_Touch && TypePnt2E != IntRes2d_Undecided ; |
549 | if (Conf3d) Conf3d = TypePnt1H == TypePnt2H && TypePnt1E == TypePnt2E ; |
550 | if (Conf3d) Conf3d = Pnt1.Value().Distance (Pnt2.Value()) <= myConfusion3d ; |
551 | } |
552 | |
553 | if (Conf2d || Conf3d) { |
554 | |
555 | HatchGen_PointOnElement PntE ; |
556 | PntE.SetIndex (IndE) ; |
557 | PntE.SetParameter ((Pnt1.ParamOnSecond() + Pnt2.ParamOnSecond()) / 2.) ; |
558 | switch (TrsPnt1E.PositionOnCurve()) { |
559 | case IntRes2d_Head: { |
560 | PntE.SetPosition(TopAbs_FORWARD) ; |
561 | break ; |
562 | } |
563 | case IntRes2d_Middle: { |
564 | switch (TrsPnt2E.PositionOnCurve()) { |
565 | case IntRes2d_Head: { |
566 | PntE.SetPosition (TopAbs_FORWARD); |
567 | break; |
568 | } |
569 | case IntRes2d_Middle: { |
570 | PntE.SetPosition (TopAbs_INTERNAL) ; |
571 | break ; |
572 | } |
573 | case IntRes2d_End: { |
574 | PntE.SetPosition (TopAbs_REVERSED) ; |
575 | break ; |
576 | } |
577 | default: { |
578 | break; |
579 | } |
580 | } |
581 | break; |
582 | } |
583 | case IntRes2d_End: { |
584 | PntE.SetPosition(TopAbs_REVERSED) ; |
585 | break ; |
586 | } |
587 | default: { |
588 | break; |
589 | } |
590 | } |
591 | PntE.SetIntersectionType |
592 | ((PntE.Position() == TopAbs_INTERNAL) ? HatchGen_TRUE : HatchGen_TOUCH) ; |
593 | PntE.SetStateBefore ((TypePnt1H == IntRes2d_In) ? TopAbs_OUT : TopAbs_IN) ; |
594 | PntE.SetStateAfter ((TypePnt2H == IntRes2d_In) ? TopAbs_OUT : TopAbs_IN) ; |
595 | |
596 | HatchGen_PointOnHatching PntH ; |
597 | PntH.SetIndex (IndH) ; |
598 | PntH.SetParameter ((Pnt1.ParamOnFirst() + Pnt2.ParamOnFirst()) / 2.) ; |
599 | switch (TrsPnt1H.PositionOnCurve()) { |
600 | case IntRes2d_Head: { |
601 | PntH.SetPosition (TopAbs_FORWARD) ; |
602 | break ; |
603 | } |
604 | case IntRes2d_Middle: { |
605 | switch (TrsPnt2H.PositionOnCurve()) { |
606 | case IntRes2d_Head: { |
607 | PntH.SetPosition (TopAbs_FORWARD) ; |
608 | break ; |
609 | } |
610 | case IntRes2d_Middle: { |
611 | PntH.SetPosition (TopAbs_INTERNAL) ; |
612 | break ; |
613 | } |
614 | case IntRes2d_End: { |
615 | PntH.SetPosition (TopAbs_REVERSED) ; |
616 | break ; |
617 | } |
618 | default : { |
619 | break ; |
620 | } |
621 | } |
622 | break ; |
623 | } |
624 | case IntRes2d_End: { |
625 | PntH.SetPosition (TopAbs_REVERSED) ; |
626 | break ; |
627 | } |
628 | default : { |
629 | break ; |
630 | } |
631 | } |
632 | |
633 | PntH.AddPoint (PntE, myConfusion2d) ; |
634 | Hatching.AddPoint (PntH, myConfusion2d) ; |
635 | |
636 | #if TRACE_HATCHER |
637 | IntersectionPointDump (Pnt1, 1) ; |
638 | IntersectionPointDump (Pnt2, 2) ; |
639 | cout << "THESE TWO POINTS ARE " |
640 | << (Conf2d ? "2D" : "3D") |
641 | << " CONFUSED INTO THE FOLLOWING" << endl ; |
642 | PntH.Dump() ; |
643 | #endif |
644 | continue ; |
645 | |
646 | } |
647 | |
648 | //----------------------------------------------------------------------- |
649 | // Traitement du premier point du segment. |
650 | //----------------------------------------------------------------------- |
651 | |
652 | if (FirstPoint) { |
653 | |
654 | const IntRes2d_IntersectionPoint& PntI = Seg.FirstPoint() ; |
655 | |
656 | #if TRACE_HATCHER |
657 | IntersectionPointDump (PntI, 1) ; |
658 | #endif |
659 | |
660 | HatchGen_PointOnElement PntE (PntI) ; |
661 | PntE.SetIndex (IndE) ; |
662 | PntE.SetSegmentBeginning (Standard_True) ; |
663 | PntE.SetSegmentEnd (Standard_False) ; |
664 | |
665 | HatchGen_PointOnHatching PntH (PntI) ; |
666 | PntH.SetIndex (IndH) ; |
667 | PntH.AddPoint (PntE, myConfusion2d) ; |
668 | |
669 | Hatching.AddPoint (PntH, myConfusion2d) ; |
670 | |
671 | #if TRACE_HATCHER |
672 | } |
673 | else { |
674 | cout << "----- Has no first point --------" << endl ; |
675 | cout << "---------------------------------" << endl ; |
676 | #endif |
677 | |
678 | } |
679 | |
680 | //----------------------------------------------------------------------- |
681 | // Traitement du deuxieme point du segment. |
682 | //----------------------------------------------------------------------- |
683 | |
684 | if (LastPoint) { |
685 | |
686 | const IntRes2d_IntersectionPoint& PntI = Seg.LastPoint() ; |
687 | |
688 | #if TRACE_HATCHER |
689 | IntersectionPointDump (PntI, 2) ; |
690 | #endif |
691 | |
692 | HatchGen_PointOnElement PntE (PntI) ; |
693 | PntE.SetIndex (IndE) ; |
694 | PntE.SetSegmentBeginning (Standard_False) ; |
695 | PntE.SetSegmentEnd (Standard_True) ; |
696 | |
697 | HatchGen_PointOnHatching PntH (PntI) ; |
698 | PntH.SetIndex (IndH) ; |
699 | PntH.AddPoint (PntE, myConfusion2d) ; |
700 | |
701 | Hatching.AddPoint (PntH, myConfusion2d) ; |
702 | |
703 | #if TRACE_HATCHER |
704 | } |
705 | else { |
706 | cout << "----- Has no last point ---------" << endl ; |
707 | cout << "---------------------------------" << endl ; |
708 | #endif |
709 | } |
710 | } |
711 | #if TRACE_HATCHER |
712 | cout << "--------------------------------------------------------------------" << endl ; |
713 | #endif |
714 | |
715 | } |
716 | return Standard_True; |
717 | } |
718 | //======================================================================= |
719 | //======================================================================= |
720 | // Category : Computation - Domains |
721 | //======================================================================= |
722 | //======================================================================= |
723 | |
724 | //======================================================================= |
725 | // Function : GlobalTransition |
726 | // Purpose : Returns the before and after states of the complex |
727 | // transition of the IndP-th intersection point of the |
728 | // IndH-th hatching. |
729 | //======================================================================= |
730 | |
731 | Standard_Boolean HatchGen_Hatcher::GlobalTransition (HatchGen_PointOnHatching& Point) |
732 | { |
733 | TopAbs_State StateBefore = TopAbs_UNKNOWN ; |
734 | TopAbs_State StateAfter = TopAbs_UNKNOWN ; |
735 | Standard_Boolean SegmentBegin = Standard_False ; |
736 | Standard_Boolean SegmentEnd = Standard_False ; |
737 | |
738 | gp_Dir2d Tangente2d, Normale2d ; |
739 | gp_Dir Tangente, Normale ; |
740 | Standard_Real Courbure ; |
741 | |
742 | const TheCurveH& CurveH = HatchingCurve (Point.Index()) ; |
743 | |
a8195d65 |
744 | myIntersector.LocalGeometry(CurveH.Curve(), Point.Parameter(), Tangente2d, Normale2d, Courbure); |
7fd59977 |
745 | |
746 | Tangente.SetCoord (Tangente2d.X(), Tangente2d.Y(), 0.0) ; |
747 | if (Courbure < Precision::Confusion()) { |
748 | Normale.SetCoord (-Tangente2d.Y(), Tangente2d.X(), 0.0) ; |
749 | } else { |
750 | Normale.SetCoord (Normale2d.X(), Normale2d.Y(), 0.0) ; |
751 | } |
752 | |
753 | TopTrans_CurveTransition ComplexTransition ; |
754 | ComplexTransition.Reset (Tangente, Normale, Courbure) ; |
755 | |
756 | #if TRACE_HATCHER |
757 | printf("\n ----- Global Transition Complex Transition Reset \n"); |
758 | printf("\n P:%+10.5g Tg2d:%+10.5g , %+10.5g N2d:%+10.5g , %+10.5g Crv:%+10.5g\n\n", |
a8195d65 |
759 | Point.Parameter(),Tangente.X(),Tangente.Y(),Normale.X(),Normale.Y(),Courbure); |
7fd59977 |
760 | #endif |
a8195d65 |
761 | for (Standard_Integer IPntE = 1 ; IPntE <= Point.NbPoints() ; IPntE++) |
762 | { |
7fd59977 |
763 | const HatchGen_PointOnElement& PntE = Point.Point (IPntE) ; |
764 | |
765 | SegmentBegin = SegmentBegin || PntE.SegmentBeginning() ; |
766 | SegmentEnd = SegmentEnd || PntE.SegmentEnd() ; |
767 | |
768 | const HatchGen_Element& Element = myElements.Find (PntE.Index()) ; |
769 | const TheCurveE& CurveE = Element.Curve() ; |
770 | |
771 | TopAbs_Orientation ElementOrientation = Element.Orientation() ; |
772 | Standard_Boolean ToReverse = (ElementOrientation == TopAbs_REVERSED); |
773 | Standard_Real Param ; |
a8195d65 |
774 | switch (PntE.Position()) |
775 | { |
776 | case TopAbs_FORWARD : |
777 | Param = ToReverse ? CurveE.LastParameter() : CurveE.FirstParameter() ; |
778 | break ; |
779 | |
780 | case TopAbs_INTERNAL : |
781 | Param = PntE.Parameter() ; |
782 | break ; |
783 | |
784 | case TopAbs_REVERSED : |
785 | Param = ToReverse ? CurveE.FirstParameter() : CurveE.LastParameter() ; |
786 | break ; |
787 | |
788 | default: |
789 | break; |
7fd59977 |
790 | } |
791 | |
792 | //-- |
793 | #if TRACE_HATCHER |
794 | printf("\n ******** ToReverse: %d Param : %g ANParam : %g \n",ToReverse,Param,PntE.Parameter()); |
795 | #endif |
796 | Param = PntE.Parameter(); |
797 | |
a8195d65 |
798 | myIntersector.LocalGeometry(CurveE.Curve(), Param, Tangente2d, Normale2d, Courbure); |
7fd59977 |
799 | |
7fd59977 |
800 | //----------------------------------------------------------------------- |
801 | // Calcul de la transition locale. On suppose les relations suivantes : |
802 | // - Si l orientation de l element est INTERNAL ==> INTERNAL |
803 | // - Si l orientation de l element est EXTERNAL ==> EXTERNAL |
804 | // - Si tangence, on a IN-IN ou OUT-OUT ==> INTERNAL/EXTERNAL |
805 | // - Sinon, on a IN-OUT ou OUT-IN ==> REVERSED/FORWARD |
806 | // Les deux dernieres conditions avec l element vu en FORWARD. |
807 | //----------------------------------------------------------------------- |
7fd59977 |
808 | TopAbs_Orientation LocalTransition = TopAbs_EXTERNAL; |
a8195d65 |
809 | |
810 | if (ElementOrientation == TopAbs_INTERNAL) |
7fd59977 |
811 | LocalTransition = TopAbs_INTERNAL ; |
a8195d65 |
812 | |
813 | else if (ElementOrientation == TopAbs_EXTERNAL) |
7fd59977 |
814 | LocalTransition = TopAbs_EXTERNAL ; |
a8195d65 |
815 | |
816 | else if (PntE.IntersectionType() == HatchGen_TANGENT) |
817 | { |
818 | if (PntE.Position() == TopAbs_INTERNAL) |
819 | { |
820 | switch (PntE.StateBefore()) |
821 | { |
822 | case TopAbs_IN : LocalTransition = ToReverse ? TopAbs_EXTERNAL : TopAbs_INTERNAL ; break ; |
823 | case TopAbs_OUT : LocalTransition = ToReverse ? TopAbs_INTERNAL : TopAbs_EXTERNAL ; break ; |
824 | default: break; |
825 | } |
826 | } |
827 | else |
828 | { |
829 | switch (PntE.StateBefore()) |
830 | { |
831 | case TopAbs_IN : LocalTransition = ToReverse ? TopAbs_FORWARD : TopAbs_REVERSED ; break ; |
832 | case TopAbs_OUT : LocalTransition = ToReverse ? TopAbs_REVERSED : TopAbs_FORWARD ; break ; |
833 | default: break; |
834 | } |
7fd59977 |
835 | } |
a8195d65 |
836 | } |
837 | else |
838 | { |
839 | switch (PntE.StateBefore()) |
840 | { |
841 | case TopAbs_IN : LocalTransition = ToReverse ? TopAbs_FORWARD : TopAbs_REVERSED ; break ; |
842 | case TopAbs_OUT : LocalTransition = ToReverse ? TopAbs_REVERSED : TopAbs_FORWARD ; break ; |
843 | default: break; |
7fd59977 |
844 | } |
845 | } |
7fd59977 |
846 | |
847 | //----------------------------------------------------------------------- |
848 | // Orientation de la tangente au point d interference. |
849 | //----------------------------------------------------------------------- |
7fd59977 |
850 | TopAbs_Orientation TangenteOrientation = TopAbs_FORWARD; |
a8195d65 |
851 | switch (PntE.Position()) |
852 | { |
853 | case TopAbs_FORWARD : TangenteOrientation = ToReverse ? TopAbs_REVERSED : TopAbs_FORWARD ; break ; |
854 | case TopAbs_INTERNAL : TangenteOrientation = TopAbs_INTERNAL ; break ; |
855 | case TopAbs_REVERSED : TangenteOrientation = ToReverse ? TopAbs_FORWARD : TopAbs_REVERSED ; break ; |
856 | |
857 | default: |
858 | break; |
7fd59977 |
859 | } |
860 | |
861 | //----------------------------------------------------------------------- |
862 | // Proprietes geometriques. |
863 | //----------------------------------------------------------------------- |
864 | |
865 | if (ToReverse) { |
866 | Tangente.SetCoord (-Tangente2d.X(), -Tangente2d.Y(), 0.0) ; |
867 | } else { |
868 | Tangente.SetCoord ( Tangente2d.X(), Tangente2d.Y(), 0.0) ; |
869 | } |
870 | Normale.SetCoord ( Normale2d.X(), Normale2d.Y(), 0.0) ; |
a8195d65 |
871 | |
7fd59977 |
872 | #if TRACE_HATCHER |
873 | printf("\n \n----- Global Transition Complex Transition Compare" ); |
874 | char *str1 = " ??? "; |
875 | char *str2 = " ??? "; |
a8195d65 |
876 | if(LocalTransition == TopAbs_INTERNAL) str1=" INTERNAL "; |
877 | if(LocalTransition == TopAbs_REVERSED) str1=" REVERSED "; |
878 | if(LocalTransition == TopAbs_FORWARD) str1=" FORWARD "; |
7fd59977 |
879 | |
a8195d65 |
880 | if(TangenteOrientation == TopAbs_INTERNAL) str2=" INTERNAL "; |
881 | if(TangenteOrientation == TopAbs_REVERSED) str2=" REVERSED "; |
882 | if(TangenteOrientation == TopAbs_FORWARD) str2=" FORWARD "; |
7fd59977 |
883 | |
884 | printf("\n P:%+10.5g Tg2d:%+10.5g , %+10.5g N2d:%+10.5g , %+10.5g Crv:%+10.5g LocalTr:%s TangOrie:%s\n", |
a8195d65 |
885 | Param,Tangente.X(),Tangente.Y(),Normale.X(),Normale.Y(),Courbure,str1,str2); |
7fd59977 |
886 | #endif |
887 | |
7fd59977 |
888 | ComplexTransition.Compare (Precision::Angular(), |
a8195d65 |
889 | Tangente, Normale, Courbure, |
890 | LocalTransition, TangenteOrientation) ; |
7fd59977 |
891 | } |
892 | |
893 | switch (ComplexTransition.StateBefore()) { |
894 | case TopAbs_IN : StateBefore = TopAbs_IN ; break ; |
895 | case TopAbs_OUT : StateBefore = TopAbs_OUT ; break ; |
896 | case TopAbs_ON : return Standard_False ; |
897 | case TopAbs_UNKNOWN : return Standard_False ; |
898 | } |
899 | switch (ComplexTransition.StateAfter()) { |
900 | case TopAbs_IN : StateAfter = TopAbs_IN ; break ; |
901 | case TopAbs_OUT : StateAfter = TopAbs_OUT ; break ; |
902 | case TopAbs_ON : return Standard_False ; |
903 | case TopAbs_UNKNOWN : return Standard_False ; |
904 | } |
905 | |
906 | |
907 | #if TRACE_HATCHER |
908 | printf("\n"); |
909 | printf("\n --> StateBef :"); if(StateBefore==TopAbs_IN) printf(" IN "); else printf(" OUT "); |
910 | printf("\n --> StateAft :"); if(StateAfter==TopAbs_IN) printf(" IN "); else printf(" OUT "); |
911 | printf("\n------ Fin GlobalTransition\n"); |
912 | #endif |
913 | |
914 | Point.SetStateBefore (StateBefore) ; |
915 | Point.SetStateAfter (StateAfter) ; |
916 | Point.SetSegmentBeginning (SegmentBegin) ; |
917 | Point.SetSegmentEnd (SegmentEnd) ; |
918 | return Standard_True ; |
919 | } |
920 | |
921 | //======================================================================= |
922 | // Function : ComputeDomains |
923 | // Purpose : Computes the domains of all the hatchings. |
924 | //======================================================================= |
925 | |
926 | void HatchGen_Hatcher::ComputeDomains () |
927 | { |
928 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) |
929 | if (myHatchings.IsBound (IndH)) ComputeDomains (IndH) ; |
930 | } |
931 | |
932 | //======================================================================= |
933 | // Function : ComputeDomains |
934 | // Purpose : Computes the domains of the IndH-th hatching. |
935 | //======================================================================= |
936 | |
937 | void HatchGen_Hatcher::ComputeDomains (const Standard_Integer IndH) |
938 | { |
939 | #if RAISE_IF_NOSUCHOBJECT |
940 | Standard_NoSuchObject_Raise_if (!myHatchings.IsBound (IndH), "") ; |
941 | #endif |
942 | |
943 | HatchGen_Hatching& Hatching = myHatchings.ChangeFind (IndH) ; |
944 | Hatching.ClrDomains() ; |
945 | |
946 | Hatching.IsDone (Standard_False) ; |
947 | |
948 | if (!Hatching.TrimDone()) Trim (IndH) ; |
949 | if (Hatching.Status() != HatchGen_NoProblem) return ; |
950 | |
951 | Standard_Boolean Points = myKeepPoints ; |
952 | Standard_Boolean Segments = myKeepSegments ; |
953 | Standard_Integer ISav = 0 ; |
954 | Standard_Boolean SavPnt = Standard_False ; |
955 | Standard_Integer NbOpenedSegments = 0 ; |
956 | Standard_Integer NbPnt = Hatching.NbPoints() ; |
957 | Standard_Integer IPnt =1; |
958 | |
959 | if (NbPnt == 0) { |
960 | //-- cout << "The hatching # " << setw(3) << IndH << " has to be classified" << endl ; |
961 | HatchGen_Classifier Classifier(myElements,Hatching.ClassificationPoint(),0.0000001); |
962 | if(Classifier.State() == TopAbs_IN) { |
963 | HatchGen_Domain domain ; |
964 | Hatching.AddDomain (domain) ; |
965 | } |
966 | Hatching.IsDone (Standard_True) ; |
967 | return ; |
968 | } |
969 | |
970 | //for (Standard_Integer IPnt = 1 ; IPnt <= NbPnt ; IPnt++) { |
971 | for (IPnt = 1 ; IPnt <= NbPnt ; IPnt++) { |
972 | Standard_Boolean NoDomain = Hatching.NbDomains() == 0 ; |
973 | Standard_Boolean FirstPoint = IPnt == 1 ; |
974 | Standard_Boolean LastPoint = IPnt == NbPnt ; |
975 | |
976 | const HatchGen_PointOnHatching& CurPnt = Hatching.Point (IPnt) ; |
977 | |
978 | #if TRACE_HATCHER |
979 | cout << "===== ComputeDomains:: Hatching # " << setw(3) << IndH << " =====" << endl ; |
980 | CurPnt.Dump (IPnt) ; |
981 | cout << "==========================================" << endl ; |
982 | #endif |
983 | |
984 | |
985 | //----------------------------------------------------------------------- |
986 | // Calcul des domaines. |
987 | //----------------------------------------------------------------------- |
988 | |
989 | TopAbs_State StateBefore = CurPnt.StateBefore() ; |
990 | TopAbs_State StateAfter = CurPnt.StateAfter() ; |
991 | Standard_Boolean SegmentBegin = CurPnt.SegmentBeginning() ; |
992 | Standard_Boolean SegmentEnd = CurPnt.SegmentEnd() ; |
993 | |
994 | HatchGen_Domain domain ; |
995 | |
996 | //----------------------------------------------------------------------- |
997 | // Initialisations dues au premier point. |
998 | //----------------------------------------------------------------------- |
999 | |
1000 | if (FirstPoint) { |
1001 | SavPnt = Standard_False ; |
1002 | ISav = 0 ; |
1003 | NbOpenedSegments = 0 ; |
1004 | if (SegmentEnd && SegmentBegin) { |
1005 | if (StateAfter == TopAbs_UNKNOWN) StateAfter = TopAbs_IN ; |
1006 | if (StateBefore == TopAbs_UNKNOWN) StateBefore = TopAbs_IN ; |
1007 | if (Segments) { |
1008 | SavPnt = Standard_True ; |
1009 | ISav = 0 ; |
1010 | } |
1011 | } else if (SegmentEnd) { |
1012 | if (StateAfter == TopAbs_UNKNOWN) StateAfter = TopAbs_IN ; |
1013 | if (Segments) { |
1014 | SavPnt = Standard_True ; |
1015 | ISav = 0 ; |
1016 | } |
1017 | } else if (SegmentBegin) { |
1018 | if (StateBefore == TopAbs_UNKNOWN) StateBefore = TopAbs_IN ; |
1019 | if (StateBefore == TopAbs_IN) { |
1020 | SavPnt = Standard_True ; |
1021 | ISav = 0 ; |
1022 | } |
1023 | } else { |
1024 | if (StateBefore == TopAbs_IN) { |
1025 | SavPnt = Standard_True ; |
1026 | ISav = 0 ; |
1027 | } |
1028 | } |
1029 | } |
1030 | |
1031 | //----------------------------------------------------------------------- |
1032 | // Initialisations dues au dernier point. |
1033 | //----------------------------------------------------------------------- |
1034 | |
1035 | if (LastPoint) { |
1036 | if (SegmentEnd && SegmentBegin) { |
1037 | if (StateAfter == TopAbs_UNKNOWN) StateAfter = TopAbs_IN ; |
1038 | if (StateBefore == TopAbs_UNKNOWN) StateBefore = TopAbs_IN ; |
1039 | } else if (SegmentEnd) { |
1040 | if (StateAfter == TopAbs_UNKNOWN) StateAfter = TopAbs_IN ; |
1041 | } else if (SegmentBegin) { |
1042 | if (StateBefore == TopAbs_UNKNOWN) StateBefore = TopAbs_IN ; |
1043 | } else { |
1044 | } |
1045 | } |
1046 | |
1047 | //----------------------------------------------------------------------- |
1048 | // Cas general. |
1049 | //----------------------------------------------------------------------- |
1050 | |
1051 | Standard_Boolean ToAppend = Standard_False ; |
1052 | |
1053 | if (SegmentEnd && SegmentBegin) { |
1054 | |
1055 | if (StateBefore != TopAbs_IN && StateAfter != TopAbs_IN) { |
1056 | Hatching.Status (HatchGen_IncompatibleStates) ; |
1057 | return ; |
1058 | } |
1059 | if (Points) { |
1060 | if (Segments) { |
1061 | if (!SavPnt) { |
1062 | if(NoDomain) { |
1063 | Hatching.Status (HatchGen_IncoherentParity) ; |
1064 | } |
1065 | else { |
1066 | Hatching.IsDone(Standard_True); |
1067 | } |
1068 | return ; |
1069 | } |
1070 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1071 | domain.SetSecondPoint (CurPnt) ; |
1072 | ToAppend = Standard_True ; |
1073 | SavPnt = Standard_True ; |
1074 | ISav = IPnt ; |
1075 | } else { |
1076 | Standard_Boolean isININ = (StateBefore == TopAbs_IN && StateAfter == TopAbs_IN); |
1077 | if (SavPnt && !isININ) { |
1078 | if(NoDomain) { |
1079 | Hatching.Status (HatchGen_IncoherentParity) ; |
1080 | } |
1081 | else { |
1082 | Hatching.IsDone(Standard_True); |
1083 | } |
1084 | return ; |
1085 | } |
1086 | domain.SetPoints (CurPnt, CurPnt) ; |
1087 | ToAppend = Standard_True ; |
1088 | SavPnt = Standard_False ; |
1089 | ISav = 0 ; |
1090 | } |
1091 | } |
1092 | |
1093 | } else if (SegmentEnd) { |
1094 | |
1095 | if (Segments) { |
1096 | if (StateAfter == TopAbs_OUT) { |
1097 | if (!SavPnt) { |
1098 | if(NoDomain) { |
1099 | Hatching.Status (HatchGen_IncoherentParity) ; |
1100 | } |
1101 | else { |
1102 | Hatching.IsDone(Standard_True); |
1103 | } |
1104 | return ; |
1105 | } |
1106 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1107 | domain.SetSecondPoint (CurPnt) ; |
1108 | ToAppend = Standard_True ; |
1109 | } else { |
1110 | if (Points) { |
1111 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1112 | domain.SetSecondPoint (CurPnt) ; |
1113 | ToAppend = Standard_True ; |
1114 | SavPnt = Standard_True ; |
1115 | ISav = IPnt ; |
1116 | } |
1117 | } |
1118 | } else { |
1119 | if (StateAfter == TopAbs_IN) { |
1120 | SavPnt = Standard_True ; |
1121 | ISav = IPnt ; |
1122 | } |
1123 | } |
1124 | NbOpenedSegments-- ; |
1125 | |
1126 | } else if (SegmentBegin) { |
1127 | |
1128 | if (Segments) { |
1129 | if (StateBefore == TopAbs_OUT) { |
1130 | SavPnt = Standard_True ; |
1131 | ISav = IPnt ; |
1132 | } else { |
1133 | if (Points) { |
1134 | if (!SavPnt) { |
1135 | if(NoDomain) { |
1136 | Hatching.Status (HatchGen_IncoherentParity) ; |
1137 | } |
1138 | else { |
1139 | Hatching.IsDone(Standard_True); |
1140 | } |
1141 | |
1142 | return ; |
1143 | } |
1144 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1145 | domain.SetSecondPoint (CurPnt) ; |
1146 | ToAppend = Standard_True ; |
1147 | SavPnt = Standard_True ; |
1148 | ISav = IPnt ; |
1149 | } |
1150 | } |
1151 | } else { |
1152 | if (StateBefore == TopAbs_IN) { |
1153 | if (!SavPnt) { |
1154 | if(NoDomain) { |
1155 | Hatching.Status (HatchGen_IncoherentParity) ; |
1156 | } |
1157 | else { |
1158 | Hatching.IsDone(Standard_True); |
1159 | } |
1160 | |
1161 | return ; |
1162 | } |
1163 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1164 | domain.SetSecondPoint (CurPnt) ; |
1165 | ToAppend = Standard_True ; |
1166 | // Modified by Sergey KHROMOV - Fri Jan 5 12:05:30 2001 |
1167 | // SavPnt = Standard_False ; |
1168 | // ISav = 0 ; |
1169 | SavPnt = Standard_True ; |
1170 | ISav = IPnt ; |
1171 | // Modified by Sergey KHROMOV - Fri Jan 5 12:05:31 2001 |
1172 | } |
1173 | } |
1174 | NbOpenedSegments++ ; |
1175 | |
1176 | } else { |
1177 | //-- ??????????????????????????????????????????????????????????????????????????? |
1178 | //-- Solution provisoire (lbr le 11 Aout 97 ) |
1179 | //-- si On a 2 points dont des points OUT OUT ou IN IN qui delimitent une isos |
1180 | //-- on transforme les transitions |
1181 | if (StateBefore == TopAbs_OUT && StateAfter == TopAbs_OUT) { |
1182 | if(NbPnt == 2) { |
1183 | if(FirstPoint) |
1184 | StateAfter = TopAbs_IN; |
1185 | else |
1186 | StateBefore = TopAbs_IN; |
1187 | } |
1188 | } |
1189 | //-- ??????????????????????????????????????????????????????????????????????????? |
1190 | if (StateBefore == TopAbs_OUT && StateAfter == TopAbs_OUT) { |
1191 | |
1192 | if (SavPnt) { |
1193 | if(NoDomain) { |
1194 | Hatching.Status (HatchGen_IncoherentParity) ; |
1195 | } |
1196 | else { |
1197 | Hatching.IsDone(Standard_True); |
1198 | } |
1199 | |
1200 | return ; |
1201 | } |
1202 | if (Points) { |
1203 | domain.SetPoints (CurPnt, CurPnt) ; |
1204 | ToAppend = Standard_True ; |
1205 | SavPnt = Standard_True ; |
1206 | ISav = IPnt ; |
1207 | } |
1208 | |
1209 | } else if (StateBefore == TopAbs_OUT && StateAfter == TopAbs_IN ) { |
1210 | |
1211 | SavPnt = Standard_True ; |
1212 | ISav = IPnt ; |
1213 | |
1214 | } else if (StateBefore == TopAbs_IN && StateAfter == TopAbs_OUT) { |
1215 | |
1216 | if (!SavPnt) { |
1217 | if(NoDomain) { |
1218 | Hatching.Status (HatchGen_IncoherentParity) ; |
1219 | } |
1220 | else { |
1221 | Hatching.IsDone(Standard_True); |
1222 | } |
1223 | |
1224 | return ; |
1225 | } |
1226 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1227 | domain.SetSecondPoint (CurPnt) ; |
1228 | ToAppend = Standard_True ; |
1229 | SavPnt = Standard_False ; |
1230 | ISav = 0 ; |
1231 | |
1232 | } else if (StateBefore == TopAbs_IN && StateAfter == TopAbs_IN ) { |
1233 | |
1234 | if (Points) { |
1235 | if (NbOpenedSegments == 0) { |
1236 | if (!SavPnt) { |
1237 | if(NoDomain) { |
1238 | Hatching.Status (HatchGen_IncoherentParity) ; |
1239 | } |
1240 | else { |
1241 | Hatching.IsDone(Standard_True); |
1242 | } |
1243 | |
1244 | return ; |
1245 | } |
1246 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1247 | domain.SetSecondPoint (CurPnt) ; |
1248 | ToAppend = Standard_True ; |
1249 | SavPnt = Standard_True ; |
1250 | ISav = IPnt ; |
1251 | } else { |
1252 | if (Segments) { |
1253 | if (!SavPnt) { |
1254 | if(NoDomain) { |
1255 | Hatching.Status (HatchGen_IncoherentParity) ; |
1256 | } |
1257 | else { |
1258 | Hatching.IsDone(Standard_True); |
1259 | } |
1260 | |
1261 | return ; |
1262 | } |
1263 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1264 | domain.SetSecondPoint (CurPnt) ; |
1265 | ToAppend = Standard_True ; |
1266 | SavPnt = Standard_True ; |
1267 | ISav = IPnt ; |
1268 | } else { |
1269 | if (SavPnt) { |
1270 | if(NoDomain) { |
1271 | Hatching.Status (HatchGen_IncoherentParity) ; |
1272 | } |
1273 | else { |
1274 | Hatching.IsDone(Standard_True); |
1275 | } |
1276 | |
1277 | return ; |
1278 | } |
1279 | domain.SetPoints (CurPnt, CurPnt) ; |
1280 | ToAppend = Standard_True ; |
1281 | SavPnt = Standard_False ; |
1282 | ISav = 0 ; |
1283 | } |
1284 | } |
1285 | } |
1286 | |
1287 | } else { |
1288 | |
1289 | Hatching.Status (HatchGen_IncompatibleStates) ; |
1290 | return ; |
1291 | |
1292 | } |
1293 | |
1294 | } |
1295 | |
1296 | //----------------------------------------------------------------------- |
1297 | // Ajout du domaine. |
1298 | //----------------------------------------------------------------------- |
1299 | |
1300 | if (ToAppend) Hatching.AddDomain (domain) ; |
1301 | |
1302 | //----------------------------------------------------------------------- |
1303 | // Traitement lie au dernier point. |
1304 | //----------------------------------------------------------------------- |
1305 | |
1306 | if (LastPoint) { |
1307 | |
1308 | domain.SetPoints () ; |
1309 | ToAppend = Standard_False ; |
1310 | |
1311 | if (SegmentEnd && SegmentBegin) { |
1312 | |
1313 | if (Segments) { |
1314 | if (!SavPnt) { |
1315 | if(NoDomain) { |
1316 | Hatching.Status (HatchGen_IncoherentParity) ; |
1317 | } |
1318 | else { |
1319 | Hatching.IsDone(Standard_True); |
1320 | } |
1321 | |
1322 | return ; |
1323 | } |
1324 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1325 | ToAppend = Standard_True ; |
1326 | } |
1327 | |
1328 | } else if (SegmentEnd) { |
1329 | |
1330 | if (StateAfter == TopAbs_IN) { |
1331 | if (!SavPnt) { |
1332 | if(NoDomain) { |
1333 | Hatching.Status (HatchGen_IncoherentParity) ; |
1334 | } |
1335 | else { |
1336 | Hatching.IsDone(Standard_True); |
1337 | } |
1338 | |
1339 | return ; |
1340 | } |
1341 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1342 | ToAppend = Standard_True ; |
1343 | } |
1344 | |
1345 | } else if (SegmentBegin) { |
1346 | |
1347 | if (Segments) { |
1348 | if (!SavPnt) { |
1349 | if(NoDomain) { |
1350 | Hatching.Status (HatchGen_IncoherentParity) ; |
1351 | } |
1352 | else { |
1353 | Hatching.IsDone(Standard_True); |
1354 | } |
1355 | |
1356 | return ; |
1357 | } |
1358 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1359 | ToAppend = Standard_True ; |
1360 | } |
1361 | |
1362 | } else { |
1363 | |
1364 | if (StateAfter == TopAbs_IN) { |
1365 | if (!SavPnt) { |
1366 | if(NoDomain) { |
1367 | Hatching.Status (HatchGen_IncoherentParity) ; |
1368 | } |
1369 | else { |
1370 | Hatching.IsDone(Standard_True); |
1371 | } |
1372 | |
1373 | return ; |
1374 | } |
1375 | if (ISav != 0) domain.SetFirstPoint (Hatching.Point(ISav)) ; |
1376 | ToAppend = Standard_True ; |
1377 | } |
1378 | |
1379 | } |
1380 | if (ToAppend) Hatching.AddDomain (domain) ; |
1381 | } |
1382 | |
1383 | } |
1384 | Hatching.IsDone(Standard_True) ; |
1385 | } |
1386 | |
1387 | //======================================================================= |
1388 | //======================================================================= |
1389 | // Category : Results. |
1390 | //======================================================================= |
1391 | //======================================================================= |
1392 | |
1393 | |
1394 | //======================================================================= |
1395 | // Function : Domain |
1396 | // Purpose : Returns the IDom-th domain of the IndH-th hatching. |
1397 | //======================================================================= |
1398 | |
1399 | const HatchGen_Domain& HatchGen_Hatcher::Domain (const Standard_Integer IndH, |
1400 | const Standard_Integer IDom) const |
1401 | { |
1402 | #if RAISE_IF_NOSUCHOBJECT |
1403 | Standard_NoSuchObject_Raise_if (!myHatchings.IsBound (IndH), "") ; |
1404 | #endif |
1405 | const HatchGen_Hatching& Hatching = myHatchings.Find (IndH) ; |
1406 | StdFail_NotDone_Raise_if (!Hatching.IsDone(), "HatchGen_Hatcher::Domain") ; |
1407 | #if RAISE_IF_NOSUCHOBJECT |
1408 | Standard_OutOfRange_Raise_if (IDom < 1 || IDom > Hatching.NbDomains(), "") ; |
1409 | #endif |
1410 | const HatchGen_Domain& Domain = Hatching.Domain (IDom) ; |
1411 | return Domain ; |
1412 | } |
1413 | |
1414 | //======================================================================= |
1415 | //======================================================================= |
1416 | // Category : Dump. |
1417 | //======================================================================= |
1418 | //======================================================================= |
1419 | |
1420 | //======================================================================= |
1421 | // Function : Dump |
1422 | // Purpose : Dumps the hatcher. |
1423 | //======================================================================= |
1424 | |
1425 | void HatchGen_Hatcher::Dump () const |
1426 | { |
1427 | cout << endl ; |
1428 | cout << "========================================================" << endl ; |
1429 | cout << "=== Dump of the hatcher ================================" << endl ; |
1430 | cout << "========================================================" << endl ; |
1431 | cout << endl ; |
1432 | |
1433 | cout << "The points are " |
1434 | << (myKeepPoints ? " " : "not ") |
1435 | << "considered." |
1436 | << endl ; |
1437 | cout << "The segments are " |
1438 | << (myKeepSegments ? " " : "not ") |
1439 | << "considered." |
1440 | << endl ; |
1441 | cout << "2D Confusion tolerance : " << myConfusion2d << endl ; |
1442 | cout << "3D Confusion tolerance : " << myConfusion3d << endl ; |
1443 | |
1444 | cout << myNbHatchings |
1445 | << " hatching" |
1446 | << ((myNbHatchings == 1) ? "" : "s") |
1447 | << endl ; |
1448 | cout << myNbElements |
1449 | << " element" |
1450 | << ((myNbElements == 1) ? "" : "s") |
1451 | << endl ; |
1452 | |
1453 | cout << endl ; |
1454 | cout << "========================================================" << endl ; |
1455 | cout << "=== Hatchings ==========================================" << endl ; |
1456 | cout << "========================================================" << endl ; |
1457 | cout << endl ; |
1458 | |
1459 | for (Standard_Integer IndH = 1 ; IndH <= myNbHatchings ; IndH++) { |
1460 | cout << "Hatching # " << IndH ; |
1461 | if (!myHatchings.IsBound (IndH)) { |
1462 | cout << " is not bound" << endl ; |
1463 | } else { |
1464 | const HatchGen_Hatching& Hatching = myHatchings.Find (IndH) ; |
1465 | Standard_Integer NbPnt = Hatching.NbPoints() ; |
1466 | cout << " contains " << NbPnt << " restriction points :" << endl ; |
1467 | for (Standard_Integer IPnt = 1 ; IPnt <= NbPnt ; IPnt++) { |
1468 | const HatchGen_PointOnHatching& PntH = Hatching.Point (IPnt) ; |
1469 | PntH.Dump (IPnt) ; |
1470 | } |
1471 | cout << "----------------------------------------------" << endl ; |
1472 | } |
1473 | } |
1474 | |
1475 | cout << endl ; |
1476 | cout << "========================================================" << endl ; |
1477 | cout << "=== Elements ===========================================" << endl ; |
1478 | cout << "========================================================" << endl ; |
1479 | cout << endl ; |
1480 | |
1481 | for (Standard_Integer IndE = 1 ; IndE <= myNbElements ; IndE++) { |
1482 | cout << "Element # " << IndE ; |
1483 | if (!myElements.IsBound (IndE)) { |
1484 | cout << " is not bound" << endl ; |
1485 | } else { |
1486 | const HatchGen_Element& Element = myElements.Find (IndE) ; |
1487 | switch (Element.Orientation()) { |
1488 | case TopAbs_FORWARD : cout << " is FORWARD" << endl ; break ; |
1489 | case TopAbs_REVERSED : cout << " is REVERSED" << endl ; break ; |
1490 | case TopAbs_INTERNAL : cout << " is INTERNAL" << endl ; break ; |
1491 | case TopAbs_EXTERNAL : cout << " is EXTERNAL" << endl ; break ; |
1492 | } |
1493 | } |
1494 | } |
1495 | |
1496 | cout << endl ; |
1497 | } |