1 // Created on: 1994-10-25
2 // Created by: Laurent BOURESCHE
3 // Copyright (c) 1994-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
6 // This file is part of Open CASCADE Technology software library.
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.
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
17 // modif : jlr branchement F(t) pour Edge/Face
19 // Modified by skv - Wed Jun 9 17:16:26 2004 OCC5898
20 // modified by Edward AGAPOV (eap) Fri Feb 8 2002 (bug occ67 == BUC61052)
21 // ComputeData(), case where BRepBlend_Walking::Continu() can't get up to Target
25 #include <ChFi3d_Builder.jxx>
26 #include <ChFi3d_Builder_0.hxx>
28 #include <Precision.hxx>
29 #include <math_Vector.hxx>
30 #include <BSplCLib.hxx>
34 #include <gp_Pnt2d.hxx>
35 #include <gp_Dir2d.hxx>
36 #include <gp_Vec2d.hxx>
38 #include <Geom2d_TrimmedCurve.hxx>
39 #include <Geom2d_BSplineCurve.hxx>
40 #include <Geom2d_Curve.hxx>
41 #include <Geom2d_Line.hxx>
42 #include <Geom_Curve.hxx>
43 #include <Geom_BSplineSurface.hxx>
44 #include <GeomLib.hxx>
46 #include <Adaptor3d_HSurface.hxx>
47 #include <Adaptor3d_TopolTool.hxx>
48 #include <GeomAdaptor_HCurve.hxx>
49 #include <GeomAdaptor_HSurface.hxx>
50 #include <BRepAdaptor_Surface.hxx>
51 #include <BRepAdaptor_Curve2d.hxx>
52 #include <BRepAdaptor_Curve.hxx>
53 #include <BRepAdaptor_HCurve2d.hxx>
54 #include <BRepTopAdaptor_TopolTool.hxx>
55 #include <BRepTopAdaptor_HVertex.hxx>
56 #include <BRep_Tool.hxx>
58 #include <Approx_SweepFunction.hxx>
59 #include <Blend_Point.hxx>
60 #include <BRepBlend_Extremity.hxx>
61 #include <BRepBlend_PointOnRst.hxx>
62 #include <BRepBlend_Line.hxx>
63 #include <BRepBlend_AppSurf.hxx>
64 #include <BRepBlend_AppSurface.hxx>
65 #include <BRepBlend_AppFunc.hxx>
66 #include <BRepBlend_AppFuncRst.hxx>
67 #include <BRepBlend_AppFuncRstRst.hxx>
68 #include <BRepBlend_CSWalking.hxx>
69 #include <BRepBlend_Walking.hxx>
70 #include <BRepBlend_SurfRstLineBuilder.hxx>
71 #include <BRepBlend_RstRstLineBuilder.hxx>
72 #include <BRepBlend_ConstRad.hxx>
73 #include <BRepBlend_ConstRadInv.hxx>
75 #include <TopOpeBRepDS_DataStructure.hxx>
76 #include <TopOpeBRepDS_Curve.hxx>
77 #include <TopOpeBRepDS_Surface.hxx>
79 #include <IntRes2d_IntersectionPoint.hxx>
80 #include <Geom2dInt_GInter.hxx>
81 #include <Geom2dAPI_ProjectPointOnCurve.hxx>
83 #include <ChFiDS_SurfData.hxx>
84 #include <ChFiDS_FaceInterference.hxx>
85 #include <ChFiDS_CommonPoint.hxx>
88 #include <TopTools_ListOfShape.hxx>
89 #include <TopTools_ListIteratorOfListOfShape.hxx>
93 #include <OSD_Chronometer.hxx>
94 //static OSD_Chronometer appclock;
100 #include <Draw_Appli.hxx>
101 #include <Draw_Segment2D.hxx>
102 #include <Draw_Marker2D.hxx>
103 #include <Draw_Segment3D.hxx>
104 #include <Draw_Marker3D.hxx>
106 #include <DrawTrSurf.hxx>
107 static Standard_Integer IndexOfConge = 0;
111 extern Standard_Boolean ChFi3d_GettraceDRAWFIL();
112 extern Standard_Boolean ChFi3d_GettraceDRAWWALK();
113 extern Standard_Boolean ChFi3d_GetcontextNOOPT();
114 extern void ChFi3d_SettraceDRAWFIL(const Standard_Boolean b);
115 extern void ChFi3d_SettraceDRAWWALK(const Standard_Boolean b);
116 extern void ChFi3d_SetcontextNOOPT(const Standard_Boolean b);
120 static void drawline(const Handle(BRepBlend_Line)& lin,
121 const Standard_Boolean iscs)
123 Handle(Draw_Marker3D) p3d;
124 Handle(Draw_Marker2D) p2d;
125 Handle(Draw_Segment3D) tg3d;
126 Handle(Draw_Segment2D) tg2d;
128 for(Standard_Integer i = 1; i <= lin->NbPoints(); i++){
129 const Blend_Point& pt = lin->Point(i);
130 gp_Pnt point = pt.PointOnS1();
131 gp_Pnt extr = point.Translated(pt.TangentOnS1());
132 p3d = new Draw_Marker3D(point,Draw_Square,Draw_rouge);
134 tg3d = new Draw_Segment3D(point,extr,Draw_rouge);
136 point = pt.PointOnS2();
137 extr = point.Translated(pt.TangentOnS2());
138 p3d = new Draw_Marker3D(point,Draw_Plus,Draw_jaune);
140 tg3d = new Draw_Segment3D(point,extr,Draw_jaune);
144 pt.ParametersOnS1(u,v);
145 gp_Pnt2d point2d(u,v);
146 gp_Pnt2d extr2d = point2d.Translated(pt.Tangent2dOnS1());
147 p2d = new Draw_Marker2D(point2d,Draw_Square,Draw_rouge);
149 tg2d = new Draw_Segment2D(point2d,extr2d,Draw_rouge);
151 pt.ParametersOnS2(u,v);
152 point2d.SetCoord(u,v);
153 extr2d = point2d.Translated(pt.Tangent2dOnS2());
154 p2d = new Draw_Marker2D(point2d,Draw_Plus,Draw_jaune);
156 tg2d = new Draw_Segment2D(point2d,extr2d,Draw_jaune);
162 //=======================================================================
163 //function : SearchIndex
166 //=======================================================================
167 static Standard_Integer SearchIndex(const Standard_Real Value,
168 Handle(BRepBlend_Line)& Lin)
170 Standard_Integer NbPnt = Lin->NbPoints(), Ind;
173 (Ind < NbPnt) && (Lin->Point(Ind).Parameter() < Value); )
179 //=======================================================================
183 //=======================================================================
184 static Standard_Integer nbedconnex(const TopTools_ListOfShape& L)
186 Standard_Integer nb = 0, i = 0;
187 TopTools_ListIteratorOfListOfShape It1(L);
188 for(;It1.More();It1.Next(),i++){
189 const TopoDS_Shape& curs = It1.Value();
190 Standard_Boolean dejavu = 0;
191 TopTools_ListIteratorOfListOfShape It2(L);
192 for(Standard_Integer j = 0; j < i && It2.More(); j++, It2.Next()){
193 if(curs.IsSame(It2.Value())){
203 static Standard_Boolean IsVois(const TopoDS_Edge& E,
204 const TopoDS_Vertex& Vref,
205 const ChFiDS_Map& VEMap,
206 TopTools_MapOfShape& DONE,
207 const Standard_Integer prof,
208 const Standard_Integer profmax)
210 if(prof > profmax) return Standard_False;
211 if(DONE.Contains(E)) return Standard_False;
213 TopExp::Vertices(E,V1,V2);
214 if(Vref.IsSame(V1) || Vref.IsSame(V2)) return Standard_True;
216 const TopTools_ListOfShape& L1 = VEMap(V1);
217 Standard_Integer i1 = nbedconnex(L1);
218 TopTools_ListIteratorOfListOfShape It1(L1);
219 for(;It1.More();It1.Next()){
220 const TopoDS_Edge& curE = TopoDS::Edge(It1.Value());
222 if(IsVois(curE,Vref,VEMap,DONE,prof,profmax)) return Standard_True;
224 else if(IsVois(curE,Vref,VEMap,DONE,prof+1,profmax)) return Standard_True;
226 const TopTools_ListOfShape& L2 = VEMap(V2);
228 // Standard_Integer i2 = nbedconnex(L2);
230 TopTools_ListIteratorOfListOfShape It2(L2);
231 for(;It2.More();It2.Next()){
232 const TopoDS_Edge& curE = TopoDS::Edge(It2.Value());
234 if(IsVois(curE,Vref,VEMap,DONE,prof,profmax)) return Standard_True;
236 else if(IsVois(curE,Vref,VEMap,DONE,prof+1,profmax)) return Standard_True;
238 return Standard_False;
241 static Standard_Boolean IsObst(const ChFiDS_CommonPoint& CP,
242 const TopoDS_Vertex& Vref,
243 const ChFiDS_Map& VEMap)
245 if(!CP.IsOnArc()) return Standard_False;
246 const TopoDS_Edge& E = CP.Arc();
247 TopTools_MapOfShape DONE;
248 Standard_Integer prof = 4;
249 return !IsVois(E,Vref,VEMap,DONE,0,prof);
252 //=======================================================================
253 //function : CompParam
256 //=======================================================================
258 static void CompParam(Geom2dAdaptor_Curve Carc,
259 Handle(Geom2d_Curve) Ctg,
262 const Standard_Real prefarc,
263 const Standard_Real preftg)
265 Standard_Boolean found = 0;
266 //(1) It is checked if the provided parameters are good
267 // if pcurves have the same parameters as the spine.
268 gp_Pnt2d point = Carc.Value(prefarc);
269 Standard_Real distini = point.Distance(Ctg->Value(preftg));
270 if (distini <= Precision::PConfusion()) {
273 found = Standard_True;
278 cout<< "CompParam : bad intersection parameters"<<endl;
280 IntRes2d_IntersectionPoint int2d;
281 Geom2dInt_GInter Intersection;
282 Standard_Integer nbpt,nbseg;
283 Intersection.Perform(Geom2dAdaptor_Curve(Ctg),Carc,
284 Precision::PIntersection(),
285 Precision::PIntersection());
287 Standard_Real dist = Precision::Infinite(), p1, p2;
288 if (Intersection.IsDone()){
289 if (!Intersection.IsEmpty()){
290 nbseg = Intersection.NbSegments();
293 cout<< "segments of intersection on the restrictions"<<endl;
296 nbpt = Intersection.NbPoints();
297 for (Standard_Integer i = 1; i <= nbpt; i++) {
298 int2d = Intersection.Point(i);
299 p1 = int2d.ParamOnFirst();
300 p2 = int2d.ParamOnSecond();
301 if(Abs(prefarc - p2) < dist){
304 dist = Abs(prefarc - p2);
315 cout<<"CompParam : failed intersection PC, projection is created."<<endl;
318 Geom2dAPI_ProjectPointOnCurve projector(point,Ctg);
320 if(projector.NbPoints() == 0){
321 // This happens in some cases when there is a vertex
322 // at the end of spine...
325 cout<<"CompParam : failed proj p2d/c2d, the extremity is taken!" <<endl;
329 // It is checked if everything was calculated correctly (EDC402 C2)
330 if (projector.LowerDistance() < distini)
331 ptg = projector.LowerDistanceParameter();
337 //=======================================================================
338 //function : CompBlendPoint
339 //purpose : create BlendPoint corresponding to a tangency on Vertex
340 // pmn : 15/10/1997 : returns false, if there is no pcurve
341 //=======================================================================
343 static Standard_Boolean CompBlendPoint(const TopoDS_Vertex& V,
344 const TopoDS_Edge& E,
345 const Standard_Real W,
346 const TopoDS_Face F1,
347 const TopoDS_Face F2,
352 Standard_Real param, f, l;
353 Handle(Geom2d_Curve) pc;
355 P3d = BRep_Tool::Pnt(V);
356 param = BRep_Tool::Parameter(V,E,F1);
357 pc = BRep_Tool::CurveOnSurface(E,F1,f,l);
358 if (pc.IsNull()) return Standard_False;
359 P1 = pc->Value(param);
360 param = BRep_Tool::Parameter(V,E,F2);
361 pc = BRep_Tool::CurveOnSurface(E,F2,f,l);
362 if (pc.IsNull()) return Standard_False;
363 P2 = pc->Value(param);
364 BP.SetValue(P3d, P3d, W, P1.X(), P1.Y(), P2.X(), P2.Y());
365 return Standard_True;
368 //=======================================================================
369 //function : UpdateLine
370 //purpose : Updates extremities after a partial invalidation
371 //=======================================================================
373 static void UpdateLine(Handle(BRepBlend_Line)& Line,
374 const Standard_Boolean isfirst)
376 Standard_Real tguide, U, V;
378 const Blend_Point& BP = Line->Point(1);
379 tguide = BP.Parameter();
380 if (Line->StartPointOnFirst().ParameterOnGuide() < tguide) {
381 BRepBlend_Extremity BE;
382 BP.ParametersOnS1(U, V);
383 BE.SetValue(BP.PointOnS1(), U, V, Precision::Confusion());
384 Line->SetStartPoints(BE, Line->StartPointOnSecond());
386 if (Line->StartPointOnSecond().ParameterOnGuide() < tguide) {
387 BRepBlend_Extremity BE;
388 BP.ParametersOnS2(U, V);
389 BE.SetValue(BP.PointOnS2(), U, V, Precision::Confusion());
390 Line->SetStartPoints(Line->StartPointOnFirst(), BE);
394 const Blend_Point& BP = Line->Point(Line->NbPoints());
395 tguide = BP.Parameter();
396 if (Line->EndPointOnFirst().ParameterOnGuide() > tguide) {
397 BRepBlend_Extremity BE;
398 BP.ParametersOnS1(U, V);
399 BE.SetValue(BP.PointOnS1(), U, V, Precision::Confusion());
400 Line->SetEndPoints(BE, Line->EndPointOnSecond());
402 if (Line->EndPointOnSecond().ParameterOnGuide() > tguide) {
403 BRepBlend_Extremity BE;
404 BP.ParametersOnS2(U, V);
405 BE.SetValue(BP.PointOnS2(), U, V, Precision::Confusion());
406 Line->SetEndPoints(Line->EndPointOnFirst(), BE);
411 //=======================================================================
412 //function : CompleteData
413 //purpose : Calculates curves and CommonPoints from the data
414 // calculated by filling.
415 //=======================================================================
417 Standard_Boolean ChFi3d_Builder::CompleteData
418 (Handle(ChFiDS_SurfData)& Data,
419 const Handle(Geom_Surface)& Surfcoin,
420 const Handle(Adaptor3d_HSurface)& S1,
421 const Handle(Geom2d_Curve)& PC1,
422 const Handle(Adaptor3d_HSurface)& S2,
423 const Handle(Geom2d_Curve)& PC2,
424 const TopAbs_Orientation Or,
425 const Standard_Boolean On1,
426 const Standard_Boolean Gd1,
427 const Standard_Boolean Gd2,
428 const Standard_Boolean Gf1,
429 const Standard_Boolean Gf2)
431 TopOpeBRepDS_DataStructure& DStr = myDS->ChangeDS();
432 Data->ChangeSurf(DStr.AddSurface(TopOpeBRepDS_Surface(Surfcoin,tolesp)));
434 ChFi3d_SettraceDRAWFIL(Standard_True);
435 if (ChFi3d_GettraceDRAWFIL()) {
438 char* name = new char[100];
439 sprintf(name,"%s_%d","Surf",IndexOfConge);
440 DrawTrSurf::Set(name,Surfcoin);
444 Standard_Real UFirst,ULast,VFirst,VLast;
445 Surfcoin->Bounds(UFirst,ULast,VFirst,VLast);
446 if(!Gd1) Data->ChangeVertexFirstOnS1().SetPoint(Surfcoin->Value(UFirst,VFirst));
447 if(!Gd2) Data->ChangeVertexFirstOnS2().SetPoint(Surfcoin->Value(UFirst,VLast));
448 if(!Gf1) Data->ChangeVertexLastOnS1().SetPoint(Surfcoin->Value(ULast,VFirst));
449 if(!Gf2) Data->ChangeVertexLastOnS2().SetPoint(Surfcoin->Value(ULast,VLast));
451 //calculate curves side S1
452 Handle(Geom_Curve) Crv3d1;
453 if(!PC1.IsNull()) Crv3d1= Surfcoin->VIso(VFirst);
454 gp_Pnt2d pd1(UFirst,VFirst), pf1(ULast,VFirst);
455 gp_Lin2d lfil1(pd1,gp_Dir2d(gp_Vec2d(pd1,pf1)));
456 Handle(Geom2d_Curve) PCurveOnSurf = new Geom2d_Line(lfil1);
457 TopAbs_Orientation tra1 = TopAbs_FORWARD, orsurf = Or;
458 Standard_Real x,y,w = 0.5*(UFirst+ULast);
461 Handle(Geom2d_Curve) c2dtrim;
462 Standard_Real tolreached = 1.e-5;
464 Handle(GeomAdaptor_HCurve) hcS1 = new GeomAdaptor_HCurve(Crv3d1);
465 c2dtrim = new Geom2d_TrimmedCurve(PC1,UFirst,ULast);
466 ChFi3d_SameParameter(hcS1,c2dtrim,S1,tolapp3d,tolreached);
467 c2dtrim->Value(w).Coord(x,y);
469 gp_Vec nf = du.Crossed(dv);
470 Surfcoin->D1(w,VFirst,p,du,dv);
471 gp_Vec ns = du.Crossed(dv);
472 if(nf.Dot(ns) > 0.) tra1 = TopAbs_REVERSED;
473 else if(On1) orsurf = TopAbs::Reverse(orsurf);
475 Standard_Integer Index1OfCurve =
476 DStr.AddCurve(TopOpeBRepDS_Curve(Crv3d1,tolreached));
477 ChFiDS_FaceInterference& Fint1 = Data->ChangeInterferenceOnS1();
478 Fint1.SetFirstParameter(UFirst);
479 Fint1.SetLastParameter(ULast);
480 Fint1.SetInterference(Index1OfCurve,tra1,c2dtrim,PCurveOnSurf);
481 //calculate curves side S2
482 Handle(Geom_Curve) Crv3d2;
483 if(!PC2.IsNull()) Crv3d2 = Surfcoin->VIso(VLast);
484 gp_Pnt2d pd2(UFirst,VLast), pf2(ULast,VLast);
485 gp_Lin2d lfil2(pd2,gp_Dir2d(gp_Vec2d(pd2,pf2)));
486 PCurveOnSurf = new Geom2d_Line(lfil2);
487 TopAbs_Orientation tra2 = TopAbs_FORWARD;
489 Handle(GeomAdaptor_HCurve) hcS2 = new GeomAdaptor_HCurve(Crv3d2);
490 c2dtrim = new Geom2d_TrimmedCurve(PC2,UFirst,ULast);
491 ChFi3d_SameParameter(hcS2,c2dtrim,S2,tolapp3d,tolreached);
492 c2dtrim->Value(w).Coord(x,y);
494 gp_Vec np = du.Crossed(dv);
495 Surfcoin->D1(w,VLast,p,du,dv);
496 gp_Vec ns = du.Crossed(dv);
497 if(np.Dot(ns) < 0.) {
498 tra2 = TopAbs_REVERSED;
499 if(!On1) orsurf = TopAbs::Reverse(orsurf);
502 Standard_Integer Index2OfCurve =
503 DStr.AddCurve(TopOpeBRepDS_Curve(Crv3d2,tolreached));
504 ChFiDS_FaceInterference& Fint2 = Data->ChangeInterferenceOnS2();
505 Fint2.SetFirstParameter(UFirst);
506 Fint2.SetLastParameter(ULast);
507 Fint2.SetInterference(Index2OfCurve,tra2,c2dtrim,PCurveOnSurf);
508 Data->ChangeOrientation() = orsurf;
509 return Standard_True;
512 //=======================================================================
513 //function : CompleteData
514 //purpose : Calculates the surface of curves and eventually
515 // CommonPoints from the data calculated in ComputeData.
517 // 11/08/1996 : Use of F(t)
519 //=======================================================================
521 Standard_Boolean ChFi3d_Builder::CompleteData
522 (Handle(ChFiDS_SurfData)& Data,
523 Blend_Function& Func,
524 Handle(BRepBlend_Line)& lin,
525 const Handle(Adaptor3d_HSurface)& S1,
526 const Handle(Adaptor3d_HSurface)& S2,
527 const TopAbs_Orientation Or1,
528 const Standard_Boolean Gd1,
529 const Standard_Boolean Gd2,
530 const Standard_Boolean Gf1,
531 const Standard_Boolean Gf2,
532 const Standard_Boolean Reversed)
534 Handle(BRepBlend_AppFunc) TheFunc
535 = new (BRepBlend_AppFunc)(lin, Func, tolapp3d, 1.e-5);
537 Standard_Integer Degmax = 20, Segmax = 5000;
538 BRepBlend_AppSurface approx (TheFunc,
539 lin->Point(1).Parameter(),
540 lin->Point(lin->NbPoints()).Parameter(),
541 tolapp3d, 1.e-5, //tolapp2d, tolerance max
542 tolappangle, // Contact G1
543 myConti, Degmax, Segmax);
544 if (!approx.IsDone()) {
546 cout << "Approximation non faite !!!" << endl;
548 return Standard_False;
553 return StoreData( Data, approx, lin, S1, S2, Or1, Gd1, Gd2, Gf1, Gf2, Reversed);
557 //=======================================================================
558 //function : CompleteData
559 //purpose : New overload for functions surf/rst
560 // jlr le 28/07/97 branchement F(t)
561 //=======================================================================
563 Standard_Boolean ChFi3d_Builder::CompleteData
564 (Handle(ChFiDS_SurfData)& Data,
565 Blend_SurfRstFunction& Func,
566 Handle(BRepBlend_Line)& lin,
567 const Handle(Adaptor3d_HSurface)& S1,
568 const Handle(Adaptor3d_HSurface)& S2,
569 const TopAbs_Orientation Or,
570 const Standard_Boolean Reversed)
572 Handle(BRepBlend_AppFuncRst) TheFunc
573 = new (BRepBlend_AppFuncRst)(lin, Func, tolapp3d, 1.e-5);
574 BRepBlend_AppSurface approx (TheFunc,
575 lin->Point(1).Parameter(),
576 lin->Point(lin->NbPoints()).Parameter(),
577 tolapp3d, 1.e-5, //tolapp2d, tolerance max
578 tolappangle, // Contact G1
580 if (!approx.IsDone()) {
582 cout << "Approximation is not done!" << endl;
584 return Standard_False;
590 return StoreData(Data,approx,lin,S1,S2,Or,0,0,0,0,Reversed);
595 //=======================================================================
596 //function : CompleteData
597 //purpose : New overload for functions rst/rst
598 // jlr le 28/07/97 branchement F(t)
599 //=======================================================================
601 Standard_Boolean ChFi3d_Builder::CompleteData
602 (Handle(ChFiDS_SurfData)& Data,
603 Blend_RstRstFunction& Func,
604 Handle(BRepBlend_Line)& lin,
605 const Handle(Adaptor3d_HSurface)& S1,
606 const Handle(Adaptor3d_HSurface)& S2,
607 const TopAbs_Orientation Or)
609 Handle(BRepBlend_AppFuncRstRst) TheFunc
610 = new (BRepBlend_AppFuncRstRst)(lin, Func, tolapp3d, 1.e-5);
611 BRepBlend_AppSurface approx (TheFunc,
612 lin->Point(1).Parameter(),
613 lin->Point(lin->NbPoints()).Parameter(),
614 tolapp3d, 1.e-5, //tolapp2d, tolerance max
615 tolappangle, // Contact G1
617 if (!approx.IsDone()) {
619 cout << "Approximation non faite !!!" << endl;
621 return Standard_False;
627 return StoreData(Data,approx,lin,S1,S2,Or,0,0,0,0);
633 //=======================================================================
634 //function : StoreData
635 //purpose : Copy of an approximation result in SurfData.
636 //=======================================================================
638 Standard_Boolean ChFi3d_Builder::StoreData(Handle(ChFiDS_SurfData)& Data,
639 const AppBlend_Approx& approx,
640 const Handle(BRepBlend_Line)& lin,
641 const Handle(Adaptor3d_HSurface)& S1,
642 const Handle(Adaptor3d_HSurface)& S2,
643 const TopAbs_Orientation Or1,
644 const Standard_Boolean Gd1,
645 const Standard_Boolean Gd2,
646 const Standard_Boolean Gf1,
647 const Standard_Boolean Gf2,
648 const Standard_Boolean Reversed)
650 // Small control tools.
651 static Handle(GeomAdaptor_HCurve) checkcurve;
652 if(checkcurve.IsNull()) checkcurve = new GeomAdaptor_HCurve();
653 GeomAdaptor_Curve& chc = checkcurve->ChangeCurve();
654 Standard_Real tolget3d, tolget2d, tolaux, tolC1, tolcheck;
655 Standard_Real tolC2 = 0.;
656 approx.TolReached(tolget3d, tolget2d);
657 tolaux = approx.TolCurveOnSurf(1);
658 tolC1 = tolget3d + tolaux;
660 tolaux = approx.TolCurveOnSurf(2);
661 tolC2 = tolget3d + tolaux;
664 TopOpeBRepDS_DataStructure& DStr = myDS->ChangeDS();
665 // By default parametric space is created using a square surface
666 // to be able to parameterize in U by # R*teta // a revoir lbo 29/08/97
667 const TColStd_Array1OfReal& ku = approx.SurfUKnots();
668 const TColStd_Array1OfReal& kv = approx.SurfVKnots();
669 Standard_Real larg = (kv(kv.Upper())-kv(kv.Lower()));
670 TColStd_Array1OfReal& kku = *((TColStd_Array1OfReal*)((void*)&ku));
671 BSplCLib::Reparametrize(0.,larg,kku);
672 Handle(Geom_BSplineSurface) Surf =
673 new Geom_BSplineSurface(approx.SurfPoles(),approx.SurfWeights(),
675 approx.SurfUMults(),approx.SurfVMults(),
676 approx.UDegree(),approx.VDegree());
677 // extension of the surface
679 Standard_Real length1,length2;
680 length1=Data->FirstExtensionValue();
681 length2=Data->LastExtensionValue();
682 if (length1 > Precision::Confusion())
683 GeomLib::ExtendSurfByLength(Surf,length1,1,Standard_False,Standard_False);
684 if (length2 > Precision::Confusion())
685 GeomLib::ExtendSurfByLength(Surf,length2,1,Standard_False,Standard_True);
687 Data->ChangeSurf(DStr.AddSurface(TopOpeBRepDS_Surface(Surf,tolget3d)));
690 ChFi3d_SettraceDRAWFIL(Standard_True);
691 if (ChFi3d_GettraceDRAWFIL()) {
694 char* name=new char[100];
695 sprintf(name,"%s_%d","Surf",IndexOfConge);
696 DrawTrSurf::Set(name,Surf);
699 Standard_Real UFirst,ULast,VFirst,VLast,pppdeb,pppfin;
700 Surf->Bounds(UFirst,ULast,VFirst,VLast);
701 BRepAdaptor_Curve2d brc;
702 BRepAdaptor_Curve CArc;
703 Handle(BRepAdaptor_HSurface)
704 BS1 = Handle(BRepAdaptor_HSurface)::DownCast(S1);
705 Handle(BRepAdaptor_HSurface)
706 BS2 = Handle(BRepAdaptor_HSurface)::DownCast(S2);
707 Geom2dAPI_ProjectPointOnCurve projector;
709 Standard_Real Uon1 = UFirst, Uon2 = ULast;
710 Standard_Integer ion1 = 1, ion2 = 2;
711 if(Reversed) { Uon1 = ULast; Uon2 = UFirst; ion1 = 2; ion2 = 1; }
713 // The SurfData is filled in what concerns S1,
714 Handle(Geom_Curve) Crv3d1 = Surf->UIso(Uon1);
715 gp_Pnt2d pori1(Uon1,0.);
716 gp_Lin2d lfil1(pori1,gp::DY2d());
717 Handle(Geom2d_Curve) PCurveOnSurf = new Geom2d_Line(lfil1);
718 Handle(Geom2d_Curve) PCurveOnFace;
720 Geom2d_BSplineCurve(approx.Curve2dPoles(ion1),approx.Curves2dKnots(),
721 approx.Curves2dMults(),approx.Curves2dDegree());
724 Standard_Real par1=PCurveOnFace->FirstParameter();
725 Standard_Real par2= PCurveOnFace->LastParameter();
726 chc.Load(Crv3d1,par1,par2);
728 if(!ChFi3d_CheckSameParameter(checkcurve,PCurveOnFace,S1,tolC1,tolcheck)){
730 cout<<"aaproximate tolerance under-valued : "<<tolC1<<" for "<<tolcheck<<endl;
734 Standard_Integer Index1OfCurve =
735 DStr.AddCurve(TopOpeBRepDS_Curve(Crv3d1,tolC1));
737 Standard_Real uarc,utg;
739 TopoDS_Face forwfac = BS1->ChangeSurface().Face();
740 forwfac.Orientation(TopAbs_FORWARD);
741 brc.Initialize(Data->VertexFirstOnS1().Arc(),forwfac);
742 ChFiDS_CommonPoint& V = Data->ChangeVertexFirstOnS1();
743 CArc.Initialize(V.Arc());
744 CompParam(brc,PCurveOnFace,uarc,utg, V.ParameterOnArc(), V.Parameter());
745 tolcheck = CArc.Value(uarc).Distance(V.Point());
746 V.SetArc(tolC1+tolcheck,V.Arc(),uarc,V.TransitionOnArc());
749 else pppdeb = VFirst;
751 TopoDS_Face forwfac = BS1->ChangeSurface().Face();
752 forwfac.Orientation(TopAbs_FORWARD);
753 ChFiDS_CommonPoint& V = Data->ChangeVertexLastOnS1();
754 brc.Initialize(V.Arc(),forwfac);
755 CArc.Initialize(V.Arc());
756 CompParam(brc,PCurveOnFace,uarc,utg, V.ParameterOnArc(), V.Parameter());
757 tolcheck = CArc.Value(uarc).Distance(V.Point());
758 V.SetArc(tolC1+tolcheck,V.Arc(),uarc,V.TransitionOnArc());
762 ChFiDS_FaceInterference& Fint1 = Data->ChangeInterferenceOnS1();
763 Fint1.SetFirstParameter(pppdeb);
764 Fint1.SetLastParameter(pppfin);
765 TopAbs_Orientation TraOn1;
766 if(Reversed) TraOn1 = ChFi3d_TrsfTrans(lin->TransitionOnS2());
767 else TraOn1 = ChFi3d_TrsfTrans(lin->TransitionOnS1());
768 Fint1.SetInterference(Index1OfCurve,TraOn1,PCurveOnFace,PCurveOnSurf);
770 // SurfData is filled in what concerns S2,
771 Handle(Geom_Curve) Crv3d2 = Surf->UIso(Uon2);
772 gp_Pnt2d pori2(Uon2,0.);
773 gp_Lin2d lfil2(pori2,gp::DY2d());
774 PCurveOnSurf = new Geom2d_Line(lfil2);
776 PCurveOnFace = new Geom2d_BSplineCurve(approx.Curve2dPoles(ion2),
777 approx.Curves2dKnots(),
778 approx.Curves2dMults(),
779 approx.Curves2dDegree());
780 chc.Load(Crv3d2,par1,par2);
781 if(!ChFi3d_CheckSameParameter(checkcurve,PCurveOnFace,S2,tolC2,tolcheck)){
783 cout<<"approximate tolerance under-evaluated : "<<tolC2<<" for "<<tolcheck<<endl;
788 Standard_Integer Index2OfCurve =
789 DStr.AddCurve(TopOpeBRepDS_Curve(Crv3d2,tolC2));
791 TopoDS_Face forwfac = BS2->ChangeSurface().Face();
792 forwfac.Orientation(TopAbs_FORWARD);
793 brc.Initialize(Data->VertexFirstOnS2().Arc(),forwfac);
794 ChFiDS_CommonPoint& V = Data->ChangeVertexFirstOnS2();
795 CArc.Initialize(V.Arc());
796 CompParam(brc,PCurveOnFace,uarc,utg, V.ParameterOnArc(), V.Parameter());
797 tolcheck = CArc.Value(uarc).Distance(V.Point());
798 V.SetArc(tolC2+tolcheck,V.Arc(),uarc,V.TransitionOnArc());
801 else pppdeb = VFirst;
803 TopoDS_Face forwfac = BS2->ChangeSurface().Face();
804 forwfac.Orientation(TopAbs_FORWARD);
805 brc.Initialize(Data->VertexLastOnS2().Arc(),forwfac);
806 ChFiDS_CommonPoint& V = Data->ChangeVertexLastOnS2();
807 CArc.Initialize(V.Arc());
808 CompParam(brc,PCurveOnFace,uarc,utg, V.ParameterOnArc(), V.Parameter());
809 tolcheck = CArc.Value(uarc).Distance(V.Point());
810 V.SetArc(tolC2+tolcheck,V.Arc(),uarc,V.TransitionOnArc());
814 ChFiDS_FaceInterference& Fint2 = Data->ChangeInterferenceOnS2();
815 Fint2.SetFirstParameter(pppdeb);
816 Fint2.SetLastParameter(pppfin);
818 TopAbs_Orientation TraOn2;
819 if(Reversed) TraOn2 = ChFi3d_TrsfTrans(lin->TransitionOnS1());
820 else TraOn2 = ChFi3d_TrsfTrans(lin->TransitionOnS2());
821 Fint2.SetInterference(Index2OfCurve,TraOn2,PCurveOnFace,PCurveOnSurf);
824 Handle(Geom2d_Curve) bidpc;
825 Fint2.SetInterference
826 (Index2OfCurve,TopAbs_FORWARD,bidpc,PCurveOnSurf);
829 // the orientation of the fillet in relation to the faces is evaluated,
831 Handle(Adaptor3d_HSurface) Sref = S1;
832 PCurveOnFace = Fint1.PCurveOnFace();
833 if(Reversed){ Sref = S2; PCurveOnFace = Fint2.PCurveOnFace(); }
835 // Modified by skv - Wed Jun 9 17:16:26 2004 OCC5898 Begin
836 // gp_Pnt2d PUV = PCurveOnFace->Value((VFirst+VLast)/2.);
838 // gp_Vec Du1,Du2,Dv1,Dv2;
839 // Sref->D1(PUV.X(),PUV.Y(),P,Du1,Dv1);
841 // if (Or1 == TopAbs_REVERSED) Du1.Reverse();
842 // Surf->D1(UFirst,(VFirst+VLast)/2.,P,Du2,Dv2);
844 // if (Du1.Dot(Du2)>0) Data->ChangeOrientation() = TopAbs_FORWARD;
845 // else Data->ChangeOrientation() = TopAbs_REVERSED;
847 Standard_Real aDelta = VLast - VFirst;
848 Standard_Integer aDenom = 2;
851 Standard_Real aDeltav = aDelta/aDenom;
852 Standard_Real aParam = VFirst + aDeltav;
853 gp_Pnt2d PUV = PCurveOnFace->Value(aParam);
855 gp_Vec Du1,Du2,Dv1,Dv2;
857 Sref->D1(PUV.X(),PUV.Y(),P,Du1,Dv1);
860 if (Or1 == TopAbs_REVERSED)
863 Surf->D1(UFirst, aParam, P, Du2, Dv2);
866 if (Du1.Magnitude() <= tolget3d ||
867 Du2.Magnitude() <= tolget3d) {
870 if (Abs(aDeltav) <= tolget2d)
871 return Standard_False;
877 Data->ChangeOrientation() = TopAbs_FORWARD;
879 Data->ChangeOrientation() = TopAbs_REVERSED;
883 // Modified by skv - Wed Jun 9 17:16:26 2004 OCC5898 End
885 if(!Gd1 && !S1.IsNull())
886 ChFi3d_FilCommonPoint(lin->StartPointOnFirst(),lin->TransitionOnS1(),
887 Standard_True, Data->ChangeVertex(1,ion1),tolC1);
888 if(!Gf1 && !S1.IsNull())
889 ChFi3d_FilCommonPoint(lin->EndPointOnFirst(),lin->TransitionOnS1(),
890 Standard_False,Data->ChangeVertex(0,ion1),tolC1);
891 if(!Gd2 && !S2.IsNull())
892 ChFi3d_FilCommonPoint(lin->StartPointOnSecond(),lin->TransitionOnS2(),
893 Standard_True, Data->ChangeVertex(1,ion2),tolC2);
894 if(!Gf2 && !S2.IsNull())
895 ChFi3d_FilCommonPoint(lin->EndPointOnSecond(),lin->TransitionOnS2(),
896 Standard_False, Data->ChangeVertex(0,ion2),tolC2);
897 // Parameters on ElSpine
898 Standard_Integer nbp = lin->NbPoints();
899 Data->FirstSpineParam(lin->Point(1).Parameter());
900 Data->LastSpineParam(lin->Point(nbp).Parameter());
901 return Standard_True;
906 //=======================================================================
907 //function : ComputeData
908 //purpose : Head of the path edge/face for the bypass of obstacle.
909 //=======================================================================
911 Standard_Boolean ChFi3d_Builder::ComputeData
912 (Handle(ChFiDS_SurfData)& Data,
913 const Handle(ChFiDS_HElSpine)& HGuide,
914 Handle(BRepBlend_Line)& Lin,
915 const Handle(Adaptor3d_HSurface)& S1,
916 const Handle(Adaptor3d_TopolTool)& I1,
917 const Handle(Adaptor3d_HSurface)& S2,
918 const Handle(Adaptor2d_HCurve2d)& PC2,
919 const Handle(Adaptor3d_TopolTool)& I2,
920 Standard_Boolean& Decroch,
921 Blend_SurfRstFunction& Func,
923 Blend_SurfPointFuncInv& FInvP,
924 Blend_SurfCurvFuncInv& FInvC,
925 const Standard_Real PFirst,
926 const Standard_Real MaxStep,
927 const Standard_Real Fleche,
928 const Standard_Real TolGuide,
929 Standard_Real& First,
931 const math_Vector& Soldep,
932 const Standard_Boolean Inside,
933 const Standard_Boolean Appro,
934 const Standard_Boolean Forward,
935 const Standard_Boolean RecP,
936 const Standard_Boolean RecS,
937 const Standard_Boolean RecRst)
939 BRepBlend_SurfRstLineBuilder TheWalk(S1,I1,S2,PC2,I2);
941 Data->FirstExtensionValue(0);
942 Data->LastExtensionValue(0);
944 Standard_Boolean reverse = (!Forward || Inside);
945 Standard_Real SpFirst = HGuide->FirstParameter();
946 Standard_Real SpLast = HGuide->LastParameter();
947 Standard_Real Target = SpLast;
948 if(reverse) Target = SpFirst;
949 Standard_Real Targetsov = Target;
951 Standard_Real MS = MaxStep;
952 Standard_Integer again = 0;
953 Standard_Integer nbptmin = 3; //jlr
954 Standard_Integer Nbpnt = 1;
955 // the initial solution is reframed if necessary.
956 math_Vector ParSol(1,3);
957 Standard_Real NewFirst = PFirst;
958 if(RecP || RecS || RecRst){
959 if(!TheWalk.PerformFirstSection(Func,FInv,FInvP,FInvC,PFirst,Target,Soldep,
960 tolesp,TolGuide,RecRst,RecP,RecS,
963 cout<<"ChFi3d_Builder::ComputeData : calculation fail first section"<<endl;
965 return Standard_False;
973 TheWalk.Perform (Func,FInv,FInvP,FInvC,NewFirst,Last,
974 MS,TolGuide,ParSol,tolesp,Fleche,Appro);
976 if (!TheWalk.IsDone()) {
978 cout << "Path not created" << endl;
980 return Standard_False;
984 if (!TheWalk.Complete(Func,FInv,FInvP,FInvC,SpLast)) {
986 cout << "Not completed" << endl;
992 Lin = TheWalk.Line();
993 Nbpnt = Lin->NbPoints();
994 if (Nbpnt <= 1 && again == 0) {
997 cout <<"one point of the path MS/50 is attempted."<<endl;
999 MS = MS/50.; Target = Targetsov;
1001 else if (Nbpnt<=nbptmin && again == 0) {
1004 cout <<"Number of points is too small, the step is reduced"<<endl;
1006 Standard_Real u1 = Lin->Point(1).Parameter();
1007 Standard_Real u2 = Lin->Point(Nbpnt).Parameter();
1008 MS = (u2-u1)/(nbptmin+1.0);
1009 // cout << " MS : " << MS << " u1 : " << u1 << " u2 : " << u2 << " nbptmin : " << nbptmin << endl;
1012 else if(Nbpnt<=nbptmin){
1014 cout <<"Number of points is still too small, quit"<<endl;
1016 return Standard_False;
1023 ChFi3d_SettraceDRAWWALK(Standard_True);
1024 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_True);
1026 if(Forward) Decroch = TheWalk.DecrochEnd();
1027 else Decroch = TheWalk.DecrochStart();
1028 Last = Lin->Point(Nbpnt).Parameter();
1029 First = Lin->Point(1).Parameter();
1030 return Standard_True;
1034 //=======================================================================
1035 //function : ComputeData
1036 //purpose : Heading of the path edge/edge for the bypass of obstacle.
1037 //=======================================================================
1039 Standard_Boolean ChFi3d_Builder::ComputeData
1040 (Handle(ChFiDS_SurfData)& Data,
1041 const Handle(ChFiDS_HElSpine)& HGuide,
1042 Handle(BRepBlend_Line)& Lin,
1043 const Handle(Adaptor3d_HSurface)& S1,
1044 const Handle(Adaptor2d_HCurve2d)& PC1,
1045 const Handle(Adaptor3d_TopolTool)& I1,
1046 Standard_Boolean& Decroch1,
1047 const Handle(Adaptor3d_HSurface)& S2,
1048 const Handle(Adaptor2d_HCurve2d)& PC2,
1049 const Handle(Adaptor3d_TopolTool)& I2,
1050 Standard_Boolean& Decroch2,
1051 Blend_RstRstFunction& Func,
1052 Blend_SurfCurvFuncInv& FInv1,
1053 Blend_CurvPointFuncInv& FInvP1,
1054 Blend_SurfCurvFuncInv& FInv2,
1055 Blend_CurvPointFuncInv& FInvP2,
1056 const Standard_Real PFirst,
1057 const Standard_Real MaxStep,
1058 const Standard_Real Fleche,
1059 const Standard_Real TolGuide,
1060 Standard_Real& First,
1061 Standard_Real& Last,
1062 const math_Vector& Soldep,
1063 const Standard_Boolean Inside,
1064 const Standard_Boolean Appro,
1065 const Standard_Boolean Forward,
1066 const Standard_Boolean RecP1,
1067 const Standard_Boolean RecRst1,
1068 const Standard_Boolean RecP2,
1069 const Standard_Boolean RecRst2)
1071 BRepBlend_RstRstLineBuilder TheWalk(S1, PC1, I1, S2, PC2, I2);
1073 Data->FirstExtensionValue(0);
1074 Data->LastExtensionValue(0);
1076 Standard_Boolean reverse = (!Forward || Inside);
1077 Standard_Real SpFirst = HGuide->FirstParameter();
1078 Standard_Real SpLast = HGuide->LastParameter();
1079 Standard_Real Target = SpLast;
1080 if(reverse) Target = SpFirst;
1081 Standard_Real Targetsov = Target;
1083 Standard_Real MS = MaxStep;
1084 Standard_Integer again = 0;
1085 Standard_Integer nbptmin = 3; //jlr
1086 Standard_Integer Nbpnt = 0;
1087 // the initial solution is reframed if necessary.
1088 math_Vector ParSol(1,2);
1089 Standard_Real NewFirst = PFirst;
1090 if (RecP1 || RecRst1 || RecP2 || RecRst2) {
1091 if (!TheWalk.PerformFirstSection(Func, FInv1, FInvP1, FInv2, FInvP2, PFirst, Target, Soldep,
1092 tolesp, TolGuide, RecRst1, RecP1, RecRst2, RecP2,
1095 cout<<"ChFi3d_Builder::ComputeData : fail calculation first section"<<endl;
1097 return Standard_False;
1105 TheWalk.Perform (Func, FInv1, FInvP1, FInv2, FInvP2, NewFirst, Last,
1106 MS, TolGuide, ParSol, tolesp, Fleche, Appro);
1108 if (!TheWalk.IsDone()) {
1110 cout << "Path not done" << endl;
1112 return Standard_False;
1116 if (!TheWalk.Complete(Func, FInv1, FInvP1, FInv2, FInvP2, SpLast)) {
1118 cout << "Not completed" << endl;
1124 Lin = TheWalk.Line();
1125 Nbpnt = Lin->NbPoints();
1126 if (Nbpnt <= 1 && again == 0) {
1129 cout <<"one point of path MS/50 is attempted."<<endl;
1131 MS = MS/50.; Target = Targetsov;
1133 else if (Nbpnt<=nbptmin && again == 0) {
1136 cout <<"Number of points is too small, the step is reduced"<<endl;
1138 Standard_Real u1 = Lin->Point(1).Parameter();
1139 Standard_Real u2 = Lin->Point(Nbpnt).Parameter();
1140 MS = (u2-u1)/(nbptmin+1);
1143 else if(Nbpnt<=nbptmin){
1145 cout <<"Number of points is still too small, quit"<<endl;
1147 return Standard_False;
1154 ChFi3d_SettraceDRAWWALK(Standard_True);
1155 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_True);
1158 Decroch1 = TheWalk.Decroch1End();
1159 Decroch2 = TheWalk.Decroch2End();
1162 Decroch1 = TheWalk.Decroch1Start();
1163 Decroch2 = TheWalk.Decroch2Start();
1165 Last = Lin->Point(Nbpnt).Parameter();
1166 First = Lin->Point(1).Parameter();
1167 return Standard_True;
1171 //=======================================================================
1172 //function : SimulData
1173 //purpose : Heading of the path edge/face for the bypass of obstacle in simulation mode.
1174 //=======================================================================
1176 Standard_Boolean ChFi3d_Builder::SimulData
1177 (Handle(ChFiDS_SurfData)& /*Data*/,
1178 const Handle(ChFiDS_HElSpine)& HGuide,
1179 Handle(BRepBlend_Line)& Lin,
1180 const Handle(Adaptor3d_HSurface)& S1,
1181 const Handle(Adaptor3d_TopolTool)& I1,
1182 const Handle(Adaptor3d_HSurface)& S2,
1183 const Handle(Adaptor2d_HCurve2d)& PC2,
1184 const Handle(Adaptor3d_TopolTool)& I2,
1185 Standard_Boolean& Decroch,
1186 Blend_SurfRstFunction& Func,
1187 Blend_FuncInv& FInv,
1188 Blend_SurfPointFuncInv& FInvP,
1189 Blend_SurfCurvFuncInv& FInvC,
1190 const Standard_Real PFirst,
1191 const Standard_Real MaxStep,
1192 const Standard_Real Fleche,
1193 const Standard_Real TolGuide,
1194 Standard_Real& First,
1195 Standard_Real& Last,
1196 const math_Vector& Soldep,
1197 const Standard_Integer NbSecMin,
1198 const Standard_Boolean Inside,
1199 const Standard_Boolean Appro,
1200 const Standard_Boolean Forward,
1201 const Standard_Boolean RecP,
1202 const Standard_Boolean RecS,
1203 const Standard_Boolean RecRst)
1205 BRepBlend_SurfRstLineBuilder TheWalk(S1,I1,S2,PC2,I2);
1207 Standard_Boolean reverse = (!Forward || Inside);
1208 Standard_Real SpFirst = HGuide->FirstParameter();
1209 Standard_Real SpLast = HGuide->LastParameter();
1210 Standard_Real Target = SpLast;
1211 if(reverse) Target = SpFirst;
1212 Standard_Real Targetsov = Target;
1214 Standard_Real MS = MaxStep;
1215 Standard_Integer again = 0;
1216 Standard_Integer Nbpnt = 0;
1217 // the starting solution is reframed if needed.
1218 math_Vector ParSol(1,3);
1219 Standard_Real NewFirst = PFirst;
1220 if(RecP || RecS || RecRst){
1221 if(!TheWalk.PerformFirstSection(Func,FInv,FInvP,FInvC,PFirst,Target,Soldep,
1222 tolesp,TolGuide,RecRst,RecP,RecS,
1226 cout<<"ChFi3d_Builder::SimulData : fail calculate first section"<<endl;
1228 return Standard_False;
1236 TheWalk.Perform (Func,FInv,FInvP,FInvC,NewFirst,Last,
1237 MS,TolGuide,ParSol,tolesp,Fleche,Appro);
1238 if (!TheWalk.IsDone()) {
1240 cout << "Path not done" << endl;
1242 return Standard_False;
1245 if (!TheWalk.Complete(Func,FInv,FInvP,FInvC,SpLast)) {
1247 cout << "Not completed" << endl;
1251 Lin = TheWalk.Line();
1252 Nbpnt = Lin->NbPoints();
1253 if (Nbpnt <= 1 && again == 0) {
1256 cout <<"one point of path MS/50 is attempted."<<endl;
1258 MS = MS/50.; Target = Targetsov;
1260 else if (Nbpnt <= NbSecMin && again == 0) {
1263 cout <<"Number of points is too small, the step is reduced"<<endl;
1265 Standard_Real u1 = Lin->Point(1).Parameter();
1266 Standard_Real u2 = Lin->Point(Nbpnt).Parameter();
1267 MS = (u2-u1)/(NbSecMin+1);
1270 else if(Nbpnt<=NbSecMin){
1272 cout <<"Number of points is still too small, quit"<<endl;
1274 return Standard_False;
1281 ChFi3d_SettraceDRAWWALK(Standard_True);
1282 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_True);
1284 if(Forward) Decroch = TheWalk.DecrochEnd();
1285 else Decroch = TheWalk.DecrochStart();
1286 Last = Lin->Point(Nbpnt).Parameter();
1287 First = Lin->Point(1).Parameter();
1288 return Standard_True;
1292 //=======================================================================
1293 //function : SimulData
1294 //purpose : Heading of path edge/edge for the bypass
1295 // of obstacle in simulation mode.
1296 //=======================================================================
1298 Standard_Boolean ChFi3d_Builder::SimulData
1299 (Handle(ChFiDS_SurfData)& /*Data*/,
1300 const Handle(ChFiDS_HElSpine)& HGuide,
1301 Handle(BRepBlend_Line)& Lin,
1302 const Handle(Adaptor3d_HSurface)& S1,
1303 const Handle(Adaptor2d_HCurve2d)& PC1,
1304 const Handle(Adaptor3d_TopolTool)& I1,
1305 Standard_Boolean& Decroch1,
1306 const Handle(Adaptor3d_HSurface)& S2,
1307 const Handle(Adaptor2d_HCurve2d)& PC2,
1308 const Handle(Adaptor3d_TopolTool)& I2,
1309 Standard_Boolean& Decroch2,
1310 Blend_RstRstFunction& Func,
1311 Blend_SurfCurvFuncInv& FInv1,
1312 Blend_CurvPointFuncInv& FInvP1,
1313 Blend_SurfCurvFuncInv& FInv2,
1314 Blend_CurvPointFuncInv& FInvP2,
1315 const Standard_Real PFirst,
1316 const Standard_Real MaxStep,
1317 const Standard_Real Fleche,
1318 const Standard_Real TolGuide,
1319 Standard_Real& First,
1320 Standard_Real& Last,
1321 const math_Vector& Soldep,
1322 const Standard_Integer NbSecMin,
1323 const Standard_Boolean Inside,
1324 const Standard_Boolean Appro,
1325 const Standard_Boolean Forward,
1326 const Standard_Boolean RecP1,
1327 const Standard_Boolean RecRst1,
1328 const Standard_Boolean RecP2,
1329 const Standard_Boolean RecRst2)
1331 BRepBlend_RstRstLineBuilder TheWalk(S1, PC1, I1, S2, PC2, I2);
1333 Standard_Boolean reverse = (!Forward || Inside);
1334 Standard_Real SpFirst = HGuide->FirstParameter();
1335 Standard_Real SpLast = HGuide->LastParameter();
1336 Standard_Real Target = SpLast;
1337 if(reverse) Target = SpFirst;
1338 Standard_Real Targetsov = Target;
1340 Standard_Real MS = MaxStep;
1341 Standard_Integer again = 0;
1342 Standard_Integer Nbpnt = 0;
1343 // The initial solution is reframed if necessary.
1344 math_Vector ParSol(1,2);
1345 Standard_Real NewFirst = PFirst;
1346 if (RecP1 || RecRst1 || RecP2 || RecRst2) {
1347 if(!TheWalk.PerformFirstSection(Func, FInv1, FInvP1, FInv2, FInvP2, PFirst, Target, Soldep,
1348 tolesp, TolGuide, RecRst1, RecP1, RecRst2, RecP2,
1352 cout<<"ChFi3d_Builder::SimulData : calculation fail first section"<<endl;
1354 return Standard_False;
1362 TheWalk.Perform (Func, FInv1, FInvP1, FInv2, FInvP2, NewFirst, Last,
1363 MS, TolGuide, ParSol, tolesp, Fleche, Appro);
1364 if (!TheWalk.IsDone()) {
1366 cout << "Path not created" << endl;
1368 return Standard_False;
1371 if (!TheWalk.Complete(Func, FInv1, FInvP1, FInv2, FInvP2, SpLast)) {
1373 cout << "Not completed" << endl;
1377 Lin = TheWalk.Line();
1378 Nbpnt = Lin->NbPoints();
1379 if (Nbpnt <= 1 && again == 0) {
1382 cout <<"only one point of path MS/50 is attempted."<<endl;
1384 MS = MS/50.; Target = Targetsov;
1386 else if (Nbpnt <= NbSecMin && again == 0) {
1389 cout <<"Number of points is too small, the step is reduced"<<endl;
1391 Standard_Real u1 = Lin->Point(1).Parameter();
1392 Standard_Real u2 = Lin->Point(Nbpnt).Parameter();
1393 MS = (u2-u1)/(NbSecMin+1);
1396 else if(Nbpnt<=NbSecMin){
1398 cout <<"Number of points is still too small, quit"<<endl;
1400 return Standard_False;
1407 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_True);
1410 Decroch1 = TheWalk.Decroch1End();
1411 Decroch2 = TheWalk.Decroch2End();
1414 Decroch1 = TheWalk.Decroch1Start();
1415 Decroch2 = TheWalk.Decroch2Start();
1418 Last = Lin->Point(Nbpnt).Parameter();
1419 First = Lin->Point(1).Parameter();
1420 return Standard_True;
1426 //=======================================================================
1427 //function : ComputeData
1428 //purpose : Construction of elementary fillet by path.
1430 //=======================================================================
1432 Standard_Boolean ChFi3d_Builder::ComputeData
1433 (Handle(ChFiDS_SurfData)& Data,
1434 const Handle(ChFiDS_HElSpine)& HGuide,
1435 const Handle(ChFiDS_Spine)& Spine,
1436 Handle(BRepBlend_Line)& Lin,
1437 const Handle(Adaptor3d_HSurface)& S1,
1438 const Handle(Adaptor3d_TopolTool)& I1,
1439 const Handle(Adaptor3d_HSurface)& S2,
1440 const Handle(Adaptor3d_TopolTool)& I2,
1441 Blend_Function& Func,
1442 Blend_FuncInv& FInv,
1443 const Standard_Real PFirst,
1444 const Standard_Real MaxStep,
1445 const Standard_Real Fleche,
1446 const Standard_Real tolguide,
1447 Standard_Real& First,
1448 Standard_Real& Last,
1449 const Standard_Boolean Inside,
1450 const Standard_Boolean Appro,
1451 const Standard_Boolean Forward,
1452 const math_Vector& Soldep,
1453 Standard_Boolean& intf,
1454 Standard_Boolean& intl,
1455 Standard_Boolean& Gd1,
1456 Standard_Boolean& Gd2,
1457 Standard_Boolean& Gf1,
1458 Standard_Boolean& Gf2,
1459 const Standard_Boolean RecOnS1,
1460 const Standard_Boolean RecOnS2)
1462 //The extrensions are created in case of output of two domains
1463 //directly and not by path ( too hasardous ).
1464 Data->FirstExtensionValue(0);
1465 Data-> LastExtensionValue(0);
1467 //The eventual faces are restored to test the jump of edge.
1469 Handle(BRepAdaptor_HSurface) HS = Handle(BRepAdaptor_HSurface)::DownCast(S1);
1470 if(!HS.IsNull()) F1 = HS->ChangeSurface().Face();
1471 HS = Handle(BRepAdaptor_HSurface)::DownCast(S2);
1472 if(!HS.IsNull()) F2 = HS->ChangeSurface().Face();
1474 // Path framing variables
1475 Standard_Real TolGuide=tolguide, TolEsp = tolesp;
1476 Standard_Integer nbptmin = 4;
1478 BRepBlend_Walking TheWalk(S1,S2,I1,I2);
1480 //Start of removal, 2D path controls
1481 //that qui s'accomodent mal des surfaces a parametrages non homogenes
1482 //en u et en v are extinguished.
1485 Standard_Real MS = MaxStep;
1486 Standard_Integer Nbpnt;
1487 Standard_Real SpFirst = HGuide->FirstParameter();
1488 Standard_Real SpLast = HGuide->LastParameter();
1490 // When the start point is inside, the path goes first to the left
1491 // to determine the Last for the periodicals.
1492 Standard_Boolean reverse = (!Forward || Inside);
1493 Standard_Real Target;
1496 if(!intf) Target = Last;
1499 Target = SpLast + Abs(SpLast);
1500 if(!intl) Target = Last;
1503 // In case if the singularity is pre-determined,
1504 // the path is indicated.
1505 if (!Spine.IsNull()){
1506 if (Spine->IsTangencyExtremity(Standard_True)) {
1507 TopoDS_Vertex V = Spine->FirstVertex();
1508 TopoDS_Edge E = Spine->Edges(1);
1509 Standard_Real param = Spine->FirstParameter();
1511 if (CompBlendPoint(V, E, param, F1, F2, BP)) {
1512 math_Vector vec(1,4);
1513 BP.ParametersOnS1(vec(1),vec(2));
1514 BP.ParametersOnS2(vec(3),vec(4));
1516 if (Func.IsSolution(vec, tolesp)) {
1517 TheWalk.AddSingularPoint(BP);
1521 if (Spine->IsTangencyExtremity(Standard_False)) {
1522 TopoDS_Vertex V = Spine->LastVertex();
1523 TopoDS_Edge E = Spine->Edges( Spine->NbEdges());
1524 Standard_Real param = Spine->LastParameter();
1526 if (CompBlendPoint(V, E, param, F1, F2, BP)) {
1527 math_Vector vec(1,4);
1528 BP.ParametersOnS1(vec(1),vec(2));
1529 BP.ParametersOnS2(vec(3),vec(4));
1531 if (Func.IsSolution(vec, tolesp)) {
1532 TheWalk.AddSingularPoint(BP);
1538 //The starting solution is reframed if necessary.
1539 //**********************************************//
1540 math_Vector ParSol(1,4);
1541 Standard_Real NewFirst = PFirst;
1542 if(RecOnS1 || RecOnS2){
1543 if(!TheWalk.PerformFirstSection(Func,FInv,PFirst,Target,Soldep,
1544 tolesp,TolGuide,RecOnS1,RecOnS2,
1547 cout<<"ChFi3d_Builder::ComputeData : calculation fail first section"<<endl;
1549 return Standard_False;
1556 //First the valid part is calculate, without caring for the extensions.
1557 //******************************************************************//
1558 Standard_Integer again = 0;
1559 Standard_Boolean tchernobyl = 0;
1560 Standard_Real u1sov = 0., u2sov = 0.;
1562 //Max step is relevant, but too great, the vector is required to detect
1564 if( (Abs(Last-First) <= MS * 5.) &&
1565 (Abs(Last-First) >= 0.01*Abs(NewFirst-Target)) ){
1566 MS = Abs(Last-First)*0.2;
1571 if(!again && (MS < 5*TolGuide)) MS = 5*TolGuide;
1573 if (5*TolGuide > MS) TolGuide = MS/5;
1574 if (5*TolEsp > MS) TolEsp = MS/5;
1576 TheWalk.Perform(Func,FInv,NewFirst,Target,MS,TolGuide,
1577 ParSol,TolEsp,Fleche,Appro);
1578 if (!TheWalk.IsDone()) {
1580 cout << "Path is not created" << endl;
1582 return Standard_False;
1584 Lin = TheWalk.Line();
1585 if(HGuide->IsPeriodic() && Inside) {
1586 SpFirst = Lin->Point(1).Parameter();
1587 SpLast = SpFirst + HGuide->Period();
1588 HGuide->ChangeCurve().FirstParameter(SpFirst);
1589 HGuide->ChangeCurve().LastParameter (SpLast );
1590 HGuide->ChangeCurve().SetOrigin(SpFirst);
1592 Standard_Boolean complmnt = Standard_True;
1593 if (Inside) complmnt = TheWalk.Complete(Func,FInv,SpLast);
1596 cout << "Not completed" << endl;
1598 return Standard_False;
1601 //The result is controlled using two criterions :
1602 //- if there is enough points,
1603 //- if one has gone far enough.
1604 Nbpnt = Lin->NbPoints();
1607 cout <<"0 point of path, quit."<<endl;
1609 return Standard_False;
1611 Standard_Real fpointpar = Lin->Point(1).Parameter();
1612 Standard_Real lpointpar = Lin->Point(Nbpnt).Parameter();
1614 Standard_Real factor = 1./(nbptmin + 1);
1615 Standard_Boolean okdeb = (Forward && !Inside);
1616 Standard_Boolean okfin = (!Forward && !Inside);
1618 Standard_Integer narc1 = Lin->StartPointOnFirst().NbPointOnRst();
1619 Standard_Integer narc2 = Lin->StartPointOnSecond().NbPointOnRst();
1620 okdeb = (narc1 > 0 || narc2 > 0 || (fpointpar-First) < 10*TolGuide);
1623 Standard_Integer narc1 = Lin->EndPointOnFirst().NbPointOnRst();
1624 Standard_Integer narc2 = Lin->EndPointOnSecond().NbPointOnRst();
1625 okfin = (narc1 > 0 || narc2 > 0 || (Last-lpointpar) < 10*TolGuide);
1627 if(!okdeb || !okfin || Nbpnt == 1){
1628 //It drags, the controls are extended, it is expected to evaluate a
1629 //satisfactory maximum step. If it already done, quit.
1632 cout <<"If it drags without control, quit."<<endl;
1634 return Standard_False;
1636 tchernobyl = Standard_True;
1640 cout <<"only one point of path MS/100 is attempted"<<endl;
1641 cout <<"and the controls are extended."<<endl;
1647 cout <<"It drags, the controls are extended."<<endl;
1649 MS = (lpointpar-fpointpar)/Nbpnt; //EvalStep(Lin);
1652 else if (Nbpnt < nbptmin){
1655 cout <<"Number of points is too small, the step is reduced"<<endl;
1659 MS = (lpointpar - fpointpar) * factor;
1661 else if(again == 1){
1662 if(Abs(fpointpar-u1sov)>=TolGuide ||
1663 Abs(lpointpar-u2sov)>=TolGuide){
1665 cout <<"Number of points is still too small, the step is reduced"<<endl;
1667 MS = (lpointpar - fpointpar) * factor;
1671 cout <<"Number of points is still too small, quit"<<endl;
1673 return Standard_False;
1683 if(TheWalk.TwistOnS1()){
1684 Data->TwistOnS1(Standard_True);
1686 cout<<"Path completed, but TWIST on S1"<<endl;
1689 if(TheWalk.TwistOnS2()){
1690 Data->TwistOnS2(Standard_True);
1692 cout<<"Parh completed, but TWIST on S2"<<endl;
1697 //Here there is a more or less presentable result
1698 //however it covers a the minimum zone.
1699 //The extensions are targeted.
1700 //*****************************//
1702 Gd1 = Gd2 = Gf1 = Gf2 = Standard_False;
1704 Standard_Boolean unseulsuffitdeb = (intf >= 2);
1705 Standard_Boolean unseulsuffitfin = (intl >= 2);
1706 Standard_Boolean noproldeb = (intf >= 3);
1707 Standard_Boolean noprolfin = (intl >= 3);
1709 Standard_Real Rab = 0.03*(SpLast-SpFirst);
1711 Standard_Boolean debarc1 = 0, debarc2 = 0;
1712 Standard_Boolean debcas1 = 0, debcas2 = 0;
1713 Standard_Boolean debobst1 = 0, debobst2 = 0;
1715 Standard_Boolean finarc1 = 0, finarc2 = 0;
1716 Standard_Boolean fincas1 = 0, fincas2 = 0;
1717 Standard_Boolean finobst1 = 0, finobst2 = 0;
1719 Standard_Integer narc1, narc2;
1721 Standard_Boolean backwContinueFailed = Standard_False; // eap
1722 if(reverse && intf) {
1723 narc1 = Lin->StartPointOnFirst().NbPointOnRst();
1724 narc2 = Lin->StartPointOnSecond().NbPointOnRst();
1726 ChFi3d_FilCommonPoint(Lin->StartPointOnFirst(),Lin->TransitionOnS1(),
1727 Standard_True, Data->ChangeVertexFirstOnS1(),tolesp);
1728 debarc1 = Standard_True;
1729 if(!SearchFace(Spine,Data->VertexFirstOnS1(),F1,bif)){
1730 //It is checked if there is not an obstacle.
1731 debcas1 = Standard_True;
1732 if(!Spine.IsNull()){
1733 if(Spine->IsPeriodic()){
1737 debobst1 = IsObst(Data->VertexFirstOnS1(),
1738 Spine->FirstVertex(),myVEMap);
1744 ChFi3d_FilCommonPoint(Lin->StartPointOnSecond(),Lin->TransitionOnS2(),
1745 Standard_True, Data->ChangeVertexFirstOnS2(),tolesp);
1746 debarc2 = Standard_True;
1747 if(!SearchFace(Spine,Data->VertexFirstOnS2(),F2,bif)){
1748 //It is checked if it is not an obstacle.
1749 debcas2 = Standard_True;
1750 if(!Spine.IsNull()){
1751 if(Spine->IsPeriodic()){
1755 debobst2 = IsObst(Data->VertexFirstOnS2(),
1756 Spine->FirstVertex(),myVEMap);
1761 Standard_Boolean oncontinue = !noproldeb && (narc1 != 0 || narc2 != 0);
1762 if(debobst1 || debobst2) oncontinue = Standard_False;
1763 else if(debcas1 && debcas2) oncontinue = Standard_False;
1764 else if((!debcas1 && debarc1) || (!debcas2 && debarc2)) oncontinue = Standard_False;
1767 TheWalk.ClassificationOnS1(!debarc1);
1768 TheWalk.ClassificationOnS2(!debarc2);
1769 TheWalk.Check2d(Standard_True); // It should be strict (PMN)
1770 TheWalk.Continu(Func,FInv,Target);
1771 TheWalk.ClassificationOnS1(Standard_True);
1772 TheWalk.ClassificationOnS2(Standard_True);
1773 TheWalk.Check2d(Standard_False);
1774 narc1 = Lin->StartPointOnFirst().NbPointOnRst();
1775 narc2 = Lin->StartPointOnSecond().NbPointOnRst();
1776 // modified by eap Fri Feb 8 11:43:48 2002 ___BEGIN___
1779 backwContinueFailed = Lin->StartPointOnFirst().ParameterOnGuide() > Target;
1781 ChFi3d_FilCommonPoint(Lin->StartPointOnFirst(),Lin->TransitionOnS1(),
1782 Standard_True, Data->ChangeVertexFirstOnS1(),tolesp);
1783 debarc1 = Standard_True;
1784 if(!SearchFace(Spine,Data->VertexFirstOnS1(),F1,bif)){
1785 //It is checked if it is not an obstacle.
1786 debcas1 = Standard_True;
1787 // if(!Spine.IsNull()) {
1788 // if(Spine->IsPeriodic()){
1792 // debobst1 = IsObst(Data->VertexFirstOnS1(),
1793 // Spine->FirstVertex(),myVEMap);
1801 backwContinueFailed = Lin->StartPointOnSecond().ParameterOnGuide() > Target;
1803 ChFi3d_FilCommonPoint(Lin->StartPointOnSecond(),Lin->TransitionOnS2(),
1804 Standard_True, Data->ChangeVertexFirstOnS2(),tolesp);
1805 debarc2 = Standard_True;
1806 if(!SearchFace(Spine,Data->VertexFirstOnS2(),F2,bif)){
1807 //It is checked if it is not an obstacle.
1808 debcas2 = Standard_True;
1809 // if(!Spine.IsNull()){
1810 // if(Spine->IsPeriodic()){
1814 // debobst2 = IsObst(Data->VertexFirstOnS2(),
1815 // Spine->FirstVertex(),myVEMap);
1821 if (backwContinueFailed) {
1822 // if we leave backwContinueFailed as is, we will stop in this direction
1823 // but we are to continue if there are no more faces on the side with arc
1824 // check this condition
1825 const ChFiDS_CommonPoint& aCP
1826 = debarc1 ? Data->VertexFirstOnS1() : Data->VertexFirstOnS2();
1827 if (aCP.IsOnArc() && bif.IsNull())
1828 backwContinueFailed = Standard_False;
1832 Standard_Boolean forwContinueFailed = Standard_False;
1833 // modified by eap Fri Feb 8 11:44:11 2002 ___END___
1834 if(Forward && intl) {
1836 narc1 = Lin->EndPointOnFirst().NbPointOnRst();
1837 narc2 = Lin->EndPointOnSecond().NbPointOnRst();
1839 ChFi3d_FilCommonPoint(Lin->EndPointOnFirst(),Lin->TransitionOnS1(),
1840 Standard_False, Data->ChangeVertexLastOnS1(),tolesp);
1841 finarc1 = Standard_True;
1842 if(!SearchFace(Spine,Data->VertexLastOnS1(),F1,bif)){
1843 //It is checked if it is not an obstacle.
1844 fincas1 = Standard_True;
1845 if(!Spine.IsNull()){
1846 finobst1 = IsObst(Data->VertexLastOnS1(),
1847 Spine->LastVertex(),myVEMap);
1852 ChFi3d_FilCommonPoint(Lin->EndPointOnSecond(),Lin->TransitionOnS2(),
1853 Standard_False, Data->ChangeVertexLastOnS2(),tolesp);
1854 finarc2 = Standard_True;
1855 if(!SearchFace(Spine,Data->VertexLastOnS2(),F2,bif)){
1856 //It is checked if it is not an obstacle.
1857 fincas2 = Standard_True;
1858 if(!Spine.IsNull()){
1859 finobst2 = IsObst(Data->VertexLastOnS2(),
1860 Spine->LastVertex(),myVEMap);
1864 Standard_Boolean oncontinue = !noprolfin && (narc1 != 0 || narc2 != 0);
1865 if(finobst1 || finobst2) oncontinue = Standard_False;
1866 else if(fincas1 && fincas2) oncontinue = Standard_False;
1867 else if((!fincas1 && finarc1) || (!fincas2 && finarc2)) oncontinue = Standard_False;
1870 TheWalk.ClassificationOnS1(!finarc1);
1871 TheWalk.ClassificationOnS2(!finarc2);
1872 TheWalk.Check2d(Standard_True); // It should be strict (PMN)
1873 TheWalk.Continu(Func,FInv,Target);
1874 TheWalk.ClassificationOnS1(Standard_True);
1875 TheWalk.ClassificationOnS2(Standard_True);
1876 TheWalk.Check2d(Standard_False);
1877 narc1 = Lin->EndPointOnFirst().NbPointOnRst();
1878 narc2 = Lin->EndPointOnSecond().NbPointOnRst();
1879 // modified by eap Fri Feb 8 11:44:57 2002 ___BEGIN___
1882 forwContinueFailed = Lin->EndPointOnFirst().ParameterOnGuide() < Target;
1884 ChFi3d_FilCommonPoint(Lin->EndPointOnFirst(),Lin->TransitionOnS1(),
1885 Standard_False, Data->ChangeVertexLastOnS1(),tolesp);
1886 finarc1 = Standard_True;
1887 if(!SearchFace(Spine,Data->VertexLastOnS1(),F1,bif)){
1888 //It is checked if it is not an obstacle.
1889 fincas1 = Standard_True;
1890 // if(!Spine.IsNull()){
1891 // finobst1 = IsObst(Data->VertexLastOnS1(),
1892 // Spine->LastVertex(),myVEMap);
1899 forwContinueFailed = Lin->EndPointOnSecond().ParameterOnGuide() < Target;
1901 ChFi3d_FilCommonPoint(Lin->EndPointOnSecond(),Lin->TransitionOnS2(),
1902 Standard_False, Data->ChangeVertexLastOnS2(),tolesp);
1903 finarc2 = Standard_True;
1904 if(!SearchFace(Spine,Data->VertexLastOnS2(),F2,bif)){
1905 //On regarde si ce n'est pas un obstacle.
1906 fincas2 = Standard_True;
1907 // if(!Spine.IsNull()){
1908 // finobst2 = IsObst(Data->VertexLastOnS2(),
1909 // Spine->LastVertex(),myVEMap);
1914 if (forwContinueFailed) {
1915 // if we leave forwContinueFailed as is, we will stop in this direction
1916 // but we are to continue if there are no more faces on the side with arc
1917 // check this condition
1918 const ChFiDS_CommonPoint& aCP
1919 = finarc1 ? Data->VertexLastOnS1() : Data->VertexLastOnS2();
1920 if (aCP.IsOnArc() && bif.IsNull())
1921 forwContinueFailed = Standard_False;
1923 // modified by eap Fri Feb 8 11:45:10 2002 ___END___
1926 Nbpnt = Lin->NbPoints();
1928 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_False);
1930 First = Lin->Point(1).Parameter();
1931 Last = Lin->Point(Nbpnt).Parameter();
1933 // ============= INVALIDATION EVENTUELLE =============
1934 // ------ Preparation des prolongement par plan tangent -----
1935 if(reverse && intf){
1936 Gd1 = debcas1/* && !debobst1*/; // skv(occ67)
1937 Gd2 = debcas2/* && !debobst2*/; // skv(occ67)
1938 if ((debarc1^debarc2) && !unseulsuffitdeb && (First!=SpFirst)) {
1939 // Case of incomplete path, of course this ends badly :
1940 // the result is truncated instead of exit.
1941 Standard_Real sortie;
1942 Standard_Integer ind;
1943 if (debarc1) sortie = Data->VertexFirstOnS1().Parameter();
1944 else sortie = Data->VertexFirstOnS2().Parameter();
1945 if (sortie - First > tolesp) {
1946 ind = SearchIndex(sortie, Lin);
1947 if (Lin->Point(ind).Parameter() == sortie) ind--;
1949 Lin->Remove(1, ind);
1950 UpdateLine(Lin, Standard_True);
1952 Nbpnt = Lin->NbPoints();
1953 First = Lin->Point(1).Parameter();
1956 else if ((intf>=5) && !debarc1 && !debarc2 && (First!=SpFirst)) {
1957 Standard_Real sortie = (2*First+Last)/3;
1958 Standard_Integer ind;
1959 if (sortie - First > tolesp) {
1960 ind = SearchIndex(sortie, Lin);
1961 if (Lin->Point(ind).Parameter() == sortie) ind--;
1962 if (Nbpnt-ind < 3) ind = Nbpnt -3;
1964 Lin->Remove(1, ind);
1965 UpdateLine(Lin, Standard_True);
1967 Nbpnt = Lin->NbPoints();
1968 First = Lin->Point(1).Parameter();
1972 Target = Min((Lin->Point(1).Parameter() - Rab),First);
1973 Target = Max(Target,SpFirst);
1974 Data->FirstExtensionValue(Abs(Lin->Point(1).Parameter()-Target));
1976 if (intf && !unseulsuffitdeb) intf = (Gd1 && Gd2)//;
1977 || backwContinueFailed; // eap
1978 else if (intf && unseulsuffitdeb && (intf<5)) {
1979 intf = (Gd1 || Gd2);
1980 // It is checked if there is no new face.
1982 ((!debcas1 && debarc1) || (!debcas2 && debarc2)) ) intf = 0;
1984 else if (intf < 5) intf = 0;
1987 if(Forward && intl){
1988 Gf1 = fincas1/* && !finobst1*/; // skv(occ67)
1989 Gf2 = fincas2/* && !finobst2*/; // skv(occ67)
1990 if ((finarc1 ^finarc2) && !unseulsuffitfin && (Last!=SpLast)) {
1991 // Case of incomplete path, of course, this ends badly :
1992 // the result is truncated instead of exit.
1993 Standard_Real sortie;
1994 Standard_Integer ind;
1995 if (finarc1) sortie = Data->VertexLastOnS1().Parameter();
1996 else sortie = Data->VertexLastOnS2().Parameter();
1997 if (Last - sortie > tolesp) {
1998 ind = SearchIndex(sortie, Lin);
1999 if (Lin->Point(ind).Parameter() == sortie) ind++;
2001 Lin->Remove(ind, Nbpnt);
2002 UpdateLine(Lin, Standard_False);
2004 Nbpnt = Lin->NbPoints();
2005 Last = Lin->Point(Nbpnt).Parameter();
2008 else if ((intl>=5) && !finarc1 && !finarc2 && (Last!=SpLast) ) {
2009 // The same in case when the entire "Lin" is an extension
2010 Standard_Real sortie = (First+2*Last)/3;
2011 Standard_Integer ind;
2012 if (Last - sortie > tolesp) {
2013 ind = SearchIndex(sortie, Lin);
2014 if (Lin->Point(ind).Parameter() == sortie) ind++;
2015 if (ind < 3) ind = 3;
2017 Lin->Remove(ind, Nbpnt);
2018 UpdateLine(Lin, Standard_False);
2020 Nbpnt = Lin->NbPoints();
2021 Last = Lin->Point(Nbpnt).Parameter();
2025 Target = Max((Lin->Point(Nbpnt).Parameter() + Rab),Last);
2026 Target = Min(Target,SpLast);
2027 Data->LastExtensionValue(Abs(Target-Lin->Point(Nbpnt).Parameter()));
2030 if (intl && !unseulsuffitfin) intl = (Gf1 && Gf2)//;
2031 || forwContinueFailed; // eap
2032 else if (intl && unseulsuffitfin && (intl<5)) {
2033 intl = (Gf1 || Gf2);// It is checked if there is no new face.
2035 ((!fincas1 && finarc1) || (!fincas2 && finarc2)) ) intl = 0;
2037 else if (intl <5) intl = 0;
2039 return Standard_True;
2042 //=======================================================================
2043 //function : SimulData
2045 //=======================================================================
2047 Standard_Boolean ChFi3d_Builder::SimulData
2048 (Handle(ChFiDS_SurfData)& /*Data*/,
2049 const Handle(ChFiDS_HElSpine)& HGuide,
2050 Handle(BRepBlend_Line)& Lin,
2051 const Handle(Adaptor3d_HSurface)& S1,
2052 const Handle(Adaptor3d_TopolTool)& I1,
2053 const Handle(Adaptor3d_HSurface)& S2,
2054 const Handle(Adaptor3d_TopolTool)& I2,
2055 Blend_Function& Func,
2056 Blend_FuncInv& FInv,
2057 const Standard_Real PFirst,
2058 const Standard_Real MaxStep,
2059 const Standard_Real Fleche,
2060 const Standard_Real tolguide,
2061 Standard_Real& First,
2062 Standard_Real& Last,
2063 const Standard_Boolean Inside,
2064 const Standard_Boolean Appro,
2065 const Standard_Boolean Forward,
2066 const math_Vector& Soldep,
2067 const Standard_Integer NbSecMin,
2068 const Standard_Boolean RecOnS1,
2069 const Standard_Boolean RecOnS2)
2071 BRepBlend_Walking TheWalk(S1,S2,I1,I2);
2072 TheWalk.Check2d(Standard_False);
2074 Standard_Real MS = MaxStep;
2075 Standard_Real TolGuide=tolguide, TolEsp = tolesp;
2076 Standard_Integer Nbpnt = 0;
2077 Standard_Real SpFirst = HGuide->FirstParameter();
2078 Standard_Real SpLast = HGuide->LastParameter();
2079 Standard_Boolean reverse = (!Forward || Inside);
2080 Standard_Real Target;
2088 Standard_Real Targetsov = Target;
2089 Standard_Real u1sov = 0., u2sov = 0.;
2090 // on recadre la solution de depart a la demande.
2091 math_Vector ParSol(1,4);
2092 Standard_Real NewFirst = PFirst;
2093 if(RecOnS1 || RecOnS2){
2094 if(!TheWalk.PerformFirstSection(Func,FInv,PFirst,Target,Soldep,
2095 tolesp,TolGuide,RecOnS1,RecOnS2,
2098 cout<<"ChFi3d_Builder::SimulData : calculation fail first section"<<endl;
2100 return Standard_False;
2106 Standard_Integer again = 0;
2108 // When the start point is inside, the path goes first to the left
2109 // to determine the Last for the periodicals.
2110 if(!again && (MS < 5*TolGuide)) MS = 5*TolGuide;
2112 if (5*TolGuide > MS) TolGuide = MS/5;
2113 if (5*TolEsp > MS) TolEsp = MS/5;
2116 TheWalk.Perform(Func,FInv,NewFirst,Target,MS,TolGuide,
2117 ParSol,TolEsp,Fleche,Appro);
2119 if (!TheWalk.IsDone()) {
2121 cout << "Path not created" << endl;
2123 return Standard_False;
2125 Lin = TheWalk.Line();
2127 if(HGuide->IsPeriodic()) {
2128 SpFirst = Lin->Point(1).Parameter();
2129 SpLast = SpFirst + HGuide->Period();
2130 HGuide->ChangeCurve().FirstParameter(SpFirst);
2131 HGuide->ChangeCurve().LastParameter (SpLast );
2133 Standard_Boolean complmnt = Standard_True;
2134 if (Inside) complmnt = TheWalk.Complete(Func,FInv,SpLast);
2137 cout << "Not completed" << endl;
2139 return Standard_False;
2142 Nbpnt = Lin->NbPoints();
2143 Standard_Real factor = 1./(NbSecMin + 1);
2146 cout <<"0 point of path, quit."<<endl;
2148 return Standard_False;
2150 else if (Nbpnt == 1 && again == 0) {
2153 cout <<"only one point of path, MS/100 is attempted."<<endl;
2155 MS *= 0.01; Target = Targetsov;
2156 u1sov = u2sov = Lin->Point(1).Parameter();
2158 else if (Nbpnt< NbSecMin && again == 0) {
2161 cout <<"Number of points is too small, the step is reduced"<<endl;
2163 Standard_Real u1 = u1sov = Lin->Point(1).Parameter();
2164 Standard_Real u2 = u2sov = Lin->Point(Nbpnt).Parameter();
2165 MS = (u2-u1)*factor;
2168 else if (Nbpnt < NbSecMin && again == 1) {
2169 Standard_Real u1 = Lin->Point(1).Parameter();
2170 Standard_Real u2 = Lin->Point(Nbpnt).Parameter();
2171 if(Abs(u1-u1sov)>=TolGuide || Abs(u2-u2sov)>=TolGuide){
2174 cout <<"Number of points is still too small, the step is reduced"<<endl;
2181 cout <<"Number of points is still too small, quit"<<endl;
2183 return Standard_False;
2186 else if(Nbpnt < NbSecMin){
2188 cout <<"Number of points is still too small, quit"<<endl;
2190 return Standard_False;
2197 if(ChFi3d_GettraceDRAWWALK()) drawline(Lin,Standard_False);
2199 First = Lin->Point(1).Parameter();
2200 Last = Lin->Point(Nbpnt).Parameter();
2201 return Standard_True;