0031682: Visualization - Prs3d_ShadingAspect::SetTransparency() has no effect with...
[occt.git] / src / HLRBRep / HLRBRep_PolyAlgo.cxx
1 // Created on: 1995-05-05
2 // Created by: Christophe MARION
3 // Copyright (c) 1995-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
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
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.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 // Modified by cma, Tue Apr  1 11:39:48 1997
18 // Modified by cma, Tue Apr  1 11:40:30 1997
19
20 #include <BRep_Builder.hxx>
21 #include <BRep_Tool.hxx>
22 #include <BRepLib_MakeEdge.hxx>
23 #include <CSLib.hxx>
24 #include <CSLib_DerivativeStatus.hxx>
25 #include <CSLib_NormalStatus.hxx>
26 #include <Geom_RectangularTrimmedSurface.hxx>
27 #include <Geom_Surface.hxx>
28 #include <gp.hxx>
29 #include <HLRAlgo_BiPoint.hxx>
30 #include <HLRAlgo_EdgeStatus.hxx>
31 #include <HLRAlgo_ListIteratorOfListOfBPoint.hxx>
32 #include <HLRAlgo_PolyAlgo.hxx>
33 #include <HLRAlgo_PolyData.hxx>
34 #include <HLRAlgo_PolyInternalData.hxx>
35 #include <HLRAlgo_PolyMask.hxx>
36 #include <HLRAlgo_PolyShellData.hxx>
37 #include <HLRAlgo_Projector.hxx>
38 #include <HLRBRep_PolyAlgo.hxx>
39 #include <Poly_Polygon3D.hxx>
40 #include <Poly_PolygonOnTriangulation.hxx>
41 #include <Poly_Triangulation.hxx>
42 #include <Precision.hxx>
43 #include <Standard_ErrorHandler.hxx>
44 #include <Standard_OutOfRange.hxx>
45 #include <Standard_Stream.hxx>
46 #include <Standard_Type.hxx>
47 #include <TColStd_HArray1OfInteger.hxx>
48 #include <TColStd_HArray1OfTransient.hxx>
49 #include <TopExp.hxx>
50 #include <TopExp_Explorer.hxx>
51 #include <TopoDS.hxx>
52 #include <TopoDS_Edge.hxx>
53 #include <TopoDS_Shape.hxx>
54 #include <TopTools_Array1OfShape.hxx>
55 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
56 #include <TopTools_ListIteratorOfListOfShape.hxx>
57
58 IMPLEMENT_STANDARD_RTTIEXT(HLRBRep_PolyAlgo,Standard_Transient)
59
60 enum
61 {
62   NMsk_Vert =  1,
63   NMsk_OutL =  2,
64   NMsk_Norm =  4,
65   NMsk_Fuck =  8,
66   NMsk_Edge = 16,
67   NMsk_Move = 32
68 };
69
70 #ifdef OCCT_DEBUG
71 static Standard_Integer DoTrace = Standard_False; 
72 static Standard_Integer DoError = Standard_False; 
73 #endif
74 //=======================================================================
75 //function : HLRBRep_PolyAlgo
76 //purpose  : 
77 //=======================================================================
78
79 HLRBRep_PolyAlgo::HLRBRep_PolyAlgo () :
80 myDebug     (Standard_False),
81 myTolSta    (0.1),
82 myTolEnd    (0.9),
83 myTolAngular(0.001)
84 {
85   myAlgo = new HLRAlgo_PolyAlgo();
86 }
87
88 //=======================================================================
89 //function : HLRBRep_PolyAlgo
90 //purpose  : 
91 //=======================================================================
92
93 HLRBRep_PolyAlgo::HLRBRep_PolyAlgo (const Handle(HLRBRep_PolyAlgo)& A)
94 {
95   myDebug      = A->Debug();
96   myTolAngular = A->TolAngular();
97   myTolSta     = A->TolCoef();
98   myTolEnd     = 1 - myTolSta;
99   myAlgo       = A->Algo();
100   myProj       = A->Projector();
101
102   Standard_Integer n = A->NbShapes();
103
104   for (Standard_Integer i = 1; i <= n; i++)
105     Load(A->Shape(i));
106 }
107
108 //=======================================================================
109 //function : HLRBRep_PolyAlgo
110 //purpose  : 
111 //=======================================================================
112
113 HLRBRep_PolyAlgo::HLRBRep_PolyAlgo (const TopoDS_Shape& S) :
114 myDebug     (Standard_False),
115 myTolSta    (0.1),
116 myTolEnd    (0.9),
117 myTolAngular(0.001)
118 {
119   myShapes.Append(S);
120   myAlgo = new HLRAlgo_PolyAlgo();
121 }
122
123 //=======================================================================
124 //function : Shape
125 //purpose  : 
126 //=======================================================================
127
128 TopoDS_Shape & HLRBRep_PolyAlgo::Shape (const Standard_Integer I)
129 {
130   Standard_OutOfRange_Raise_if (I == 0 || I > myShapes.Length(),
131                                "HLRBRep_PolyAlgo::Shape : unknown Shape");
132   return myShapes(I);
133 }
134
135 //=======================================================================
136 //function : Remove
137 //purpose  : 
138 //=======================================================================
139
140 void HLRBRep_PolyAlgo::Remove (const Standard_Integer I)
141 {
142   Standard_OutOfRange_Raise_if (I == 0 || I > myShapes.Length(),
143                                 "HLRBRep_PolyAlgo::Remove : unknown Shape");
144   myShapes.Remove(I);
145   myAlgo->Clear();
146   myEMap.Clear();
147   myFMap.Clear();
148 }
149
150 //=======================================================================
151 //function : Index
152 //purpose  : 
153 //=======================================================================
154
155 Standard_Integer HLRBRep_PolyAlgo::Index (const TopoDS_Shape& S) const
156 {
157   Standard_Integer n = myShapes.Length();
158
159   for (Standard_Integer i = 1; i <= n; i++)
160     if (myShapes(i) == S) return i;
161
162   return 0;
163 }
164
165 //=======================================================================
166 //function : Algo
167 //purpose  : 
168 //=======================================================================
169
170 Handle(HLRAlgo_PolyAlgo) HLRBRep_PolyAlgo::Algo () const
171 {
172   return myAlgo;
173 }
174
175 //=======================================================================
176 //function : Update
177 //purpose  : 
178 //=======================================================================
179
180 void HLRBRep_PolyAlgo::Update ()
181 {
182   myAlgo->Clear();
183   myEMap.Clear();
184   myFMap.Clear();
185   TopoDS_Shape Shape = MakeShape();
186
187   if (!Shape.IsNull()) {
188     TopExp_Explorer exshell;
189     Standard_Boolean IsoledF,IsoledE;//,closed;
190     TopLoc_Location L;
191     TopTools_MapOfShape ShapeMap1,ShapeMap2;
192     TopExp::MapShapes(Shape,TopAbs_EDGE,myEMap);
193     TopExp::MapShapes(Shape,TopAbs_FACE,myFMap);
194     Standard_Integer nbEdge = myEMap.Extent();
195     Standard_Integer nbFace = myFMap.Extent();
196     TColStd_Array1OfInteger   ES (0,nbEdge); // index of the Shell
197     TColStd_Array1OfTransient PD (0,nbFace); // HLRAlgo_PolyData
198     TColStd_Array1OfTransient PID(0,nbFace); // PolyInternalData
199     Standard_Integer nbShell = InitShape(Shape,IsoledF,IsoledE);
200     if (nbShell > 0) {
201       TColStd_Array1OfTransient& Shell = myAlgo->PolyShell();
202       Standard_Integer iShell = 0;
203       
204       for (exshell.Init(Shape, TopAbs_SHELL);
205            exshell.More(); 
206            exshell.Next())
207         StoreShell(exshell.Current(),iShell,Shell,
208                    Standard_False,Standard_False,
209                    ES,PD,PID,ShapeMap1,ShapeMap2);
210       if (IsoledF)
211         StoreShell(Shape,iShell,Shell,IsoledF,Standard_False,
212                    ES,PD,PID,ShapeMap1,ShapeMap2);
213       if (IsoledE)
214         StoreShell(Shape,iShell,Shell,Standard_False,IsoledE,
215                    ES,PD,PID,ShapeMap1,ShapeMap2);
216       myAlgo->Update();
217     }
218   }
219 }
220
221 //=======================================================================
222 //function : MakeShape
223 //purpose  : 
224 //=======================================================================
225
226 TopoDS_Shape HLRBRep_PolyAlgo::MakeShape () const
227 {
228   Standard_Integer n = myShapes.Length();
229   Standard_Boolean FirstTime = Standard_True;
230   BRep_Builder B;
231   TopoDS_Shape Shape;
232   
233   for (Standard_Integer i = 1; i <= n; i++) {
234     if (FirstTime) {
235       FirstTime = Standard_False;
236       B.MakeCompound(TopoDS::Compound(Shape));
237     }
238     B.Add(Shape,myShapes(i));
239   }
240   return Shape;
241 }
242   
243 //=======================================================================
244 //function : InitShape
245 //purpose  : 
246 //=======================================================================
247
248 Standard_Integer
249 HLRBRep_PolyAlgo::InitShape (const TopoDS_Shape& Shape,
250                              Standard_Boolean& IsoledF,
251                              Standard_Boolean& IsoledE)
252 {
253   TopTools_MapOfShape ShapeMap0;
254   Standard_Integer nbShell = 0;
255   IsoledF = Standard_False;
256   IsoledE = Standard_False;
257   TopExp_Explorer exshell,exface,exedge;
258   TopLoc_Location L;
259   
260   for (exshell.Init(Shape, TopAbs_SHELL);
261        exshell.More(); 
262        exshell.Next()) {
263     Standard_Boolean withTrian = Standard_False;
264     
265     for (exface.Init(exshell.Current(), TopAbs_FACE);
266          exface.More(); 
267          exface.Next()) {
268       const TopoDS_Face& F = TopoDS::Face(exface.Current());
269       if (!BRep_Tool::Triangulation(F,L).IsNull()) {
270         if (ShapeMap0.Add(F))
271           withTrian = Standard_True;
272       }
273     }
274     if (withTrian) nbShell++;
275   }
276   
277   for (exface.Init(Shape, TopAbs_FACE, TopAbs_SHELL);
278        exface.More() && !IsoledF; 
279        exface.Next()) {
280     const TopoDS_Face& F = TopoDS::Face(exface.Current());
281     if (!BRep_Tool::Triangulation(F,L).IsNull()) {
282       if (ShapeMap0.Add(F))
283         IsoledF = Standard_True;
284     }
285   }
286   if (IsoledF) nbShell++;
287   
288   for (exedge.Init(Shape, TopAbs_EDGE, TopAbs_FACE);
289        exedge.More() && !IsoledE; 
290        exedge.Next())
291     IsoledE = Standard_True;
292   if (IsoledE) nbShell++;
293   if (nbShell > 0)
294     myAlgo->Init(new TColStd_HArray1OfTransient(1,nbShell));
295   return nbShell;
296 }
297
298 //=======================================================================
299 //function : StoreShell
300 //purpose  : 
301 //=======================================================================
302
303 void HLRBRep_PolyAlgo::StoreShell (const TopoDS_Shape& Shape,
304                                    Standard_Integer& iShell,
305                                    TColStd_Array1OfTransient& Shell,
306                                    const Standard_Boolean IsoledF,
307                                    const Standard_Boolean IsoledE,
308                                    TColStd_Array1OfInteger& ES,
309                                    TColStd_Array1OfTransient& PD,
310                                    TColStd_Array1OfTransient& PID,
311                                    TopTools_MapOfShape& ShapeMap1,
312                                    TopTools_MapOfShape& ShapeMap2)
313 {
314   TopLoc_Location L;
315   TopExp_Explorer exface,exedge;
316   Standard_Integer f = 0,i,j;
317   Standard_Integer nbFaceShell = 0;
318   Standard_Boolean reversed;
319   Standard_Boolean closed    = Standard_False;
320   const gp_Trsf& T  = myProj.Transformation();
321   const gp_Trsf& TI = myProj.InvertedTransformation();
322   const gp_XYZ& tloc = T.TranslationPart();
323   TLoc[0] = tloc.X();
324   TLoc[1] = tloc.Y();
325   TLoc[2] = tloc.Z();
326   const gp_Mat& tmat = T.VectorialPart();
327   TMat[0][0] = tmat.Value(1,1);
328   TMat[0][1] = tmat.Value(1,2);
329   TMat[0][2] = tmat.Value(1,3);
330   TMat[1][0] = tmat.Value(2,1);
331   TMat[1][1] = tmat.Value(2,2);
332   TMat[1][2] = tmat.Value(2,3);
333   TMat[2][0] = tmat.Value(3,1);
334   TMat[2][1] = tmat.Value(3,2);
335   TMat[2][2] = tmat.Value(3,3);
336   const gp_XYZ& tilo = TI.TranslationPart();
337   TILo[0] = tilo.X();
338   TILo[1] = tilo.Y();
339   TILo[2] = tilo.Z();
340   const gp_Mat& tima = TI.VectorialPart();
341   TIMa[0][0] = tima.Value(1,1);
342   TIMa[0][1] = tima.Value(1,2);
343   TIMa[0][2] = tima.Value(1,3);
344   TIMa[1][0] = tima.Value(2,1);
345   TIMa[1][1] = tima.Value(2,2);
346   TIMa[1][2] = tima.Value(2,3);
347   TIMa[2][0] = tima.Value(3,1);
348   TIMa[2][1] = tima.Value(3,2);
349   TIMa[2][2] = tima.Value(3,3);
350   if (!IsoledE) {
351     if (!IsoledF) {
352       closed = Shape.Closed();
353       if (!closed) {
354         TopTools_IndexedMapOfShape EM;
355         TopExp::MapShapes(Shape,TopAbs_EDGE,EM);
356         Standard_Integer ie;
357         Standard_Integer nbEdge = EM.Extent ();
358         Standard_Integer *flag = new Standard_Integer[nbEdge + 1];
359
360         for (ie = 1; ie <= nbEdge; ie++)
361           flag[ie] = 0;
362         
363         for (exedge.Init(Shape, TopAbs_EDGE);
364              exedge.More(); 
365              exedge.Next()) {
366           const TopoDS_Edge& E = TopoDS::Edge(exedge.Current());
367           ie = EM.FindIndex(E);
368           TopAbs_Orientation orient = E.Orientation();
369           if (!BRep_Tool::Degenerated(E)) {
370             if      (orient == TopAbs_FORWARD ) flag[ie] += 1;
371             else if (orient == TopAbs_REVERSED) flag[ie] -= 1;
372           }
373         }
374         closed = Standard_True;
375         
376         for (ie = 1; ie <= nbEdge && closed; ie++)
377           closed = (flag[ie] == 0); 
378         delete [] flag;
379         flag = NULL;
380       }
381       
382       exface.Init(Shape, TopAbs_FACE);
383     }
384     else
385       exface.Init(Shape, TopAbs_FACE, TopAbs_SHELL);
386     
387     for (; exface.More(); exface.Next()) {
388       const TopoDS_Face& F = TopoDS::Face(exface.Current());
389       if (!BRep_Tool::Triangulation(F,L).IsNull()) {
390         if (ShapeMap1.Add(F))
391           nbFaceShell++;
392       }
393     }
394   }
395   if (nbFaceShell > 0 || IsoledE) {
396     iShell++;
397     Shell(iShell) = new HLRAlgo_PolyShellData(nbFaceShell);
398   }
399   if (nbFaceShell > 0) {
400     const Handle(HLRAlgo_PolyShellData)& psd =
401       *(Handle(HLRAlgo_PolyShellData)*)&(Shell(iShell));
402     Standard_Integer iFace = 0;
403     if (!IsoledF) exface.Init(Shape, TopAbs_FACE);
404     else          exface.Init(Shape, TopAbs_FACE, TopAbs_SHELL);
405     TopTools_MapOfShape ShapeMapBis;
406     
407     for (; exface.More(); exface.Next()) {
408       const TopoDS_Face& F = TopoDS::Face(exface.Current());  
409       const Handle(Poly_Triangulation)& Tr = BRep_Tool::Triangulation(F,L);
410       if (!Tr.IsNull()) {
411         if (ShapeMap2.Add(F)) {
412           iFace++;
413           f = myFMap.FindIndex(F);
414           reversed = F.Orientation() == TopAbs_REVERSED;
415           gp_Trsf TT = L.Transformation();
416           TT.PreMultiply(T);
417           const gp_XYZ& ttlo = TT.TranslationPart();
418           TTLo[0] = ttlo.X();
419           TTLo[1] = ttlo.Y();
420           TTLo[2] = ttlo.Z();
421           const gp_Mat& ttma = TT.VectorialPart();
422           TTMa[0][0] = ttma.Value(1,1);
423           TTMa[0][1] = ttma.Value(1,2);
424           TTMa[0][2] = ttma.Value(1,3);
425           TTMa[1][0] = ttma.Value(2,1);
426           TTMa[1][1] = ttma.Value(2,2);
427           TTMa[1][2] = ttma.Value(2,3);
428           TTMa[2][0] = ttma.Value(3,1);
429           TTMa[2][1] = ttma.Value(3,2);
430           TTMa[2][2] = ttma.Value(3,3);
431           Poly_Array1OfTriangle & Tri = Tr->ChangeTriangles();
432           TColgp_Array1OfPnt    & Nod = Tr->ChangeNodes();
433           Standard_Integer nbN = Nod.Upper();
434           Standard_Integer nbT = Tri.Upper();
435           PD (f) = new HLRAlgo_PolyData();
436           psd->PolyData().ChangeValue(iFace) = PD(f);
437           PID(f) = new HLRAlgo_PolyInternalData(nbN,nbT);
438           Handle(HLRAlgo_PolyInternalData)& pid = *(Handle(HLRAlgo_PolyInternalData)*)&(PID(f));
439           if (Handle(Geom_Surface) S = BRep_Tool::Surface(F))
440           {
441             if (Handle(Geom_RectangularTrimmedSurface) aRectTrimSurf = Handle(Geom_RectangularTrimmedSurface)::DownCast(S))
442             {
443               S = aRectTrimSurf->BasisSurface();
444             }
445             GeomAdaptor_Surface AS(S);
446             pid->Planar(AS.GetType() == GeomAbs_Plane);
447           }
448           else
449           {
450             pid->Planar (false);
451           }
452           HLRAlgo_Array1OfTData* TData = &pid->TData();
453           HLRAlgo_Array1OfPISeg* PISeg = &pid->PISeg();
454           HLRAlgo_Array1OfPINod* PINod = &pid->PINod();
455           Poly_Triangle       * OT = &(Tri.ChangeValue(1));
456           HLRAlgo_TriangleData* NT = &TData->ChangeValue(1);
457
458           for (i = 1; i <= nbT; i++) {
459             OT->Get(NT->Node1, NT->Node2, NT->Node3);
460             NT->Flags = 0;
461             if (reversed) {
462               j         = NT->Node1;
463               NT->Node1 = NT->Node3;
464               NT->Node3 = j;
465             }
466             OT++;
467             NT++;
468           }
469
470           gp_Pnt                          * ON = &(Nod.ChangeValue(1));
471           Handle(HLRAlgo_PolyInternalNode)* NN = &PINod->ChangeValue(1);
472
473           for (i = 1; i <= nbN; i++) {
474             HLRAlgo_PolyInternalNode::NodeData& Nod1RValues = (*NN)->Data();
475             HLRAlgo_PolyInternalNode::NodeIndices& aNodIndices = (*NN)->Indices();
476             aNodIndices.NdSg = 0;
477             aNodIndices.Flag = 0;
478       Nod1RValues.Point = ON->Coord();
479             TTMultiply(Nod1RValues.Point);
480             ON++;
481             NN++;
482           }
483           pid->UpdateLinks(TData,PISeg,PINod);
484           if (Tr->HasUVNodes()) {
485             myBSurf.Initialize(F,Standard_False);
486             TColgp_Array1OfPnt2d & UVN = Tr->ChangeUVNodes();
487             gp_Pnt2d* OUVN = &(UVN.ChangeValue(1));
488             NN             = &(((HLRAlgo_Array1OfPINod*)PINod)->
489                                ChangeValue(1));
490             
491             for (i = 1; i <= nbN; i++) {
492               HLRAlgo_PolyInternalNode::NodeIndices& aNodIndices = (*NN)->Indices();
493               HLRAlgo_PolyInternalNode::NodeData& Nod1RValues = (*NN)->Data();
494         Nod1RValues.UV = OUVN->Coord();
495               if (Normal(i,aNodIndices,Nod1RValues,
496                          TData,PISeg,PINod,Standard_False))
497                 aNodIndices.Flag |=  NMsk_Norm;
498               else {
499                 aNodIndices.Flag &= ~NMsk_Norm;
500                 Nod1RValues.Scal = 0;
501               }
502               OUVN++;
503               NN++;
504             }
505           }
506 #ifdef OCCT_DEBUG
507           else if (DoError) {
508             std::cout << " HLRBRep_PolyAlgo::StoreShell : Face ";
509             std::cout << f << " non triangulated" << std::endl;
510           }
511 #endif
512           NT = &(((HLRAlgo_Array1OfTData*)TData)->ChangeValue(1));
513
514           for (i = 1; i <= nbT; i++) {
515             const Handle(HLRAlgo_PolyInternalNode)* PN1 = 
516         &PINod->ChangeValue(NT->Node1);
517             const Handle(HLRAlgo_PolyInternalNode)* PN2 = 
518         &PINod->ChangeValue(NT->Node2);
519             const Handle(HLRAlgo_PolyInternalNode)* PN3 = 
520         &PINod->ChangeValue(NT->Node3);
521             HLRAlgo_PolyInternalNode::NodeData& Nod1RValues = (*PN1)->Data();
522             HLRAlgo_PolyInternalNode::NodeData& Nod2RValues = (*PN2)->Data();
523             HLRAlgo_PolyInternalNode::NodeData& Nod3RValues = (*PN3)->Data();
524             OrientTriangle(i,*NT,
525                            (*PN1)->Indices(),Nod1RValues,
526                            (*PN2)->Indices(),Nod2RValues,
527                            (*PN3)->Indices(),Nod3RValues);
528             NT++;
529           }
530         }
531       }
532 #ifdef OCCT_DEBUG
533       else if (DoError) {
534         std::cout << "HLRBRep_PolyAlgo::StoreShell : Face ";
535         std::cout << f << " deja stockee" << std::endl;
536       }
537 #endif
538     }
539     Standard_Integer nbFace = myFMap.Extent();
540     HLRAlgo_ListOfBPoint& List = psd->Edges();
541     TopTools_IndexedDataMapOfShapeListOfShape EF;
542     TopExp::MapShapesAndAncestors(Shape,TopAbs_EDGE,TopAbs_FACE,EF);
543     Handle(HLRAlgo_PolyInternalData)* pid = 
544         (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
545     
546     for (f = 1; f <= nbFace; f++) {
547       if (!(*pid).IsNull()) {
548
549         for (exedge.Init(myFMap(f),TopAbs_EDGE);
550              exedge.More(); 
551              exedge.Next()) {
552           TopoDS_Edge E = TopoDS::Edge(exedge.Current());
553           if (ShapeMap1.Add(E)) {
554             Standard_Integer e = myEMap.FindIndex(E);
555             ES(e) = iShell;
556             Standard_Integer anIndexE = EF.FindIndex(E);
557             if (anIndexE > 0) {
558               TopTools_ListOfShape& LS = EF(anIndexE);
559               InitBiPointsWithConnexity(e,E,List,PID,LS,Standard_True);
560             }
561             else {
562               TopTools_ListOfShape LS;
563               InitBiPointsWithConnexity(e,E,List,PID,LS,Standard_False);
564             }
565           }
566         }
567       }
568       pid++;
569     }
570     InsertOnOutLine(PID);
571     CheckFrBackTriangles(List,PID);
572     UpdateOutLines(List,PID);
573     UpdateEdgesBiPoints(List,PID,closed);
574     UpdatePolyData(PD,PID,closed);
575     pid = (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
576     
577     for (f = 1; f <= nbFace; f++) {
578       (*pid).Nullify();  
579       pid++;
580     }
581   }
582   else if (IsoledE) {
583     const Handle(HLRAlgo_PolyShellData)& psd =
584       *(Handle(HLRAlgo_PolyShellData)*)&(Shell(iShell));
585     HLRAlgo_ListOfBPoint& List = psd->Edges();
586     
587     for (exedge.Init(Shape, TopAbs_EDGE, TopAbs_FACE);
588          exedge.More(); 
589          exedge.Next()) {
590       TopoDS_Edge E = TopoDS::Edge(exedge.Current());
591       if (ShapeMap1.Add(E)) {
592         Standard_Integer e = myEMap.FindIndex(E);
593         ES(e) = iShell;
594         TopTools_ListOfShape LS;
595         InitBiPointsWithConnexity(e,E,List,PID,LS,Standard_False);
596       }
597     }
598   }
599 }
600
601 //=======================================================================
602 //function : Normal
603 //purpose  : 
604 //=======================================================================
605
606 Standard_Boolean HLRBRep_PolyAlgo::
607 Normal (const Standard_Integer iNode,
608         HLRAlgo_PolyInternalNode::NodeIndices& theNodIndices,
609         HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
610         HLRAlgo_Array1OfTData*& TData,
611         HLRAlgo_Array1OfPISeg*& PISeg,
612         HLRAlgo_Array1OfPINod*& PINod,
613         const Standard_Boolean orient) const
614 {
615   gp_Vec D1U,D1V,D2U,D2V,D2UV;
616   gp_Pnt P;
617   gp_Dir Norma;
618   Standard_Boolean OK;
619   CSLib_DerivativeStatus aStatus;
620   CSLib_NormalStatus NStat;
621   myBSurf.D1(Nod1RValues.UV.X(), Nod1RValues.UV.Y(), P, D1U, D1V);
622   CSLib::Normal(D1U,D1V,Standard_Real(Precision::Angular()),
623                 aStatus,Norma);
624   if (aStatus != CSLib_Done) {
625     myBSurf.D2(Nod1RValues.UV.X(), Nod1RValues.UV.Y(), P, D1U, D1V, D2U, D2V, D2UV);
626     CSLib::Normal(D1U,D1V,D2U,D2V,D2UV,
627                   Precision::Angular(),OK,NStat,Norma);
628     if (!OK)
629       return Standard_False;
630   }
631   Standard_Real EyeX =  0;
632   Standard_Real EyeY =  0;
633   Standard_Real EyeZ = -1;
634   if (myProj.Perspective()) {
635     EyeX = Nod1RValues.Point.X();
636     EyeY = Nod1RValues.Point.Y();
637     EyeZ = Nod1RValues.Point.Z() - myProj.Focus();
638     Standard_Real d = sqrt(EyeX * EyeX + EyeY * EyeY + EyeZ * EyeZ);
639     if (d > 0) {
640       EyeX /= d;
641       EyeY /= d;
642       EyeZ /= d;
643     }
644   }
645   Nod1RValues.Normal = Norma.XYZ();
646 //  TMultiply(Nod1NrmX,Nod1NrmY,Nod1NrmZ);
647   TMultiply(Nod1RValues.Normal,myProj.Perspective()); //OCC349
648   gp_XYZ Norm;
649   
650   if (AverageNormal(iNode,theNodIndices,TData,PISeg,PINod,Norm))
651   {
652     if (Nod1RValues.Normal * Norm < 0)
653     {
654       Nod1RValues.Normal.Reverse();
655     }
656     Nod1RValues.Scal = (Nod1RValues.Normal * gp_XYZ(EyeX, EyeY, EyeZ));
657   }
658   else {
659     Nod1RValues.Scal = 0;
660     Nod1RValues.Normal = gp_XYZ(1., 0., 0.);
661 #ifdef OCCT_DEBUG
662     if (DoError) {
663       std::cout << "HLRBRep_PolyAlgo::Normal : AverageNormal error";
664       std::cout << std::endl;
665     }
666 #endif
667   }
668   if (Nod1RValues.Scal > 0) {
669     if ( Nod1RValues.Scal < myTolAngular) {
670       Nod1RValues.Scal  = 0;
671       theNodIndices.Flag |= NMsk_OutL;
672     }
673   }
674   else {
675     if (-Nod1RValues.Scal < myTolAngular) {
676       Nod1RValues.Scal  = 0;
677       theNodIndices.Flag |= NMsk_OutL;
678     }
679   }
680   if (orient) UpdateAroundNode(iNode,theNodIndices,
681                                TData,PISeg,PINod);
682   return Standard_True;
683 }
684
685 //=======================================================================
686 //function : AverageNormal
687 //purpose  : 
688 //=======================================================================
689
690 Standard_Boolean
691 HLRBRep_PolyAlgo::AverageNormal(const Standard_Integer iNode,
692                                 HLRAlgo_PolyInternalNode::NodeIndices& theNodeIndices,
693                                 HLRAlgo_Array1OfTData*& TData,
694                                 HLRAlgo_Array1OfPISeg*& PISeg,
695                                 HLRAlgo_Array1OfPINod*& PINod,
696                                 Standard_Real& X,
697                                 Standard_Real& Y,
698                                 Standard_Real& Z) const
699 {
700   Standard_Boolean OK = Standard_False;
701   Standard_Integer jNode = 0,kNode,iiii,iTri1,iTri2;
702   X = 0;
703   Y = 0;
704   Z = 0;
705   iiii = theNodeIndices.NdSg;
706
707   while (iiii != 0 && !OK) {
708     HLRAlgo_PolyInternalSegment& aSegIndices =
709       ((HLRAlgo_Array1OfPISeg*)PISeg)->ChangeValue(iiii);
710     iTri1 = aSegIndices.Conex1;
711     iTri2 = aSegIndices.Conex2;
712     if ( iTri1 != 0) AddNormalOnTriangle
713       (iTri1,iNode,jNode,TData,PINod,X,Y,Z,OK);
714     if ( iTri2 != 0) AddNormalOnTriangle
715       (iTri2,iNode,jNode,TData,PINod,X,Y,Z,OK);
716     if (aSegIndices.LstSg1 == iNode) iiii = aSegIndices.NxtSg1;
717     else                     iiii = aSegIndices.NxtSg2;
718   }
719
720   if (jNode != 0) {
721     iiii = theNodeIndices.NdSg;
722     
723     while (iiii != 0 && !OK) {
724       HLRAlgo_PolyInternalSegment& aSegIndices = PISeg->ChangeValue(iiii);
725       iTri1 = aSegIndices.Conex1;
726       iTri2 = aSegIndices.Conex2;
727       if ( iTri1 != 0) AddNormalOnTriangle
728         (iTri1,jNode,kNode,TData,PINod,X,Y,Z,OK);
729       if ( iTri2 != 0) AddNormalOnTriangle
730         (iTri2,jNode,kNode,TData,PINod,X,Y,Z,OK);
731       if (aSegIndices.LstSg1 == jNode) iiii = aSegIndices.NxtSg1;
732       else                     iiii = aSegIndices.NxtSg2;
733     }
734   }
735   Standard_Real d = sqrt (X * X + Y * Y + Z * Z);
736   if (OK && d < 1.e-10) {
737     OK = Standard_False;
738 #ifdef OCCT_DEBUG
739     if (DoError) {
740       std::cout << "HLRAlgo_PolyInternalData:: inverted normals on ";
741       std::cout << "node " << iNode << std::endl;
742     }
743 #endif
744   }
745   return OK;
746 }
747
748 //=======================================================================
749 //function : AddNormalOnTriangle
750 //purpose  : 
751 //=======================================================================
752
753 void
754 HLRBRep_PolyAlgo::
755 AddNormalOnTriangle(const Standard_Integer iTri,
756                     const Standard_Integer iNode,
757                     Standard_Integer& jNode,
758                     HLRAlgo_Array1OfTData*& TData,
759                     HLRAlgo_Array1OfPINod*& PINod,
760                     Standard_Real& X,
761                     Standard_Real& Y,
762                     Standard_Real& Z,
763                     Standard_Boolean& OK) const
764 {
765   HLRAlgo_TriangleData& aTriangle = TData->ChangeValue(iTri);
766   HLRAlgo_PolyInternalNode::NodeData& Nod1RValues =
767     PINod->ChangeValue(aTriangle.Node1)->Data();
768   HLRAlgo_PolyInternalNode::NodeData& Nod2RValues =
769     PINod->ChangeValue(aTriangle.Node2)->Data();
770   HLRAlgo_PolyInternalNode::NodeData& Nod3RValues =
771     PINod->ChangeValue(aTriangle.Node3)->Data();
772   const gp_XYZ aD1 = Nod2RValues.Point - Nod1RValues.Point;
773   const Standard_Real aD1Norm = aD1.Modulus();
774   if (aD1Norm < 1.e-10) {
775     if      (aTriangle.Node1 == iNode) jNode = aTriangle.Node2;
776     else if (aTriangle.Node2 == iNode) jNode = aTriangle.Node1;
777   }
778   else {
779     const gp_XYZ aD2 = Nod3RValues.Point - Nod2RValues.Point;
780     const Standard_Real aD2Norm = aD2.Modulus();
781     if (aD2Norm < 1.e-10) {
782       if      (aTriangle.Node2 == iNode) jNode = aTriangle.Node3;
783       else if (aTriangle.Node3 == iNode) jNode = aTriangle.Node2;
784     }
785     else {
786       const gp_XYZ aD3 = Nod1RValues.Point - Nod3RValues.Point;
787       const Standard_Real aD3Norm = aD3.Modulus();
788       if (aD3Norm < 1.e-10) {
789         if      (aTriangle.Node3 == iNode) jNode = aTriangle.Node1;
790         else if (aTriangle.Node1 == iNode) jNode = aTriangle.Node3;
791       }
792       else {
793         const gp_XYZ aDN = (1 / (aD1Norm * aD2Norm)) * (aD1 ^ aD2);
794         const Standard_Real aDNNorm = aDN.Modulus();
795         if (aDNNorm > 1.e-10) {
796           OK = Standard_True;
797           X += aDN.X();
798           Y += aDN.Y();
799           Z += aDN.Z();
800         }
801       }
802     }
803   }
804 }
805
806 //=======================================================================
807 //function : InitBiPointsWithConnexity
808 //purpose  : 
809 //=======================================================================
810
811 void HLRBRep_PolyAlgo::
812 InitBiPointsWithConnexity (const Standard_Integer e,
813                            TopoDS_Edge& E,
814                            HLRAlgo_ListOfBPoint& List,
815                            TColStd_Array1OfTransient& PID,
816                            TopTools_ListOfShape& LS,
817                            const Standard_Boolean connex)
818 {
819   Standard_Integer iPol,nbPol,i1,i1p1,i1p2,i2,i2p1,i2p2;
820   Standard_Real X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ;
821   Standard_Real XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2;
822   Standard_Real U1,U2 = 0.;
823   Handle(Poly_PolygonOnTriangulation) HPol[2];
824   TopLoc_Location L;
825   myBCurv.Initialize(E);
826   if (connex) {
827     Standard_Integer nbConnex = LS.Extent();
828     if      (nbConnex == 1) {
829       TopTools_ListIteratorOfListOfShape itn(LS);
830       const TopoDS_Face& F1 = TopoDS::Face(itn.Value());
831       i1      = myFMap.FindIndex(F1);
832       const Handle(Poly_Triangulation)& Tr1 = BRep_Tool::Triangulation(F1,L);
833       HPol[0] = BRep_Tool::PolygonOnTriangulation(E,Tr1,L);
834       const Handle(HLRAlgo_PolyInternalData)& pid1 = 
835         *(Handle(HLRAlgo_PolyInternalData)*)&(PID(i1));
836       if (!HPol[0].IsNull()) {
837         myPC.Initialize(E,F1);
838         const Handle(TColStd_HArray1OfReal)& par = HPol[0]->Parameters();
839         const TColStd_Array1OfInteger&      Pol1 = HPol[0]->Nodes();
840         nbPol = Pol1.Upper();
841         HLRAlgo_Array1OfTData* TData1 = &pid1->TData();
842         HLRAlgo_Array1OfPISeg* PISeg1 = &pid1->PISeg();
843         HLRAlgo_Array1OfPINod* PINod1 = &pid1->PINod();
844   HLRAlgo_PolyInternalNode::NodeIndices* aNode11Indices;
845   HLRAlgo_PolyInternalNode::NodeIndices* aNode12Indices;
846         const Handle(HLRAlgo_PolyInternalNode)* pi1p1 =
847           &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(Pol1(1    )));
848         aNode11Indices = &(*pi1p1)->Indices();
849   HLRAlgo_PolyInternalNode::NodeData* Nod11RValues = &(*pi1p1)->Data();
850         const Handle(HLRAlgo_PolyInternalNode)* pi1p2 =
851           &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(Pol1(nbPol)));
852         aNode12Indices = &(*pi1p2)->Indices();
853   HLRAlgo_PolyInternalNode::NodeData* Nod12RValues = &(*pi1p2)->Data();
854         aNode11Indices->Flag |=  NMsk_Vert;
855         aNode12Indices->Flag |=  NMsk_Vert;
856         
857         for (iPol = 1; iPol <= nbPol; iPol++) {
858           const Handle(HLRAlgo_PolyInternalNode)* pi1pA =
859             &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(Pol1(iPol)));
860           HLRAlgo_PolyInternalNode::NodeIndices& aNodeIndices1A = (*pi1pA)->Indices();
861           HLRAlgo_PolyInternalNode::NodeData& Nod1ARValues = (*pi1pA)->Data();
862           if (aNodeIndices1A.Edg1 == 0 || aNodeIndices1A.Edg1 == e) {
863             aNodeIndices1A.Edg1 = e;
864             Nod1ARValues.PCu1 = par->Value(iPol);
865           }
866           else {
867             aNodeIndices1A.Edg2 = e;
868             Nod1ARValues.PCu2 = par->Value(iPol);
869           }
870         }
871         
872         i1p2 = Pol1(1);
873         aNode12Indices = aNode11Indices;
874         Nod12RValues = Nod11RValues;
875         XTI2 = X2 = Nod12RValues->Point.X();
876         YTI2 = Y2 = Nod12RValues->Point.Y();
877         ZTI2 = Z2 = Nod12RValues->Point.Z();
878         if      (aNode12Indices->Edg1 == e) U2 = Nod12RValues->PCu1;
879         else if (aNode12Indices->Edg2 == e) U2 = Nod12RValues->PCu2;
880 #ifdef OCCT_DEBUG
881         else {
882           std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
883           std::cout << "Parameter error on Node " << i1p2 << std::endl;
884         }
885 #endif
886         aNode12Indices->Flag |= NMsk_Edge;
887         TIMultiply(XTI2,YTI2,ZTI2);
888         if (Pol1(1) == Pol1(nbPol) && myPC.IsPeriodic())
889           U2 = U2 - myPC.Period();
890         
891         if (nbPol == 2 && BRep_Tool::Degenerated(E)) {
892           CheckDegeneratedSegment(*aNode11Indices,*Nod11RValues,
893                                   *aNode12Indices,*Nod12RValues);
894           UpdateAroundNode(Pol1(1    ),*aNode11Indices,TData1,PISeg1,PINod1);
895           UpdateAroundNode(Pol1(nbPol),*aNode12Indices,TData1,PISeg1,PINod1);
896         }
897         else {
898
899           for (iPol = 2; iPol <= nbPol; iPol++) {
900             i1p1 = i1p2;
901             aNode11Indices = aNode12Indices;
902             Nod11RValues = Nod12RValues;
903             i1p2 = Pol1(iPol);
904             const Handle(HLRAlgo_PolyInternalNode)* pi1p2iPol =
905               &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(Pol1(iPol)));
906             aNode12Indices = &(*pi1p2iPol)->Indices();
907             Nod12RValues = &(*pi1p2iPol)->Data();
908 #ifdef OCCT_DEBUG
909             if (DoError) {
910               if (Nod11RValues->Normal.X()*Nod12RValues->Normal.X() +
911                   Nod11RValues->Normal.Y()*Nod12RValues->Normal.Y() +
912                   Nod11RValues->Normal.Z()*Nod12RValues->Normal.Z() < 0) {
913                 std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
914                 std::cout << "Too big angle between " << i1p1 << std::setw(6);
915                 std::cout << " and " << i1p2 << std::setw(6);
916                 std::cout << " in face " << i1 << std::endl;
917               }
918             }
919 #endif
920             X1   = X2;
921             Y1   = Y2;
922             Z1   = Z2;
923             XTI1 = XTI2;
924             YTI1 = YTI2;
925             ZTI1 = ZTI2;
926             U1   = U2;
927             XTI2 = X2 = Nod12RValues->Point.X();
928             YTI2 = Y2 = Nod12RValues->Point.Y();
929             ZTI2 = Z2 = Nod12RValues->Point.Z();
930             if      (aNode12Indices->Edg1 == e) U2 = Nod12RValues->PCu1;
931             else if (aNode12Indices->Edg2 == e) U2 = Nod12RValues->PCu2;
932 #ifdef OCCT_DEBUG
933             else {
934               std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
935               std::cout << "Parameter error on Node " << i1p2 << std::endl;
936             }
937 #endif
938             aNode12Indices->Flag |= NMsk_Edge;
939             TIMultiply(XTI2,YTI2,ZTI2);
940             Interpolation(List,
941                           X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
942                           XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
943                           e,U1,U2,
944                           *aNode11Indices,*Nod11RValues,
945                           *aNode12Indices,*Nod12RValues,
946                           i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1);
947           }
948         }
949       }
950 #ifdef OCCT_DEBUG
951       else if (DoError) {
952         std::cout << "HLRBRep_PolyAlgo::InitBiPointsWithConnexity : Edge ";
953         std::cout << e << " connex 1 sans PolygonOnTriangulation" << std::endl;
954       }
955 #endif
956     }
957     else if (nbConnex == 2) {
958       TopTools_ListIteratorOfListOfShape itn(LS);
959       const TopoDS_Face& F1 = TopoDS::Face(itn.Value());
960       i1      = myFMap.FindIndex(F1);
961       const Handle(Poly_Triangulation)& Tr1 = BRep_Tool::Triangulation(F1,L);
962       HPol[0] = BRep_Tool::PolygonOnTriangulation(E,Tr1,L);
963       itn.Next();
964       const TopoDS_Face& F2 = TopoDS::Face(itn.Value());
965       i2      = myFMap.FindIndex(F2);
966       if (i1 == i2) E.Reverse();
967       const Handle(Poly_Triangulation)& Tr2 = BRep_Tool::Triangulation(F2,L);
968       HPol[1] = BRep_Tool::PolygonOnTriangulation(E,Tr2,L);
969       GeomAbs_Shape rg = BRep_Tool::Continuity(E,F1,F2);
970       const Handle(HLRAlgo_PolyInternalData)& pid1 = 
971         *(Handle(HLRAlgo_PolyInternalData)*)&(PID(i1));
972       const Handle(HLRAlgo_PolyInternalData)& pid2 = 
973         *(Handle(HLRAlgo_PolyInternalData)*)&(PID(i2));
974       if (!HPol[0].IsNull() && !HPol[1].IsNull()) {
975         myPC.Initialize(E,F1);
976         const TColStd_Array1OfInteger&      Pol1 = HPol[0]->Nodes();
977         const TColStd_Array1OfInteger&      Pol2 = HPol[1]->Nodes();
978         const Handle(TColStd_HArray1OfReal)& par = HPol[0]->Parameters();
979         Standard_Integer nbPol1 = Pol1.Upper();
980         HLRAlgo_Array1OfTData* TData1 = &pid1->TData();
981         HLRAlgo_Array1OfPISeg* PISeg1 = &pid1->PISeg();
982         HLRAlgo_Array1OfPINod* PINod1 = &pid1->PINod();
983         HLRAlgo_Array1OfTData* TData2 = &pid2->TData();
984         HLRAlgo_Array1OfPISeg* PISeg2 = &pid2->PISeg();
985         HLRAlgo_Array1OfPINod* PINod2 = &pid2->PINod();
986         const Handle(HLRAlgo_PolyInternalNode)* pi1p1 =
987           &PINod1->ChangeValue(Pol1(1));
988         HLRAlgo_PolyInternalNode::NodeIndices* aNode11Indices = &(*pi1p1)->Indices();
989   HLRAlgo_PolyInternalNode::NodeData* Nod11RValues = &(*pi1p1)->Data();
990         const Handle(HLRAlgo_PolyInternalNode)* pi1p2nbPol1 =
991           &PINod1->ChangeValue(Pol1(nbPol1));
992         HLRAlgo_PolyInternalNode::NodeIndices* aNode12Indices = &(*pi1p2nbPol1)->Indices();
993   HLRAlgo_PolyInternalNode::NodeData* Nod12RValues = &(*pi1p2nbPol1)->Data();
994         const Handle(HLRAlgo_PolyInternalNode)* pi2p1 =
995           &PINod2->ChangeValue(Pol2(1));
996         HLRAlgo_PolyInternalNode::NodeIndices* Nod21Indices = &(*pi2p1)->Indices();
997   HLRAlgo_PolyInternalNode::NodeData* Nod21RValues = &(*pi2p1)->Data();
998         const Handle(HLRAlgo_PolyInternalNode)* pi2p2 =
999     &PINod2->ChangeValue(Pol2(nbPol1));
1000         HLRAlgo_PolyInternalNode::NodeIndices* Nod22Indices = &(*pi2p2)->Indices();
1001   HLRAlgo_PolyInternalNode::NodeData* Nod22RValues = &(*pi2p2)->Data();
1002         aNode11Indices->Flag |=  NMsk_Vert;
1003         aNode12Indices->Flag |=  NMsk_Vert;
1004         Nod21Indices->Flag |=  NMsk_Vert;
1005         Nod22Indices->Flag |=  NMsk_Vert;
1006         
1007         for (iPol = 1; iPol <= nbPol1; iPol++) {
1008           const Handle(HLRAlgo_PolyInternalNode)* pi1pA =
1009             &PINod1->ChangeValue(Pol1(iPol));
1010           HLRAlgo_PolyInternalNode::NodeIndices* Nod1AIndices = &(*pi1pA)->Indices();
1011     HLRAlgo_PolyInternalNode::NodeData* Nod1ARValues = &(*pi1pA)->Data();
1012           const Handle(HLRAlgo_PolyInternalNode)* pi2pA =
1013       &PINod2->ChangeValue(Pol2(iPol));
1014           HLRAlgo_PolyInternalNode::NodeIndices* Nod2AIndices = &(*pi2pA)->Indices();
1015     HLRAlgo_PolyInternalNode::NodeData* Nod2ARValues = &(*pi2pA)->Data();
1016           Standard_Real PCu = par->Value(iPol);
1017           if (Nod1AIndices->Edg1 == 0 || Nod1AIndices->Edg1 == e) {
1018             Nod1AIndices->Edg1 = e;
1019             Nod1ARValues->PCu1 = PCu;
1020           }
1021           else {
1022             Nod1AIndices->Edg2 = e;
1023             Nod1ARValues->PCu2 = PCu;
1024           }
1025           if (Nod2AIndices->Edg1 == 0 || Nod2AIndices->Edg1 == e) {
1026             Nod2AIndices->Edg1 = e;
1027             Nod2ARValues->PCu1 = PCu;
1028           }
1029           else {
1030             Nod2AIndices->Edg2 = e;
1031             Nod2ARValues->PCu2 = PCu;
1032           }
1033         }
1034
1035         i1p2 = Pol1(1);
1036         aNode12Indices = aNode11Indices;
1037         Nod12RValues = Nod11RValues;
1038         i2p2 = Pol2(1);
1039         Nod22Indices = Nod21Indices;
1040         Nod22RValues = Nod21RValues;
1041         XTI2 = X2 = Nod12RValues->Point.X();
1042         YTI2 = Y2 = Nod12RValues->Point.Y();
1043         ZTI2 = Z2 = Nod12RValues->Point.Z();
1044         if      (aNode12Indices->Edg1 == e) U2 = Nod12RValues->PCu1;
1045         else if (aNode12Indices->Edg2 == e) U2 = Nod12RValues->PCu2;
1046 #ifdef OCCT_DEBUG
1047         else {
1048           std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
1049           std::cout << "Parameter error on Node " << i1p2 << std::endl;
1050         }
1051 #endif
1052         aNode12Indices->Flag |= NMsk_Edge;
1053         Nod22Indices->Flag |= NMsk_Edge;
1054         TIMultiply(XTI2,YTI2,ZTI2);
1055         if (Pol1(1) == Pol1(nbPol1) && myPC.IsPeriodic())
1056           U2 = U2 - myPC.Period();
1057         
1058         if (nbPol1 == 2 && BRep_Tool::Degenerated(E)) {
1059           CheckDegeneratedSegment(*aNode11Indices,*Nod11RValues,
1060                                   *aNode12Indices,*Nod12RValues);
1061           CheckDegeneratedSegment(*Nod21Indices,*Nod21RValues,
1062                                   *Nod22Indices,*Nod22RValues);
1063           UpdateAroundNode(Pol1(1    ),*aNode11Indices,TData1,PISeg1,PINod1);
1064           UpdateAroundNode(Pol1(nbPol1),*aNode12Indices,TData1,PISeg1,PINod1);
1065           UpdateAroundNode(Pol2(1    ),*Nod21Indices,TData2,PISeg2,PINod2);
1066           UpdateAroundNode(Pol2(nbPol1),*Nod22Indices,TData2,PISeg2,PINod2);
1067         }
1068         else {
1069
1070           for (iPol = 2; iPol <= nbPol1; iPol++) {
1071             i1p1 = i1p2;
1072             aNode11Indices = aNode12Indices;
1073             Nod11RValues = Nod12RValues;
1074             i2p1 = i2p2;
1075             Nod21Indices = Nod22Indices;
1076             Nod21RValues = Nod22RValues;
1077             i1p2 = Pol1(iPol);
1078             const Handle(HLRAlgo_PolyInternalNode)* pi1p2iPol =
1079               &PINod1->ChangeValue(Pol1(iPol));
1080             aNode12Indices = &(*pi1p2iPol)->Indices();
1081       Nod12RValues = &(*pi1p2iPol)->Data();
1082             i2p2 = Pol2(iPol);
1083             const Handle(HLRAlgo_PolyInternalNode)* pi2p2iPol =
1084         &PINod2->ChangeValue(Pol2(iPol));
1085             Nod22Indices = &(*pi2p2iPol)->Indices();
1086       Nod22RValues = &(*pi2p2iPol)->Data();
1087 #ifdef OCCT_DEBUG
1088             if (DoError) {
1089               if (Nod11RValues->Normal.X()*Nod12RValues->Normal.X() +
1090                   Nod11RValues->Normal.Y()*Nod12RValues->Normal.Y() +
1091                   Nod11RValues->Normal.Z()*Nod12RValues->Normal.Z() < 0) {
1092                 std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
1093                 std::cout << "To big angle between " << i1p1 << std::setw(6);
1094                 std::cout << " and " << i1p2 << std::setw(6);
1095                 std::cout << " in face " << i1 << std::endl;
1096               }
1097               if (Nod21RValues->Normal.X()*Nod22RValues->Normal.X() +
1098                   Nod21RValues->Normal.Y()*Nod22RValues->Normal.Y() +
1099                   Nod21RValues->Normal.Z()*Nod22RValues->Normal.Z() < 0) {
1100                 std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
1101                 std::cout << "To big angle between " << i2p1 << std::setw(6);
1102                 std::cout << " and " << i2p2 << std::setw(6);
1103                 std::cout<< " in face " << i2 << std::endl;
1104               }
1105             }
1106 #endif
1107             X1   = X2;
1108             Y1   = Y2;
1109             Z1   = Z2;
1110             XTI1 = XTI2;
1111             YTI1 = YTI2;
1112             ZTI1 = ZTI2;
1113             U1   = U2;
1114             XTI2 = X2 = Nod12RValues->Point.X();
1115             YTI2 = Y2 = Nod12RValues->Point.Y();
1116             ZTI2 = Z2 = Nod12RValues->Point.Z();
1117             if      (aNode12Indices->Edg1 == e) U2 = Nod12RValues->PCu1;
1118             else if (aNode12Indices->Edg2 == e) U2 = Nod12RValues->PCu2;
1119 #ifdef OCCT_DEBUG
1120             else {
1121               std::cout << " HLRBRep_PolyAlgo::InitBiPointsWithConnexity : ";
1122               std::cout << "Parameter error on Node " << i1p2 << std::endl;
1123             }
1124 #endif
1125             aNode12Indices->Flag |= NMsk_Edge;
1126             aNode12Indices->Flag |= NMsk_Edge;
1127             TIMultiply(XTI2,YTI2,ZTI2);
1128             Interpolation(List,
1129                           X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1130                           XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1131                           e,U1,U2,rg,
1132                           *aNode11Indices,*Nod11RValues,
1133                           *aNode12Indices,*Nod12RValues,
1134                           i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1135                           *Nod21Indices,*Nod21RValues,
1136                           *Nod22Indices,*Nod22RValues,
1137                           i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2);
1138           }
1139         }
1140       }
1141 #ifdef OCCT_DEBUG
1142       else if (DoError) {
1143         std::cout << "HLRBRep_PolyAlgo::InitBiPointsWithConnexity : Edge ";
1144         std::cout << e << " connect 2 without PolygonOnTriangulation" << std::endl;
1145       }
1146 #endif
1147     }
1148   }
1149   else {  // no connexity
1150     const Handle(Poly_Polygon3D)& Polyg = BRep_Tool::Polygon3D(E,L);
1151     if (!Polyg.IsNull()) {
1152       const TColgp_Array1OfPnt& Pol = Polyg->Nodes();
1153       gp_Trsf TT       = L.Transformation();
1154       const gp_Trsf& T = myProj.Transformation();
1155       TT.PreMultiply(T);
1156       const gp_XYZ& ttlo = TT.TranslationPart();
1157       TTLo[0] = ttlo.X();
1158       TTLo[1] = ttlo.Y();
1159       TTLo[2] = ttlo.Z();
1160       const gp_Mat& ttma = TT.VectorialPart();
1161       TTMa[0][0] = ttma.Value(1,1);
1162       TTMa[0][1] = ttma.Value(1,2);
1163       TTMa[0][2] = ttma.Value(1,3);
1164       TTMa[1][0] = ttma.Value(2,1);
1165       TTMa[1][1] = ttma.Value(2,2);
1166       TTMa[1][2] = ttma.Value(2,3);
1167       TTMa[2][0] = ttma.Value(3,1);
1168       TTMa[2][1] = ttma.Value(3,2);
1169       TTMa[2][2] = ttma.Value(3,3);
1170       Standard_Integer nbPol1 = Pol.Upper();
1171       const gp_XYZ& P1 = Pol(1).XYZ();
1172       X2 = P1.X();
1173       Y2 = P1.Y();
1174       Z2 = P1.Z();
1175       TTMultiply(X2,Y2,Z2);
1176       XTI2 = X2;
1177       YTI2 = Y2;
1178       ZTI2 = Z2;
1179       TIMultiply(XTI2,YTI2,ZTI2);
1180       
1181       for (Standard_Integer jPol = 2; jPol <= nbPol1; jPol++) {
1182         X1   = X2;
1183         Y1   = Y2;
1184         Z1   = Z2;
1185         XTI1 = XTI2;
1186         YTI1 = YTI2;
1187         ZTI1 = ZTI2;
1188         const gp_XYZ& P2 = Pol(jPol).XYZ();
1189         X2 = P2.X();
1190         Y2 = P2.Y();
1191         Z2 = P2.Z();
1192         TTMultiply(X2,Y2,Z2);
1193         XTI2 = X2;
1194         YTI2 = Y2;
1195         ZTI2 = Z2;
1196         TIMultiply(XTI2,YTI2,ZTI2);
1197         List.Prepend(HLRAlgo_BiPoint
1198                      (XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1199                       X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,   e,
1200                       0));
1201       }
1202     }
1203 #ifdef OCCT_DEBUG
1204     else if (DoError) {
1205       std::cout << "HLRBRep_PolyAlgo::InitBiPointsWithConnexity : Edge ";
1206       std::cout << e << " Isolated, without Polygone 3D" << std::endl;
1207     }
1208 #endif
1209   }
1210 }
1211
1212 //=======================================================================
1213 //function : Interpolation
1214 //purpose  : 
1215 //=======================================================================
1216
1217 void
1218 HLRBRep_PolyAlgo::
1219 Interpolation (HLRAlgo_ListOfBPoint& List,
1220                Standard_Real& X1,
1221                Standard_Real& Y1,
1222                Standard_Real& Z1,
1223                Standard_Real& X2,
1224                Standard_Real& Y2,
1225                Standard_Real& Z2,
1226                Standard_Real& XTI1,
1227                Standard_Real& YTI1,
1228                Standard_Real& ZTI1,
1229                Standard_Real& XTI2,
1230                Standard_Real& YTI2,
1231                Standard_Real& ZTI2,
1232                const Standard_Integer e,
1233                Standard_Real& U1,
1234                Standard_Real& U2,
1235                HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices,
1236                HLRAlgo_PolyInternalNode::NodeData& Nod11RValues,
1237                HLRAlgo_PolyInternalNode::NodeIndices& Nod12Indices,
1238                HLRAlgo_PolyInternalNode::NodeData& Nod12RValues,
1239                const Standard_Integer i1p1,
1240                const Standard_Integer i1p2,
1241                const Standard_Integer i1,
1242                const Handle(HLRAlgo_PolyInternalData)& pid1,
1243                HLRAlgo_Array1OfTData*& TData1,
1244                HLRAlgo_Array1OfPISeg*& PISeg1,
1245                HLRAlgo_Array1OfPINod*& PINod1) const
1246 {
1247   Standard_Boolean insP3,mP3P1;
1248   Standard_Real X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3;
1249 //  gp_Pnt P3,PT3;
1250   insP3 = Interpolation(U1,U2,Nod11RValues,Nod12RValues,
1251                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,mP3P1);
1252   MoveOrInsertPoint(List,
1253                     X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1254                     XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1255                     e,U1,U2,
1256                     Nod11Indices,Nod11RValues,
1257                     Nod12Indices,Nod12RValues,
1258                     i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1259                     X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,insP3,mP3P1,0);
1260 }
1261
1262 //=======================================================================
1263 //function : Interpolation
1264 //purpose  : 
1265 //=======================================================================
1266
1267 void
1268 HLRBRep_PolyAlgo::
1269 Interpolation (HLRAlgo_ListOfBPoint& List,
1270                Standard_Real& X1,
1271                Standard_Real& Y1,
1272                Standard_Real& Z1,
1273                Standard_Real& X2,
1274                Standard_Real& Y2,
1275                Standard_Real& Z2,
1276                Standard_Real& XTI1,
1277                Standard_Real& YTI1,
1278                Standard_Real& ZTI1,
1279                Standard_Real& XTI2,
1280                Standard_Real& YTI2,
1281                Standard_Real& ZTI2,
1282                const Standard_Integer e,
1283                Standard_Real& U1,
1284                Standard_Real& U2,
1285                const GeomAbs_Shape rg,
1286                HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices,
1287                HLRAlgo_PolyInternalNode::NodeData& Nod11RValues,
1288                HLRAlgo_PolyInternalNode::NodeIndices& Nod12Indices,
1289                HLRAlgo_PolyInternalNode::NodeData& Nod12RValues,
1290                const Standard_Integer i1p1,
1291                const Standard_Integer i1p2,
1292                const Standard_Integer i1,
1293                const Handle(HLRAlgo_PolyInternalData)& pid1,
1294                HLRAlgo_Array1OfTData*& TData1,
1295                HLRAlgo_Array1OfPISeg*& PISeg1,
1296                HLRAlgo_Array1OfPINod*& PINod1,
1297                HLRAlgo_PolyInternalNode::NodeIndices& Nod21Indices,
1298                HLRAlgo_PolyInternalNode::NodeData& Nod21RValues,
1299                HLRAlgo_PolyInternalNode::NodeIndices& Nod22Indices,
1300                HLRAlgo_PolyInternalNode::NodeData& Nod22RValues,
1301                const Standard_Integer i2p1,
1302                const Standard_Integer i2p2,
1303                const Standard_Integer i2,
1304                const Handle(HLRAlgo_PolyInternalData)& pid2,
1305                HLRAlgo_Array1OfTData*& TData2,
1306                HLRAlgo_Array1OfPISeg*& PISeg2,
1307                HLRAlgo_Array1OfPINod*& PINod2) const
1308 {
1309   Standard_Boolean insP3,mP3P1,insP4,mP4P1;
1310   Standard_Real X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3;
1311   Standard_Real X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4;
1312 //  gp_Pnt P3,PT3,P4,PT4;
1313   Standard_Integer flag = 0;
1314   if (rg >= GeomAbs_G1) flag += 1;
1315   if (rg >= GeomAbs_G2) flag += 2;
1316   insP3 = Interpolation(U1,U2,Nod11RValues,Nod12RValues,
1317                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,mP3P1);
1318   insP4 = Interpolation(U1,U2,Nod21RValues,Nod22RValues,
1319                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,mP4P1);
1320   Standard_Boolean OK = insP3 || insP4;
1321   if (OK) {
1322     if      (!insP4)                               // p1 i1p3 p2
1323       MoveOrInsertPoint(List,
1324                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1325                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1326                         e,U1,U2,
1327                         Nod11Indices,Nod11RValues,
1328                         Nod12Indices,Nod12RValues,
1329                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1330                         Nod21Indices,Nod21RValues,
1331                         Nod22Indices,Nod22RValues,
1332                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1333                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,insP3,mP3P1,flag);
1334     else if (!insP3)                               // p1 i2p4 p2
1335       MoveOrInsertPoint(List,
1336                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1337                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1338                         e,U1,U2,
1339                         Nod21Indices,Nod21RValues,
1340                         Nod22Indices,Nod22RValues,
1341                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1342                         Nod11Indices,Nod11RValues,
1343                         Nod12Indices,Nod12RValues,
1344                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1345                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,insP4,mP4P1,flag);
1346     else if (Abs(coef4 - coef3) < myTolSta)       // p1 i1p3-i2p4 p2
1347       MoveOrInsertPoint(List,
1348                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1349                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1350                         e,U1,U2,
1351                         Nod21Indices,Nod21RValues,
1352                         Nod22Indices,Nod22RValues,
1353                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1354                         Nod11Indices,Nod11RValues,
1355                         Nod12Indices,Nod12RValues,
1356                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1357                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,insP4,mP4P1,flag);
1358     else if (coef4 < coef3)                        // p1 i2p4 i1p3 p2
1359       MoveOrInsertPoint(List,
1360                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1361                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1362                         e,U1,U2,
1363                         Nod21Indices,Nod21RValues,
1364                         Nod22Indices,Nod22RValues,
1365                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1366                         Nod11Indices,Nod11RValues,
1367                         Nod12Indices,Nod12RValues,
1368                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1369                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,insP4,mP4P1,
1370                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,insP3,mP3P1,flag);
1371     else                                           // p1 i1p3 i2p4 p2
1372       MoveOrInsertPoint(List,
1373                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1374                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1375                         e,U1,U2,
1376                         Nod11Indices,Nod11RValues,
1377                         Nod12Indices,Nod12RValues,
1378                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1379                         Nod21Indices,Nod21RValues,
1380                         Nod22Indices,Nod22RValues,
1381                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1382                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,insP3,mP3P1,
1383                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,insP4,mP4P1,flag);
1384   }
1385   else                                             // p1 p2
1386     List.Prepend(HLRAlgo_BiPoint
1387                  (XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1388                   X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,   e,
1389                   i1  ,i1p1,i1p2,i2  ,i2p1,i2p2,flag));
1390 }
1391
1392 //=======================================================================
1393 //function : Interpolation
1394 //purpose  : 
1395 //=======================================================================
1396
1397 Standard_Boolean
1398 HLRBRep_PolyAlgo::
1399 Interpolation (const Standard_Real U1,
1400                const Standard_Real U2,
1401                HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
1402                HLRAlgo_PolyInternalNode::NodeData& Nod2RValues,
1403                Standard_Real& X3,
1404                Standard_Real& Y3,
1405                Standard_Real& Z3,
1406                Standard_Real& XTI3,
1407                Standard_Real& YTI3,
1408                Standard_Real& ZTI3,
1409                Standard_Real& coef3,
1410                Standard_Real& U3,
1411                Standard_Boolean& mP3P1) const
1412 {
1413   if (NewNode(Nod1RValues,Nod2RValues,coef3,mP3P1)) {
1414     U3 = U1 + (U2 - U1) * coef3;
1415     const gp_Pnt& P3 = myBCurv.Value(U3);
1416     XTI3 = X3 = P3.X();
1417     YTI3 = Y3 = P3.Y();
1418     ZTI3 = Z3 = P3.Z();
1419     TMultiply(X3,Y3,Z3);
1420     return Standard_True;
1421   }
1422   X3 = Y3 = Z3 = XTI3 = YTI3 = ZTI3 = coef3 = U3 = 0.;
1423   return Standard_False;
1424 }
1425
1426 //=======================================================================
1427 //function : MoveOrInsertPoint
1428 //purpose  : 
1429 //=======================================================================
1430
1431 void
1432 HLRBRep_PolyAlgo::
1433 MoveOrInsertPoint (HLRAlgo_ListOfBPoint& List,
1434                    Standard_Real& X1,
1435                    Standard_Real& Y1,
1436                    Standard_Real& Z1,
1437                    Standard_Real& X2,
1438                    Standard_Real& Y2,
1439                    Standard_Real& Z2,
1440                    Standard_Real& XTI1,
1441                    Standard_Real& YTI1,
1442                    Standard_Real& ZTI1,
1443                    Standard_Real& XTI2,
1444                    Standard_Real& YTI2,
1445                    Standard_Real& ZTI2,
1446                    const Standard_Integer e,
1447                    Standard_Real& U1,
1448                    Standard_Real& U2,
1449                    HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices,
1450                    HLRAlgo_PolyInternalNode::NodeData& Nod11RValues,
1451                    HLRAlgo_PolyInternalNode::NodeIndices& Nod12Indices,
1452                    HLRAlgo_PolyInternalNode::NodeData& Nod12RValues,
1453                    const Standard_Integer i1p1,
1454                    const Standard_Integer i1p2,
1455                    const Standard_Integer i1,
1456                    const Handle(HLRAlgo_PolyInternalData)& pid1,
1457                    HLRAlgo_Array1OfTData*& TData1,
1458                    HLRAlgo_Array1OfPISeg*& PISeg1,
1459                    HLRAlgo_Array1OfPINod*& PINod1,
1460                    const Standard_Real X3,
1461                    const Standard_Real Y3,
1462                    const Standard_Real Z3,
1463                    const Standard_Real XTI3,
1464                    const Standard_Real YTI3,
1465                    const Standard_Real ZTI3,
1466                    const Standard_Real coef3,
1467                    const Standard_Real U3,
1468                    const Standard_Boolean insP3,
1469                    const Standard_Boolean mP3P1,
1470                    const Standard_Integer flag) const
1471 {
1472   HLRAlgo_Array1OfTData* TData2 = 0;
1473   HLRAlgo_Array1OfPISeg* PISeg2 = 0;
1474   HLRAlgo_Array1OfPINod* PINod2 = 0;
1475   Standard_Boolean ins3 = insP3;
1476   if (ins3 && mP3P1) {                             // P1 ---> P3
1477     if (!(Nod11Indices.Flag & NMsk_Vert) && coef3 < myTolSta) {
1478       ins3 = Standard_False;
1479       ChangeNode(i1p1,i1p2,
1480                  Nod11Indices,Nod11RValues,
1481                  Nod12Indices,Nod12RValues,
1482                  coef3,X3,Y3,Z3,Standard_True,
1483                  TData1,PISeg1,PINod1);
1484       X1   = X3;
1485       Y1   = Y3;
1486       Z1   = Z3;
1487       XTI1 = XTI3;
1488       YTI1 = YTI3;
1489       ZTI1 = ZTI3;
1490       U1   = U3;
1491       Nod11RValues.Point = gp_XYZ(X3, Y3, Z3);
1492       if      (Nod11Indices.Edg1 == e) Nod11RValues.PCu1 = U3;
1493       else if (Nod11Indices.Edg2 == e) Nod11RValues.PCu2 = U3;
1494 #ifdef OCCT_DEBUG
1495       else {
1496         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1497         std::cout << "Parameter error on Node " << i1p1 << std::endl;
1498       }
1499 #endif
1500       Nod11RValues.Scal  = 0;
1501       Nod11Indices.Flag |= NMsk_OutL;
1502       UpdateAroundNode(i1p1,Nod11Indices,TData1,PISeg1,PINod1);
1503       HLRAlgo_BiPoint::PointsT& aPoints = List.First().Points();
1504       aPoints.PntP2 = gp_XYZ(X3, Y3, Z3);
1505       aPoints.Pnt2 = gp_XYZ(XTI3, YTI3, ZTI3);
1506     }
1507   }
1508   if (ins3 && !mP3P1) {                            // P2 ---> P3
1509     if (!(Nod12Indices.Flag & NMsk_Vert) && coef3 > myTolEnd) {
1510       ins3 = Standard_False;
1511       ChangeNode(i1p1,i1p2,
1512                  Nod11Indices,Nod11RValues,
1513                  Nod12Indices,Nod12RValues,
1514                  coef3,X3,Y3,Z3,Standard_False,
1515                  TData1,PISeg1,PINod1);
1516       X2   = X3;
1517       Y2   = Y3;
1518       Z2   = Z3;
1519       XTI2 = XTI3;
1520       YTI2 = YTI3;
1521       ZTI2 = ZTI3;
1522       U2   = U3;
1523       Nod12RValues.Point = gp_XYZ(X3, Y3, Z3);
1524       if      (Nod12Indices.Edg1 == e) Nod12RValues.PCu1 = U3;
1525       else if (Nod12Indices.Edg2 == e) Nod12RValues.PCu2 = U3;
1526 #ifdef OCCT_DEBUG
1527       else {
1528         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1529         std::cout << "Parameter error on Node " << i1p2 << std::endl;
1530       }
1531 #endif
1532       Nod12RValues.Scal  = 0;
1533       Nod12Indices.Flag |= NMsk_OutL;
1534       UpdateAroundNode(i1p2,Nod12Indices,TData1,PISeg1,PINod1);
1535     }
1536   }
1537   if (ins3) {                                      // p1 i1p3 p2
1538     Standard_Integer i1p3 = pid1->AddNode
1539       (Nod11RValues,Nod12RValues,PINod1,PINod2,coef3,X3,Y3,Z3);
1540     const Handle(HLRAlgo_PolyInternalNode)* pi1p3 =
1541       &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(i1p3));
1542     HLRAlgo_PolyInternalNode::NodeIndices& Nod13Indices = (*pi1p3)->Indices();
1543     HLRAlgo_PolyInternalNode::NodeData& Nod13RValues = (*pi1p3)->Data();
1544     Nod13Indices.Edg1  = e;
1545     Nod13RValues.PCu1  = U3;
1546     Nod13RValues.Scal  = 0;
1547     Nod13Indices.Flag |= NMsk_OutL;
1548     Nod13Indices.Flag |= NMsk_Edge;
1549     pid1->UpdateLinks(i1p1,i1p2,i1p3,
1550                       TData1,TData2,PISeg1,PISeg2,PINod1,PINod2);
1551     UpdateAroundNode(i1p3,Nod13Indices,TData1,PISeg1,PINod1);
1552     List.Prepend(HLRAlgo_BiPoint
1553                  (XTI1,YTI1,ZTI1,XTI3,YTI3,ZTI3,
1554                   X1  ,Y1  ,Z1  ,X3  ,Y3  ,Z3  ,   e,
1555                   i1  ,i1p1,i1p3,flag));
1556     List.Prepend(HLRAlgo_BiPoint
1557                  (XTI3,YTI3,ZTI3,XTI2,YTI2,ZTI2,
1558                   X3  ,Y3  ,Z3  ,X2  ,Y2  ,Z2  ,   e,
1559                   i1  ,i1p3,i1p2,flag));
1560   }
1561   else                                             // p1 p2
1562     List.Prepend(HLRAlgo_BiPoint
1563                  (XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1564                   X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,   e,
1565                   i1  ,i1p1,i1p2,flag));
1566 }
1567
1568 //=======================================================================
1569 //function : MoveOrInsertPoint
1570 //purpose  : 
1571 //=======================================================================
1572
1573 void
1574 HLRBRep_PolyAlgo::
1575 MoveOrInsertPoint (HLRAlgo_ListOfBPoint& List,
1576                    Standard_Real& X1,
1577                    Standard_Real& Y1,
1578                    Standard_Real& Z1,
1579                    Standard_Real& X2,
1580                    Standard_Real& Y2,
1581                    Standard_Real& Z2,
1582                    Standard_Real& XTI1,
1583                    Standard_Real& YTI1,
1584                    Standard_Real& ZTI1,
1585                    Standard_Real& XTI2,
1586                    Standard_Real& YTI2,
1587                    Standard_Real& ZTI2,
1588                    const Standard_Integer e,
1589                    Standard_Real& U1,
1590                    Standard_Real& U2,
1591                    HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices,
1592                    HLRAlgo_PolyInternalNode::NodeData& Nod11RValues,
1593                    HLRAlgo_PolyInternalNode::NodeIndices& Nod12Indices,
1594                    HLRAlgo_PolyInternalNode::NodeData& Nod12RValues,
1595                    const Standard_Integer i1p1,
1596                    const Standard_Integer i1p2,
1597                    const Standard_Integer i1,
1598                    const Handle(HLRAlgo_PolyInternalData)& pid1,
1599                    HLRAlgo_Array1OfTData*& TData1,
1600                    HLRAlgo_Array1OfPISeg*& PISeg1,
1601                    HLRAlgo_Array1OfPINod*& PINod1,
1602                    HLRAlgo_PolyInternalNode::NodeIndices& Nod21Indices,
1603                    HLRAlgo_PolyInternalNode::NodeData& Nod21RValues,
1604                    HLRAlgo_PolyInternalNode::NodeIndices& Nod22Indices,
1605                    HLRAlgo_PolyInternalNode::NodeData& Nod22RValues,
1606                    const Standard_Integer i2p1,
1607                    const Standard_Integer i2p2,
1608                    const Standard_Integer i2,
1609                    const Handle(HLRAlgo_PolyInternalData)& pid2,
1610                    HLRAlgo_Array1OfTData*& TData2,
1611                    HLRAlgo_Array1OfPISeg*& PISeg2,
1612                    HLRAlgo_Array1OfPINod*& PINod2,
1613                    const Standard_Real X3,
1614                    const Standard_Real Y3,
1615                    const Standard_Real Z3,
1616                    const Standard_Real XTI3,
1617                    const Standard_Real YTI3,
1618                    const Standard_Real ZTI3,
1619                    const Standard_Real coef3,
1620                    const Standard_Real U3,
1621                    const Standard_Boolean insP3,
1622                    const Standard_Boolean mP3P1,
1623                    const Standard_Integer flag) const
1624 {
1625   Standard_Boolean ins3 = insP3;
1626   if (ins3 && mP3P1) {                             // P1 ---> P3
1627     if (!(Nod11Indices.Flag & NMsk_Vert) && coef3 < myTolSta) {
1628       ins3 = Standard_False;
1629       ChangeNode(i1p1,i1p2,
1630                  Nod11Indices,Nod11RValues,
1631                  Nod12Indices,Nod12RValues,
1632                  coef3,X3,Y3,Z3,Standard_True,
1633                  TData1,PISeg1,PINod1);
1634       ChangeNode(i2p1,i2p2,
1635                  Nod21Indices,Nod21RValues,
1636                  Nod22Indices,Nod22RValues,
1637                  coef3,X3,Y3,Z3,Standard_True,
1638                  TData2,PISeg2,PINod2);
1639       X1   = X3;
1640       Y1   = Y3;
1641       Z1   = Z3;
1642       XTI1 = XTI3;
1643       YTI1 = YTI3;
1644       ZTI1 = ZTI3;
1645       U1   = U3;
1646       Nod11RValues.Point = gp_XYZ(X3, Y3, Z3);
1647       if      (Nod11Indices.Edg1 == e) Nod11RValues.PCu1 = U3;
1648       else if (Nod11Indices.Edg2 == e) Nod11RValues.PCu2 = U3;
1649 #ifdef OCCT_DEBUG
1650       else {
1651         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1652         std::cout << "Parameter error on Node " << i1p1 << std::endl;
1653       }
1654 #endif
1655       Nod11RValues.Scal  = 0;
1656       Nod11Indices.Flag |= NMsk_OutL;
1657       UpdateAroundNode(i1p1,Nod11Indices,TData1,PISeg1,PINod1);
1658       Nod21RValues.Point = gp_XYZ(X3, Y3, Z3);
1659       if      (Nod21Indices.Edg1 == e) Nod21RValues.PCu1 = U3;
1660       else if (Nod21Indices.Edg2 == e) Nod21RValues.PCu2 = U3;
1661 #ifdef OCCT_DEBUG
1662       else {
1663         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1664         std::cout << "Parameter error on Node " << i2p1 << std::endl;
1665       }
1666 #endif
1667       Nod21RValues.Scal  = 0;
1668       Nod21Indices.Flag |= NMsk_OutL;
1669       UpdateAroundNode(i2p1,Nod21Indices,TData2,PISeg2,PINod2);
1670       HLRAlgo_BiPoint::PointsT& aPoints = List.First().Points();
1671       aPoints.PntP2 = gp_XYZ(X3, Y3, Z3);
1672       aPoints.Pnt2 = gp_XYZ(XTI3, YTI3, ZTI3);
1673     }
1674   }
1675   if (ins3 && !mP3P1) {                            // P2 ---> P3
1676     if (!(Nod12Indices.Flag & NMsk_Vert) && coef3 > myTolEnd) {
1677       ins3 = Standard_False;
1678       ChangeNode(i1p1,i1p2,
1679                  Nod11Indices,Nod11RValues,
1680                  Nod12Indices,Nod12RValues,
1681                  coef3,X3,Y3,Z3,Standard_False,
1682                  TData1,PISeg1,PINod1);
1683       ChangeNode(i2p1,i2p2,
1684                  Nod21Indices,Nod21RValues,
1685                  Nod22Indices,Nod22RValues,
1686                  coef3,X3,Y3,Z3,Standard_False,
1687                  TData2,PISeg2,PINod2);
1688       X2   = X3;
1689       Y2   = Y3;
1690       Z2   = Z3;
1691       XTI2 = XTI3;
1692       YTI2 = YTI3;
1693       ZTI2 = ZTI3;
1694       U2   = U3;
1695       Nod12RValues.Point = gp_XYZ(X3, Y3, Z3);
1696       if      (Nod12Indices.Edg1 == e) Nod12RValues.PCu1 = U3;
1697       else if (Nod12Indices.Edg2 == e) Nod12RValues.PCu2 = U3;
1698 #ifdef OCCT_DEBUG
1699       else {
1700         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1701         std::cout << "Parameter error on Node " << i1p2 << std::endl;
1702       }
1703 #endif
1704       Nod12RValues.Scal  = 0;
1705       Nod12Indices.Flag |= NMsk_OutL;
1706       UpdateAroundNode(i1p2,Nod12Indices,TData1,PISeg1,PINod1);
1707       Nod22RValues.Point = gp_XYZ(X3, Y3, Z3);
1708       if      (Nod22Indices.Edg1 == e) Nod22RValues.PCu1 = U3;
1709       else if (Nod22Indices.Edg2 == e) Nod22RValues.PCu2 = U3;
1710 #ifdef OCCT_DEBUG
1711       else {
1712         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1713         std::cout << "Parameter error on Node " << i2p2 << std::endl;
1714       }
1715 #endif
1716       Nod22RValues.Scal = 0;
1717       Nod22Indices.Flag |=  NMsk_OutL;
1718       UpdateAroundNode(i2p2,Nod22Indices,TData2,PISeg2,PINod2);
1719     }
1720   }
1721   if (ins3) {                                      // p1 i1p3 p2
1722     Standard_Integer i1p3 = pid1->AddNode
1723       (Nod11RValues,Nod12RValues,PINod1,PINod2,coef3,X3,Y3,Z3);
1724     Standard_Integer i2p3 = pid2->AddNode
1725       (Nod21RValues,Nod22RValues,PINod2,PINod1,coef3,X3,Y3,Z3); 
1726     const Handle(HLRAlgo_PolyInternalNode)* pi1p3 =
1727       &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(i1p3));
1728     HLRAlgo_PolyInternalNode::NodeIndices& Nod13Indices = (*pi1p3)->Indices();
1729     HLRAlgo_PolyInternalNode::NodeData& Nod13RValues = (*pi1p3)->Data();
1730     const Handle(HLRAlgo_PolyInternalNode)* pi2p3 =
1731       &(((HLRAlgo_Array1OfPINod*)PINod2)->ChangeValue(i2p3));
1732     HLRAlgo_PolyInternalNode::NodeIndices& Nod23Indices = (*pi2p3)->Indices();
1733     HLRAlgo_PolyInternalNode::NodeData& Nod23RValues = (*pi2p3)->Data();
1734     Nod13Indices.Edg1  = e;
1735     Nod13RValues.PCu1  = U3;
1736     Nod13RValues.Scal  = 0;
1737     Nod13Indices.Flag |= NMsk_OutL;
1738     Nod13Indices.Flag |= NMsk_Edge;
1739     Nod23Indices.Edg1  = e;
1740     Nod23RValues.PCu1  = U3;
1741     Nod23RValues.Scal  = 0;
1742     Nod23Indices.Flag |= NMsk_OutL;
1743     Nod23Indices.Flag |= NMsk_Edge;
1744     pid1->UpdateLinks(i1p1,i1p2,i1p3,
1745                       TData1,TData2,PISeg1,PISeg2,PINod1,PINod2);
1746     pid2->UpdateLinks(i2p1,i2p2,i2p3,
1747                       TData2,TData1,PISeg2,PISeg1,PINod2,PINod1);
1748     UpdateAroundNode(i1p3,Nod13Indices,TData1,PISeg1,PINod1);
1749     UpdateAroundNode(i2p3,Nod23Indices,TData2,PISeg2,PINod2);
1750     List.Prepend(HLRAlgo_BiPoint
1751                  (XTI1,YTI1,ZTI1,XTI3,YTI3,ZTI3,
1752                   X1  ,Y1  ,Z1  ,X3  ,Y3  ,Z3  ,   e,
1753                   i1  ,i1p1,i1p3,i2  ,i2p1,i2p3,flag));
1754     List.Prepend(HLRAlgo_BiPoint
1755                  (XTI3,YTI3,ZTI3,XTI2,YTI2,ZTI2,
1756                   X3  ,Y3  ,Z3  ,X2  ,Y2  ,Z2  ,   e,
1757                   i1  ,i1p3,i1p2,i2  ,i2p3,i2p2,flag));
1758   }
1759   else                                             // p1 p2
1760     List.Prepend(HLRAlgo_BiPoint
1761                  (XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1762                   X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,   e,
1763                   i1  ,i1p1,i1p2,i2  ,i2p1,i2p2,flag));
1764 }
1765
1766 //=======================================================================
1767 //function : MoveOrInsertPoint
1768 //purpose  : 
1769 //=======================================================================
1770
1771 void
1772 HLRBRep_PolyAlgo::
1773 MoveOrInsertPoint (HLRAlgo_ListOfBPoint& List,
1774                    Standard_Real& X1,
1775                    Standard_Real& Y1,
1776                    Standard_Real& Z1,
1777                    Standard_Real& X2,
1778                    Standard_Real& Y2,
1779                    Standard_Real& Z2,
1780                    Standard_Real& XTI1,
1781                    Standard_Real& YTI1,
1782                    Standard_Real& ZTI1,
1783                    Standard_Real& XTI2,
1784                    Standard_Real& YTI2,
1785                    Standard_Real& ZTI2,
1786                    const Standard_Integer e,
1787                    Standard_Real& U1,
1788                    Standard_Real& U2,
1789                    HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices,
1790                    HLRAlgo_PolyInternalNode::NodeData& Nod11RValues,
1791                    HLRAlgo_PolyInternalNode::NodeIndices& Nod12Indices,
1792                    HLRAlgo_PolyInternalNode::NodeData& Nod12RValues,
1793                    const Standard_Integer i1p1,
1794                    const Standard_Integer i1p2,
1795                    const Standard_Integer i1,
1796                    const Handle(HLRAlgo_PolyInternalData)& pid1,
1797                    HLRAlgo_Array1OfTData*& TData1,
1798                    HLRAlgo_Array1OfPISeg*& PISeg1,
1799                    HLRAlgo_Array1OfPINod*& PINod1,
1800                    HLRAlgo_PolyInternalNode::NodeIndices& Nod21Indices,
1801                    HLRAlgo_PolyInternalNode::NodeData& Nod21RValues,
1802                    HLRAlgo_PolyInternalNode::NodeIndices& Nod22Indices,
1803                    HLRAlgo_PolyInternalNode::NodeData& Nod22RValues,
1804                    const Standard_Integer i2p1,
1805                    const Standard_Integer i2p2,
1806                    const Standard_Integer i2,
1807                    const Handle(HLRAlgo_PolyInternalData)& pid2,
1808                    HLRAlgo_Array1OfTData*& TData2,
1809                    HLRAlgo_Array1OfPISeg*& PISeg2,
1810                    HLRAlgo_Array1OfPINod*& PINod2,
1811                    const Standard_Real X3,
1812                    const Standard_Real Y3,
1813                    const Standard_Real Z3,
1814                    const Standard_Real XTI3,
1815                    const Standard_Real YTI3,
1816                    const Standard_Real ZTI3,
1817                    const Standard_Real coef3,
1818                    const Standard_Real U3,
1819                    const Standard_Boolean insP3,
1820                    const Standard_Boolean mP3P1,
1821                    const Standard_Real X4,
1822                    const Standard_Real Y4,
1823                    const Standard_Real Z4,
1824                    const Standard_Real XTI4,
1825                    const Standard_Real YTI4,
1826                    const Standard_Real ZTI4,
1827                    const Standard_Real coef4,
1828                    const Standard_Real U4,
1829                    const Standard_Boolean insP4,
1830                    const Standard_Boolean mP4P1,
1831                    const Standard_Integer flag) const
1832 {
1833   Standard_Boolean ins3 = insP3;
1834   Standard_Boolean ins4 = insP4;
1835   if (ins3 && mP3P1) {                             // P1 ---> P3
1836     if (!(Nod11Indices.Flag & NMsk_Vert) && coef3 < myTolSta) {
1837       ins3 = Standard_False;
1838       ChangeNode(i1p1,i1p2,
1839                  Nod11Indices,Nod11RValues,
1840                  Nod12Indices,Nod12RValues,
1841                  coef3,X3,Y3,Z3,Standard_True,
1842                  TData1,PISeg1,PINod1);
1843       ChangeNode(i2p1,i2p2,
1844                  Nod21Indices,Nod21RValues,
1845                  Nod22Indices,Nod22RValues,
1846                  coef3,X3,Y3,Z3,Standard_True,
1847                  TData2,PISeg2,PINod2);
1848       X1   = X3;
1849       Y1   = Y3;
1850       Z1   = Z3;
1851       XTI1 = XTI3;
1852       YTI1 = YTI3;
1853       ZTI1 = ZTI3;
1854       U1   = U3;
1855       Nod11RValues.Point = gp_XYZ(X3, Y3, Z3);
1856       if      (Nod11Indices.Edg1 == e) Nod11RValues.PCu1 = U3;
1857       else if (Nod11Indices.Edg2 == e) Nod11RValues.PCu2 = U3;
1858 #ifdef OCCT_DEBUG
1859       else {
1860         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1861         std::cout << "Parameter error on Node " << i1p1 << std::endl;
1862       }
1863 #endif
1864       Nod11RValues.Scal  = 0;
1865       Nod11Indices.Flag |= NMsk_OutL;
1866       UpdateAroundNode(i1p1,Nod11Indices,TData1,PISeg1,PINod1);
1867       Nod21RValues.Point = gp_XYZ(X3, Y3, Z3);
1868       if      (Nod21Indices.Edg1 == e) Nod21RValues.PCu1 = U3;
1869       else if (Nod21Indices.Edg2 == e) Nod21RValues.PCu2 = U3;
1870 #ifdef OCCT_DEBUG
1871       else {
1872         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1873         std::cout << "Parameter error on Node " << i2p1 << std::endl;
1874       }
1875 #endif
1876       Nod21RValues.Scal  = 0;
1877       Nod21Indices.Flag |= NMsk_OutL;
1878       UpdateAroundNode(i2p1,Nod21Indices,TData2,PISeg2,PINod2);
1879       HLRAlgo_BiPoint::PointsT& aPoints = List.First().Points();
1880       aPoints.PntP2 = gp_XYZ(X3, Y3, Z3);
1881       aPoints.Pnt2 = gp_XYZ(XTI3, YTI3, ZTI3);
1882     }
1883   }
1884   if (ins4 && !mP4P1) {                            // P2 ---> P4
1885     if (!(Nod12Indices.Flag & NMsk_Vert) && coef4 > myTolEnd) {
1886       ins4 = Standard_False;
1887       ChangeNode(i2p1,i2p2,
1888                  Nod21Indices,Nod21RValues,
1889                  Nod22Indices,Nod22RValues,
1890                  coef4,X4,Y4,Z4,Standard_False,
1891                  TData2,PISeg2,PINod2);
1892       ChangeNode(i1p1,i1p2,
1893                  Nod11Indices,Nod11RValues,
1894                  Nod12Indices,Nod12RValues,
1895                  coef4,X4,Y4,Z4,Standard_False,
1896                  TData1,PISeg1,PINod1);
1897       X2   = X4;
1898       Y2   = Y4;
1899       Z2   = Z4;
1900       XTI2 = XTI4;
1901       YTI2 = YTI4;
1902       ZTI2 = ZTI4;
1903       U2   = U4;
1904       Nod12RValues.Point = gp_XYZ(X4, Y4, Z4);
1905       if      (Nod12Indices.Edg1 == e) Nod12RValues.PCu1 = U4;
1906       else if (Nod12Indices.Edg2 == e) Nod12RValues.PCu2 = U4;
1907 #ifdef OCCT_DEBUG
1908       else {
1909         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1910         std::cout << "Parameter error on Node " << i1p2 << std::endl;
1911       }
1912 #endif
1913       Nod12RValues.Scal  = 0;
1914       Nod12Indices.Flag |= NMsk_OutL;
1915       UpdateAroundNode(i1p2,Nod12Indices,TData1,PISeg1,PINod1);
1916       Nod22RValues.Point = gp_XYZ(X4, Y4, Z4);
1917       if      (Nod22Indices.Edg1 == e) Nod22RValues.PCu1 = U4;
1918       else if (Nod22Indices.Edg2 == e) Nod22RValues.PCu2 = U4;
1919 #ifdef OCCT_DEBUG
1920       else {
1921         std::cout << " HLRBRep_PolyAlgo::MoveOrInsertPoint : ";
1922         std::cout << "Parameter error on Node " << i2p2 << std::endl;
1923       }
1924 #endif
1925       Nod22RValues.Scal  = 0;
1926       Nod22Indices.Flag |= NMsk_OutL;
1927       UpdateAroundNode(i2p2,Nod22Indices,TData2,PISeg2,PINod2);
1928     }
1929   }
1930   if (ins3 || ins4) {
1931     if      (!ins4)                                // p1 i1p3 p2
1932       MoveOrInsertPoint(List,
1933                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1934                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1935                         e,U1,U2,
1936                         Nod11Indices,Nod11RValues,
1937                         Nod12Indices,Nod12RValues,
1938                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1939                         Nod21Indices,Nod21RValues,
1940                         Nod22Indices,Nod22RValues,
1941                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1942                         X3,Y3,Z3,XTI3,YTI3,ZTI3,coef3,U3,insP3,mP3P1,flag);
1943     else if (!ins3)                                // p1 i2p4 p2
1944       MoveOrInsertPoint(List,
1945                         X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
1946                         XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
1947                         e,U1,U2,
1948                         Nod21Indices,Nod21RValues,
1949                         Nod22Indices,Nod22RValues,
1950                         i2p1,i2p2,i2,pid2,TData2,PISeg2,PINod2,
1951                         Nod11Indices,Nod11RValues,
1952                         Nod12Indices,Nod12RValues,
1953                         i1p1,i1p2,i1,pid1,TData1,PISeg1,PINod1,
1954                         X4,Y4,Z4,XTI4,YTI4,ZTI4,coef4,U4,insP4,mP4P1,flag);
1955     else {                                         // p1 i1p3 i2p4 p2
1956       Standard_Integer i1p3 = pid1->AddNode
1957         (Nod11RValues,Nod12RValues,PINod1,PINod2,coef3,X3,Y3,Z3);
1958       Standard_Integer i2p3 = pid2->AddNode
1959         (Nod21RValues,Nod22RValues,PINod2,PINod1,coef3,X3,Y3,Z3);
1960       Standard_Integer i1p4 = pid1->AddNode
1961         (Nod11RValues,Nod12RValues,PINod1,PINod2,coef4,X4,Y4,Z4);
1962       Standard_Integer i2p4 = pid2->AddNode
1963         (Nod21RValues,Nod22RValues,PINod2,PINod1,coef4,X4,Y4,Z4);
1964       const Handle(HLRAlgo_PolyInternalNode)* pi1p3 =
1965         &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(i1p3));
1966       HLRAlgo_PolyInternalNode::NodeIndices& Nod13Indices = (*pi1p3)->Indices();
1967       HLRAlgo_PolyInternalNode::NodeData& Nod13RValues = (*pi1p3)->Data();
1968       const Handle(HLRAlgo_PolyInternalNode)* pi1p4 =
1969         &(((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(i1p4));
1970       HLRAlgo_PolyInternalNode::NodeIndices& Nod14Indices = (*pi1p4)->Indices();
1971       HLRAlgo_PolyInternalNode::NodeData& Nod14RValues = (*pi1p4)->Data();
1972       const Handle(HLRAlgo_PolyInternalNode)* pi2p3 =
1973         &(((HLRAlgo_Array1OfPINod*)PINod2)->ChangeValue(i2p3));
1974       HLRAlgo_PolyInternalNode::NodeIndices& Nod23Indices = (*pi2p3)->Indices();
1975       HLRAlgo_PolyInternalNode::NodeData& Nod23RValues = (*pi2p3)->Data();
1976       const Handle(HLRAlgo_PolyInternalNode)* pi2p4 = 
1977         &(((HLRAlgo_Array1OfPINod*)PINod2)->ChangeValue(i2p4));
1978       HLRAlgo_PolyInternalNode::NodeIndices& Nod24Indices = (*pi2p4)->Indices();
1979       HLRAlgo_PolyInternalNode::NodeData& Nod24RValues = (*pi2p4)->Data();
1980       Nod13Indices.Edg1  = e;
1981       Nod13RValues.PCu1  = U3;
1982       Nod13RValues.Scal  = 0;
1983       Nod13Indices.Flag |= NMsk_OutL;
1984       Nod13Indices.Flag |= NMsk_Edge;
1985       Nod23Indices.Edg1  = e;
1986       Nod23RValues.PCu1  = U3;
1987       Nod23RValues.Scal  = 0;
1988       Nod23Indices.Flag |= NMsk_OutL;
1989       Nod23Indices.Flag |= NMsk_Edge;
1990       Nod14Indices.Edg1  = e;
1991       Nod14RValues.PCu1  = U4;
1992       Nod14RValues.Scal  = 0;
1993       Nod14Indices.Flag |= NMsk_OutL;
1994       Nod14Indices.Flag |= NMsk_Edge;
1995       Nod24Indices.Edg1  = e;
1996       Nod24RValues.PCu1  = U4;
1997       Nod24RValues.Scal  = 0;
1998       Nod24Indices.Flag |= NMsk_OutL;
1999       Nod24Indices.Flag |= NMsk_Edge;
2000       pid1->UpdateLinks(i1p1,i1p2,i1p3,
2001                         TData1,TData2,PISeg1,PISeg2,PINod1,PINod2);
2002       pid2->UpdateLinks(i2p1,i2p2,i2p3,
2003                         TData2,TData1,PISeg2,PISeg1,PINod2,PINod1);
2004       pid2->UpdateLinks(i2p3,i2p2,i2p4,
2005                         TData2,TData1,PISeg2,PISeg1,PINod2,PINod1);
2006       pid1->UpdateLinks(i1p3,i1p2,i1p4,
2007                         TData1,TData2,PISeg1,PISeg2,PINod1,PINod2);
2008       UpdateAroundNode(i1p3,Nod13Indices,TData1,PISeg1,PINod1);
2009       UpdateAroundNode(i2p3,Nod23Indices,TData2,PISeg2,PINod2);
2010       UpdateAroundNode(i1p4,Nod14Indices,TData1,PISeg1,PINod1);
2011       UpdateAroundNode(i2p4,Nod24Indices,TData2,PISeg2,PINod2);
2012       List.Prepend(HLRAlgo_BiPoint
2013                    (XTI1,YTI1,ZTI1,XTI3,YTI3,ZTI3,
2014                     X1  ,Y1  ,Z1  ,X3  ,Y3  ,Z3  ,   e,
2015                     i1  ,i1p1,i1p3,i2  ,i2p1,i2p3,flag));
2016       List.Prepend(HLRAlgo_BiPoint
2017                    (XTI3,YTI3,ZTI3,XTI4,YTI4,ZTI4,
2018                     X3  ,Y3  ,Z3  ,X4  ,Y4  ,Z4  ,   e,
2019                     i1  ,i1p3,i1p4,i2  ,i2p3,i2p4,flag));
2020       List.Prepend(HLRAlgo_BiPoint
2021                    (XTI4,YTI4,ZTI4,XTI2,YTI2,ZTI2,
2022                     X4  ,Y4  ,Z4  ,X2  ,Y2  ,Z2  ,   e,
2023                     i1  ,i1p4,i1p2,i2  ,i2p4,i2p2,flag));
2024     }
2025   }
2026   else                                             // p1 p2
2027     List.Prepend(HLRAlgo_BiPoint
2028                  (XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
2029                   X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,   e,
2030                   i1  ,i1p1,i1p2,i2  ,i2p1,i2p2,flag));
2031 }
2032
2033 //=======================================================================
2034 //function : InsertOnOutLine
2035 //purpose  : 
2036 //=======================================================================
2037
2038 void
2039 HLRBRep_PolyAlgo::InsertOnOutLine (TColStd_Array1OfTransient& PID)
2040 {
2041   HLRAlgo_Array1OfTData* TData2 = 0;
2042   HLRAlgo_Array1OfPISeg* PISeg2 = 0;
2043   HLRAlgo_Array1OfPINod* PINod2 = 0;
2044   Handle(HLRAlgo_PolyInternalData)* pid = 
2045     (Handle(HLRAlgo_PolyInternalData)*) (&(PID.ChangeValue(1)));
2046
2047   TopLoc_Location L;
2048   Standard_Boolean insP3,mP3P1,IntOutL;
2049   Standard_Integer f,ip1,ip2,ip3;//, i;
2050   Standard_Real U3,V3,coef3,X3 = 0.,Y3 = 0.,Z3 = 0.;
2051
2052   const gp_Trsf& T  = myProj.Transformation();
2053   
2054   Standard_Integer nbFace = myFMap.Extent();
2055   for (f = 1; f <= nbFace; f++) {
2056
2057     if (!((*pid).IsNull())) {
2058       IntOutL = Standard_False;
2059       HLRAlgo_Array1OfTData* TData1= &((*pid)->TData());
2060       HLRAlgo_Array1OfPISeg* PISeg1= &(*pid)->PISeg();
2061       HLRAlgo_Array1OfPINod* PINod1= &((*pid)->PINod());
2062       TopoDS_Shape LocalShape = myFMap(f);
2063       const TopoDS_Face& F = TopoDS::Face(LocalShape);
2064       myBSurf.Initialize(F,Standard_False);
2065       myGSurf = BRep_Tool::Surface(F,L);
2066       gp_Trsf TT = L.Transformation();
2067       TT.PreMultiply(T);
2068       const gp_XYZ& ttlo = TT.TranslationPart();
2069       TTLo[0] = ttlo.X();
2070       TTLo[1] = ttlo.Y();
2071       TTLo[2] = ttlo.Z();
2072       const gp_Mat& ttma = TT.VectorialPart();
2073       TTMa[0][0] = ttma.Value(1,1);
2074       TTMa[0][1] = ttma.Value(1,2);
2075       TTMa[0][2] = ttma.Value(1,3);
2076       TTMa[1][0] = ttma.Value(2,1);
2077       TTMa[1][1] = ttma.Value(2,2);
2078       TTMa[1][2] = ttma.Value(2,3);
2079       TTMa[2][0] = ttma.Value(3,1);
2080       TTMa[2][1] = ttma.Value(3,2);
2081       TTMa[2][2] = ttma.Value(3,3);
2082
2083 #ifdef OCCT_DEBUG
2084       if (DoTrace) {
2085         std::cout << " InsertOnOutLine : NbTData " << (*pid)->NbTData() << std::endl;
2086         std::cout << " InsertOnOutLine : NbPISeg " << (*pid)->NbPISeg() << std::endl;
2087         std::cout << " InsertOnOutLine : NbPINod " << (*pid)->NbPINod() << std::endl;
2088       }
2089 #endif
2090
2091       Standard_Integer iseg,nbS;
2092       nbS = (*pid)->NbPISeg();
2093       for (iseg = 1; iseg <= nbS; iseg++) {
2094         HLRAlgo_PolyInternalSegment& aSegIndices = PISeg1->ChangeValue(iseg);
2095 //      Standard_Boolean Cutted = Standard_False;
2096         if (aSegIndices.Conex1 != 0 && aSegIndices.Conex2 != 0) {
2097           ip1 = aSegIndices.LstSg1;
2098           ip2 = aSegIndices.LstSg2;
2099           const Handle(HLRAlgo_PolyInternalNode)* pip1 = &PINod1->ChangeValue(ip1);
2100           HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices = (*pip1)->Indices();
2101           HLRAlgo_PolyInternalNode::NodeData& Nod1RValues = (*pip1)->Data();
2102           const Handle(HLRAlgo_PolyInternalNode)* pip2 = &PINod1->ChangeValue(ip2);
2103           HLRAlgo_PolyInternalNode::NodeIndices& Nod2Indices = (*pip2)->Indices();
2104           HLRAlgo_PolyInternalNode::NodeData& Nod2RValues = (*pip2)->Data();
2105           if (Nod1Indices.Flag & NMsk_OutL && Nod2Indices.Flag & NMsk_OutL)
2106             IntOutL = Standard_True;
2107           else if ((Nod1RValues.Scal >=  myTolAngular &&
2108                     Nod2RValues.Scal <= -myTolAngular) ||
2109                    (Nod2RValues.Scal >=  myTolAngular &&
2110                     Nod1RValues.Scal <= -myTolAngular)) {
2111             IntOutL = Standard_True;
2112             insP3 = NewNode(Nod1RValues,Nod2RValues,coef3,mP3P1);
2113             if (insP3) {
2114               UVNode(Nod1RValues,Nod2RValues,coef3,U3,V3);
2115               const gp_Pnt& PT3 = myGSurf->Value(U3,V3);
2116               X3 = PT3.X();
2117               Y3 = PT3.Y();
2118               Z3 = PT3.Z();
2119               TTMultiply(X3,Y3,Z3);
2120             }
2121             
2122             if (insP3 && mP3P1) {                        // P1 ---> P3
2123               if ((Nod1Indices.Flag & NMsk_Edge) == 0 && coef3 < myTolSta) {
2124                 insP3 = Standard_False;
2125                 ChangeNode(ip1,ip2,
2126                            Nod1Indices,Nod1RValues,
2127                            Nod2Indices,Nod2RValues,
2128                            coef3,X3,Y3,Z3,Standard_True,
2129                            TData1,PISeg1,PINod1);
2130                 Nod1RValues.Scal  = 0;
2131                 Nod1Indices.Flag |= NMsk_OutL;
2132               }
2133             }
2134             if (insP3 && !mP3P1) {                       // P2 ---> P3
2135               if ((Nod2Indices.Flag & NMsk_Edge) == 0 && coef3 > myTolEnd) {
2136                 insP3 = Standard_False;
2137                 ChangeNode(ip1,ip2,
2138                            Nod1Indices,Nod1RValues,
2139                            Nod2Indices,Nod2RValues,
2140                            coef3,X3,Y3,Z3,Standard_False,
2141                            TData1,PISeg1,PINod1);
2142                 Nod2RValues.Scal  = 0;
2143                 Nod2Indices.Flag |= NMsk_OutL;
2144               }
2145             }
2146             if (insP3) {                                 // p1 ip3 p2
2147               ip3 = (*pid)->AddNode(Nod1RValues,Nod2RValues,PINod1,PINod2,
2148                                     coef3,X3,Y3,Z3);
2149               const Handle(HLRAlgo_PolyInternalNode)* pip3 =
2150                 (&((HLRAlgo_Array1OfPINod*)PINod1)->ChangeValue(ip3));
2151               HLRAlgo_PolyInternalNode::NodeIndices& Nod3Indices = (*pip3)->Indices();
2152               HLRAlgo_PolyInternalNode::NodeData& Nod3RValues = (*pip3)->Data();
2153               (*pid)->UpdateLinks(ip1,ip2,ip3,
2154                                   TData1,TData2,PISeg1,PISeg2,PINod1,PINod2);
2155               UpdateAroundNode(ip3,Nod3Indices,TData1,PISeg1,PINod1);
2156               Nod3RValues.Scal  = 0;
2157               Nod3Indices.Flag |= NMsk_OutL;
2158             }
2159           }
2160         }
2161       }
2162       if (IntOutL)
2163         (*pid)->IntOutL(Standard_True);
2164
2165       nbS = (*pid)->NbPISeg();
2166
2167 #ifdef OCCT_DEBUG
2168       if (DoTrace) {
2169         std::cout << " InsertOnOutLine : NbTData " << (*pid)->NbTData() << std::endl;
2170         std::cout << " InsertOnOutLine : NbPISeg " << (*pid)->NbPISeg() << std::endl;
2171         std::cout << " InsertOnOutLine : NbPINod " << (*pid)->NbPINod() << std::endl;
2172       }
2173 #endif
2174     }
2175     pid++;
2176   }
2177 }
2178
2179 //=======================================================================
2180 //function : CheckFrBackTriangles
2181 //purpose  : 
2182 //=======================================================================
2183
2184 void
2185 HLRBRep_PolyAlgo::CheckFrBackTriangles (HLRAlgo_ListOfBPoint& List,
2186                                         TColStd_Array1OfTransient& PID)
2187 {
2188   Standard_Integer f,i,nbN,nbT,nbFace;
2189   Standard_Real X1 =0.,Y1 =0.,X2 =0.,Y2 =0.,X3 =0.,Y3 =0.;
2190   Standard_Real D1,D2,D3;
2191   Standard_Real dd,dX,dY,nX,nY;
2192   Standard_Boolean FrBackInList;
2193   HLRAlgo_Array1OfTData* TData;
2194   HLRAlgo_Array1OfPISeg* PISeg;
2195   HLRAlgo_Array1OfPINod* PINod;
2196
2197   //Standard_Address IndexPtr = NULL; 
2198   //const Handle(HLRAlgo_PolyInternalData)& pid1 =
2199   //  *(Handle(HLRAlgo_PolyInternalData)*)&(PID(F1Index));
2200   //Standard_Address TData1 = &pid1->TData(),
2201   //PISeg1 = &pid1->PISeg(),
2202   //PINod1 = &pid1->PINod();
2203
2204   //const Handle(HLRAlgo_PolyInternalData)& pid2 =
2205   //  *(Handle(HLRAlgo_PolyInternalData)*)&(PID(F2Index));
2206   //Standard_Address TData2 = &pid2->TData(),
2207   //PISeg2 = &pid2->PISeg(),
2208   //PINod2 = &pid2->PISeg();
2209
2210   HLRAlgo_Array1OfTData* TData1 = NULL;
2211   HLRAlgo_Array1OfPISeg* PISeg1 = NULL;
2212   HLRAlgo_Array1OfPINod* PINod1 = NULL;
2213   HLRAlgo_Array1OfTData* TData2 = NULL;
2214   HLRAlgo_Array1OfPISeg* PISeg2 = NULL;
2215   HLRAlgo_Array1OfPINod* PINod2 = NULL;
2216   HLRAlgo_PolyInternalNode::NodeIndices* Nod11Indices;
2217   HLRAlgo_PolyInternalNode::NodeIndices* Nod12Indices;
2218   HLRAlgo_PolyInternalNode::NodeIndices* Nod13Indices;
2219   HLRAlgo_PolyInternalNode::NodeData* Nod11RValues;
2220   HLRAlgo_PolyInternalNode::NodeData* Nod12RValues;
2221   HLRAlgo_PolyInternalNode::NodeData* Nod13RValues;
2222
2223   Handle(HLRAlgo_PolyInternalData)* pid;
2224
2225   nbFace = myFMap.Extent();
2226   Standard_Boolean Modif = Standard_True;
2227   Standard_Integer iLoop = 0;
2228   
2229   while (Modif && iLoop < 4) {
2230     iLoop++;
2231     Modif        = Standard_False;
2232     FrBackInList = Standard_False;
2233     pid = (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
2234     
2235     for (f = 1; f <= nbFace; f++) {
2236       if (!(*pid).IsNull()) {
2237         nbT   =  (*pid)->NbTData();
2238         TData = &(*pid)->TData();
2239         PISeg = &(*pid)->PISeg();
2240         PINod = &(*pid)->PINod();
2241         HLRAlgo_TriangleData* tdata = &TData->ChangeValue(1);
2242         
2243         for (i = 1; i <= nbT; i++) {
2244           if ((tdata->Flags & HLRAlgo_PolyMask_FMskSide) == 0 &&
2245               (tdata->Flags & HLRAlgo_PolyMask_FMskFrBack)) {
2246 #ifdef OCCT_DEBUG
2247             if (DoTrace)
2248               std::cout << " face : " << f << " , triangle " << i << std::endl;
2249 #endif
2250             Modif        = Standard_True;
2251             const Handle(HLRAlgo_PolyInternalNode)* pi1p1 =
2252               &PINod->ChangeValue(tdata->Node1);
2253             Nod11Indices = &(*pi1p1)->Indices();
2254             Nod11RValues = &(*pi1p1)->Data();
2255             const Handle(HLRAlgo_PolyInternalNode)* pi1p2 =
2256               &PINod->ChangeValue(tdata->Node2);
2257             Nod12Indices = &(*pi1p2)->Indices();
2258             Nod12RValues = &(*pi1p2)->Data();
2259             const Handle(HLRAlgo_PolyInternalNode)* pi1p3 =
2260         &PINod->ChangeValue(tdata->Node3);
2261             Nod13Indices = &(*pi1p3)->Indices();
2262             Nod13RValues = &(*pi1p3)->Data();
2263             D1 = 0.; D2 = 0.; D3 = 0.;
2264             if (((Nod11Indices->Flag & NMsk_Edge) == 0 || iLoop > 1) &&
2265                 ((Nod11Indices->Flag & NMsk_OutL) == 0 || iLoop > 1) &&
2266                 ((Nod11Indices->Flag & NMsk_Vert) == 0)) {
2267         dX = Nod13RValues->Point.X() - Nod12RValues->Point.X();
2268         dY = Nod13RValues->Point.Y() - Nod12RValues->Point.Y();
2269               D1 = dX * dX + dY * dY;
2270               D1 = sqrt(D1);
2271               nX = - dY / D1; nY =   dX / D1;
2272               dX = Nod11RValues->Point.X() - Nod12RValues->Point.X();
2273         dY = Nod11RValues->Point.Y() - Nod12RValues->Point.Y();
2274               dd = - (dX * nX + dY * nY);
2275               if (dd < 0) dd -= D1 * 0.01;
2276               else        dd += D1 * 0.01;
2277               X1 = nX * dd; Y1 = nY * dd;
2278             }
2279             if (((Nod12Indices->Flag & NMsk_Edge) == 0 || iLoop > 1) &&
2280                 ((Nod12Indices->Flag & NMsk_OutL) == 0 || iLoop > 1) &&
2281                 ((Nod12Indices->Flag & NMsk_Vert) == 0)) {
2282         dX = Nod11RValues->Point.X() - Nod13RValues->Point.X();
2283         dY = Nod11RValues->Point.Y() - Nod13RValues->Point.Y();
2284               D2 = dX * dX + dY * dY;
2285               D2 = sqrt(D2);
2286               nX = - dY / D2; nY =   dX / D2;
2287         dX = Nod12RValues->Point.X() - Nod13RValues->Point.X();
2288         dY = Nod12RValues->Point.Y() - Nod13RValues->Point.Y();
2289               dd = - (dX * nX + dY * nY);
2290               if (dd < 0) dd -= D2 * 0.01;
2291               else        dd += D2 * 0.01;
2292               X2 = nX * dd; Y2 = nY * dd;
2293             }
2294             if (((Nod13Indices->Flag & NMsk_Edge) == 0 || iLoop > 1) &&
2295                 ((Nod13Indices->Flag & NMsk_OutL) == 0 || iLoop > 1) &&
2296                 ((Nod13Indices->Flag & NMsk_Vert) == 0)) {
2297         dX = Nod12RValues->Point.X() - Nod11RValues->Point.X();
2298         dY = Nod12RValues->Point.Y() - Nod11RValues->Point.Y();
2299               D3 = dX * dX + dY * dY;
2300               D3 = sqrt(D3);
2301               nX = - dY / D3; nY =   dX / D3;
2302         dX = Nod13RValues->Point.X() - Nod11RValues->Point.X();
2303         dY = Nod13RValues->Point.Y() - Nod11RValues->Point.Y();
2304               dd = - (dX * nX + dY * nY);
2305               if (dd < 0) dd -= D3 * 0.01;
2306               else        dd += D3 * 0.01;
2307               X3 = nX * dd; Y3 = nY * dd;
2308             }
2309             if      (D1 > D2 && D1 > D3) {
2310         Nod11RValues->Point.ChangeCoord(1) += X1;
2311         Nod11RValues->Point.ChangeCoord(2) += Y1;
2312               Nod11Indices->Flag |= NMsk_Move;
2313               UpdateAroundNode(tdata->Node1,*Nod11Indices,TData,PISeg,PINod);
2314               FrBackInList = Standard_True;
2315 #ifdef OCCT_DEBUG
2316               if (DoTrace) {
2317                 std::cout << tdata->Node1 << " modifies  : DX,DY ";
2318                 std::cout << X1 << " , " << Y1 << std::endl;
2319               }
2320 #endif
2321             }
2322             else if (D2 > D3 && D2 > D1) {
2323         Nod12RValues->Point.ChangeCoord(1) += X2;
2324         Nod12RValues->Point.ChangeCoord(2) += Y2;
2325               Nod12Indices->Flag |= NMsk_Move;
2326               UpdateAroundNode(tdata->Node2,*Nod12Indices,TData,PISeg,PINod);
2327               FrBackInList = Standard_True;
2328 #ifdef OCCT_DEBUG
2329               if (DoTrace) {
2330                 std::cout << tdata->Node2 << " modifies  : DX,DY ";
2331                 std::cout << X2 << " , " << Y2 << std::endl;
2332               }
2333 #endif
2334             }
2335             else if (D3 > D1 && D3 > D2) {
2336         Nod13RValues->Point.ChangeCoord(1) += X3;
2337         Nod13RValues->Point.ChangeCoord(2) += Y3;
2338               Nod13Indices->Flag |= NMsk_Move;
2339               UpdateAroundNode(tdata->Node3,*Nod13Indices,TData,PISeg,PINod);
2340               FrBackInList = Standard_True;
2341 #ifdef OCCT_DEBUG
2342               if (DoTrace) {
2343                 std::cout << tdata->Node3 << " modifies  : DX,DY ";
2344                 std::cout << X3 << " , " << Y3 << std::endl;
2345               }
2346 #endif
2347             }
2348 #ifdef OCCT_DEBUG
2349             else if (DoTrace)
2350               std::cout << "modification error" << std::endl;
2351 #endif
2352           }
2353           tdata++;
2354         }
2355       }
2356       pid++;
2357     }
2358     if (FrBackInList) {
2359       HLRAlgo_ListIteratorOfListOfBPoint it;
2360       
2361       for (it.Initialize(List); it.More(); it.Next()) {      
2362         HLRAlgo_BiPoint& BP = it.Value();
2363         HLRAlgo_BiPoint::IndicesT& theIndices = BP.Indices();
2364         if (theIndices.FaceConex1 != 0) {
2365           const Handle(HLRAlgo_PolyInternalData)& pid1 =
2366             *(Handle(HLRAlgo_PolyInternalData)*)&(PID(theIndices.FaceConex1));
2367           TData1 = &pid1->TData();
2368           PISeg1 = &pid1->PISeg();
2369           PINod1 = &pid1->PINod();
2370         }
2371         if (theIndices.FaceConex2 != 0) {
2372           if (theIndices.FaceConex1 == theIndices.FaceConex2) {
2373             TData2 = TData1;
2374             PISeg2 = PISeg1;
2375             PINod2 = PINod1;
2376           }
2377           else {
2378             const Handle(HLRAlgo_PolyInternalData)& pid2 =
2379               *(Handle(HLRAlgo_PolyInternalData)*)&(PID(theIndices.FaceConex2));
2380             TData2 = &pid2->TData();
2381             PISeg2 = &pid2->PISeg();
2382             PINod2 = &pid2->PINod();
2383           }
2384         }
2385         if (theIndices.FaceConex1 != 0) {
2386           Nod11Indices = &PINod1->ChangeValue(theIndices.Face1Pt1)->Indices();
2387           if (Nod11Indices->Flag & NMsk_Move) {
2388 #ifdef OCCT_DEBUG
2389             if (DoTrace)
2390               std::cout << theIndices.Face1Pt1 << " modifies 11" << std::endl;
2391 #endif
2392             Nod11RValues = &PINod1->ChangeValue(theIndices.Face1Pt1)->Data();
2393             HLRAlgo_BiPoint::PointsT& aPoints = BP.Points();
2394       aPoints.Pnt1 = aPoints.PntP1 = Nod11RValues->Point;
2395             TIMultiply(aPoints.Pnt1);
2396             if (theIndices.FaceConex2 != 0) {
2397               Nod12Indices = &PINod2->ChangeValue(theIndices.Face2Pt1)->Indices();
2398               Nod12RValues = &PINod2->ChangeValue(theIndices.Face2Pt1)->Data();
2399         Nod12RValues->Point.ChangeCoord(1) = Nod11RValues->Point.X();
2400         Nod12RValues->Point.ChangeCoord(2) = Nod11RValues->Point.Y();
2401               UpdateAroundNode(theIndices.Face2Pt1,*Nod12Indices,
2402                                TData2,PISeg2,PINod2);
2403             }
2404           }
2405           Nod11Indices = &PINod1->ChangeValue(theIndices.Face1Pt2)->Indices();
2406           if (Nod11Indices->Flag & NMsk_Move) {
2407 #ifdef OCCT_DEBUG
2408             if (DoTrace)
2409               std::cout << theIndices.Face1Pt2 << " modifies 12" << std::endl;
2410 #endif
2411             Nod11RValues = &PINod1->ChangeValue(theIndices.Face1Pt2)->Data();
2412             HLRAlgo_BiPoint::PointsT& aPoints = BP.Points();
2413             aPoints.Pnt2 = aPoints.PntP2 = Nod11RValues->Point;
2414             TIMultiply(aPoints.Pnt2);
2415             if (theIndices.FaceConex2 != 0) {
2416               Nod12Indices = &PINod2->ChangeValue(theIndices.Face2Pt2)->Indices();
2417               Nod12RValues = &PINod2->ChangeValue(theIndices.Face2Pt2)->Data();
2418         Nod12RValues->Point.ChangeCoord(1) = Nod11RValues->Point.X();
2419         Nod12RValues->Point.ChangeCoord(2) = Nod11RValues->Point.Y();
2420               UpdateAroundNode(theIndices.Face2Pt2,*Nod12Indices,
2421                                TData2,PISeg2,PINod2);
2422             }
2423           }
2424         }
2425         if (theIndices.FaceConex2 != 0) {
2426           const Handle(HLRAlgo_PolyInternalData)& pid2 =
2427             *(Handle(HLRAlgo_PolyInternalData)*)&(PID(theIndices.FaceConex2));
2428           PINod2 = &pid2->PINod();
2429           Nod11Indices = &PINod2->ChangeValue(theIndices.Face2Pt1)->Indices();
2430           if (Nod11Indices->Flag & NMsk_Move) {
2431 #ifdef OCCT_DEBUG
2432             if (DoTrace)
2433               std::cout << theIndices.Face2Pt1 << " modifies 21" << std::endl;
2434 #endif
2435             Nod11RValues = &PINod2->ChangeValue(theIndices.Face2Pt1)->Data();
2436             HLRAlgo_BiPoint::PointsT& aPoints = BP.Points();
2437       aPoints.Pnt1 = aPoints.PntP1 = Nod11RValues->Point;
2438             TIMultiply(aPoints.Pnt1);
2439             if (theIndices.FaceConex1 != 0) {
2440               Nod12Indices = &PINod1->ChangeValue(theIndices.Face1Pt1)->Indices();
2441               Nod12RValues = &PINod1->ChangeValue(theIndices.Face1Pt1)->Data();
2442         Nod12RValues->Point.ChangeCoord(1) = Nod11RValues->Point.X();
2443         Nod12RValues->Point.ChangeCoord(2) = Nod11RValues->Point.Y();
2444               UpdateAroundNode(theIndices.Face1Pt1,*Nod12Indices,
2445                                TData1,PISeg1,PINod1);
2446             }
2447           }
2448           Nod11Indices = &PINod2->ChangeValue(theIndices.Face2Pt2)->Indices();
2449           if (Nod11Indices->Flag & NMsk_Move) {
2450 #ifdef OCCT_DEBUG
2451             if (DoTrace)
2452               std::cout << theIndices.Face2Pt2 << " modifies 22" << std::endl;
2453 #endif
2454             Nod11RValues = &PINod2->ChangeValue(theIndices.Face2Pt2)->Data();
2455             HLRAlgo_BiPoint::PointsT& aPoints = BP.Points();
2456       aPoints.Pnt2 = aPoints.PntP2 = Nod11RValues->Point;
2457             TIMultiply(aPoints.Pnt2);
2458             if (theIndices.FaceConex1 != 0) {
2459               Nod12Indices = &PINod1->ChangeValue(theIndices.Face1Pt2)->Indices();
2460               Nod12RValues = &PINod1->ChangeValue(theIndices.Face1Pt2)->Data();
2461         Nod12RValues->Point.ChangeCoord(1) = Nod11RValues->Point.X();
2462         Nod12RValues->Point.ChangeCoord(2) = Nod11RValues->Point.Y();
2463               UpdateAroundNode(theIndices.Face1Pt2,*Nod12Indices,
2464                                TData1,PISeg1,PINod1);
2465             }
2466           }
2467         }
2468       }
2469       pid = (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
2470       
2471       for (f = 1; f <= nbFace; f++) {
2472         if (!(*pid).IsNull()) {
2473           nbN   =  (*pid)->NbPINod();
2474           PINod = &(*pid)->PINod();
2475
2476     for (i = 1; i <= nbN; i++)
2477     {
2478       Nod11Indices = &PINod->ChangeValue(i)->Indices();
2479             Nod11Indices->Flag   &= ~NMsk_Move;
2480           }
2481         }
2482         pid++;
2483       }
2484     }
2485   }
2486 }
2487
2488 //=======================================================================
2489 //function : FindEdgeOnTriangle
2490 //purpose  : 
2491 //=======================================================================
2492
2493 void
2494 HLRBRep_PolyAlgo::
2495 FindEdgeOnTriangle (const HLRAlgo_TriangleData& theTriangle,
2496                     const Standard_Integer ip1,
2497                     const Standard_Integer ip2,
2498                     Standard_Integer& jtrouv,
2499                     Standard_Boolean& isDirect) const
2500 {
2501   Standard_Integer n1 = theTriangle.Node1;
2502   Standard_Integer n2 = theTriangle.Node2;
2503   Standard_Integer n3 = theTriangle.Node3;
2504   if      (ip1 == n1 && ip2 == n2) {
2505     jtrouv = 0;
2506     isDirect = Standard_True;
2507     return;
2508   }
2509   else if (ip2 == n1 && ip1 == n2) {
2510     jtrouv = 0;
2511     isDirect = Standard_False;
2512     return;
2513   }
2514   else if (ip1 == n2 && ip2 == n3) {
2515     jtrouv = 1;
2516     isDirect = Standard_True;
2517     return;
2518   }
2519   else if (ip2 == n2 && ip1 == n3) {
2520     jtrouv = 1;
2521     isDirect = Standard_False;
2522     return;
2523   }
2524   else if (ip1 == n3 && ip2 == n1) {
2525     jtrouv = 2;
2526     isDirect = Standard_True;
2527     return;
2528   }
2529   else if (ip2 == n3 && ip1 == n1) {
2530     jtrouv = 2;
2531     isDirect = Standard_False;
2532     return;
2533   }
2534 }
2535
2536 //=======================================================================
2537 //function : ChangeNode
2538 //purpose  : 
2539 //=======================================================================
2540
2541 void HLRBRep_PolyAlgo::ChangeNode (const Standard_Integer ip1,
2542                                    const Standard_Integer ip2,
2543                                    HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices,
2544                                    HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
2545                                    HLRAlgo_PolyInternalNode::NodeIndices& Nod2Indices,
2546                                    HLRAlgo_PolyInternalNode::NodeData& Nod2RValues,
2547                                    const Standard_Real coef1,
2548                                    const Standard_Real X3,
2549                                    const Standard_Real Y3,
2550                                    const Standard_Real Z3,
2551                                    const Standard_Boolean first,
2552                                    HLRAlgo_Array1OfTData*& TData,
2553                                    HLRAlgo_Array1OfPISeg*& PISeg,
2554                                    HLRAlgo_Array1OfPINod*& PINod) const
2555 {
2556   Standard_Real coef2 = 1 - coef1;
2557   if (first) {
2558     Nod1RValues.Point = gp_XYZ(X3, Y3, Z3);
2559     Nod1RValues.UV = coef2 * Nod1RValues.UV + coef1 * Nod2RValues.UV;
2560     Nod1RValues.Scal = Nod1RValues.Scal * coef2 + Nod2RValues.Scal * coef1;
2561     const gp_XYZ aXYZ = coef2 * Nod1RValues.Normal + coef1 * Nod2RValues.Normal;
2562     const Standard_Real aNorm = aXYZ.Modulus();
2563     if (aNorm > 0) {
2564       Nod1RValues.Normal = (1 / aNorm) * aXYZ;
2565     }
2566     else {
2567       Nod1RValues.Normal = gp_XYZ(1., 0., 0.);
2568 #ifdef OCCT_DEBUG
2569       if (DoError) {
2570         std::cout << "HLRBRep_PolyAlgo::ChangeNode between " << ip1;
2571         std::cout << " and " << ip2 << std::endl;
2572       }
2573 #endif
2574     }
2575     UpdateAroundNode(ip1,Nod1Indices,TData,PISeg,PINod);
2576   }
2577   else {
2578     Nod2RValues.Point = gp_XYZ(X3, Y3, Z3);
2579     Nod2RValues.UV = coef2 * Nod1RValues.UV + coef1 * Nod2RValues.UV;
2580     Nod2RValues.Scal = Nod1RValues.Scal * coef2 + Nod2RValues.Scal * coef1;
2581     const gp_XYZ aXYZ = coef2 * Nod1RValues.Normal + coef1 * Nod2RValues.Normal;
2582     const Standard_Real aNorm = aXYZ.Modulus();
2583     if (aNorm > 0) {
2584       Nod2RValues.Normal = (1 / aNorm) * aXYZ;
2585     }
2586     else {
2587       Nod2RValues.Normal = gp_XYZ(1., 0., 0.);
2588 #ifdef OCCT_DEBUG
2589       if (DoError) {
2590         std::cout << "HLRBRep_PolyAlgo::ChangeNode between " << ip2;
2591         std::cout << " and " << ip1 << std::endl;
2592       }
2593 #endif
2594     }
2595     UpdateAroundNode(ip2,Nod2Indices,TData,PISeg,PINod);
2596   }
2597 }
2598
2599 //=======================================================================
2600 //function : UpdateAroundNode
2601 //purpose  : 
2602 //=======================================================================
2603
2604 void HLRBRep_PolyAlgo::
2605 UpdateAroundNode (const Standard_Integer iNode,
2606                   HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices,
2607       HLRAlgo_Array1OfTData* TData,
2608       HLRAlgo_Array1OfPISeg* PISeg,
2609       HLRAlgo_Array1OfPINod* PINod) const
2610 {
2611   Standard_Integer iiii,iTri1,iTri2;
2612   iiii = Nod1Indices.NdSg;
2613   
2614   while (iiii != 0) {
2615     HLRAlgo_PolyInternalSegment& aSegIndices = PISeg->ChangeValue(iiii);
2616     iTri1 = aSegIndices.Conex1;
2617     iTri2 = aSegIndices.Conex2;
2618     if ( iTri1 != 0) {
2619       HLRAlgo_TriangleData& aTriangle = TData->ChangeValue(iTri1);
2620       const Handle(HLRAlgo_PolyInternalNode)* PN1 = 
2621         &PINod->ChangeValue(aTriangle.Node1);
2622       const Handle(HLRAlgo_PolyInternalNode)* PN2 = 
2623         &PINod->ChangeValue(aTriangle.Node2);
2624       const Handle(HLRAlgo_PolyInternalNode)* PN3 = 
2625         &PINod->ChangeValue(aTriangle.Node3);
2626       HLRAlgo_PolyInternalNode::NodeIndices& aNod1Indices = (*PN1)->Indices();
2627       HLRAlgo_PolyInternalNode::NodeIndices& aNod2Indices = (*PN2)->Indices();
2628       HLRAlgo_PolyInternalNode::NodeIndices& aNod3Indices = (*PN3)->Indices();
2629       HLRAlgo_PolyInternalNode::NodeData& aNod1RValues = (*PN1)->Data();
2630       HLRAlgo_PolyInternalNode::NodeData& aNod2RValues = (*PN2)->Data();
2631       HLRAlgo_PolyInternalNode::NodeData& aNod3RValues = (*PN3)->Data();
2632       OrientTriangle(iTri1,aTriangle,
2633                      aNod1Indices,aNod1RValues,
2634                      aNod2Indices,aNod2RValues,
2635                      aNod3Indices,aNod3RValues);
2636     }
2637     if ( iTri2 != 0) {
2638       HLRAlgo_TriangleData& aTriangle2 = TData->ChangeValue(iTri2);
2639       const Handle(HLRAlgo_PolyInternalNode)* PN1 = 
2640         &PINod->ChangeValue(aTriangle2.Node1);
2641       const Handle(HLRAlgo_PolyInternalNode)* PN2 = 
2642         &PINod->ChangeValue(aTriangle2.Node2);
2643       const Handle(HLRAlgo_PolyInternalNode)* PN3 = 
2644         &PINod->ChangeValue(aTriangle2.Node3);
2645       HLRAlgo_PolyInternalNode::NodeIndices& aNod1Indices = (*PN1)->Indices();
2646       HLRAlgo_PolyInternalNode::NodeIndices& aNod2Indices = (*PN2)->Indices();
2647       HLRAlgo_PolyInternalNode::NodeIndices& aNod3Indices = (*PN3)->Indices();
2648       HLRAlgo_PolyInternalNode::NodeData& aNod1RValues = (*PN1)->Data();
2649       HLRAlgo_PolyInternalNode::NodeData& aNod2RValues = (*PN2)->Data();
2650       HLRAlgo_PolyInternalNode::NodeData& aNod3RValues = (*PN3)->Data();
2651       OrientTriangle(iTri2,aTriangle2,
2652                      aNod1Indices,aNod1RValues,
2653                      aNod2Indices,aNod2RValues,
2654                      aNod3Indices,aNod3RValues);
2655     }
2656     if (aSegIndices.LstSg1 == iNode) iiii = aSegIndices.NxtSg1;
2657     else                     iiii = aSegIndices.NxtSg2;
2658   }
2659 }
2660
2661 //=======================================================================
2662 //function : OrientTriangle
2663 //purpose  : 
2664 //=======================================================================
2665
2666 void 
2667 #ifdef OCCT_DEBUG
2668 HLRBRep_PolyAlgo::OrientTriangle(const Standard_Integer iTri,
2669 #else
2670 HLRBRep_PolyAlgo::OrientTriangle(const Standard_Integer,
2671 #endif
2672                                  HLRAlgo_TriangleData& theTriangle,
2673                                  HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices,
2674                                  HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
2675                                  HLRAlgo_PolyInternalNode::NodeIndices& Nod2Indices,
2676                                  HLRAlgo_PolyInternalNode::NodeData& Nod2RValues,
2677                                  HLRAlgo_PolyInternalNode::NodeIndices& Nod3Indices,
2678                                  HLRAlgo_PolyInternalNode::NodeData& Nod3RValues) const
2679 {
2680   Standard_Boolean o1 = (Nod1Indices.Flag & NMsk_OutL) != 0;
2681   Standard_Boolean o2 = (Nod2Indices.Flag & NMsk_OutL) != 0;
2682   Standard_Boolean o3 = (Nod3Indices.Flag & NMsk_OutL) != 0;
2683   theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskFlat;
2684   theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskOnOutL;
2685   if (o1 && o2 && o3) {
2686     theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2687     theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2688     theTriangle.Flags |=  HLRAlgo_PolyMask_FMskOnOutL;
2689 #ifdef OCCT_DEBUG
2690     if (DoTrace) {
2691       std::cout << "HLRBRep_PolyAlgo::OrientTriangle : OnOutL";
2692       std::cout << " triangle " << iTri << std::endl;
2693     }
2694 #endif
2695   }
2696   else {
2697     Standard_Real s1 = Nod1RValues.Scal;
2698     Standard_Real s2 = Nod2RValues.Scal;
2699     Standard_Real s3 = Nod3RValues.Scal;
2700     Standard_Real as1 = s1;
2701     Standard_Real as2 = s2;
2702     Standard_Real as3 = s3;
2703     if (s1 < 0) as1 = -s1;
2704     if (s2 < 0) as2 = -s2;
2705     if (s3 < 0) as3 = -s3;
2706     Standard_Real  s = 0;
2707     Standard_Real as = 0;
2708     if (!o1            ) {s = s1; as = as1;}
2709     if (!o2 && as < as2) {s = s2; as = as2;}
2710     if (!o3 && as < as3) {s = s3; as = as3;}
2711     if (s > 0) {
2712       theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskSide;
2713       theTriangle.Flags |=  HLRAlgo_PolyMask_FMskBack;
2714     }
2715     else {
2716       theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskSide;
2717       theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2718     }
2719     gp_XYZ aD12 = Nod2RValues.Point - Nod1RValues.Point;
2720     const Standard_Real aD12Norm = aD12.Modulus();
2721     if (aD12Norm <= 1.e-10) {
2722 #ifdef OCCT_DEBUG
2723       if (DoTrace) {
2724         std::cout << "HLRBRep_PolyAlgo::OrientTriangle : Flat";
2725         std::cout << " triangle " << iTri << std::endl;
2726       }
2727 #endif
2728       theTriangle.Flags |=  HLRAlgo_PolyMask_FMskFlat;
2729       theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2730       theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2731     }
2732     else {
2733       gp_XYZ aD23 = Nod3RValues.Point - Nod2RValues.Point;
2734       const Standard_Real aD23Norm = aD23.Modulus();
2735       if (aD23Norm < 1.e-10) {
2736 #ifdef OCCT_DEBUG
2737         if (DoTrace) {
2738           std::cout << "HLRBRep_PolyAlgo::OrientTriangle : Flat";
2739           std::cout << " triangle " << iTri << std::endl;
2740         }
2741 #endif
2742         theTriangle.Flags |=  HLRAlgo_PolyMask_FMskFlat;
2743         theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2744         theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2745       }
2746       else {
2747         const gp_XYZ aD31 = Nod1RValues.Point - Nod3RValues.Point;
2748         const Standard_Real aD31Norm = aD31.Modulus();
2749         if (aD31Norm < 1.e-10) {
2750 #ifdef OCCT_DEBUG
2751           if (DoTrace) {
2752             std::cout << "HLRBRep_PolyAlgo::OrientTriangle : Flat";
2753             std::cout << " triangle " << iTri << std::endl;
2754           }
2755 #endif
2756           theTriangle.Flags |=  HLRAlgo_PolyMask_FMskFlat;
2757           theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2758           theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2759         }
2760         else {
2761     aD12 *= 1 / aD12Norm;
2762     aD23 *= 1 / aD23Norm;
2763     gp_XYZ aD = aD12 ^ aD23;
2764     const Standard_Real aDNorm = aD.Modulus();
2765           if (aDNorm < 1.e-5) {
2766 #ifdef OCCT_DEBUG
2767             if (DoTrace) {
2768               std::cout << "HLRBRep_PolyAlgo::OrientTriangle : Flat";
2769               std::cout << " triangle " << iTri << std::endl;
2770             }
2771 #endif
2772             theTriangle.Flags |=  HLRAlgo_PolyMask_FMskFlat;
2773             theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2774             theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2775           }
2776           else {
2777             Standard_Real o;
2778             if (myProj.Perspective()) {
2779         aD *= 1 / aDNorm;
2780               o = aD.Z() * myProj.Focus() - aD * Nod1RValues.Point;
2781             }
2782             else
2783               o = aD.Z() / aDNorm;
2784             if (o < 0) {
2785               theTriangle.Flags |=  HLRAlgo_PolyMask_FMskOrBack;
2786               o = -o;
2787             }
2788             else
2789               theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskOrBack;
2790             if (o < 1.e-10) {
2791               theTriangle.Flags |=  HLRAlgo_PolyMask_FMskSide;
2792               theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskBack;
2793             }
2794           }
2795         }
2796       }
2797     }
2798   }
2799   if ((!(theTriangle.Flags & HLRAlgo_PolyMask_FMskBack) &&  (theTriangle.Flags & HLRAlgo_PolyMask_FMskOrBack)) ||
2800       ( (theTriangle.Flags & HLRAlgo_PolyMask_FMskBack) && !(theTriangle.Flags & HLRAlgo_PolyMask_FMskOrBack)))
2801     theTriangle.Flags |=  HLRAlgo_PolyMask_FMskFrBack;
2802   else 
2803     theTriangle.Flags &= ~HLRAlgo_PolyMask_FMskFrBack;
2804 }
2805
2806 //=======================================================================
2807 //function : Triangles
2808 //purpose  : 
2809 //=======================================================================
2810
2811 Standard_Boolean
2812 HLRBRep_PolyAlgo::Triangles(const Standard_Integer ip1,
2813                             const Standard_Integer ip2,
2814                             HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices,
2815                             HLRAlgo_Array1OfPISeg*& PISeg,
2816                             Standard_Integer& iTri1,
2817                             Standard_Integer& iTri2) const
2818 {
2819   Standard_Integer iiii = Nod1Indices.NdSg;
2820   
2821   while (iiii != 0) {
2822     HLRAlgo_PolyInternalSegment& aSegIndices =
2823       ((HLRAlgo_Array1OfPISeg*)PISeg)->ChangeValue(iiii);
2824     if (aSegIndices.LstSg1 == ip1) {
2825       if (aSegIndices.LstSg2 == ip2) {
2826         iTri1 = aSegIndices.Conex1;
2827         iTri2 = aSegIndices.Conex2;
2828         return Standard_True;
2829       }
2830       else iiii = aSegIndices.NxtSg1;
2831     }
2832     else {
2833       if (aSegIndices.LstSg1 == ip2) {
2834         iTri1 = aSegIndices.Conex1;
2835         iTri2 = aSegIndices.Conex2;
2836         return Standard_True;
2837       }
2838       else iiii = aSegIndices.NxtSg2;
2839     }
2840   }
2841   iTri1 = 0;
2842   iTri2 = 0;
2843 #ifdef OCCT_DEBUG
2844   if (DoError) {
2845     std::cout << "HLRBRep_PolyAlgo::Triangles : error";
2846     std::cout << " between " << ip1 << " and " << ip2 << std::endl;
2847   }
2848 #endif
2849   return Standard_False;
2850 }
2851
2852 //=======================================================================
2853 //function : NewNode
2854 //purpose  : 
2855 //=======================================================================
2856
2857 Standard_Boolean
2858 HLRBRep_PolyAlgo::
2859 NewNode (
2860   HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
2861   HLRAlgo_PolyInternalNode::NodeData& Nod2RValues,
2862   Standard_Real& coef1,
2863   Standard_Boolean& moveP1) const
2864 {
2865   Standard_Real TolAng = myTolAngular * 0.5;
2866   if ((Nod1RValues.Scal >= TolAng && Nod2RValues.Scal <= -TolAng) ||
2867       (Nod2RValues.Scal >= TolAng && Nod1RValues.Scal <= -TolAng)) {
2868     coef1 = Nod1RValues.Scal / ( Nod2RValues.Scal - Nod1RValues.Scal );
2869     if (coef1 < 0) coef1 = - coef1;
2870     moveP1 = coef1 < 0.5;
2871     return Standard_True;
2872   }
2873   return Standard_False;
2874 }
2875
2876 //=======================================================================
2877 //function : UVNode
2878 //purpose  : 
2879 //=======================================================================
2880
2881 void
2882 HLRBRep_PolyAlgo::UVNode (
2883   HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
2884   HLRAlgo_PolyInternalNode::NodeData& Nod2RValues,
2885   const Standard_Real coef1,
2886   Standard_Real& U3,
2887   Standard_Real& V3) const
2888 {
2889   Standard_Real coef2 = 1 - coef1;
2890   const gp_XY aUV3 = coef2 * Nod1RValues.UV + coef1 * Nod2RValues.UV;
2891   U3 = aUV3.X();
2892   V3 = aUV3.Y();
2893 }
2894
2895 //=======================================================================
2896 //function : CheckDegeneratedSegment
2897 //purpose  : 
2898 //=======================================================================
2899
2900 void
2901 HLRBRep_PolyAlgo::
2902 CheckDegeneratedSegment(
2903   HLRAlgo_PolyInternalNode::NodeIndices& Nod1Indices,
2904   HLRAlgo_PolyInternalNode::NodeData& Nod1RValues,
2905   HLRAlgo_PolyInternalNode::NodeIndices& Nod2Indices,
2906   HLRAlgo_PolyInternalNode::NodeData& Nod2RValues) const
2907 {
2908   Nod1Indices.Flag |=  NMsk_Fuck;
2909   Nod2Indices.Flag |=  NMsk_Fuck;
2910   if ((Nod1RValues.Scal >= myTolAngular && Nod2RValues.Scal <= -myTolAngular) ||
2911       (Nod2RValues.Scal >= myTolAngular && Nod1RValues.Scal <= -myTolAngular)) {
2912     Nod1RValues.Scal  = 0.;
2913     Nod1Indices.Flag |= NMsk_OutL;
2914     Nod2RValues.Scal  = 0.;
2915     Nod2Indices.Flag |= NMsk_OutL;
2916   }
2917 }
2918
2919 //=======================================================================
2920 //function : UpdateOutLines
2921 //purpose  : 
2922 //=======================================================================
2923
2924 void
2925 HLRBRep_PolyAlgo::UpdateOutLines (HLRAlgo_ListOfBPoint& List,
2926                                   TColStd_Array1OfTransient& PID)
2927 {
2928   Standard_Integer f;
2929   Standard_Integer nbFace = myFMap.Extent();
2930   Standard_Real X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ;
2931   Standard_Real XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2;
2932     
2933   Handle(HLRAlgo_PolyInternalData)* pid = 
2934     (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
2935
2936   for (f = 1; f <= nbFace; f++) { 
2937     if (!(*pid).IsNull()) {
2938       if ((*pid)->IntOutL()) {
2939   HLRAlgo_Array1OfTData* TData = &(*pid)->TData();
2940   HLRAlgo_Array1OfPISeg* PISeg = &(*pid)->PISeg();
2941         HLRAlgo_Array1OfPINod* PINod = &(*pid)->PINod();
2942         Standard_Integer i,j,it1,it2,tn1,tn2,tn3,pd,pf;
2943         Standard_Boolean outl;
2944         Standard_Integer nbS = (*pid)->NbPISeg();
2945
2946         for (i = 1; i <= nbS; i++)
2947   {
2948     HLRAlgo_PolyInternalSegment* psg = &PISeg->ChangeValue(i);
2949           it1 = psg->Conex1;
2950           it2 = psg->Conex2;
2951           if (it1 != 0 && it2 != 0 && it1 != it2) {  // debile but sure !
2952             HLRAlgo_TriangleData& aTriangle = TData->ChangeValue(it1);
2953             HLRAlgo_TriangleData& aTriangle2 = TData->ChangeValue(it2);
2954             if      (!(aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) && !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide))
2955               outl =  (aTriangle.Flags & HLRAlgo_PolyMask_FMskBack) !=  (aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack);
2956             else if ( (aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) &&  (aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide))
2957               outl = Standard_False;
2958             else if (  aTriangle.Flags & HLRAlgo_PolyMask_FMskSide)
2959               outl = !(aTriangle.Flags & HLRAlgo_PolyMask_FMskFlat) && !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack);
2960             else
2961               outl = !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskFlat) && !(aTriangle.Flags & HLRAlgo_PolyMask_FMskBack);
2962             
2963             if (outl) {
2964               pd = psg->LstSg1;
2965               pf = psg->LstSg2;
2966               tn1 = aTriangle.Node1;
2967               tn2 = aTriangle.Node2;
2968               tn3 = aTriangle.Node3;
2969               if (!(aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) && (aTriangle.Flags & HLRAlgo_PolyMask_FMskOrBack)) {
2970                 j   = tn1;
2971                 tn1 = tn3;
2972                 tn3 = j;
2973               }
2974               if      ((tn1 == pd && tn2 == pf) || (tn1 == pf && tn2 == pd))
2975                 aTriangle.Flags |=  HLRAlgo_PolyMask_EMskOutLin1;
2976               else if ((tn2 == pd && tn3 == pf) || (tn2 == pf && tn3 == pd))
2977                 aTriangle.Flags |=  HLRAlgo_PolyMask_EMskOutLin2;
2978               else if ((tn3 == pd && tn1 == pf) || (tn3 == pf && tn1 == pd))
2979                 aTriangle.Flags |=  HLRAlgo_PolyMask_EMskOutLin3;
2980 #ifdef OCCT_DEBUG
2981               else if (DoError) {
2982                 std::cout << "HLRAlgo_PolyInternalData::UpdateOutLines";
2983                 std::cout << " : segment not found" << std::endl;
2984               }
2985 #endif
2986               tn1 = aTriangle2.Node1;
2987               tn2 = aTriangle2.Node2;
2988               tn3 = aTriangle2.Node3;
2989               if (!(aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide) && (aTriangle2.Flags & HLRAlgo_PolyMask_FMskOrBack)) {
2990                 j   = tn1;
2991                 tn1 = tn3;
2992                 tn3 = j;
2993               }
2994               if      ((tn1 == pd && tn2 == pf) || (tn1 == pf && tn2 == pd))
2995                 aTriangle2.Flags |=  HLRAlgo_PolyMask_EMskOutLin1;
2996               else if ((tn2 == pd && tn3 == pf) || (tn2 == pf && tn3 == pd))
2997                 aTriangle2.Flags |=  HLRAlgo_PolyMask_EMskOutLin2;
2998               else if ((tn3 == pd && tn1 == pf) || (tn3 == pf && tn1 == pd))
2999                 aTriangle2.Flags |=  HLRAlgo_PolyMask_EMskOutLin3;
3000 #ifdef OCCT_DEBUG
3001               else if (DoError) {
3002                 std::cout << "HLRAlgo_PolyInternalData::UpdateOutLines";
3003                 std::cout << " : segment not found" << std::endl;
3004               }
3005 #endif
3006               HLRAlgo_PolyInternalNode::NodeData& Nod1RValues =
3007           PINod->ChangeValue(pd)->Data();
3008               HLRAlgo_PolyInternalNode::NodeData& Nod2RValues =
3009           PINod->ChangeValue(pf)->Data();
3010               XTI1 = X1 = Nod1RValues.Point.X();
3011               YTI1 = Y1 = Nod1RValues.Point.Y();
3012               ZTI1 = Z1 = Nod1RValues.Point.Z();
3013               XTI2 = X2 = Nod2RValues.Point.X();
3014               YTI2 = Y2 = Nod2RValues.Point.Y();
3015               ZTI2 = Z2 = Nod2RValues.Point.Z();
3016               TIMultiply(XTI1,YTI1,ZTI1);
3017               TIMultiply(XTI2,YTI2,ZTI2);
3018               List.Append(HLRAlgo_BiPoint(XTI1,YTI1,ZTI1,XTI2,YTI2,ZTI2,
3019                                           X1  ,Y1  ,Z1  ,X2  ,Y2  ,Z2  ,
3020                                           f,f,pd,pf,f,pd,pf,12));
3021             }
3022           }
3023         }
3024       }
3025     }
3026     pid++;
3027   }
3028 }
3029
3030 //=======================================================================
3031 //function : UpdateEdgesBiPoints
3032 //purpose  : 
3033 //=======================================================================
3034
3035 void HLRBRep_PolyAlgo::
3036 UpdateEdgesBiPoints (HLRAlgo_ListOfBPoint& List,
3037                      const TColStd_Array1OfTransient& PID,
3038                      const Standard_Boolean closed)
3039 {
3040   Standard_Integer itri1,itri2,tbid;
3041   HLRAlgo_ListIteratorOfListOfBPoint it;
3042   
3043   for (it.Initialize(List); it.More(); it.Next()) {      
3044     HLRAlgo_BiPoint& BP = it.Value();
3045 //    Standard_Integer i[5];
3046     HLRAlgo_BiPoint::IndicesT& aIndices = BP.Indices();
3047     if (aIndices.FaceConex1 != 0 && aIndices.FaceConex2 != 0) {
3048       const Handle(HLRAlgo_PolyInternalData)& pid1 =
3049         *(Handle(HLRAlgo_PolyInternalData)*)&(PID(aIndices.FaceConex1));
3050       const Handle(HLRAlgo_PolyInternalData)& pid2 =
3051         *(Handle(HLRAlgo_PolyInternalData)*)&(PID(aIndices.FaceConex2));
3052       HLRAlgo_Array1OfPISeg* PISeg1 = &pid1->PISeg();
3053       HLRAlgo_Array1OfPISeg* PISeg2 = &pid2->PISeg();
3054       HLRAlgo_PolyInternalNode::NodeIndices& Nod11Indices = 
3055         pid1->PINod().ChangeValue(aIndices.Face1Pt1)->Indices();
3056       HLRAlgo_PolyInternalNode::NodeIndices& Nod21Indices = 
3057         pid2->PINod().ChangeValue(aIndices.Face2Pt1)->Indices();
3058       Triangles(aIndices.Face1Pt1,aIndices.Face1Pt2,Nod11Indices,PISeg1,itri1,tbid);
3059       Triangles(aIndices.Face2Pt1,aIndices.Face2Pt2,Nod21Indices,PISeg2,itri2,tbid);
3060
3061       if (itri1 != 0 && itri2 != 0) {
3062         if (aIndices.FaceConex1 != aIndices.FaceConex2 || itri1 != itri2) {
3063           HLRAlgo_Array1OfTData* TData1 = &pid1->TData();
3064           HLRAlgo_Array1OfTData* TData2 = &pid2->TData();
3065           HLRAlgo_TriangleData& aTriangle = TData1->ChangeValue(itri1);
3066           HLRAlgo_TriangleData& aTriangle2 = TData2->ChangeValue(itri2);
3067           if (closed) {
3068             if (((aTriangle.Flags & HLRAlgo_PolyMask_FMskBack) && (aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack)) ||
3069                 ((aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) && (aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide)) ||
3070                 ((aTriangle.Flags & HLRAlgo_PolyMask_FMskBack) && (aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide)) ||
3071                 ((aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) && (aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack)))
3072               BP.Hidden(Standard_True);
3073           }
3074           Standard_Boolean outl;
3075           if      (!(aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) && !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide))
3076             outl =  (aTriangle.Flags & HLRAlgo_PolyMask_FMskBack) !=  (aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack);
3077           else if ( (aTriangle.Flags & HLRAlgo_PolyMask_FMskSide) &&  (aTriangle2.Flags & HLRAlgo_PolyMask_FMskSide))
3078             outl = Standard_False;
3079           else if ( (aTriangle.Flags & HLRAlgo_PolyMask_FMskSide))
3080             outl = !(aTriangle.Flags & HLRAlgo_PolyMask_FMskFlat) && !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskBack);
3081           else
3082             outl = !(aTriangle2.Flags & HLRAlgo_PolyMask_FMskFlat) && !(aTriangle.Flags & HLRAlgo_PolyMask_FMskBack);
3083           BP.OutLine(outl);
3084         }
3085       }
3086 #ifdef OCCT_DEBUG
3087       else if (DoError) {
3088         std::cout << "HLRBRep_PolyAlgo::UpdateEdgesBiPoints : error ";
3089         std::cout << " between " << aIndices.FaceConex1 << std::setw(6);
3090         std::cout << " and " << aIndices.FaceConex2 << std::endl;
3091       }
3092 #endif
3093     }
3094   }
3095 }
3096
3097 //=======================================================================
3098 //function : UpdatePolyData
3099 //purpose  : 
3100 //=======================================================================
3101
3102 void
3103 HLRBRep_PolyAlgo::UpdatePolyData (TColStd_Array1OfTransient& PD,
3104                                   TColStd_Array1OfTransient& PID,
3105                                   const Standard_Boolean closed)
3106 {
3107   Standard_Integer f,i;//,n[3];
3108   Handle(TColgp_HArray1OfXYZ)    HNodes;
3109   Handle(HLRAlgo_HArray1OfTData) HTData;
3110   Handle(HLRAlgo_HArray1OfPHDat) HPHDat;
3111   Standard_Integer nbFace = myFMap.Extent();
3112   Handle(HLRAlgo_PolyInternalData)* pid = 
3113     (Handle(HLRAlgo_PolyInternalData)*)&(PID.ChangeValue(1));
3114   Handle(HLRAlgo_PolyData)* pd =
3115     (Handle(HLRAlgo_PolyData)*)&(PD.ChangeValue(1));
3116
3117   for (f = 1; f <= nbFace; f++) {
3118     if (!(*pid).IsNull()) {
3119       Standard_Integer nbN = (*pid)->NbPINod();
3120       Standard_Integer nbT = (*pid)->NbTData();
3121       HNodes = new TColgp_HArray1OfXYZ   (1,nbN);
3122       HTData = new HLRAlgo_HArray1OfTData(1,nbT);
3123       TColgp_Array1OfXYZ&    Nodes = HNodes->ChangeArray1();
3124       HLRAlgo_Array1OfTData& Trian = HTData->ChangeArray1();
3125       HLRAlgo_Array1OfTData* TData = &(*pid)->TData();
3126       HLRAlgo_Array1OfPINod* PINod = &(*pid)->PINod();
3127       Standard_Integer nbHide = 0;
3128
3129       for (i = 1; i <= nbN; i++) {
3130         HLRAlgo_PolyInternalNode::NodeData& Nod1RValues = PINod->ChangeValue(i)->Data();
3131         Nodes.ChangeValue(i) = Nod1RValues.Point;
3132       }
3133       
3134       for (i = 1; i <= nbT; i++) {
3135         HLRAlgo_TriangleData* OT = &TData->ChangeValue(i);
3136         HLRAlgo_TriangleData* NT = &(Trian.ChangeValue(i));
3137         if (!(OT->Flags & HLRAlgo_PolyMask_FMskSide)) {
3138 #ifdef OCCT_DEBUG
3139           if ((OT->Flags & HLRAlgo_PolyMask_FMskFrBack) && DoTrace) {
3140             std::cout << "HLRBRep_PolyAlgo::ReverseBackTriangle :";
3141             std::cout << " face " << f << std::setw(6);
3142             std::cout << " triangle " << i << std::endl;
3143           }
3144 #endif
3145           if (OT->Flags & HLRAlgo_PolyMask_FMskOrBack) {
3146             Standard_Integer j = OT->Node1;
3147             OT->Node1          = OT->Node3;
3148             OT->Node3          = j;
3149             OT->Flags |=  HLRAlgo_PolyMask_FMskBack;
3150           }
3151           else
3152             OT->Flags &= ~HLRAlgo_PolyMask_FMskBack;
3153             //Tri1Flags |= HLRAlgo_PolyMask_FMskBack;//OCC349
3154         }
3155         NT->Node1 = OT->Node1;
3156         NT->Node2 = OT->Node2;
3157         NT->Node3 = OT->Node3;
3158         NT->Flags = OT->Flags;
3159         if (!(NT->Flags & HLRAlgo_PolyMask_FMskSide) &&
3160             (!(NT->Flags & HLRAlgo_PolyMask_FMskBack) || !closed)) {
3161           NT->Flags |=  HLRAlgo_PolyMask_FMskHiding;
3162           nbHide++;
3163         }
3164         else
3165           NT->Flags &= ~HLRAlgo_PolyMask_FMskHiding;
3166       }
3167       if (nbHide > 0) HPHDat = new HLRAlgo_HArray1OfPHDat(1,nbHide);
3168       else            HPHDat.Nullify();
3169       (*pd)->HNodes(HNodes);
3170       (*pd)->HTData(HTData);
3171       (*pd)->HPHDat(HPHDat);
3172       (*pd)->FaceIndex(f);
3173     }
3174     pid++;
3175     pd++;
3176   }
3177 }
3178
3179 //=======================================================================
3180 //function : TMultiply
3181 //purpose  : 
3182 //=======================================================================
3183
3184 void
3185 HLRBRep_PolyAlgo::TMultiply (Standard_Real& X,
3186                              Standard_Real& Y,
3187                              Standard_Real& Z,
3188                              const Standard_Boolean VPO) const
3189 {
3190   Standard_Real Xt = TMat[0][0]*X + TMat[0][1]*Y + TMat[0][2]*Z + (VPO ? 0 : TLoc[0]);//OCC349
3191   Standard_Real Yt = TMat[1][0]*X + TMat[1][1]*Y + TMat[1][2]*Z + (VPO ? 0 : TLoc[1]);//OCC349
3192   Z                = TMat[2][0]*X + TMat[2][1]*Y + TMat[2][2]*Z + (VPO ? 0 : TLoc[2]);//OCC349
3193   X                = Xt;
3194   Y                = Yt;
3195 }
3196
3197 //=======================================================================
3198 //function : TTMultiply
3199 //purpose  : 
3200 //=======================================================================
3201
3202 void
3203 HLRBRep_PolyAlgo::TTMultiply (Standard_Real& X,
3204                               Standard_Real& Y,
3205                               Standard_Real& Z,
3206                               const Standard_Boolean VPO) const
3207 {
3208   Standard_Real Xt = TTMa[0][0]*X + TTMa[0][1]*Y + TTMa[0][2]*Z + (VPO ? 0 : TTLo[0]);//OCC349
3209   Standard_Real Yt = TTMa[1][0]*X + TTMa[1][1]*Y + TTMa[1][2]*Z + (VPO ? 0 : TTLo[1]);//OCC349
3210   Z                = TTMa[2][0]*X + TTMa[2][1]*Y + TTMa[2][2]*Z + (VPO ? 0 : TTLo[2]);//OCC349
3211   X                = Xt;
3212   Y                = Yt;
3213 }
3214
3215 //=======================================================================
3216 //function : TIMultiply
3217 //purpose  : 
3218 //=======================================================================
3219
3220 void
3221 HLRBRep_PolyAlgo::TIMultiply (Standard_Real& X,
3222                               Standard_Real& Y,
3223                               Standard_Real& Z,
3224                               const Standard_Boolean VPO) const
3225 {
3226   Standard_Real Xt = TIMa[0][0]*X + TIMa[0][1]*Y + TIMa[0][2]*Z + (VPO ? 0 : TILo[0]);//OCC349
3227   Standard_Real Yt = TIMa[1][0]*X + TIMa[1][1]*Y + TIMa[1][2]*Z + (VPO ? 0 : TILo[1]);//OCC349
3228   Z                = TIMa[2][0]*X + TIMa[2][1]*Y + TIMa[2][2]*Z + (VPO ? 0 : TILo[2]);//OCC349
3229   X                = Xt;
3230   Y                = Yt;
3231 }
3232
3233 //=======================================================================
3234 //function : Hide
3235 //purpose  : 
3236 //=======================================================================
3237
3238 HLRAlgo_BiPoint::PointsT& HLRBRep_PolyAlgo::Hide (
3239                              HLRAlgo_EdgeStatus& status,
3240                              TopoDS_Shape& S,
3241                              Standard_Boolean& reg1,
3242                              Standard_Boolean& regn,
3243                              Standard_Boolean& outl,
3244                              Standard_Boolean& intl)
3245 {
3246   Standard_Integer index;
3247   HLRAlgo_BiPoint::PointsT& aPoints = myAlgo->Hide(status,index,reg1,regn,outl,intl);
3248   if (intl) S = myFMap(index);
3249   else      S = myEMap(index);
3250   return aPoints;
3251 }
3252
3253 //=======================================================================
3254 //function : Show
3255 //purpose  : 
3256 //=======================================================================
3257
3258 HLRAlgo_BiPoint::PointsT& HLRBRep_PolyAlgo::Show (
3259                              TopoDS_Shape& S,
3260                              Standard_Boolean& reg1,
3261                              Standard_Boolean& regn,
3262                              Standard_Boolean& outl,
3263                              Standard_Boolean& intl)
3264 {
3265   Standard_Integer index;
3266   HLRAlgo_BiPoint::PointsT& aPoints = myAlgo->Show(index,reg1,regn,outl,intl);
3267   if (intl) S = myFMap(index);
3268   else      S = myEMap(index);
3269   return aPoints;
3270 }
3271
3272 //=======================================================================
3273 //function : OutLinedShape
3274 //purpose  : 
3275 //=======================================================================
3276
3277 TopoDS_Shape
3278 HLRBRep_PolyAlgo::OutLinedShape (const TopoDS_Shape& S) const
3279 {
3280   TopoDS_Shape Result;
3281
3282   if (!S.IsNull()) {
3283     BRep_Builder B;
3284     B.MakeCompound(TopoDS::Compound(Result));
3285     B.Add(Result,S);
3286
3287     TopTools_MapOfShape Map;
3288     TopExp_Explorer ex;
3289     for (ex.Init(S,TopAbs_EDGE); ex.More(); ex.Next())
3290       Map.Add(ex.Current());
3291     for (ex.Init(S,TopAbs_FACE); ex.More(); ex.Next())
3292       Map.Add(ex.Current());
3293
3294     Standard_Integer nbFace = myFMap.Extent();
3295     if (nbFace > 0) {
3296       TopTools_Array1OfShape NewF(1,nbFace);
3297       TColStd_Array1OfTransient& Shell = myAlgo->PolyShell();
3298       Standard_Integer nbShell = Shell.Upper();
3299       HLRAlgo_ListIteratorOfListOfBPoint it;
3300       
3301       for (Standard_Integer iShell = 1; iShell <= nbShell; iShell++) {
3302         HLRAlgo_ListOfBPoint& List =
3303           (*(Handle(HLRAlgo_PolyShellData)*)&(Shell(iShell)))->Edges();
3304         
3305         for (it.Initialize(List); it.More(); it.Next()) {
3306           HLRAlgo_BiPoint& BP = it.Value();
3307           if (BP.IntLine()) {
3308             HLRAlgo_BiPoint::IndicesT& aIndices = BP.Indices();
3309             if (Map.Contains(myFMap(aIndices.ShapeIndex))) {
3310               HLRAlgo_BiPoint::PointsT& aPoints = BP.Points();
3311               B.Add(Result,BRepLib_MakeEdge(aPoints.Pnt1, aPoints.Pnt2));
3312             }
3313           }
3314         }
3315       }
3316     }    
3317   }
3318   return Result;
3319 }
3320