1 // Created on: 1997-07-28
2 // Created by: Jerome LEMONIER
3 // Copyright (c) 1997-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.
18 #include <Adaptor2d_HCurve2d.hxx>
19 #include <Adaptor3d_HCurve.hxx>
20 #include <Adaptor3d_HSurface.hxx>
21 #include <Blend_Point.hxx>
22 #include <BlendFunc.hxx>
23 #include <BRepBlend_SurfRstEvolRad.hxx>
25 #include <GeomFill.hxx>
27 #include <gp_Circ.hxx>
29 #include <gp_Pnt2d.hxx>
31 #include <gp_Vec2d.hxx>
32 #include <Law_Function.hxx>
33 #include <math_Gauss.hxx>
34 #include <math_Matrix.hxx>
35 #include <math_SVD.hxx>
36 #include <Precision.hxx>
37 #include <Standard_DomainError.hxx>
38 #include <Standard_NotImplemented.hxx>
39 #include <TColStd_SequenceOfReal.hxx>
43 static void t3dto2d(Standard_Real& a,
49 Standard_Real AB = A.Dot(B);
50 Standard_Real AC = A.Dot(C);
51 Standard_Real BC = B.Dot(C);
52 Standard_Real BB = B.Dot(B);
53 Standard_Real CC = C.Dot(C);
54 Standard_Real deno = (BB*CC-BC*BC);
55 a = (AB*CC-AC*BC)/deno;
56 b = (AC*BB-AB*BC)/deno;
59 static void FusionneIntervalles(const TColStd_Array1OfReal& I1,
60 const TColStd_Array1OfReal& I2,
61 TColStd_SequenceOfReal& Seq)
63 Standard_Integer ind1=1, ind2=1;
64 Standard_Real Epspar = Precision::PConfusion()*0.99;
65 // it is supposed that positioning works with PConfusion()/2
67 // Initialisation : IND1 and IND2 point at the first element
68 // of each of 2 tables to be processed. INDS points at the last
69 // element created by TABSOR
72 //--- TABSOR is filled by parsing TABLE1 and TABLE2 simultaneously ---
73 //------------------ and eliminating multiple occurrencies ------------
75 while ((ind1<=I1.Upper()) && (ind2<=I2.Upper())) {
78 if (Abs(v1-v2)<= Epspar) {
79 // Here the elements of I1 and I2 fit.
80 Seq.Append((v1+v2)/2);
85 // Here the element of I1 fits.
90 // Here the element of TABLE2 fits.
96 if (ind1>I1.Upper()) {
97 //----- Here I1 is exhausted, completed with the end of TABLE2 -------
99 for (; ind2<=I2.Upper(); ind2++) {
100 Seq.Append(I2(ind2));
104 if (ind2>I2.Upper()) {
105 //----- Here I2 is exhausted, completed with the end of I1 -------
107 for (; ind1<=I1.Upper(); ind1++) {
108 Seq.Append(I1(ind1));
113 //=======================================================================
114 //function : BRepBlend_SurfRstEvolRad
115 //purpose : Contructor
116 //=======================================================================
117 BRepBlend_SurfRstEvolRad::BRepBlend_SurfRstEvolRad
118 (const Handle(Adaptor3d_HSurface)& Surf,
119 const Handle(Adaptor3d_HSurface)& SurfRst,
120 const Handle(Adaptor2d_HCurve2d)& Rst,
121 const Handle(Adaptor3d_HCurve)& CGuide,
122 const Handle(Law_Function)& Evol):
123 surf(Surf), surfrst(SurfRst),
124 rst(Rst), cons(Rst,SurfRst),
125 guide(CGuide), tguide(CGuide),
126 istangent(Standard_True),
127 maxang(RealFirst()), minang(RealLast()),
129 mySShape(BlendFunc_Rational)
135 //=======================================================================
138 //=======================================================================
139 Standard_Integer BRepBlend_SurfRstEvolRad::NbVariables() const
144 //=======================================================================
147 //=======================================================================
148 Standard_Integer BRepBlend_SurfRstEvolRad::NbEquations() const
153 //=======================================================================
156 //=======================================================================
157 Standard_Boolean BRepBlend_SurfRstEvolRad::Value
158 (const math_Vector& X,
161 gp_Vec d1u1,d1v1,ns,vref;
164 surf->D1(X(1),X(2),pts,d1u1,d1v1);
165 ptrst = cons.Value(X(3));
167 F(1) = nplan.XYZ().Dot(pts.XYZ()) + theD;
169 F(2) = nplan.XYZ().Dot(ptrst.XYZ()) + theD;
171 ns = d1u1.Crossed(d1v1);
172 norm = nplan.Crossed(ns).Magnitude();
173 ns.SetLinearForm(nplan.Dot(ns)/norm,nplan, -1./norm,ns);
174 vref.SetLinearForm(ray,ns,gp_Vec(ptrst,pts));
175 F(3) = vref.SquareMagnitude() - ray*ray;
176 return Standard_True;
179 //=======================================================================
180 //function : Derivatives
182 //=======================================================================
183 Standard_Boolean BRepBlend_SurfRstEvolRad::Derivatives
184 (const math_Vector& X,
186 { gp_Vec d1u1,d1v1,d2u1,d2v1,d2uv1,d1;
187 gp_Vec ns,ncrossns,resul,temp, vref;
189 Standard_Real norm,ndotns,grosterme;
191 surf->D2(X(1),X(2),pts,d1u1,d1v1,d2u1,d2v1,d2uv1);
192 cons.D1(X(3),ptrst,d1);
194 D(1,1) = nplan.Dot(d1u1);
195 D(1,2) = nplan.Dot(d1v1);
200 D(2,3) = nplan.Dot(d1);
203 ns = d1u1.Crossed(d1v1);
204 ncrossns = nplan.Crossed(ns);
205 norm = ncrossns.Magnitude();
206 ndotns = nplan.Dot(ns);
208 vref.SetLinearForm(ndotns,nplan,-1.,ns);
210 vref.SetLinearForm(ray,vref,gp_Vec(ptrst,pts));
212 // Derivative corresponding to u1
213 temp = d2u1.Crossed(d1v1).Added(d1u1.Crossed(d2uv1));
214 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
215 resul.SetLinearForm(-ray/norm*(grosterme*ndotns-nplan.Dot(temp)),nplan,
216 ray*grosterme/norm,ns,
220 D(3,1) = 2.*(resul.Dot(vref));
223 // Derivative corresponding to v1
224 temp = d2uv1.Crossed(d1v1).Added(d1u1.Crossed(d2v1));
225 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
226 resul.SetLinearForm(-ray/norm*(grosterme*ndotns-nplan.Dot(temp)),nplan,
227 ray*grosterme/norm,ns,
231 D(3,2) = 2.*(resul.Dot(vref));
233 D(3,3) = -2.*(d1.Dot(vref));
235 return Standard_True;
239 //=======================================================================
242 //=======================================================================
243 Standard_Boolean BRepBlend_SurfRstEvolRad::Values
244 (const math_Vector& X,
249 gp_Vec d2u1,d2v1,d2uv1;
250 gp_Vec ns,ncrossns,resul,temp,vref;
252 Standard_Real norm,ndotns,grosterme;
254 surf->D2(X(1),X(2),pts,d1u1,d1v1,d2u1,d2v1,d2uv1);
255 cons.D1(X(3),ptrst,d1);
257 F(1) = nplan.XYZ().Dot(pts.XYZ()) + theD;
258 F(2) = nplan.XYZ().Dot(ptrst.XYZ()) + theD;
260 D(1,1) = nplan.Dot(d1u1);
261 D(1,2) = nplan.Dot(d1v1);
266 D(2,3) = nplan.Dot(d1);
269 ns = d1u1.Crossed(d1v1);
270 ncrossns = nplan.Crossed(ns);
271 norm = ncrossns.Magnitude();
272 ndotns = nplan.Dot(ns);
274 vref.SetLinearForm(ndotns,nplan,-1.,ns);
276 vref.SetLinearForm(ray,vref,gp_Vec(ptrst,pts));
278 F(3) = vref.SquareMagnitude() - ray*ray;
281 // Derivative corresponding to u1
282 temp = d2u1.Crossed(d1v1).Added(d1u1.Crossed(d2uv1));
283 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
284 resul.SetLinearForm(-ray/norm*(grosterme*ndotns-nplan.Dot(temp)),nplan,
285 ray*grosterme/norm,ns,
289 D(3,1) = 2.*(resul.Dot(vref));
292 // Derivative corresponding to v1
293 temp = d2uv1.Crossed(d1v1).Added(d1u1.Crossed(d2v1));
294 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
295 resul.SetLinearForm(-ray/norm*(grosterme*ndotns-nplan.Dot(temp)),nplan,
296 ray*grosterme/norm,ns,
300 D(3,2) = 2.*(resul.Dot(vref));
302 D(3,3) = -2.*(d1.Dot(vref));
304 return Standard_True;
307 //=======================================================================
310 //=======================================================================
311 void BRepBlend_SurfRstEvolRad::Set
312 (const Handle(Adaptor3d_HSurface)& SurfRef,
313 const Handle(Adaptor2d_HCurve2d)& RstRef)
319 //=======================================================================
322 //=======================================================================
323 void BRepBlend_SurfRstEvolRad::Set(const Standard_Real Param)
325 d1gui = gp_Vec(0.,0.,0.);
326 nplan = gp_Vec(0.,0.,0.);
327 tguide->D2(Param,ptgui,d1gui,d2gui);
328 normtg = d1gui.Magnitude();
329 nplan.SetXYZ(d1gui.Normalized().XYZ());
330 gp_XYZ nplanXYZ(nplan.XYZ());
331 gp_XYZ ptguiXYZ(ptgui.XYZ());
332 theD = nplanXYZ.Dot(ptguiXYZ) ;
333 theD = theD * (-1.) ;
334 tevol->D1(Param,ray,dray);
339 //=======================================================================
341 //purpose : Segments the curve in its useful part.
342 // Precision is taken arbitrary small !?
343 //=======================================================================
344 void BRepBlend_SurfRstEvolRad::Set
345 (const Standard_Real First,
346 const Standard_Real Last)
348 tguide = guide->Trim(First,Last,1.e-12);
349 tevol = fevol->Trim(First,Last,1.e-12);
352 //=======================================================================
355 //=======================================================================
356 void BRepBlend_SurfRstEvolRad::GetTolerance
357 (math_Vector& Tolerance,
358 const Standard_Real Tol) const
360 Tolerance(1) = surf->UResolution(Tol);
361 Tolerance(2) = surf->VResolution(Tol);
362 Tolerance(3) = cons.Resolution(Tol);
365 //=======================================================================
368 //=======================================================================
369 void BRepBlend_SurfRstEvolRad::GetBounds
370 (math_Vector& InfBound,
371 math_Vector& SupBound) const
373 InfBound(1) = surf->FirstUParameter();
374 InfBound(2) = surf->FirstVParameter();
375 InfBound(3) = cons.FirstParameter();
376 SupBound(1) = surf->LastUParameter();
377 SupBound(2) = surf->LastVParameter();
378 SupBound(3) = cons.LastParameter();
380 if(!Precision::IsInfinite(InfBound(1)) &&
381 !Precision::IsInfinite(SupBound(1))) {
382 Standard_Real range = (SupBound(1) - InfBound(1));
383 InfBound(1) -= range;
384 SupBound(1) += range;
386 if(!Precision::IsInfinite(InfBound(2)) &&
387 !Precision::IsInfinite(SupBound(2))) {
388 Standard_Real range = (SupBound(2) - InfBound(2));
389 InfBound(2) -= range;
390 SupBound(2) += range;
394 //=======================================================================
397 //=======================================================================
398 Standard_Boolean BRepBlend_SurfRstEvolRad::IsSolution
399 (const math_Vector& Sol,
400 const Standard_Real Tol)
402 math_Vector valsol(1,3),secmember(1,3);
403 math_Matrix gradsol(1,3,1,3);
405 gp_Vec dnplan,d1u1,d1v1,d1urst,d1vrst,d1,temp,ns,ns2,ncrossns,resul;
407 Standard_Real norm,ndotns,grosterme;
408 Standard_Real Cosa,Sina,Angle;
410 Values(Sol,valsol,gradsol);
411 if (Abs(valsol(1)) <= Tol &&
412 Abs(valsol(2)) <= Tol &&
413 Abs(valsol(3)) <= 2*Tol*Abs(ray) ) {
415 // Calculation of tangents
417 pt2ds = gp_Pnt2d(Sol(1),Sol(2));
419 pt2drst = rst->Value(prmrst);
420 surf->D1(Sol(1),Sol(2),pts,d1u1,d1v1);
421 cons.D1(Sol(3),ptrst,d1);
422 dnplan.SetLinearForm(1./normtg,d2gui,
423 -1./normtg*(nplan.Dot(d2gui)),nplan);
425 temp.SetXYZ(pts.XYZ() - ptgui.XYZ());
426 secmember(1) = normtg - dnplan.Dot(temp);
428 temp.SetXYZ(ptrst.XYZ() - ptgui.XYZ());
429 secmember(2) = normtg - dnplan.Dot(temp);
431 ns = d1u1.Crossed(d1v1);
432 ncrossns = nplan.Crossed(ns);
433 ndotns = nplan.Dot(ns);
434 norm = ncrossns.Magnitude();
436 grosterme = ncrossns.Dot(dnplan.Crossed(ns))/norm/norm;
438 dnw.SetLinearForm((dnplan.Dot(ns)-grosterme*ndotns)/norm,nplan,
442 ns.SetLinearForm(ndotns/norm,nplan, -1./norm,ns);
443 resul.SetLinearForm(ray, ns, gp_Vec(ptrst,pts));
445 secmember(3) = -2.*ray*(dnw.Dot(resul)) - 2.*dray*(ns.Dot(resul)) + 2.*ray*dray;
446 math_Gauss Resol(gradsol);
447 if (Resol.IsDone()) {
448 Resol.Solve(secmember);
449 istangent = Standard_False;
452 math_SVD SingRS (gradsol);
453 if (SingRS.IsDone()) {
454 math_Vector DEDT(1,3);
456 SingRS.Solve(DEDT, secmember, 1.e-6);
457 istangent = Standard_False;
459 else istangent = Standard_True;
463 tgs.SetLinearForm(secmember(1),d1u1,secmember(2),d1v1);
464 tgrst = secmember(3)*d1;
465 tg2ds.SetCoord(secmember(1),secmember(2));
466 surfrst->D1(pt2drst.X(),pt2drst.Y(),bid,d1urst,d1vrst);
468 t3dto2d(a,b,tgrst,d1urst,d1vrst);
469 tg2drst.SetCoord(a,b);
470 istangent = Standard_False;
473 istangent = Standard_True;
476 if(ray>0.) ns.Reverse();
477 ns2 = -resul.Normalized();
480 Sina = nplan.Dot(ns.Crossed(ns2));
482 Sina = -Sina; //nplan is changed into -nplan
487 Angle = 2.*M_PI - Angle;
490 if (Angle>maxang) {maxang = Angle;}
491 if (Angle<minang) {minang = Angle;}
492 distmin = Min( distmin, pts.Distance(ptrst));
494 return Standard_True;
496 istangent = Standard_True;
497 return Standard_False;
501 //=======================================================================
502 //function : GetMinimalDistance
504 //=======================================================================
506 Standard_Real BRepBlend_SurfRstEvolRad::GetMinimalDistance() const
511 //=======================================================================
514 //=======================================================================
515 const gp_Pnt& BRepBlend_SurfRstEvolRad::PointOnS() const
520 //=======================================================================
523 //=======================================================================
524 const gp_Pnt& BRepBlend_SurfRstEvolRad::PointOnRst() const
529 //=======================================================================
532 //=======================================================================
533 const gp_Pnt2d& BRepBlend_SurfRstEvolRad::Pnt2dOnS() const
538 //=======================================================================
541 //=======================================================================
542 const gp_Pnt2d& BRepBlend_SurfRstEvolRad::Pnt2dOnRst() const
547 //=======================================================================
550 //=======================================================================
551 Standard_Real BRepBlend_SurfRstEvolRad::ParameterOnRst() const
556 //=======================================================================
559 //=======================================================================
560 Standard_Boolean BRepBlend_SurfRstEvolRad::IsTangencyPoint() const
565 //=======================================================================
568 //=======================================================================
569 const gp_Vec& BRepBlend_SurfRstEvolRad::TangentOnS() const
571 if (istangent) {Standard_DomainError::Raise();}
575 //=======================================================================
578 //=======================================================================
579 const gp_Vec2d& BRepBlend_SurfRstEvolRad::Tangent2dOnS() const
581 if (istangent) {Standard_DomainError::Raise();}
585 //=======================================================================
588 //=======================================================================
589 const gp_Vec& BRepBlend_SurfRstEvolRad::TangentOnRst() const
591 if (istangent) {Standard_DomainError::Raise();}
595 //=======================================================================
598 //=======================================================================
599 const gp_Vec2d& BRepBlend_SurfRstEvolRad::Tangent2dOnRst() const
601 if (istangent) {Standard_DomainError::Raise();}
605 //=======================================================================
608 //=======================================================================
609 Standard_Boolean BRepBlend_SurfRstEvolRad::Decroch
610 (const math_Vector& Sol,
614 gp_Vec TgRst, NRst, NRstInPlane, NSInPlane;
617 Standard_Real norm,unsurnorm;
619 surf->D1(Sol(1),Sol(2),bid,d1u,d1v);
620 NS = NSInPlane = d1u.Crossed(d1v);
622 norm = nplan.Crossed(NS).Magnitude();
624 NSInPlane.SetLinearForm(nplan.Dot(NS)*unsurnorm,nplan,-unsurnorm,NS);
626 Center.SetXYZ(bid.XYZ()+ray*NSInPlane.XYZ());
627 if(choix>2) NSInPlane.Reverse();
628 TgS = nplan.Crossed(gp_Vec(Center,bid));
633 rstref->Value(Sol(3)).Coord(u,v);
634 surfref->D1(u,v,bid,d1u,d1v);
635 NRst = d1u.Crossed(d1v);
636 norm = nplan.Crossed(NRst).Magnitude();
638 NRstInPlane.SetLinearForm(nplan.Dot(NRst)*unsurnorm,nplan,-unsurnorm,NRst);
639 gp_Vec centptrst(Center,bid);
640 if(centptrst.Dot(NRstInPlane) < 0.) NRstInPlane.Reverse();
641 TgRst = nplan.Crossed(centptrst);
646 Standard_Real dot, NT = NRstInPlane.Magnitude();
647 NT *= TgRst.Magnitude();
648 if (Abs(NT) < 1.e-7) {
649 return Standard_False; // Singularity or Incoherence.
651 dot = NRstInPlane.Dot(TgRst);
654 return (dot < 1.e-10);
657 //=======================================================================
660 //=======================================================================
661 void BRepBlend_SurfRstEvolRad::Set (const Standard_Integer Choix)
679 //=======================================================================
682 //=======================================================================
683 void BRepBlend_SurfRstEvolRad::Set(const BlendFunc_SectionShape TypeSection)
685 mySShape = TypeSection;
688 //=======================================================================
691 //=======================================================================
692 void BRepBlend_SurfRstEvolRad::Section
693 (const Standard_Real Param,
694 const Standard_Real U,
695 const Standard_Real V,
696 const Standard_Real W,
706 tguide->D1(Param,ptgui,d1gui);
707 np = d1gui.Normalized();
708 ray = sg1*tevol->Value(Param);
710 surf->D1(U,V,pts,d1u1,d1v1);
711 ptrst = cons.Value(W);
713 ns = d1u1.Crossed(d1v1);
715 norm = nplan.Crossed(ns).Magnitude();
716 ns.SetLinearForm(nplan.Dot(ns)/norm,nplan, -1./norm,ns);
717 Center.SetXYZ(pts.XYZ()+ray*ns.XYZ());
718 C.SetRadius(Abs(ray));
726 C.SetPosition(gp_Ax2(Center,np,ns));
728 Pdeb = 0.; //ElCLib::Parameter(C,pts);
729 Pfin = ElCLib::Parameter(C,ptrst);
731 // Test negative and almost null angles : Single Case
734 C.SetPosition(gp_Ax2(Center,np,ns));
735 Pfin = ElCLib::Parameter(C,ptrst);
737 if (Pfin < Precision::PConfusion()) Pfin += Precision::PConfusion();
740 //=======================================================================
743 //=======================================================================
744 Standard_Boolean BRepBlend_SurfRstEvolRad::IsRational() const
746 return (mySShape==BlendFunc_Rational || mySShape==BlendFunc_QuasiAngular);
749 //=======================================================================
752 //=======================================================================
753 Standard_Real BRepBlend_SurfRstEvolRad::GetSectionSize() const
755 return maxang*Abs(ray);
758 //=======================================================================
761 //=======================================================================
762 void BRepBlend_SurfRstEvolRad::GetMinimalWeight(TColStd_Array1OfReal& Weigths) const
764 BlendFunc::GetMinimalWeights(mySShape, myTConv, minang, maxang, Weigths );
765 // It is supposed that it does not depend on the Radius!
768 //=======================================================================
771 //=======================================================================
772 Standard_Integer BRepBlend_SurfRstEvolRad::NbIntervals(const GeomAbs_Shape S) const
774 Standard_Integer Nb_Int_Courbe, Nb_Int_Loi;
775 Nb_Int_Courbe = guide->NbIntervals(BlendFunc::NextShape(S));
776 Nb_Int_Loi = fevol->NbIntervals(S);
779 return Nb_Int_Courbe;
782 TColStd_Array1OfReal IntC(1, Nb_Int_Courbe+1);
783 TColStd_Array1OfReal IntL(1, Nb_Int_Loi+1);
784 TColStd_SequenceOfReal Inter;
785 guide->Intervals(IntC, BlendFunc::NextShape(S));
786 fevol->Intervals(IntL, S);
788 FusionneIntervalles( IntC, IntL, Inter);
789 return Inter.Length()-1;
792 //=======================================================================
795 //=======================================================================
796 void BRepBlend_SurfRstEvolRad::Intervals(TColStd_Array1OfReal& T,
797 const GeomAbs_Shape S) const
799 Standard_Integer Nb_Int_Courbe, Nb_Int_Loi;
800 Nb_Int_Courbe = guide->NbIntervals(BlendFunc::NextShape(S));
801 Nb_Int_Loi = fevol->NbIntervals(S);
804 guide->Intervals(T, BlendFunc::NextShape(S));
807 TColStd_Array1OfReal IntC(1, Nb_Int_Courbe+1);
808 TColStd_Array1OfReal IntL(1, Nb_Int_Loi+1);
809 TColStd_SequenceOfReal Inter;
810 guide->Intervals(IntC, BlendFunc::NextShape(S));
811 fevol->Intervals(IntL, S);
813 FusionneIntervalles( IntC, IntL, Inter);
814 for (Standard_Integer ii=1; ii<=Inter.Length(); ii++) {
821 //=======================================================================
824 //=======================================================================
825 void BRepBlend_SurfRstEvolRad::GetShape
826 (Standard_Integer& NbPoles,
827 Standard_Integer& NbKnots,
828 Standard_Integer& Degree,
829 Standard_Integer& NbPoles2d)
832 BlendFunc::GetShape(mySShape,maxang,NbPoles,NbKnots,Degree,myTConv);
835 //=======================================================================
838 //=======================================================================
839 void BRepBlend_SurfRstEvolRad::GetTolerance
840 (const Standard_Real BoundTol,
841 const Standard_Real SurfTol,
842 const Standard_Real AngleTol,
844 math_Vector& Tol1d) const
846 Standard_Integer low = Tol3d.Lower() , up=Tol3d.Upper();
848 Tol= GeomFill::GetTolerance(myTConv, minang, Abs(ray),
852 Tol3d(low+1) = Tol3d(up-1) = Min( Tol, SurfTol);
853 Tol3d(low) = Tol3d(up) = Min( Tol, BoundTol);
856 //=======================================================================
859 //=======================================================================
860 void BRepBlend_SurfRstEvolRad::Knots(TColStd_Array1OfReal& TKnots)
862 GeomFill::Knots(myTConv,TKnots);
865 //=======================================================================
868 //=======================================================================
869 void BRepBlend_SurfRstEvolRad::Mults(TColStd_Array1OfInteger& TMults)
871 GeomFill::Mults(myTConv,TMults);
874 //=======================================================================
877 //=======================================================================
878 Standard_Boolean BRepBlend_SurfRstEvolRad::Section
879 (const Blend_Point& P,
880 TColgp_Array1OfPnt& Poles,
881 TColgp_Array1OfVec& DPoles,
882 TColgp_Array1OfPnt2d& Poles2d,
883 TColgp_Array1OfVec2d& DPoles2d,
884 TColStd_Array1OfReal& Weigths,
885 TColStd_Array1OfReal& DWeigths)
888 gp_Vec d1u1,d1v1,d2u1,d2v1,d2uv1,d1;
889 gp_Vec ns,ns2,dnplan,dnw,dn2w;//,np2,dnp2;
891 gp_Vec resulu,resulv,temp,tgct,resul;
892 gp_Vec d1urst,d1vrst;
895 Standard_Real norm,ndotns,grosterme,aDray;
897 math_Vector sol(1,3),valsol(1,3),secmember(1,3);
898 math_Matrix gradsol(1,3,1,3);
900 Standard_Real prm = P.Parameter(),rayprim;
901 Standard_Integer low = Poles.Lower();
902 Standard_Integer upp = Poles.Upper();
903 Standard_Boolean istgt;
905 tguide->D2(prm,ptgui,d1gui,d2gui);
907 tevol->D1(prm,ray,aDray);
910 normtg = d1gui.Magnitude();
911 nplan = d1gui.Normalized();
912 dnplan.SetLinearForm(1./normtg,d2gui,
913 -1./normtg*(nplan.Dot(d2gui)),nplan);
915 P.ParametersOnS(sol(1),sol(2));
916 sol(3) = prmrst = P.ParameterOnC();
917 pt2drst = rst->Value(prmrst);
919 Values(sol,valsol,gradsol);
921 surf->D2(sol(1),sol(2),pts,d1u1,d1v1,d2u1,d2v1,d2uv1);
922 cons.D1(sol(3),ptrst,d1);
924 temp.SetXYZ(pts.XYZ()- ptgui.XYZ());
925 secmember(1) = normtg - dnplan.Dot(temp);
927 temp.SetXYZ(ptrst.XYZ()- ptgui.XYZ());
928 secmember(2) = normtg - dnplan.Dot(temp);
930 ns = d1u1.Crossed(d1v1);
931 ncrossns = nplan.Crossed(ns);
932 ndotns = nplan.Dot(ns);
933 norm = ncrossns.Magnitude();
935 norm = 1; // Not enough, but it is not necessary to stop
937 cout << " SurfRstEvolRad : Surface single " << endl;
941 // Derivative of n1 corresponding to w
943 grosterme = ncrossns.Dot(dnplan.Crossed(ns))/norm/norm;
944 dnw.SetLinearForm((dnplan.Dot(ns)-grosterme*ndotns)/norm,nplan,
948 temp.SetLinearForm(ndotns/norm,nplan, -1./norm,ns);
949 resul.SetLinearForm(ray,temp,gp_Vec(ptrst,pts));
951 //secmember(3) = -2.*ray*(dnw.Dot(resul)); // jag 950105 il manquait ray
952 secmember(3) = -2.*ray*(dnw.Dot(resul)) - 2.*aDray*(temp.Dot(resul)) + 2.*ray*aDray;
953 math_Gauss Resol(gradsol);
955 if (Resol.IsDone()) {
956 Resol.Solve(secmember);
957 istgt = Standard_False;
960 math_SVD SingRS (gradsol);
961 if (SingRS.IsDone()) {
962 math_Vector DEDT(1,3);
964 SingRS.Solve(DEDT, secmember, 1.e-6);
965 istgt = Standard_False;
967 else istgt = Standard_True;
972 tgs.SetLinearForm(secmember(1),d1u1,secmember(2),d1v1);
973 tgrst = secmember(3)*d1;
974 // Derivative of n1 corresponding to u1
975 temp = d2u1.Crossed(d1v1).Added(d1u1.Crossed(d2uv1));
976 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
977 resulu.SetLinearForm(-(grosterme*ndotns-nplan.Dot(temp))/norm,nplan,
981 // Derivative of n1 corresponding to v1
982 temp = d2uv1.Crossed(d1v1).Added(d1u1.Crossed(d2v1));
983 grosterme = ncrossns.Dot(nplan.Crossed(temp))/norm/norm;
984 resulv.SetLinearForm(-(grosterme*ndotns-nplan.Dot(temp))/norm,nplan,
989 dnw.SetLinearForm(secmember(1),resulu,secmember(2),resulv,dnw);
990 ns.SetLinearForm(ndotns/norm,nplan, -1./norm,ns);
992 dn2w.SetLinearForm(ray, dnw, -1., tgrst, tgs);
993 dn2w.SetLinearForm(aDray,ns,dn2w);
994 norm = resul.Magnitude();
996 ns2 = -resul.Normalized();
997 dn2w.SetLinearForm(ns2.Dot(dn2w),ns2,-1.,dn2w);
999 istgt = Standard_False;
1002 ns.SetLinearForm(ndotns/norm,nplan, -1./norm,ns);
1003 ns2 = -resul.Normalized();
1004 istgt = Standard_True;
1009 Poles2d(Poles2d.Lower()).SetCoord(sol(1),sol(2));
1010 Poles2d(Poles2d.Upper()).SetCoord(pt2drst.X(),pt2drst.Y());
1012 DPoles2d(Poles2d.Lower()).SetCoord(secmember(1),secmember(2));
1013 surfrst->D1(pt2drst.X(),pt2drst.Y(),bid,d1urst,d1vrst);
1015 t3dto2d(a,b,tgrst,d1urst,d1vrst);
1016 DPoles2d(Poles2d.Upper()).SetCoord(a,b);
1020 if (mySShape == BlendFunc_Linear) {
1027 DPoles(upp) = tgrst;
1028 DWeigths(low) = 0.0;
1029 DWeigths(upp) = 0.0;
1034 // Case of the circle
1035 Center.SetXYZ(pts.XYZ()+ray*ns.XYZ());
1037 tgct.SetLinearForm(ray,dnw,aDray,ns,tgs);
1051 if (ray < 0.) { // to avoid Abs(dray) some lines below
1054 else rayprim = aDray;
1056 return GeomFill::GetCircle(myTConv,
1070 GeomFill::GetCircle(myTConv,
1075 return Standard_False;
1079 //=======================================================================
1082 //=======================================================================
1083 Standard_Boolean BRepBlend_SurfRstEvolRad::Section (const Blend_Point& /*P*/,
1084 TColgp_Array1OfPnt& /*Poles*/,
1085 TColgp_Array1OfVec& /*DPoles*/,
1086 TColgp_Array1OfVec& /*D2Poles*/,
1087 TColgp_Array1OfPnt2d& /*Poles2d*/,
1088 TColgp_Array1OfVec2d& /*DPoles2d*/,
1089 TColgp_Array1OfVec2d& /*D2Poles2d*/,
1090 TColStd_Array1OfReal& /*Weigths*/,
1091 TColStd_Array1OfReal& /*DWeigths*/,
1092 TColStd_Array1OfReal& /*D2Weigths*/)
1094 return Standard_False;
1097 //=======================================================================
1100 //=======================================================================
1101 void BRepBlend_SurfRstEvolRad::Section
1102 (const Blend_Point& P,
1103 TColgp_Array1OfPnt& Poles,
1104 TColgp_Array1OfPnt2d& Poles2d,
1105 TColStd_Array1OfReal& Weigths)
1107 gp_Vec d1u1,d1v1;//,d1;
1108 gp_Vec ns,ns2;//,temp,np2;
1111 Standard_Real norm,u1,v1,w;
1113 Standard_Real prm = P.Parameter();
1114 Standard_Integer low = Poles.Lower();
1115 Standard_Integer upp = Poles.Upper();
1117 tguide->D1(prm,ptgui,d1gui);
1118 ray = tevol->Value(prm);
1120 nplan = d1gui.Normalized();
1122 P.ParametersOnS(u1,v1);
1123 w = P.ParameterOnC(); //jlr : point on curve not on surface
1124 gp_Pnt2d pt2d = rst->Value(w);
1126 surf->D1(u1,v1,pts,d1u1,d1v1);
1127 ptrst = cons.Value(w);
1129 distmin = Min (distmin, pts.Distance(ptrst));
1131 Poles2d(Poles2d.Lower()).SetCoord(u1,v1);
1132 Poles2d(Poles2d.Upper()).SetCoord(pt2d.X(),pt2d.Y());
1135 if (mySShape == BlendFunc_Linear) {
1143 ns = d1u1.Crossed(d1v1);
1144 norm = nplan.Crossed(ns).Magnitude();
1146 ns.SetLinearForm(nplan.Dot(ns)/norm,nplan, -1./norm,ns);
1148 Center.SetXYZ(pts.XYZ()+ray*ns.XYZ());
1150 ns2 = gp_Vec(Center,ptrst).Normalized();
1151 if(ray>0) ns.Reverse();
1156 GeomFill::GetCircle(myTConv,
1163 void BRepBlend_SurfRstEvolRad::Resolution(const Standard_Integer IC2d,
1164 const Standard_Real Tol,
1165 Standard_Real& TolU,
1166 Standard_Real& TolV) const
1169 TolU = surf->UResolution(Tol);
1170 TolV = surf->VResolution(Tol);
1173 TolU = surfrst->UResolution(Tol);
1174 TolV = surfrst->VResolution(Tol);