1 // File: HLRTopoBRep_FaceIsoLiner.cxx
2 // Created: Thu Jan 5 10:57:30 1995
3 // Author: Christophe MARION
7 #include <HLRTopoBRep_FaceIsoLiner.ixx>
10 #include <TopExp_Explorer.hxx>
12 #include <TopoDS_Edge.hxx>
13 #include <TopTools_Array1OfShape.hxx>
14 #include <TColStd_Array1OfBoolean.hxx>
15 #include <TopTools_ListIteratorOfListOfShape.hxx>
16 //#include <BRepAdaptor_Curve2d.hxx>
17 #include <BRepAdaptor_Surface.hxx>
18 #include <BRepTools.hxx>
19 #include <BRep_Tool.hxx>
20 #include <BRep_Builder.hxx>
21 #include <Geom2d_Curve.hxx>
22 #include <Geom2d_TrimmedCurve.hxx>
23 #include <Geom2d_Line.hxx>
24 #include <Geom2dHatch_Hatcher.hxx>
25 #include <Geom2dHatch_Intersector.hxx>
26 #include <HatchGen_ErrorStatus.hxx>
27 #include <HatchGen_Domain.hxx>
28 #include <HatchGen_PointOnHatching.hxx>
29 #include <HatchGen_PointOnElement.hxx>
30 #include <Precision.hxx>
32 const Standard_Real IntersectorConfusion = 1.e-10;
33 const Standard_Real IntersectorTangency = 1.e-10;
34 const Standard_Real HatcherConfusion2d = 1.e-8;
35 const Standard_Real HatcherConfusion3d = 1.e-8;
36 const Standard_Real Infinite = 100.;
38 //=======================================================================
40 // Purpose : Builds isoparametric curves with a hatcher.
41 //=======================================================================
43 void HLRTopoBRep_FaceIsoLiner::Perform (const Standard_Integer FI,
46 const Standard_Integer nbIsos)
48 Standard_Real UMin, UMax, VMin, VMax, U1, U2;
49 Standard_Integer ne = 0;
50 //BRep_Builder Builder;
52 TopExp_Explorer ExpEdges;
54 TF.Orientation (TopAbs_FORWARD);
57 TopoDS_Vertex V1U, V2U, V1V, V2V;
59 Geom2dHatch_Intersector Intersector
60 (IntersectorConfusion,IntersectorTangency);
61 Geom2dHatch_Hatcher Hatcher
62 (Intersector,HatcherConfusion2d,HatcherConfusion3d,Standard_True);
64 BRepTools::UVBounds (TF, UMin, UMax, VMin, VMax);
65 Standard_Boolean InfiniteUMin = Precision::IsNegativeInfinite (UMin);
66 Standard_Boolean InfiniteUMax = Precision::IsPositiveInfinite (UMax);
67 Standard_Boolean InfiniteVMin = Precision::IsNegativeInfinite (VMin);
68 Standard_Boolean InfiniteVMax = Precision::IsPositiveInfinite (VMax);
70 if (InfiniteUMin && InfiniteUMax) {
74 else if (InfiniteUMin)
75 UMin = UMax - Infinite;
76 else if (InfiniteUMax)
77 UMax = UMin + Infinite;
79 if (InfiniteVMin && InfiniteVMax) {
83 else if (InfiniteVMin)
84 VMin = VMax - Infinite;
85 else if (InfiniteVMax)
86 VMax = VMin + Infinite;
88 for (ExpEdges.Init (TF, TopAbs_EDGE); // Edges of the face TF
90 ExpEdges.Next()) ne++;
92 if (DS.FaceHasIntL(TF)) { // OutLines built on face TF.
94 TopTools_ListIteratorOfListOfShape itE;
95 for(itE.Initialize(DS.FaceIntL(TF));
101 TopTools_Array1OfShape SH(1,ne);
102 TColStd_Array1OfBoolean IL(1,ne); // internal OutLine
104 for (ExpEdges.Init (TF, TopAbs_EDGE);
107 Standard_Integer IndE;
108 const TopoDS_Edge& newE = TopoDS::Edge(ExpEdges.Current());
109 const Handle(Geom2d_Curve) PC =
110 BRep_Tool::CurveOnSurface (newE, TF, U1, U2);
111 if( Abs(PC->FirstParameter() - U1) <= Precision::PConfusion()
112 && Abs(PC->LastParameter() - U2) <= Precision::PConfusion()) {
113 IndE = Hatcher.AddElement (PC, newE.Orientation());
116 Handle (Geom2d_TrimmedCurve) TPC =
117 new Geom2d_TrimmedCurve (PC, U1, U2);
118 IndE = Hatcher.AddElement (TPC, newE.Orientation());
121 if (DS.IsOutLFaceEdge(TF,newE)) IL(IndE) = Standard_True;
122 else IL(IndE) = Standard_False;
125 if (DS.FaceHasIntL(TF)) { // get the internal OutLines built on face F.
126 TopTools_ListIteratorOfListOfShape itE;
127 for(itE.Initialize(DS.FaceIntL(TF));
130 Standard_Integer IndE;
131 const TopoDS_Edge& newE = TopoDS::Edge(itE.Value());
132 const Handle(Geom2d_Curve) PC =
133 BRep_Tool::CurveOnSurface (newE, TF, U1, U2);
134 if( Abs(PC->FirstParameter() - U1) <= Precision::PConfusion()
135 && Abs(PC->LastParameter() - U2) <= Precision::PConfusion()) {
136 IndE = Hatcher.AddElement (PC, TopAbs_INTERNAL);
139 Handle (Geom2d_TrimmedCurve) TPC =
140 new Geom2d_TrimmedCurve (PC, U1, U2);
141 IndE = Hatcher.AddElement (TPC, TopAbs_INTERNAL);
144 IL(IndE) = Standard_True;
148 //-----------------------------------------------------------------------
149 // Creation des hachures.
150 //-----------------------------------------------------------------------
152 BRepAdaptor_Surface Surface (TF);
153 Standard_Real Tolerance = BRep_Tool::Tolerance (TF);
155 Standard_Integer IIso;
156 Standard_Real DeltaU = Abs (UMax - UMin);
157 Standard_Real DeltaV = Abs (VMax - VMin);
158 Standard_Real Confusion = Min (DeltaU, DeltaV) * HatcherConfusion3d;
159 Hatcher.Confusion3d (Confusion);
161 //-----------------------------------------------------------------------
163 //-----------------------------------------------------------------------
165 Standard_Real StepU = DeltaU / (Standard_Real) nbIsos;
166 if (StepU > Confusion) {
167 Standard_Real UPrm = UMin + StepU / 2.;
168 gp_Dir2d Dir (0., 1.);
170 for (IIso = 1; IIso <= nbIsos; IIso++) {
171 gp_Pnt2d Ori (UPrm, 0.);
172 Handle (Geom2d_Line) IsoLine = new Geom2d_Line (Ori, Dir);
174 Standard_Integer IndH = Hatcher.AddHatching (IsoLine);
176 if (Hatcher.TrimDone (IndH) && !Hatcher.TrimFailed (IndH))
177 Hatcher.ComputeDomains (IndH);
178 if (!Hatcher.IsDone (IndH)) {
179 cout << "HLRTopoBRep::MakeIsoLines : Face " << FI << endl;
180 cout << "U iso of parameter: " << UPrm;
181 switch (Hatcher.Status (IndH)) {
182 case HatchGen_NoProblem :
183 cout << " No Problem" << endl;
185 case HatchGen_TrimFailure :
186 cout << " Trim Failure" << endl;
188 case HatchGen_TransitionFailure :
189 cout << " Transition Failure" << endl;
191 case HatchGen_IncoherentParity :
192 cout << " Incoherent Parity" << endl;
194 case HatchGen_IncompatibleStates :
195 cout << " Incompatible States" << endl;
198 Hatcher.RemHatching (IndH);
202 Standard_Integer NbDom = Hatcher.NbDomains (IndH);
205 for (Standard_Integer IDom = 1; IDom <= NbDom; IDom++) {
206 const HatchGen_Domain& Dom = Hatcher.Domain (IndH, IDom);
207 Standard_Real U1 = Dom.HasFirstPoint() ?
208 Dom.FirstPoint().Parameter() : VMin - Infinite;
209 Standard_Real U2 = Dom.HasSecondPoint() ?
210 Dom.SecondPoint().Parameter() : VMax + Infinite;
212 Surface.D0 (P.X(), P.Y(), P1);
214 Surface.D0 (P.X(), P.Y(), P2);
215 if (Dom.HasFirstPoint()) { // Iso U - Premier point
216 const HatchGen_PointOnHatching& PntH = Dom.FirstPoint();
218 for (Standard_Integer IPntE = 1;
219 IPntE <= PntH.NbPoints();
221 const HatchGen_PointOnElement& PntE = PntH.Point(IPntE);
222 V1U = HLRTopoBRep_FaceIsoLiner::MakeVertex
223 (TopoDS::Edge(SH(PntE.Index())),
224 P1,PntE.Parameter(),Tolerance,DS);
225 if (IL(PntE.Index())) DS.AddOutV(V1U);
228 if (Dom.HasSecondPoint()) { // Iso U - Deuxieme point
229 const HatchGen_PointOnHatching& PntH = Dom.SecondPoint();
231 for (Standard_Integer IPntE = 1;
232 IPntE <= PntH.NbPoints();
234 const HatchGen_PointOnElement& PntE = PntH.Point(IPntE);
235 V2U = HLRTopoBRep_FaceIsoLiner::MakeVertex
236 (TopoDS::Edge(SH(PntE.Index())),
237 P2,PntE.Parameter(),Tolerance,DS);
238 if (IL(PntE.Index())) DS.AddOutV(V2U);
241 if(!V1U.IsNull() && !V2U.IsNull())
242 HLRTopoBRep_FaceIsoLiner::MakeIsoLine
243 (F,IsoLine,V1U,V2U,U1,U2,Tolerance,DS);
247 Hatcher.RemHatching (IndH);
252 //-----------------------------------------------------------------------
254 //-----------------------------------------------------------------------
256 Standard_Real StepV = DeltaV / (Standard_Real) nbIsos;
257 if (StepV > Confusion) {
258 Standard_Real VPrm = VMin + StepV / 2.;
259 gp_Dir2d Dir (1., 0.);
261 for (IIso = 1; IIso <= nbIsos; IIso++) {
262 gp_Pnt2d Ori (0., VPrm);
263 Handle (Geom2d_Line) IsoLine = new Geom2d_Line (Ori, Dir);
265 Standard_Integer IndH = Hatcher.AddHatching (IsoLine);
267 if (Hatcher.TrimDone (IndH) && !Hatcher.TrimFailed (IndH))
268 Hatcher.ComputeDomains (IndH);
269 if (!Hatcher.IsDone (IndH)) {
270 cout << "HLRTopoBRep::MakeIsoLines : Face " << FI << endl;
271 cout << "V iso of parameter: " << VPrm;
272 switch (Hatcher.Status (IndH)) {
273 case HatchGen_NoProblem :
274 cout << " No Problem" << endl;
276 case HatchGen_TrimFailure :
277 cout << " Trim Failure" << endl;
279 case HatchGen_TransitionFailure :
280 cout << " Transition Failure" << endl;
282 case HatchGen_IncoherentParity :
283 cout << " Incoherent Parity" << endl;
285 case HatchGen_IncompatibleStates :
286 cout << " Incompatible States" << endl;
289 Hatcher.RemHatching (IndH);
293 Standard_Integer NbDom = Hatcher.NbDomains (IndH);
296 for (Standard_Integer IDom = 1; IDom <= NbDom; IDom++) {
297 const HatchGen_Domain& Dom = Hatcher.Domain (IndH, IDom);
298 Standard_Real U1 = Dom.HasFirstPoint() ?
299 Dom.FirstPoint().Parameter() : VMin - Infinite;
300 Standard_Real U2 = Dom.HasSecondPoint() ?
301 Dom.SecondPoint().Parameter() : VMax + Infinite;
303 Surface.D0 (P.X(), P.Y(), P1);
305 Surface.D0 (P.X(), P.Y(), P2);
306 if (Dom.HasFirstPoint()) { // Iso V - Premier point
307 const HatchGen_PointOnHatching& PntH = Dom.FirstPoint();
309 for (Standard_Integer IPntE = 1;
310 IPntE <= PntH.NbPoints();
312 const HatchGen_PointOnElement& PntE = PntH.Point(IPntE);
313 V1V = HLRTopoBRep_FaceIsoLiner::MakeVertex
314 (TopoDS::Edge(SH(PntE.Index())),
315 P1,PntE.Parameter(),Tolerance,DS);
317 if (IL(PntE.Index())) DS.AddOutV(V1V);
320 if (Dom.HasSecondPoint()) { // Iso V - Deuxieme point
321 const HatchGen_PointOnHatching& PntH = Dom.SecondPoint();
323 for (Standard_Integer IPntE = 1;
324 IPntE <= PntH.NbPoints();
326 const HatchGen_PointOnElement& PntE = PntH.Point(IPntE);
327 V2V = HLRTopoBRep_FaceIsoLiner::MakeVertex
328 (TopoDS::Edge(SH(PntE.Index())),
329 P2,PntE.Parameter(),Tolerance,DS);
330 if (IL(PntE.Index())) DS.AddOutV(V2V);
333 if(!V1V.IsNull() && !V2V.IsNull())
334 HLRTopoBRep_FaceIsoLiner::MakeIsoLine
335 (F,IsoLine,V1V,V2V,U1,U2,Tolerance,DS);
339 Hatcher.RemHatching (IndH);
345 //=======================================================================
346 //function : MakeVertex
348 //=======================================================================
351 HLRTopoBRep_FaceIsoLiner::MakeVertex (const TopoDS_Edge& E,
353 const Standard_Real Par,
354 const Standard_Real Tol,
355 HLRTopoBRep_Data& DS)
357 TopoDS_Vertex V, VF, VL;
359 TopExp::Vertices (E, VF, VL);
360 if (P.IsEqual(BRep_Tool::Pnt(VF),BRep_Tool::Tolerance(VF)))
362 if (P.IsEqual(BRep_Tool::Pnt(VL),BRep_Tool::Tolerance(VL)))
365 for (DS.InitVertex(E); DS.MoreVertex(); DS.NextVertex()) {
366 TopoDS_Vertex curV = DS.Vertex();
367 Standard_Real curP = DS.Parameter();
368 if (P.IsEqual(BRep_Tool::Pnt(curV),BRep_Tool::Tolerance(curV))) {
372 else if (Par < curP) {
373 B.MakeVertex(V,P,Tol);
374 V.Orientation(TopAbs_INTERNAL);
375 DS.InsertBefore(V,Par);
380 if (!DS.MoreVertex()) {
381 B.MakeVertex(V,P,Tol);
382 V.Orientation(TopAbs_INTERNAL);
389 //=======================================================================
390 //function : MakeIsoLine
392 //=======================================================================
394 void HLRTopoBRep_FaceIsoLiner::MakeIsoLine (const TopoDS_Face& F,
395 const Handle(Geom2d_Line)& Iso,
398 const Standard_Real U1,
399 const Standard_Real U2,
400 const Standard_Real Tol,
401 HLRTopoBRep_Data& DS)
405 E.Orientation (TopAbs_INTERNAL);
406 V1.Orientation (TopAbs_FORWARD);
407 V2.Orientation (TopAbs_REVERSED);
409 B.UpdateEdge (E, Iso, F, Tol);
411 B.UpdateVertex (V1, U1, E, Tol);
413 B.UpdateVertex (V2, U2, E, Tol);
414 DS.AddIsoL(F).Append(E);