mirror of
https://git.dev.opencascade.org/repos/occt.git
synced 2025-04-04 18:06:22 +03:00
0023824: Bad results of sweep operation when a path curve has unpredictable torsion along its way.
Adding test cases for this fix
This commit is contained in:
parent
26347898a8
commit
a31abc03d7
@ -525,7 +525,7 @@ static Standard_Boolean GoodOrientation(const Bnd_Box& B,
|
||||
BRepFill_Sweep Sweep(mySec, myLoc, Standard_True);
|
||||
Sweep.SetTolerance(myTol);
|
||||
Sweep.SetAngularControl(angmin, angmax);
|
||||
Sweep.Build(myStyle, GeomFill_Location, myCont);
|
||||
Sweep.Build(myStyle, myCont);
|
||||
if (Sweep.IsDone()) {
|
||||
myShape = Sweep.Shape();
|
||||
myShell = TopoDS::Shell(myShape);
|
||||
|
@ -41,8 +41,8 @@ uses
|
||||
Edge from TopoDS,
|
||||
Vertex from TopoDS,
|
||||
Pnt from gp,
|
||||
Trsf from gp
|
||||
|
||||
Trsf from gp,
|
||||
Trihedron from GeomFill
|
||||
|
||||
raises
|
||||
DomainError from Standard,
|
||||
@ -57,6 +57,21 @@ is
|
||||
GeneratePartCase : Boolean from Standard = Standard_False)
|
||||
returns Pipe from BRepFill;
|
||||
|
||||
SetMode(me : in out;
|
||||
aMode : Trihedron from GeomFill);
|
||||
---Purpose: Set the mode of sweeping
|
||||
-- It can be:
|
||||
-- - Frenet
|
||||
-- - Corrected Frenet
|
||||
-- - Discrete Trihedron
|
||||
-- By default the mode is Corrected Frenet
|
||||
|
||||
SetForceApproxC1(me : in out;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
Perform (me : in out; Spine : Wire from TopoDS;
|
||||
Profile : Shape from TopoDS;
|
||||
GeneratePartCase : Boolean from Standard = Standard_False)
|
||||
@ -175,4 +190,7 @@ fields
|
||||
|
||||
myDegmax : Integer from Standard;
|
||||
mySegmax : Integer from Standard;
|
||||
myMode : Trihedron from GeomFill;
|
||||
myForceApproxC1 : Boolean from Standard;
|
||||
|
||||
end Pipe;
|
||||
|
@ -30,6 +30,8 @@
|
||||
#include <BRepTools_Substitution.hxx>
|
||||
|
||||
#include <GeomFill_CorrectedFrenet.hxx>
|
||||
#include <GeomFill_Frenet.hxx>
|
||||
#include <GeomFill_DiscreteTrihedron.hxx>
|
||||
#include <GeomFill_CurveAndTrihedron.hxx>
|
||||
|
||||
#include <BRepFill_SectionPlacement.hxx>
|
||||
@ -70,6 +72,8 @@ BRepFill_Pipe::BRepFill_Pipe()
|
||||
{
|
||||
myDegmax = 10;
|
||||
mySegmax = 100;
|
||||
myMode = GeomFill_IsCorrectedFrenet;
|
||||
myForceApproxC1 = Standard_False;
|
||||
}
|
||||
|
||||
|
||||
@ -84,9 +88,39 @@ BRepFill_Pipe::BRepFill_Pipe(const TopoDS_Wire& Spine,
|
||||
{
|
||||
myDegmax = 10;
|
||||
mySegmax = 100;
|
||||
myMode = GeomFill_IsCorrectedFrenet;
|
||||
myForceApproxC1 = Standard_False;
|
||||
Perform(Spine, Profile, KPart);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetMode
|
||||
//purpose : Set the mode of sweeping
|
||||
// It can be:
|
||||
// - Frenet
|
||||
// - Corrected Frenet
|
||||
// - Discrete Trihedron
|
||||
//=======================================================================
|
||||
|
||||
void BRepFill_Pipe::SetMode(const GeomFill_Trihedron aMode)
|
||||
{
|
||||
if (aMode == GeomFill_IsFrenet ||
|
||||
aMode == GeomFill_IsCorrectedFrenet ||
|
||||
aMode == GeomFill_IsDiscreteTrihedron)
|
||||
myMode = aMode;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetForceApproxC1
|
||||
//purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
|
||||
void BRepFill_Pipe::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myForceApproxC1 = ForceApproxC1;
|
||||
}
|
||||
|
||||
|
||||
//=======================================================================
|
||||
@ -111,9 +145,19 @@ void BRepFill_Pipe::Perform(const TopoDS_Wire& Spine,
|
||||
BRepTools_WireExplorer wexp;
|
||||
TopoDS_Shape TheProf;
|
||||
|
||||
|
||||
Handle(GeomFill_CorrectedFrenet) TLaw =
|
||||
new (GeomFill_CorrectedFrenet) ();
|
||||
Handle(GeomFill_TrihedronLaw) TLaw;
|
||||
switch (myMode)
|
||||
{
|
||||
case GeomFill_IsFrenet:
|
||||
TLaw = new GeomFill_Frenet();
|
||||
break;
|
||||
case GeomFill_IsCorrectedFrenet:
|
||||
TLaw = new GeomFill_CorrectedFrenet();
|
||||
break;
|
||||
case GeomFill_IsDiscreteTrihedron:
|
||||
TLaw = new GeomFill_DiscreteTrihedron();
|
||||
break;
|
||||
}
|
||||
Handle(GeomFill_CurveAndTrihedron) Loc =
|
||||
new (GeomFill_CurveAndTrihedron) (TLaw);
|
||||
myLoc = new (BRepFill_Edge3DLaw) (mySpine, Loc);
|
||||
@ -366,7 +410,8 @@ TopoDS_Wire BRepFill_Pipe::PipeLine(const gp_Pnt& Point) const
|
||||
|
||||
// Sweeping
|
||||
BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
|
||||
MkSw.Build( BRepFill_Modified, GeomFill_Location, GeomAbs_C2, myDegmax, mySegmax );
|
||||
MkSw.SetForceApproxC1(myForceApproxC1);
|
||||
MkSw.Build( BRepFill_Modified, GeomAbs_C2, GeomFill_Location, myDegmax, mySegmax );
|
||||
TopoDS_Shape aLocalShape = MkSw.Shape();
|
||||
return TopoDS::Wire(aLocalShape);
|
||||
// return TopoDS::Wire(MkSw.Shape());
|
||||
@ -491,7 +536,8 @@ TopoDS_Shape BRepFill_Pipe::MakeShape(const TopoDS_Shape& S,
|
||||
Handle(BRepFill_ShapeLaw) Section =
|
||||
new (BRepFill_ShapeLaw) (TopoDS::Vertex(TheS));
|
||||
BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
|
||||
MkSw.Build( BRepFill_Modified, GeomFill_Location, GeomAbs_C2, myDegmax, mySegmax );
|
||||
MkSw.SetForceApproxC1(myForceApproxC1);
|
||||
MkSw.Build( BRepFill_Modified, GeomAbs_C2, GeomFill_Location, myDegmax, mySegmax );
|
||||
result = MkSw.Shape();
|
||||
}
|
||||
|
||||
@ -501,7 +547,8 @@ TopoDS_Shape BRepFill_Pipe::MakeShape(const TopoDS_Shape& S,
|
||||
BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
|
||||
MkSw.SetBounds(TopoDS::Wire(TheFirst),
|
||||
TopoDS::Wire(TheLast));
|
||||
MkSw.Build( BRepFill_Modified, GeomFill_Location, GeomAbs_C2, myDegmax, mySegmax );
|
||||
MkSw.SetForceApproxC1(myForceApproxC1);
|
||||
MkSw.Build( BRepFill_Modified, GeomAbs_C2, GeomFill_Location, myDegmax, mySegmax );
|
||||
result = MkSw.Shape();
|
||||
|
||||
// Labeling of elements
|
||||
|
@ -66,6 +66,12 @@ is
|
||||
---Level: Public
|
||||
---See Also:GeomFill_IsCorrectedFrenet
|
||||
|
||||
SetDiscrete(me : mutable);
|
||||
---Purpose: Set a Discrete trihedron
|
||||
-- to perform the sweeping
|
||||
---Level: Public
|
||||
---See Also:GeomFill_IsDiscreteTrihedron
|
||||
|
||||
Set(me : mutable; Axe : Ax2 from gp);
|
||||
---Purpose: Set an fixed trihedron to perform the sweeping
|
||||
-- all sections will be parallel.
|
||||
@ -106,6 +112,13 @@ is
|
||||
|
||||
---Level: Public
|
||||
|
||||
SetForceApproxC1(me : mutable;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
|
||||
-- =================================
|
||||
-- Methodes to define section(s)
|
||||
-- =================================
|
||||
@ -271,8 +284,9 @@ fields
|
||||
|
||||
myTol3d : Real;
|
||||
myBoundTol : Real;
|
||||
myTolAngular : Real;
|
||||
myTolAngular : Real;
|
||||
angmin, angmax : Real;
|
||||
myForceApproxC1 : Boolean;
|
||||
|
||||
myLaw : Function from Law;
|
||||
myLocation : LocationLaw from BRepFill;
|
||||
|
@ -52,6 +52,7 @@
|
||||
#include <GeomFill_TrihedronLaw.hxx>
|
||||
#include <GeomFill_CorrectedFrenet.hxx>
|
||||
#include <GeomFill_Frenet.hxx>
|
||||
#include <GeomFill_DiscreteTrihedron.hxx>
|
||||
#include <GeomFill_Fixed.hxx>
|
||||
#include <GeomFill_ConstantBiNormal.hxx>
|
||||
#include <GeomFill_SectionLaw.hxx>
|
||||
@ -211,6 +212,7 @@ BRepFill_PipeShell::BRepFill_PipeShell(const TopoDS_Wire& Spine)
|
||||
: mySpine(Spine),
|
||||
myTrihedron(GeomFill_IsCorrectedFrenet),
|
||||
myTransition(BRepFill_Modified),
|
||||
myForceApproxC1(Standard_False),
|
||||
myStatus(GeomFill_PipeOk)
|
||||
{
|
||||
myLocation.Nullify();
|
||||
@ -247,6 +249,23 @@ BRepFill_PipeShell::BRepFill_PipeShell(const TopoDS_Wire& Spine)
|
||||
mySection.Nullify(); //It is required to relocalize sections.
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetDiscrete
|
||||
//purpose : Define a law of Discrete Trihedron
|
||||
//=======================================================================
|
||||
void BRepFill_PipeShell::SetDiscrete()
|
||||
{
|
||||
Handle(GeomFill_TrihedronLaw) TLaw;
|
||||
|
||||
myTrihedron = GeomFill_IsDiscreteTrihedron;
|
||||
TLaw = new (GeomFill_DiscreteTrihedron) ();
|
||||
|
||||
Handle(GeomFill_CurveAndTrihedron) Loc =
|
||||
new (GeomFill_CurveAndTrihedron) (TLaw);
|
||||
myLocation = new (BRepFill_Edge3DLaw) (mySpine, Loc);
|
||||
mySection.Nullify(); //It is required to relocalize sections.
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Set
|
||||
//purpose : Define a law Constant
|
||||
@ -384,6 +403,17 @@ BRepFill_PipeShell::BRepFill_PipeShell(const TopoDS_Wire& Spine)
|
||||
mySection.Nullify(); //It is required to relocalize the sections.
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetForceApproxC1
|
||||
//purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
void BRepFill_PipeShell::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myForceApproxC1 = ForceApproxC1;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Add
|
||||
//purpose : Add a Section
|
||||
@ -629,9 +659,13 @@ BRepFill_PipeShell::BRepFill_PipeShell(const TopoDS_Wire& Spine)
|
||||
BRepFill_Sweep MkSw(mySection, myLocation, Standard_True);
|
||||
MkSw.SetTolerance(myTol3d, myBoundTol, 1.e-5, myTolAngular);
|
||||
MkSw.SetAngularControl(angmin, angmax);
|
||||
MkSw.SetForceApproxC1(myForceApproxC1);
|
||||
MkSw.SetBounds(TopoDS::Wire(myFirst),
|
||||
TopoDS::Wire(myLast));
|
||||
MkSw.Build(myTransition);
|
||||
GeomAbs_Shape theContinuity = GeomAbs_C2;
|
||||
if (myTrihedron == GeomFill_IsDiscreteTrihedron)
|
||||
theContinuity = GeomAbs_C0;
|
||||
MkSw.Build(myTransition, theContinuity);
|
||||
|
||||
myStatus = myLocation->GetStatus();
|
||||
Ok = (MkSw.IsDone() && (myStatus == GeomFill_PipeOk));
|
||||
|
@ -80,10 +80,17 @@ is
|
||||
-- Transition "Round" replace the Transition "Right"
|
||||
is static;
|
||||
|
||||
SetForceApproxC1(me: in out;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
|
||||
Build(me : in out;
|
||||
Transition : TransitionStyle = BRepFill_Modified;
|
||||
Approx : ApproxStyle = GeomFill_Location;
|
||||
Continuity : Shape from GeomAbs = GeomAbs_C2;
|
||||
Approx : ApproxStyle = GeomFill_Location;
|
||||
Degmax : Integer = 11;
|
||||
Segmax : Integer = 30);
|
||||
|
||||
@ -170,6 +177,7 @@ fields
|
||||
myContinuity : Shape from GeomAbs;
|
||||
myDegmax : Integer;
|
||||
mySegmax : Integer;
|
||||
myForceApproxC1 : Boolean;
|
||||
myShape : Shape from TopoDS;
|
||||
myLoc : LocationLaw from BRepFill;
|
||||
mySec : SectionLaw from BRepFill;
|
||||
|
@ -1685,6 +1685,7 @@ BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
|
||||
myContinuity = GeomAbs_C2;
|
||||
myDegmax = 11;
|
||||
mySegmax = 30;
|
||||
myForceApproxC1 = Standard_False;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
@ -1752,6 +1753,17 @@ BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
|
||||
myAngMax = Min (MaxAngle, 6.28);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetForceApproxC1
|
||||
//purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
void BRepFill_Sweep::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myForceApproxC1 = ForceApproxC1;
|
||||
}
|
||||
|
||||
///=======================================================================
|
||||
//function : CorrectApproxParameters
|
||||
//purpose :
|
||||
@ -1820,6 +1832,7 @@ BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
|
||||
// Curve by iso value
|
||||
GeomFill_Sweep Sweep(myLoc->Law(ipath), KPart);
|
||||
Sweep.SetTolerance(myTol3d, myBoundTol, myTol2d, myTolAngular);
|
||||
Sweep.SetForceApproxC1(myForceApproxC1);
|
||||
Sweep.Build(mySec->Law(isec), myApproxStyle, myContinuity, myDegmax, mySegmax);
|
||||
if (!Sweep.IsDone())
|
||||
return Standard_False;
|
||||
@ -1985,6 +1998,7 @@ BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
|
||||
|
||||
GeomFill_Sweep Sweep(myLoc->Law(IPath), KPart);
|
||||
Sweep.SetTolerance(myTol3d, myBoundTol, myTol2d, myTolAngular);
|
||||
Sweep.SetForceApproxC1(myForceApproxC1);
|
||||
|
||||
// Case of evolutionary section, definition of parametric correspondence
|
||||
if (!constSection) {
|
||||
@ -2491,13 +2505,13 @@ BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
|
||||
//purpose : Construt the result of sweeping
|
||||
//======================================================================
|
||||
void BRepFill_Sweep::Build(const BRepFill_TransitionStyle Transition,
|
||||
const GeomFill_ApproxStyle Approx,
|
||||
const GeomAbs_Shape Continuity,
|
||||
const GeomFill_ApproxStyle Approx,
|
||||
const Standard_Integer Degmax,
|
||||
const Standard_Integer Segmax)
|
||||
{
|
||||
myApproxStyle = Approx;
|
||||
myContinuity = Continuity;
|
||||
myApproxStyle = Approx;
|
||||
myDegmax = Degmax;
|
||||
mySegmax = Segmax;
|
||||
|
||||
|
@ -28,7 +28,8 @@ uses
|
||||
StdFail,
|
||||
gp,
|
||||
GeomAbs,
|
||||
Geom,
|
||||
Geom,
|
||||
GeomFill,
|
||||
Approx,
|
||||
TopoDS,
|
||||
TopTools,
|
||||
|
@ -35,6 +35,7 @@ class MakePipe from BRepOffsetAPI inherits MakeSweep from BRepPrimAPI
|
||||
-- with G1 continuous spines only.
|
||||
uses
|
||||
Pipe from BRepFill,
|
||||
Trihedron from GeomFill,
|
||||
Wire from TopoDS,
|
||||
Shape from TopoDS,
|
||||
Edge from TopoDS,
|
||||
@ -58,6 +59,21 @@ is
|
||||
-- composite solid.
|
||||
returns MakePipe from BRepOffsetAPI;
|
||||
|
||||
SetMode(me : in out;
|
||||
aMode : Trihedron from GeomFill);
|
||||
---Purpose: Set the mode of sweeping
|
||||
-- It can be:
|
||||
-- - Frenet
|
||||
-- - Corrected Frenet
|
||||
-- - Discrete Trihedron
|
||||
-- By default the mode is Corrected Frenet
|
||||
|
||||
SetForceApproxC1(me : in out;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
|
||||
Pipe(me) returns Pipe from BRepFill
|
||||
---C++: return const &
|
||||
|
@ -40,6 +40,32 @@ BRepOffsetAPI_MakePipe::BRepOffsetAPI_MakePipe(const TopoDS_Wire& Spine ,
|
||||
Build();
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetMode
|
||||
//purpose : Set the mode of sweeping
|
||||
// It can be:
|
||||
// - Frenet
|
||||
// - Corrected Frenet
|
||||
// - Discrete Trihedron
|
||||
//=======================================================================
|
||||
|
||||
void BRepOffsetAPI_MakePipe::SetMode(const GeomFill_Trihedron aMode)
|
||||
{
|
||||
myPipe.SetMode(aMode);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetForceApproxC1
|
||||
//purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
|
||||
void BRepOffsetAPI_MakePipe::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myPipe.SetForceApproxC1(ForceApproxC1);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Pipe
|
||||
//purpose :
|
||||
|
@ -73,6 +73,10 @@ is
|
||||
-- to perform the sweeping
|
||||
-- If IsFrenet is false, a corrected Frenet trihedron is used.
|
||||
|
||||
SetDiscreteMode(me : in out);
|
||||
---Purpose: Sets a Discrete trihedron
|
||||
-- to perform the sweeping
|
||||
|
||||
SetMode(me : in out; Axe : Ax2 from gp);
|
||||
---Purpose: Sets a fixed trihedron to perform the sweeping
|
||||
-- all sections will be parallel.
|
||||
@ -110,6 +114,7 @@ is
|
||||
|
||||
---Level: Public
|
||||
|
||||
|
||||
-- =================================
|
||||
-- Methodes to define section(s)
|
||||
-- =================================
|
||||
@ -212,6 +217,12 @@ is
|
||||
-- - boundary tolerance BoundTol
|
||||
-- - angular tolerance TolAngular.
|
||||
|
||||
SetForceApproxC1(me : in out;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
SetTransitionMode(me : in out;
|
||||
Mode :TransitionMode from BRepBuilderAPI = BRepBuilderAPI_Transformed)
|
||||
---Purpose: Sets the transition mode to manage discontinuities on
|
||||
|
@ -49,6 +49,15 @@ BRepOffsetAPI_MakePipeShell::BRepOffsetAPI_MakePipeShell(const TopoDS_Wire& Spin
|
||||
myPipe->Set(IsFrenet);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetDiscreteMode
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
void BRepOffsetAPI_MakePipeShell::SetDiscreteMode()
|
||||
{
|
||||
myPipe->SetDiscrete();
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetMode
|
||||
//purpose :
|
||||
@ -185,8 +194,9 @@ void BRepOffsetAPI_MakePipeShell::Delete( const TopoDS_Shape& Profile)
|
||||
}
|
||||
return Status;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetTransitionMode
|
||||
//function : SetTolerance
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
void BRepOffsetAPI_MakePipeShell::SetTolerance(const Standard_Real Tol3d,
|
||||
@ -196,6 +206,17 @@ void BRepOffsetAPI_MakePipeShell::Delete( const TopoDS_Shape& Profile)
|
||||
myPipe->SetTolerance(Tol3d, BoundTol, TolAngular);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetForceApproxC1
|
||||
//purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
void BRepOffsetAPI_MakePipeShell::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myPipe->SetForceApproxC1(ForceApproxC1);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetTransitionMode
|
||||
//purpose :
|
||||
|
@ -431,6 +431,7 @@ static Standard_Integer setsweep(Draw_Interpretor& di,
|
||||
di << " -FR : Tangent and Normal are given by Frenet trihedron" <<"\n";
|
||||
di << " -CF : Tangente is given by Frenet," << "\n";
|
||||
di << " the Normal is computed to minimize the torsion " << "\n";
|
||||
di << " -DT : discrete trihedron" << "\n";
|
||||
di << " -DX Surf : Tangent and Normal are given by Darboux trihedron," <<"\n";
|
||||
di << " Surf have to be a shell or a face" <<"\n";
|
||||
di << " -CN dx dy dz : BiNormal is given by dx dy dz" << "\n";
|
||||
@ -450,6 +451,9 @@ static Standard_Integer setsweep(Draw_Interpretor& di,
|
||||
else if (!strcmp(a[1],"-CF")) {
|
||||
Sweep->SetMode(Standard_False);
|
||||
}
|
||||
else if (!strcmp(a[1],"-DT")) {
|
||||
Sweep->SetDiscreteMode();
|
||||
}
|
||||
else if (!strcmp(a[1],"-DX")) {
|
||||
if (n!=3) {
|
||||
//cout << "bad arguments !" << endl;
|
||||
|
@ -67,7 +67,7 @@ is
|
||||
enumeration Trihedron
|
||||
is IsCorrectedFrenet, IsFixed, IsFrenet, IsConstantNormal, IsDarboux,
|
||||
IsGuideAC, IsGuidePlan,
|
||||
IsGuideACWithContact, IsGuidePlanWithContact end;
|
||||
IsGuideACWithContact, IsGuidePlanWithContact, IsDiscreteTrihedron end;
|
||||
|
||||
class Filling;
|
||||
---Purpose: Root class for Filling;
|
||||
@ -195,6 +195,13 @@ is
|
||||
class SequenceOfTrsf
|
||||
instantiates Sequence from TCollection (Trsf from gp);
|
||||
|
||||
class SequenceOfAx2
|
||||
instantiates Sequence from TCollection (Ax2 from gp);
|
||||
|
||||
class HSequenceOfAx2
|
||||
instantiates HSequence from TCollection (Ax2 from gp,
|
||||
SequenceOfAx2 from GeomFill);
|
||||
|
||||
--
|
||||
-- private classes
|
||||
--
|
||||
@ -226,6 +233,7 @@ is
|
||||
class Fixed;
|
||||
class Frenet;
|
||||
class CorrectedFrenet;
|
||||
class DiscreteTrihedron;
|
||||
class ConstantBiNormal;
|
||||
class Darboux;
|
||||
class DraftTrihedron;
|
||||
|
@ -37,7 +37,8 @@ uses
|
||||
HArray1OfReal from TColStd,
|
||||
SequenceOfReal from TColStd,
|
||||
HArray1OfVec from TColgp,
|
||||
SequenceOfVec from TColgp
|
||||
SequenceOfVec from TColgp,
|
||||
Trihedron from GeomFill
|
||||
|
||||
raises
|
||||
OutOfRange, ConstructionError
|
||||
@ -45,11 +46,14 @@ is
|
||||
|
||||
Create returns CorrectedFrenet from GeomFill;
|
||||
|
||||
Create (ForEvaluation: Boolean)
|
||||
returns CorrectedFrenet from GeomFill;
|
||||
|
||||
Copy(me)
|
||||
returns TrihedronLaw from GeomFill
|
||||
is redefined;
|
||||
|
||||
Init(me: mutable)
|
||||
Init(me: mutable)
|
||||
is static private;
|
||||
|
||||
InitInterval(me; First, Last, Step: Real;
|
||||
@ -59,7 +63,7 @@ is
|
||||
SeqPoles: out SequenceOfReal from TColStd;
|
||||
SeqAngle: out SequenceOfReal from TColStd;
|
||||
SeqTangent: out SequenceOfVec from TColgp;
|
||||
SeqNormal: out SequenceOfVec from TColgp)
|
||||
SeqNormal: out SequenceOfVec from TColgp)
|
||||
returns Boolean
|
||||
--- Purpose: Computes BSpline representation of Normal evolution at one
|
||||
--- interval of continuity of Frenet. Returns True if FuncInt = 0
|
||||
@ -142,6 +146,20 @@ is
|
||||
OutOfRange from Standard
|
||||
is redefined;
|
||||
|
||||
|
||||
-- =================== To define the best trihedron mode ===============
|
||||
|
||||
EvaluateBestMode(me : mutable)
|
||||
returns Trihedron from GeomFill;
|
||||
---Purpose: Tries to define the best trihedron mode
|
||||
-- for the curve. It can be:
|
||||
-- - Frenet
|
||||
-- - CorrectedFrenet
|
||||
-- - DiscreteTrihedron
|
||||
-- Warning: the CorrectedFrenet must be constructed
|
||||
-- with option ForEvaluation = True,
|
||||
-- the curve must be set by method SetCurve.
|
||||
|
||||
|
||||
-- =================== To help computation of Tolerance ===============
|
||||
GetAverageLaw(me : mutable;
|
||||
@ -165,11 +183,13 @@ is
|
||||
is redefined;
|
||||
|
||||
fields
|
||||
frenet : Frenet from GeomFill;
|
||||
EvolAroundT : Function from Law;
|
||||
TLaw : Function from Law;
|
||||
AT, AN : Vec from gp;
|
||||
isFrenet : Boolean;
|
||||
frenet : Frenet from GeomFill;
|
||||
EvolAroundT : Function from Law;
|
||||
TLaw : Function from Law;
|
||||
AT, AN : Vec from gp;
|
||||
isFrenet : Boolean;
|
||||
myForEvaluation : Boolean;
|
||||
|
||||
---OCC78
|
||||
HArrPoles : HArray1OfReal from TColStd;
|
||||
HArrAngle : HArray1OfReal from TColStd;
|
||||
|
@ -44,6 +44,7 @@
|
||||
#include <Geom_BSplineCurve.hxx>
|
||||
#include <TColgp_HArray1OfPnt.hxx>
|
||||
|
||||
|
||||
#ifdef DEB
|
||||
static Standard_Boolean Affich=0;
|
||||
#endif
|
||||
@ -90,6 +91,30 @@ static void draw(const Handle(Law_Function)& law)
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
static Standard_Real ComputeTorsion(const Standard_Real Param,
|
||||
const Handle(Adaptor3d_HCurve)& aCurve)
|
||||
{
|
||||
Standard_Real Torsion;
|
||||
|
||||
gp_Pnt aPoint;
|
||||
gp_Vec DC1, DC2, DC3;
|
||||
aCurve->D3(Param, aPoint, DC1, DC2, DC3);
|
||||
gp_Vec DC1crossDC2 = DC1 ^ DC2;
|
||||
Standard_Real Norm_DC1crossDC2 = DC1crossDC2.Magnitude();
|
||||
|
||||
Standard_Real DC1DC2DC3 = DC1crossDC2 * DC3 ; //mixed product
|
||||
|
||||
Standard_Real Tol = gp::Resolution();
|
||||
Standard_Real SquareNorm_DC1crossDC2 = Norm_DC1crossDC2 * Norm_DC1crossDC2;
|
||||
if (SquareNorm_DC1crossDC2 <= Tol)
|
||||
Torsion = 0.;
|
||||
else
|
||||
Torsion = DC1DC2DC3 / SquareNorm_DC1crossDC2 ;
|
||||
|
||||
return Torsion;
|
||||
}
|
||||
|
||||
//===============================================================
|
||||
// Function : smoothlaw
|
||||
// Purpose : to smooth a law : Reduce the number of knots
|
||||
@ -280,13 +305,25 @@ static Standard_Boolean FindPlane ( const Handle(Adaptor3d_HCurve)& c,
|
||||
}
|
||||
|
||||
//===============================================================
|
||||
// Function :
|
||||
// Function : Constructor
|
||||
// Purpose :
|
||||
//===============================================================
|
||||
GeomFill_CorrectedFrenet::GeomFill_CorrectedFrenet()
|
||||
: isFrenet(Standard_False)
|
||||
{
|
||||
frenet = new GeomFill_Frenet();
|
||||
myForEvaluation = Standard_False;
|
||||
}
|
||||
|
||||
//===============================================================
|
||||
// Function : Constructor
|
||||
// Purpose :
|
||||
//===============================================================
|
||||
GeomFill_CorrectedFrenet::GeomFill_CorrectedFrenet(const Standard_Boolean ForEvaluation)
|
||||
: isFrenet(Standard_False)
|
||||
{
|
||||
frenet = new GeomFill_Frenet();
|
||||
myForEvaluation = ForEvaluation;
|
||||
}
|
||||
|
||||
Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
@ -314,6 +351,7 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
{
|
||||
// No probleme isFrenet
|
||||
isFrenet = Standard_True;
|
||||
break;
|
||||
}
|
||||
default :
|
||||
{
|
||||
@ -382,8 +420,12 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
for(i = 1; i <= NbI; i++) {
|
||||
NbStep = Max(Standard_Integer((T(i+1) - T(i))/AvStep), 3);
|
||||
Step = (T(i+1) - T(i))/NbStep;
|
||||
if(!InitInterval(T(i), T(i+1), Step, StartAng, Tangent, Normal, AT, AN, Func, SeqPoles, SeqAngle, SeqTangent, SeqNormal))
|
||||
if(isFrenet) isFrenet = Standard_False;
|
||||
if(!InitInterval(T(i), T(i+1), Step, StartAng, Tangent, Normal, AT, AN, Func,
|
||||
SeqPoles, SeqAngle, SeqTangent, SeqNormal))
|
||||
{
|
||||
if(isFrenet)
|
||||
isFrenet = Standard_False;
|
||||
}
|
||||
Handle(Law_Composite)::DownCast(EvolAroundT)->ChangeLaws().Append(Func);
|
||||
}
|
||||
if(myTrimmed->IsPeriodic())
|
||||
@ -402,7 +444,7 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
HArrTangent->ChangeValue(i) = SeqTangent(i);
|
||||
HArrNormal->ChangeValue(i) = SeqNormal(i);
|
||||
};
|
||||
|
||||
|
||||
#if DRAW
|
||||
if (Affich) {
|
||||
draw(EvolAroundT);
|
||||
@ -431,6 +473,7 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
TColStd_SequenceOfReal EvolAT;
|
||||
Standard_Real Param = First, LengthMin, L, norm;
|
||||
Standard_Boolean isZero = Standard_True, isConst = Standard_True;
|
||||
const Standard_Real minnorm = 1.e-16;
|
||||
Standard_Integer i;
|
||||
gp_Pnt PonC;
|
||||
gp_Vec D1;
|
||||
@ -446,7 +489,9 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
Standard_Real angleAT, currParam, currStep = Step;
|
||||
|
||||
Handle( Geom_Plane ) aPlane;
|
||||
Standard_Boolean isPlanar = FindPlane( myCurve, aPlane );
|
||||
Standard_Boolean isPlanar = Standard_False;
|
||||
if (!myForEvaluation)
|
||||
isPlanar = FindPlane( myCurve, aPlane );
|
||||
|
||||
i = 1;
|
||||
currParam = Param;
|
||||
@ -493,13 +538,21 @@ Handle(GeomFill_TrihedronLaw) GeomFill_CorrectedFrenet::Copy() const
|
||||
|
||||
//Evaluate the Next step
|
||||
CS.D1(Param, PonC, D1);
|
||||
L = Max(PonC.XYZ().Modulus()/2, LengthMin);
|
||||
|
||||
L = PonC.XYZ().Modulus()/2;
|
||||
norm = D1.Magnitude();
|
||||
if (norm < Precision::Confusion()) {
|
||||
norm = Precision::Confusion();
|
||||
if (norm <= gp::Resolution())
|
||||
{
|
||||
//norm = 2.*gp::Resolution();
|
||||
norm = minnorm;
|
||||
}
|
||||
currStep = L / norm;
|
||||
if (currStep > Step) currStep = Step;//default value
|
||||
if (currStep <= gp::Resolution()) //L = 0 => curvature = 0, linear segment
|
||||
currStep = Step;
|
||||
if (currStep < Precision::Confusion()) //too small step
|
||||
currStep = Precision::Confusion();
|
||||
if (currStep > Step) //too big step
|
||||
currStep = Step;//default value
|
||||
}
|
||||
else
|
||||
currStep /= 2; // Step too long !
|
||||
@ -887,6 +940,59 @@ Standard_Real GeomFill_CorrectedFrenet::GetAngleAT(const Standard_Real Param) co
|
||||
Precision::PConfusion()/2);
|
||||
}
|
||||
|
||||
//===============================================================
|
||||
// Function : EvaluateBestMode
|
||||
// Purpose :
|
||||
//===============================================================
|
||||
GeomFill_Trihedron GeomFill_CorrectedFrenet::EvaluateBestMode()
|
||||
{
|
||||
if (EvolAroundT.IsNull())
|
||||
return GeomFill_IsFrenet; //Frenet
|
||||
|
||||
const Standard_Real MaxAngle = 3.*M_PI/4.;
|
||||
const Standard_Real MaxTorsion = 100.;
|
||||
|
||||
Standard_Real Step, u, v, tmin, tmax;
|
||||
Standard_Integer NbInt, i, j, k = 1;
|
||||
NbInt = EvolAroundT->NbIntervals(GeomAbs_CN);
|
||||
TColStd_Array1OfReal Int(1, NbInt+1);
|
||||
EvolAroundT->Intervals(Int, GeomAbs_CN);
|
||||
gp_Pnt2d old;
|
||||
gp_Vec2d aVec, PrevVec;
|
||||
|
||||
Standard_Integer NbSamples = 10;
|
||||
for(i = 1; i <= NbInt; i++){
|
||||
tmin = Int(i);
|
||||
tmax = Int(i+1);
|
||||
Standard_Real Torsion = ComputeTorsion(tmin, myTrimmed);
|
||||
if (Abs(Torsion) > MaxTorsion)
|
||||
return GeomFill_IsDiscreteTrihedron; //DiscreteTrihedron
|
||||
|
||||
Handle(Law_Function) trimmedlaw = EvolAroundT->Trim(tmin, tmax, Precision::PConfusion()/2);
|
||||
Step = (Int(i+1)-Int(i))/NbSamples;
|
||||
for (j = 0; j <= NbSamples; j++) {
|
||||
u = tmin + j*Step;
|
||||
v = trimmedlaw->Value(u);
|
||||
gp_Pnt2d point2d(u,v);
|
||||
if (j != 0)
|
||||
{
|
||||
aVec.SetXY(point2d.XY() - old.XY());
|
||||
if (k > 2)
|
||||
{
|
||||
Standard_Real theAngle = PrevVec.Angle(aVec);
|
||||
if (Abs(theAngle) > MaxAngle)
|
||||
return GeomFill_IsDiscreteTrihedron; //DiscreteTrihedron
|
||||
}
|
||||
PrevVec = aVec;
|
||||
}
|
||||
old = point2d;
|
||||
k++;
|
||||
}
|
||||
}
|
||||
|
||||
return GeomFill_IsCorrectedFrenet; //CorrectedFrenet
|
||||
}
|
||||
|
||||
//===============================================================
|
||||
// Function : GetAverageLaw
|
||||
// Purpose :
|
||||
|
154
src/GeomFill/GeomFill_DiscreteTrihedron.cdl
Normal file
154
src/GeomFill/GeomFill_DiscreteTrihedron.cdl
Normal file
@ -0,0 +1,154 @@
|
||||
-- Created on: 2013-02-05
|
||||
-- Created by: Julia GERASIMOVA
|
||||
-- Copyright (c) 2001-2013 OPEN CASCADE SAS
|
||||
--
|
||||
-- The content of this file is subject to the Open CASCADE Technology Public
|
||||
-- License Version 6.5 (the "License"). You may not use the content of this file
|
||||
-- except in compliance with the License. Please obtain a copy of the License
|
||||
-- at http://www.opencascade.org and read it completely before using this file.
|
||||
--
|
||||
-- The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
|
||||
-- main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
|
||||
--
|
||||
-- The Original Code and all software distributed under the License is
|
||||
-- distributed on an "AS IS" basis, without warranty of any kind, and the
|
||||
-- Initial Developer hereby disclaims all such warranties, including without
|
||||
-- limitation, any warranties of merchantability, fitness for a particular
|
||||
-- purpose or non-infringement. Please see the License for the specific terms
|
||||
-- and conditions governing the rights and limitations under the License.
|
||||
|
||||
|
||||
class DiscreteTrihedron from GeomFill
|
||||
inherits TrihedronLaw from GeomFill
|
||||
|
||||
---Purpose: Defined Discrete Trihedron Law.
|
||||
-- The requirement for path curve is only G1.
|
||||
-- The result is C0-continuous surface
|
||||
-- that can be later approximated to C1.
|
||||
|
||||
uses
|
||||
HCurve from Adaptor3d,
|
||||
Shape from GeomAbs,
|
||||
Pnt from gp,
|
||||
Vec from gp,
|
||||
Array1OfReal from TColStd,
|
||||
Frenet from GeomFill,
|
||||
HSequenceOfAx2 from GeomFill,
|
||||
HSequenceOfReal from TColStd
|
||||
|
||||
raises
|
||||
OutOfRange, ConstructionError
|
||||
is
|
||||
|
||||
Create
|
||||
returns DiscreteTrihedron from GeomFill
|
||||
raises ConstructionError;
|
||||
|
||||
Copy(me)
|
||||
returns TrihedronLaw from GeomFill
|
||||
is redefined;
|
||||
|
||||
Init(me: mutable)
|
||||
is static;
|
||||
|
||||
SetCurve(me : mutable; C : HCurve from Adaptor3d)
|
||||
is redefined;
|
||||
|
||||
--
|
||||
--
|
||||
--========== To compute Location and derivatives Location
|
||||
--
|
||||
D0(me : mutable;
|
||||
Param: Real;
|
||||
Tangent : out Vec from gp;
|
||||
Normal : out Vec from gp;
|
||||
BiNormal : out Vec from gp)
|
||||
---Purpose: compute Trihedron on curve at parameter <Param>
|
||||
returns Boolean is redefined;
|
||||
|
||||
D1(me : mutable;
|
||||
Param: Real;
|
||||
Tangent : out Vec from gp;
|
||||
DTangent : out Vec from gp;
|
||||
Normal : out Vec from gp;
|
||||
DNormal : out Vec from gp;
|
||||
BiNormal : out Vec from gp;
|
||||
DBiNormal : out Vec from gp)
|
||||
---Purpose: compute Trihedron and derivative Trihedron on curve
|
||||
-- at parameter <Param>
|
||||
-- Warning : It used only for C1 or C2 aproximation
|
||||
-- For the moment it returns null values for DTangent, DNormal
|
||||
-- and DBiNormal.
|
||||
returns Boolean
|
||||
is redefined;
|
||||
|
||||
D2(me : mutable;
|
||||
Param: Real;
|
||||
Tangent : out Vec from gp;
|
||||
DTangent : out Vec from gp;
|
||||
D2Tangent : out Vec from gp;
|
||||
Normal : out Vec from gp;
|
||||
DNormal : out Vec from gp;
|
||||
D2Normal : out Vec from gp;
|
||||
BiNormal : out Vec from gp;
|
||||
DBiNormal : out Vec from gp;
|
||||
D2BiNormal : out Vec from gp)
|
||||
---Purpose: compute Trihedron on curve
|
||||
-- first and seconde derivatives.
|
||||
-- Warning : It used only for C2 aproximation
|
||||
-- For the moment it returns null values for DTangent, DNormal
|
||||
-- DBiNormal, D2Tangent, D2Normal, D2BiNormal.
|
||||
returns Boolean
|
||||
is redefined;
|
||||
--
|
||||
-- =================== Management of continuity ===================
|
||||
--
|
||||
NbIntervals(me; S : Shape from GeomAbs)
|
||||
---Purpose: Returns the number of intervals for continuity
|
||||
-- <S>.
|
||||
-- May be one if Continuity(me) >= <S>
|
||||
returns Integer is redefined;
|
||||
|
||||
Intervals(me; T : in out Array1OfReal from TColStd;
|
||||
S : Shape from GeomAbs)
|
||||
---Purpose: Stores in <T> the parameters bounding the intervals
|
||||
-- of continuity <S>.
|
||||
--
|
||||
-- The array must provide enough room to accomodate
|
||||
-- for the parameters. i.e. T.Length() > NbIntervals()
|
||||
raises
|
||||
OutOfRange from Standard
|
||||
is redefined;
|
||||
|
||||
|
||||
-- =================== To help computation of Tolerance ===============
|
||||
GetAverageLaw(me : mutable;
|
||||
ATangent : out Vec from gp;
|
||||
ANormal : out Vec from gp;
|
||||
ABiNormal : out Vec from gp)
|
||||
---Purpose: Get average value of Tangent(t) and Normal(t) it is usful to
|
||||
-- make fast approximation of rational surfaces.
|
||||
is redefined;
|
||||
|
||||
-- =================== To help Particular case ===============
|
||||
|
||||
IsConstant(me)
|
||||
---Purpose: Say if the law is Constant.
|
||||
returns Boolean
|
||||
is redefined;
|
||||
|
||||
IsOnlyBy3dCurve(me)
|
||||
---Purpose: Return True.
|
||||
returns Boolean
|
||||
is redefined;
|
||||
|
||||
|
||||
fields
|
||||
|
||||
myPoint : Pnt from gp;
|
||||
myTrihedrons : HSequenceOfAx2 from GeomFill;
|
||||
myKnots : HSequenceOfReal from TColStd;
|
||||
myFrenet : Frenet from GeomFill;
|
||||
myUseFrenet : Boolean from Standard;
|
||||
|
||||
end DiscreteTrihedron;
|
392
src/GeomFill/GeomFill_DiscreteTrihedron.cxx
Normal file
392
src/GeomFill/GeomFill_DiscreteTrihedron.cxx
Normal file
@ -0,0 +1,392 @@
|
||||
// Created on: 2013-02-05
|
||||
// Created by: Julia GERASIMOVA
|
||||
// Copyright (c) 2001-2013 OPEN CASCADE SAS
|
||||
//
|
||||
// The content of this file is subject to the Open CASCADE Technology Public
|
||||
// License Version 6.5 (the "License"). You may not use the content of this file
|
||||
// except in compliance with the License. Please obtain a copy of the License
|
||||
// at http://www.opencascade.org and read it completely before using this file.
|
||||
//
|
||||
// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
|
||||
// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
|
||||
//
|
||||
// The Original Code and all software distributed under the License is
|
||||
// distributed on an "AS IS" basis, without warranty of any kind, and the
|
||||
// Initial Developer hereby disclaims all such warranties, including without
|
||||
// limitation, any warranties of merchantability, fitness for a particular
|
||||
// purpose or non-infringement. Please see the License for the specific terms
|
||||
// and conditions governing the rights and limitations under the License.
|
||||
|
||||
|
||||
#include <GeomFill_DiscreteTrihedron.ixx>
|
||||
#include <GeomFill_DiscreteTrihedron.hxx>
|
||||
#include <GeomFill_Frenet.hxx>
|
||||
#include <GeomAbs_CurveType.hxx>
|
||||
#include <Adaptor3d_HCurve.hxx>
|
||||
#include <TColStd_Array1OfReal.hxx>
|
||||
#include <TColStd_HSequenceOfReal.hxx>
|
||||
#include <GeomFill_HSequenceOfAx2.hxx>
|
||||
|
||||
|
||||
static const Standard_Real TolConf = Precision::Confusion();
|
||||
|
||||
//=======================================================================
|
||||
//function : GeomFill_DiscreteTrihedron
|
||||
//purpose : Constructor
|
||||
//=======================================================================
|
||||
|
||||
GeomFill_DiscreteTrihedron::GeomFill_DiscreteTrihedron()
|
||||
{
|
||||
myFrenet = new GeomFill_Frenet();
|
||||
myKnots = new TColStd_HSequenceOfReal();
|
||||
myTrihedrons = new GeomFill_HSequenceOfAx2();
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Copy
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Handle(GeomFill_TrihedronLaw) GeomFill_DiscreteTrihedron::Copy() const
|
||||
{
|
||||
Handle(GeomFill_DiscreteTrihedron) copy = new (GeomFill_DiscreteTrihedron)();
|
||||
if (!myCurve.IsNull()) copy->SetCurve(myCurve);
|
||||
return copy;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : SetCurve
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
void GeomFill_DiscreteTrihedron::SetCurve(const Handle(Adaptor3d_HCurve)& C)
|
||||
{
|
||||
GeomFill_TrihedronLaw::SetCurve(C);
|
||||
if (! C.IsNull()) {
|
||||
GeomAbs_CurveType type;
|
||||
type = C->GetType();
|
||||
switch (type) {
|
||||
case GeomAbs_Circle:
|
||||
case GeomAbs_Ellipse:
|
||||
case GeomAbs_Hyperbola:
|
||||
case GeomAbs_Parabola:
|
||||
case GeomAbs_Line:
|
||||
{
|
||||
// No probleme
|
||||
myUseFrenet = Standard_True;
|
||||
myFrenet->SetCurve(C);
|
||||
break;
|
||||
}
|
||||
default :
|
||||
{
|
||||
myUseFrenet = Standard_False;
|
||||
// We have to fill <myKnots> and <myTrihedrons>
|
||||
Init();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Init
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
void GeomFill_DiscreteTrihedron::Init()
|
||||
{
|
||||
Standard_Integer NbIntervals = myTrimmed->NbIntervals(GeomAbs_CN);
|
||||
TColStd_Array1OfReal Knots(1, NbIntervals+1);
|
||||
myTrimmed->Intervals(Knots, GeomAbs_CN);
|
||||
|
||||
//Standard_Real Tol = Precision::Confusion();
|
||||
Standard_Integer NbSamples = 10;
|
||||
|
||||
Standard_Integer i, j;
|
||||
for (i = 1; i <= NbIntervals; i++)
|
||||
{
|
||||
Standard_Real delta = (Knots(i+1) - Knots(i))/NbSamples;
|
||||
for (j = 0; j < NbSamples; j++)
|
||||
{
|
||||
Standard_Real Param = Knots(i) + j*delta;
|
||||
myKnots->Append(Param);
|
||||
}
|
||||
}
|
||||
myKnots->Append(Knots(NbIntervals+1));
|
||||
|
||||
|
||||
gp_Pnt Origin(0.,0.,0.), Pnt, SubPnt;
|
||||
gp_Vec Tangent;
|
||||
gp_Dir TangDir;
|
||||
Standard_Real norm;
|
||||
for (i = 1; i <= myKnots->Length(); i++)
|
||||
{
|
||||
Standard_Real Param = myKnots->Value(i);
|
||||
myTrimmed->D1(Param, Pnt, Tangent);
|
||||
norm = Tangent.Magnitude();
|
||||
if (norm < TolConf)
|
||||
{
|
||||
Standard_Real subdelta = (myKnots->Value(i+1) - myKnots->Value(i))/NbSamples;
|
||||
if (subdelta < Precision::PConfusion())
|
||||
subdelta = myKnots->Value(i+1) - myKnots->Value(i);
|
||||
SubPnt = myTrimmed->Value(Param + subdelta);
|
||||
Tangent.SetXYZ(SubPnt.XYZ() - Pnt.XYZ());
|
||||
}
|
||||
//Tangent.Normalize();
|
||||
TangDir = Tangent; //normalize;
|
||||
Tangent = TangDir;
|
||||
if (i == 1) //first point
|
||||
{
|
||||
gp_Ax2 FirstAxis(Origin, TangDir);
|
||||
myTrihedrons->Append(FirstAxis);
|
||||
}
|
||||
else
|
||||
{
|
||||
gp_Ax2 LastAxis = myTrihedrons->Value(myTrihedrons->Length());
|
||||
gp_Vec LastTangent = LastAxis.Direction();
|
||||
gp_Vec AxisOfRotation = LastTangent ^ Tangent;
|
||||
if (AxisOfRotation.Magnitude() <= gp::Resolution()) //tangents are equal or opposite
|
||||
{
|
||||
Standard_Real ScalarProduct = LastTangent * Tangent;
|
||||
if (ScalarProduct > 0.) //tangents are equal
|
||||
myTrihedrons->Append(LastAxis);
|
||||
else //tangents are opposite
|
||||
{
|
||||
Standard_Real NewParam = (myKnots->Value(i-1) + myKnots->Value(i))/2.;
|
||||
if (NewParam - myKnots->Value(i-1) < gp::Resolution())
|
||||
Standard_ConstructionError::Raise("GeomFill_DiscreteTrihedron : impassable singularities on path curve");
|
||||
myKnots->InsertBefore(i, NewParam);
|
||||
i--;
|
||||
}
|
||||
}
|
||||
else //good value of angle
|
||||
{
|
||||
Standard_Real theAngle = LastTangent.AngleWithRef(Tangent, AxisOfRotation);
|
||||
gp_Ax1 theAxisOfRotation(Origin, AxisOfRotation);
|
||||
gp_Ax2 NewAxis = LastAxis.Rotated(theAxisOfRotation, theAngle);
|
||||
NewAxis.SetDirection(TangDir); //to prevent accumulation of floating computations error
|
||||
myTrihedrons->Append(NewAxis);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : D0
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Boolean GeomFill_DiscreteTrihedron::D0(const Standard_Real Param,
|
||||
gp_Vec& Tangent,
|
||||
gp_Vec& Normal,
|
||||
gp_Vec& BiNormal)
|
||||
{
|
||||
if (myUseFrenet)
|
||||
{
|
||||
myFrenet->D0(Param, Tangent, Normal, BiNormal);
|
||||
}
|
||||
else
|
||||
{
|
||||
//Locate <Param> in the sequence <myKnots>
|
||||
Standard_Integer Index = -1;
|
||||
Standard_Real TolPar = Precision::PConfusion();
|
||||
//Standard_Real TolConf = Precision::Confusion();
|
||||
Standard_Integer NbSamples = 10;
|
||||
gp_Pnt Origin(0.,0.,0.);
|
||||
|
||||
Standard_Integer i;
|
||||
//gp_Ax2 PrevAxis;
|
||||
//Standard_Real PrevParam;
|
||||
|
||||
Standard_Integer I1, I2;
|
||||
I1 = 1;
|
||||
I2 = myKnots->Length();
|
||||
for (;;)
|
||||
{
|
||||
i = (I1 + I2)/2;
|
||||
if (Param <= myKnots->Value(i))
|
||||
I2 = i;
|
||||
else
|
||||
I1 = i;
|
||||
if (I2 - I1 <= 1)
|
||||
break;
|
||||
}
|
||||
Index = I1;
|
||||
if (Abs(Param - myKnots->Value(I2)) < TolPar)
|
||||
Index = I2;
|
||||
|
||||
Standard_Real PrevParam = myKnots->Value(Index);
|
||||
gp_Ax2 PrevAxis = myTrihedrons->Value(Index);
|
||||
gp_Ax2 theAxis;
|
||||
if (Abs(Param - PrevParam) < TolPar)
|
||||
theAxis = PrevAxis;
|
||||
else //<Param> is between knots
|
||||
{
|
||||
myTrimmed->D1(Param, myPoint, Tangent);
|
||||
Standard_Real norm = Tangent.Magnitude();
|
||||
if (norm < TolConf)
|
||||
{
|
||||
Standard_Real subdelta = (myKnots->Value(Index+1) - Param)/NbSamples;
|
||||
if (subdelta < Precision::PConfusion())
|
||||
subdelta = myKnots->Value(Index+1) - Param;
|
||||
gp_Pnt SubPnt = myTrimmed->Value(Param + subdelta);
|
||||
Tangent.SetXYZ(SubPnt.XYZ() - myPoint.XYZ());
|
||||
}
|
||||
//Tangent.Normalize();
|
||||
gp_Dir TangDir(Tangent); //normalize;
|
||||
Tangent = TangDir;
|
||||
gp_Vec PrevTangent = PrevAxis.Direction();
|
||||
gp_Vec AxisOfRotation = PrevTangent ^ Tangent;
|
||||
if (AxisOfRotation.Magnitude() <= gp::Resolution()) //tangents are equal
|
||||
{
|
||||
//we assume that tangents can not be opposite
|
||||
theAxis = PrevAxis;
|
||||
}
|
||||
else //good value of angle
|
||||
{
|
||||
Standard_Real theAngle = PrevTangent.AngleWithRef(Tangent, AxisOfRotation);
|
||||
gp_Ax1 theAxisOfRotation(Origin, AxisOfRotation);
|
||||
theAxis = PrevAxis.Rotated(theAxisOfRotation, theAngle);
|
||||
}
|
||||
theAxis.SetDirection(TangDir); //to prevent accumulation of floating computations error
|
||||
} //end of else (Param is between knots)
|
||||
|
||||
Tangent = theAxis.Direction();
|
||||
Normal = theAxis.XDirection();
|
||||
BiNormal = theAxis.YDirection();
|
||||
}
|
||||
return Standard_True;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : D1
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Boolean GeomFill_DiscreteTrihedron::D1(const Standard_Real Param,
|
||||
gp_Vec& Tangent,
|
||||
gp_Vec& DTangent,
|
||||
gp_Vec& Normal,
|
||||
gp_Vec& DNormal,
|
||||
gp_Vec& BiNormal,
|
||||
gp_Vec& DBiNormal)
|
||||
{
|
||||
if (myUseFrenet)
|
||||
{
|
||||
myFrenet->D1(Param, Tangent, DTangent, Normal, DNormal, BiNormal, DBiNormal);
|
||||
}
|
||||
else
|
||||
{
|
||||
D0(Param, Tangent, Normal, BiNormal);
|
||||
|
||||
DTangent.SetCoord(0.,0.,0.);
|
||||
DNormal.SetCoord(0.,0.,0.);
|
||||
DBiNormal.SetCoord(0.,0.,0.);
|
||||
}
|
||||
return Standard_True;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : D2
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Boolean GeomFill_DiscreteTrihedron::D2(const Standard_Real Param,
|
||||
gp_Vec& Tangent,
|
||||
gp_Vec& DTangent,
|
||||
gp_Vec& D2Tangent,
|
||||
gp_Vec& Normal,
|
||||
gp_Vec& DNormal,
|
||||
gp_Vec& D2Normal,
|
||||
gp_Vec& BiNormal,
|
||||
gp_Vec& DBiNormal,
|
||||
gp_Vec& D2BiNormal)
|
||||
{
|
||||
if (myUseFrenet)
|
||||
{
|
||||
myFrenet->D2(Param, Tangent, DTangent, D2Tangent,
|
||||
Normal, DNormal, D2Normal,
|
||||
BiNormal, DBiNormal, D2BiNormal);
|
||||
}
|
||||
else
|
||||
{
|
||||
D0(Param, Tangent, Normal, BiNormal);
|
||||
|
||||
DTangent.SetCoord(0.,0.,0.);
|
||||
DNormal.SetCoord(0.,0.,0.);
|
||||
DBiNormal.SetCoord(0.,0.,0.);
|
||||
D2Tangent.SetCoord(0.,0.,0.);
|
||||
D2Normal.SetCoord(0.,0.,0.);
|
||||
D2BiNormal.SetCoord(0.,0.,0.);
|
||||
}
|
||||
return Standard_True;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : NbIntervals
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Integer GeomFill_DiscreteTrihedron::NbIntervals(const GeomAbs_Shape S) const
|
||||
{
|
||||
return (myTrimmed->NbIntervals(GeomAbs_CN));
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : Intervals
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
void GeomFill_DiscreteTrihedron::Intervals(TColStd_Array1OfReal& T,
|
||||
const GeomAbs_Shape S) const
|
||||
{
|
||||
myTrimmed->Intervals(T, GeomAbs_CN);
|
||||
}
|
||||
|
||||
void GeomFill_DiscreteTrihedron::GetAverageLaw(gp_Vec& ATangent,
|
||||
gp_Vec& ANormal,
|
||||
gp_Vec& ABiNormal)
|
||||
{
|
||||
Standard_Integer Num = 20; //order of digitalization
|
||||
gp_Vec T, N, BN;
|
||||
ATangent = gp_Vec(0, 0, 0);
|
||||
ANormal = gp_Vec(0, 0, 0);
|
||||
ABiNormal = gp_Vec(0, 0, 0);
|
||||
Standard_Real Step = (myTrimmed->LastParameter() -
|
||||
myTrimmed->FirstParameter()) / Num;
|
||||
Standard_Real Param;
|
||||
for (Standard_Integer i = 0; i <= Num; i++) {
|
||||
Param = myTrimmed->FirstParameter() + i*Step;
|
||||
if (Param > myTrimmed->LastParameter()) Param = myTrimmed->LastParameter();
|
||||
D0(Param, T, N, BN);
|
||||
ATangent += T;
|
||||
ANormal += N;
|
||||
ABiNormal += BN;
|
||||
}
|
||||
ATangent /= Num + 1;
|
||||
ANormal /= Num + 1;
|
||||
|
||||
ATangent.Normalize();
|
||||
ABiNormal = ATangent.Crossed(ANormal).Normalized();
|
||||
ANormal = ABiNormal.Crossed(ATangent);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : IsConstant
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Boolean GeomFill_DiscreteTrihedron::IsConstant() const
|
||||
{
|
||||
return (myCurve->GetType() == GeomAbs_Line);
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//function : IsOnlyBy3dCurve
|
||||
//purpose :
|
||||
//=======================================================================
|
||||
|
||||
Standard_Boolean GeomFill_DiscreteTrihedron::IsOnlyBy3dCurve() const
|
||||
{
|
||||
return Standard_True;
|
||||
}
|
@ -141,7 +141,8 @@ is
|
||||
|
||||
DoSingular(me: mutable; U: Real; Index: Integer;
|
||||
Tangent, BiNormal: out Vec from gp;
|
||||
n, k, TFlag, BNFlag: out Integer)
|
||||
n, k, TFlag, BNFlag: out Integer;
|
||||
Delta: out Real)
|
||||
returns Boolean
|
||||
is private;
|
||||
|
||||
@ -149,7 +150,8 @@ is
|
||||
Param: Real; Index: Integer;
|
||||
Tangent : out Vec from gp;
|
||||
Normal : out Vec from gp;
|
||||
BiNormal : out Vec from gp)
|
||||
BiNormal : out Vec from gp;
|
||||
Delta : out Real)
|
||||
---Purpose: computes Triedrhon on curve at parameter <Param>
|
||||
returns Boolean
|
||||
is private;
|
||||
@ -161,7 +163,8 @@ is
|
||||
Normal : out Vec from gp;
|
||||
DNormal : out Vec from gp;
|
||||
BiNormal : out Vec from gp;
|
||||
DBiNormal : out Vec from gp)
|
||||
DBiNormal : out Vec from gp;
|
||||
Delta : out Real)
|
||||
---Purpose: computes Triedrhon and derivative Trihedron on curve
|
||||
-- at parameter <Param>
|
||||
-- Warning : It used only for C1 or C2 aproximation
|
||||
@ -178,7 +181,8 @@ is
|
||||
D2Normal : out Vec from gp;
|
||||
BiNormal : out Vec from gp;
|
||||
DBiNormal : out Vec from gp;
|
||||
D2BiNormal : out Vec from gp)
|
||||
D2BiNormal : out Vec from gp;
|
||||
Delta : out Real)
|
||||
---Purpose: computes Trihedron on curve
|
||||
-- first and seconde derivatives.
|
||||
-- Warning : It used only for C2 aproximation
|
||||
|
@ -326,11 +326,13 @@ Handle(GeomFill_TrihedronLaw) GeomFill_Frenet::Copy() const
|
||||
{
|
||||
Standard_Real norm;
|
||||
Standard_Integer Index;
|
||||
Standard_Real Delta = 0.;
|
||||
if(IsSingular(Param, Index))
|
||||
if (SingularD0(Param, Index, Tangent, Normal, BiNormal))
|
||||
if (SingularD0(Param, Index, Tangent, Normal, BiNormal, Delta))
|
||||
return Standard_True;
|
||||
|
||||
myTrimmed->D2(Param, P, Tangent, BiNormal);
|
||||
Standard_Real theParam = Param + Delta;
|
||||
myTrimmed->D2(theParam, P, Tangent, BiNormal);
|
||||
Tangent.Normalize();
|
||||
BiNormal = Tangent.Crossed(BiNormal);
|
||||
norm = BiNormal.Magnitude();
|
||||
@ -360,13 +362,15 @@ Handle(GeomFill_TrihedronLaw) GeomFill_Frenet::Copy() const
|
||||
gp_Vec& DBiNormal)
|
||||
{
|
||||
Standard_Integer Index;
|
||||
Standard_Real Delta = 0.;
|
||||
if(IsSingular(Param, Index))
|
||||
if (SingularD1(Param, Index, Tangent, DTangent, Normal, DNormal, BiNormal, DBiNormal))
|
||||
if (SingularD1(Param, Index, Tangent, DTangent, Normal, DNormal, BiNormal, DBiNormal, Delta))
|
||||
return Standard_True;
|
||||
|
||||
// Standard_Real Norma;
|
||||
Standard_Real theParam = Param + Delta;
|
||||
gp_Vec DC1, DC2, DC3;
|
||||
myTrimmed->D3(Param, P, DC1, DC2, DC3);
|
||||
myTrimmed->D3(theParam, P, DC1, DC2, DC3);
|
||||
Tangent = DC1.Normalized();
|
||||
|
||||
//if (DC2.Magnitude() <= NullTol || Tangent.Crossed(DC2).Magnitude() <= NullTol) {
|
||||
@ -412,16 +416,19 @@ Handle(GeomFill_TrihedronLaw) GeomFill_Frenet::Copy() const
|
||||
gp_Vec& D2BiNormal)
|
||||
{
|
||||
Standard_Integer Index;
|
||||
Standard_Real Delta = 0.;
|
||||
if(IsSingular(Param, Index))
|
||||
if(SingularD2(Param, Index, Tangent, DTangent, D2Tangent,
|
||||
Normal, DNormal, D2Normal,
|
||||
BiNormal, DBiNormal, D2BiNormal))
|
||||
BiNormal, DBiNormal, D2BiNormal,
|
||||
Delta))
|
||||
return Standard_True;
|
||||
|
||||
// Standard_Real Norma;
|
||||
Standard_Real theParam = Param + Delta;
|
||||
gp_Vec DC1, DC2, DC3, DC4;
|
||||
myTrimmed->D3(Param, P, DC1, DC2, DC3);
|
||||
DC4 = myTrimmed->DN(Param, 4);
|
||||
myTrimmed->D3(theParam, P, DC1, DC2, DC3);
|
||||
DC4 = myTrimmed->DN(theParam, 4);
|
||||
|
||||
Tangent = DC1.Normalized();
|
||||
|
||||
@ -604,9 +611,11 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
Standard_Integer& n,
|
||||
Standard_Integer& k,
|
||||
Standard_Integer& TFlag,
|
||||
Standard_Integer& BNFlag)
|
||||
Standard_Integer& BNFlag,
|
||||
Standard_Real& Delta)
|
||||
{
|
||||
Standard_Integer i, MaxN = 20;
|
||||
Delta = 0.;
|
||||
Standard_Real h;
|
||||
h = 2*mySnglLen->Value(Index);
|
||||
|
||||
@ -615,7 +624,8 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
TFlag = 1;
|
||||
BNFlag = 1;
|
||||
GetInterval(A, B);
|
||||
if (U >= (A + B)/2) h = -h;
|
||||
if (U >= (A + B)/2)
|
||||
h = -h;
|
||||
for(i = 1; i <= MaxN; i++) {
|
||||
Tangent = myTrimmed->DN(U, i);
|
||||
if(Tangent.Magnitude() > Precision::Confusion()) break;
|
||||
@ -641,7 +651,12 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (i > MaxN) return Standard_False;
|
||||
if (i > MaxN)
|
||||
{
|
||||
Delta = h;
|
||||
return Standard_False;
|
||||
}
|
||||
|
||||
BiNormal.Normalize();
|
||||
k = i;
|
||||
|
||||
@ -657,11 +672,14 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
const Standard_Integer Index,
|
||||
gp_Vec& Tangent,
|
||||
gp_Vec& Normal,
|
||||
gp_Vec& BiNormal)
|
||||
gp_Vec& BiNormal,
|
||||
Standard_Real& Delta)
|
||||
{
|
||||
Standard_Integer n, k, TFlag, BNFlag;
|
||||
if(!DoSingular(Param, Index, Tangent, BiNormal,
|
||||
n, k, TFlag, BNFlag)) return Standard_False;
|
||||
n, k, TFlag, BNFlag, Delta))
|
||||
return Standard_False;
|
||||
|
||||
Tangent *= TFlag;
|
||||
BiNormal *= BNFlag;
|
||||
Normal = BiNormal;
|
||||
@ -674,10 +692,12 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
const Standard_Integer Index,
|
||||
gp_Vec& Tangent,gp_Vec& DTangent,
|
||||
gp_Vec& Normal,gp_Vec& DNormal,
|
||||
gp_Vec& BiNormal,gp_Vec& DBiNormal)
|
||||
gp_Vec& BiNormal,gp_Vec& DBiNormal,
|
||||
Standard_Real& Delta)
|
||||
{
|
||||
Standard_Integer n, k, TFlag, BNFlag;
|
||||
if(!DoSingular(Param, Index, Tangent, BiNormal, n, k, TFlag, BNFlag)) return Standard_False;
|
||||
if(!DoSingular(Param, Index, Tangent, BiNormal, n, k, TFlag, BNFlag, Delta))
|
||||
return Standard_False;
|
||||
|
||||
gp_Vec F, DF, Dtmp;
|
||||
F = myTrimmed->DN(Param, n);
|
||||
@ -715,10 +735,11 @@ Standard_Boolean GeomFill_Frenet::DoSingular(const Standard_Real U,
|
||||
gp_Vec& D2Normal,
|
||||
gp_Vec& BiNormal,
|
||||
gp_Vec& DBiNormal,
|
||||
gp_Vec& D2BiNormal)
|
||||
gp_Vec& D2BiNormal,
|
||||
Standard_Real& Delta)
|
||||
{
|
||||
Standard_Integer n, k, TFlag, BNFlag;
|
||||
if(!DoSingular(Param, Index, Tangent, BiNormal, n, k, TFlag, BNFlag))
|
||||
if(!DoSingular(Param, Index, Tangent, BiNormal, n, k, TFlag, BNFlag, Delta))
|
||||
return Standard_False;
|
||||
|
||||
gp_Vec F, DF, D2F, Dtmp1, Dtmp2;
|
||||
|
@ -78,7 +78,12 @@ is
|
||||
-- beetween tangents on the section law and
|
||||
-- tangent of iso-v on approximed surface
|
||||
|
||||
|
||||
SetForceApproxC1(me : in out;
|
||||
ForceApproxC1 : Boolean from Standard);
|
||||
---Purpose: Set the flag that indicates attempt to approximate
|
||||
-- a C1-continuous surface if a swept surface proved
|
||||
-- to be C0.
|
||||
|
||||
ExchangeUV(me)
|
||||
---Purpose: returns true if sections are U-Iso
|
||||
-- This can be produce in some cases when <WithKpart> is True.
|
||||
@ -184,8 +189,9 @@ fields
|
||||
First, Last : Real;
|
||||
SFirst, SLast: Real;
|
||||
Tol3d, BoundTol, Tol2d, TolAngular : Real;
|
||||
SError : Real;
|
||||
|
||||
SError : Real;
|
||||
myForceApproxC1 : Boolean;
|
||||
|
||||
myLoc : LocationLaw from GeomFill;
|
||||
mySec : SectionLaw from GeomFill;
|
||||
mySurface : Surface from Geom;
|
||||
|
@ -68,6 +68,7 @@
|
||||
#include <Approx_SweepApproximation.hxx>
|
||||
#include <AdvApprox_PrefAndRec.hxx>
|
||||
#include <AdvApprox_ApproxAFunction.hxx>
|
||||
#include <GeomConvert_ApproxSurface.hxx>
|
||||
|
||||
#include <Precision.hxx>
|
||||
#include <ElCLib.hxx>
|
||||
@ -121,6 +122,7 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location,
|
||||
myLoc = Location;
|
||||
myKPart = WithKpart;
|
||||
SetTolerance(1.e-4);
|
||||
myForceApproxC1 = Standard_False;
|
||||
|
||||
myLoc->GetDomain(First, Last);
|
||||
SFirst = SLast = 30.081996;
|
||||
@ -157,6 +159,18 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location,
|
||||
TolAngular = ToleranceAngular;
|
||||
}
|
||||
|
||||
//=======================================================================
|
||||
//Function : SetForceApproxC1
|
||||
//Purpose : Set the flag that indicates attempt to approximate
|
||||
// a C1-continuous surface if a swept surface proved
|
||||
// to be C0.
|
||||
//=======================================================================
|
||||
void GeomFill_Sweep::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
|
||||
{
|
||||
myForceApproxC1 = ForceApproxC1;
|
||||
}
|
||||
|
||||
|
||||
//===============================================================
|
||||
// Function : ExchangeUV
|
||||
// Purpose :
|
||||
@ -298,56 +312,101 @@ GeomFill_Sweep::GeomFill_Sweep(const Handle(GeomFill_LocationLaw)& Location,
|
||||
Approx.UDegree(), Approx.VDegree(),
|
||||
mySec->IsUPeriodic());
|
||||
SError = Approx. MaxErrorOnSurf();
|
||||
|
||||
if (myForceApproxC1 && !mySurface->IsCNv(1))
|
||||
{
|
||||
Standard_Real theTol = 1.e-4;
|
||||
GeomAbs_Shape theUCont = GeomAbs_C1, theVCont = GeomAbs_C1;
|
||||
Standard_Integer degU = 14, degV = 14;
|
||||
Standard_Integer nmax = 16;
|
||||
Standard_Integer thePrec = 1;
|
||||
|
||||
GeomConvert_ApproxSurface ConvertApprox(mySurface,theTol,theUCont,theVCont,
|
||||
degU,degV,nmax,thePrec);
|
||||
if (ConvertApprox.HasResult())
|
||||
{
|
||||
mySurface = ConvertApprox.Surface();
|
||||
myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2);
|
||||
CError = new (TColStd_HArray2OfReal) (1,2, 1,2);
|
||||
|
||||
const Handle(Geom_BSplineSurface)& BSplSurf =
|
||||
Handle(Geom_BSplineSurface)::DownCast(mySurface);
|
||||
|
||||
gp_Dir2d D(0., 1.);
|
||||
gp_Pnt2d P(BSplSurf->UKnot(1), 0);
|
||||
Handle(Geom2d_Line) LC1 = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC1 =
|
||||
new (Geom2d_TrimmedCurve) (LC1, 0, BSplSurf->VKnot(BSplSurf->NbVKnots()));
|
||||
|
||||
myCurve2d->SetValue(1, TC1);
|
||||
CError->SetValue(1, 1, 0.);
|
||||
CError->SetValue(2, 1, 0.);
|
||||
|
||||
P.SetCoord(BSplSurf->UKnot(BSplSurf->NbUKnots()), 0);
|
||||
Handle(Geom2d_Line) LC2 = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC2 =
|
||||
new (Geom2d_TrimmedCurve) (LC2, 0, BSplSurf->VKnot(BSplSurf->NbVKnots()));
|
||||
|
||||
myCurve2d->SetValue(myCurve2d->Length(), TC2);
|
||||
CError->SetValue(1, myCurve2d->Length(), 0.);
|
||||
CError->SetValue(2, myCurve2d->Length(), 0.);
|
||||
|
||||
SError = theTol;
|
||||
}
|
||||
} //if (!mySurface->IsCNv(1))
|
||||
|
||||
// Les Courbes 2d
|
||||
myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2+myLoc->TraceNumber());
|
||||
CError = new (TColStd_HArray2OfReal) (1,2, 1, 2+myLoc->TraceNumber());
|
||||
Standard_Integer kk,ii, ifin = 1, ideb;
|
||||
|
||||
if (myLoc->HasFirstRestriction()) {
|
||||
ideb = 1;
|
||||
}
|
||||
else {
|
||||
ideb = 2;
|
||||
}
|
||||
ifin += myLoc->TraceNumber();
|
||||
if (myLoc->HasLastRestriction()) ifin++;
|
||||
|
||||
for (ii=ideb, kk=1; ii<=ifin; ii++, kk++) {
|
||||
Handle(Geom2d_BSplineCurve) C
|
||||
= new (Geom2d_BSplineCurve) (Approx.Curve2dPoles(kk),
|
||||
Approx.Curves2dKnots(),
|
||||
Approx.Curves2dMults(),
|
||||
Approx.Curves2dDegree());
|
||||
myCurve2d->SetValue(ii, C);
|
||||
CError->SetValue(1, ii, Approx.Max2dError(kk));
|
||||
CError->SetValue(2, ii, Approx.Max2dError(kk));
|
||||
}
|
||||
|
||||
// Si les courbes de restriction, ne sont pas calcules, on prend
|
||||
// les iso Bords.
|
||||
if (! myLoc->HasFirstRestriction()) {
|
||||
gp_Dir2d D(0., 1.);
|
||||
gp_Pnt2d P(UKnots(UKnots.Lower()), 0);
|
||||
Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC = new (Geom2d_TrimmedCurve)
|
||||
(LC, First, Last);
|
||||
|
||||
myCurve2d->SetValue(1, TC);
|
||||
CError->SetValue(1, 1, 0.);
|
||||
CError->SetValue(2, 1, 0.);
|
||||
}
|
||||
|
||||
if (! myLoc->HasLastRestriction()) {
|
||||
gp_Dir2d D(0., 1.);
|
||||
gp_Pnt2d P(UKnots(UKnots.Upper()), 0);
|
||||
Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC =
|
||||
new (Geom2d_TrimmedCurve) (LC, First, Last);
|
||||
myCurve2d->SetValue(myCurve2d->Length(), TC);
|
||||
CError->SetValue(1, myCurve2d->Length(), 0.);
|
||||
CError->SetValue(2, myCurve2d->Length(), 0.);
|
||||
}
|
||||
if (myCurve2d.IsNull())
|
||||
{
|
||||
myCurve2d = new (TColGeom2d_HArray1OfCurve) (1, 2+myLoc->TraceNumber());
|
||||
CError = new (TColStd_HArray2OfReal) (1,2, 1, 2+myLoc->TraceNumber());
|
||||
Standard_Integer kk,ii, ifin = 1, ideb;
|
||||
|
||||
if (myLoc->HasFirstRestriction()) {
|
||||
ideb = 1;
|
||||
}
|
||||
else {
|
||||
ideb = 2;
|
||||
}
|
||||
ifin += myLoc->TraceNumber();
|
||||
if (myLoc->HasLastRestriction()) ifin++;
|
||||
|
||||
for (ii=ideb, kk=1; ii<=ifin; ii++, kk++) {
|
||||
Handle(Geom2d_BSplineCurve) C
|
||||
= new (Geom2d_BSplineCurve) (Approx.Curve2dPoles(kk),
|
||||
Approx.Curves2dKnots(),
|
||||
Approx.Curves2dMults(),
|
||||
Approx.Curves2dDegree());
|
||||
myCurve2d->SetValue(ii, C);
|
||||
CError->SetValue(1, ii, Approx.Max2dError(kk));
|
||||
CError->SetValue(2, ii, Approx.Max2dError(kk));
|
||||
}
|
||||
|
||||
// Si les courbes de restriction, ne sont pas calcules, on prend
|
||||
// les iso Bords.
|
||||
if (! myLoc->HasFirstRestriction()) {
|
||||
gp_Dir2d D(0., 1.);
|
||||
gp_Pnt2d P(UKnots(UKnots.Lower()), 0);
|
||||
Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC = new (Geom2d_TrimmedCurve)
|
||||
(LC, First, Last);
|
||||
|
||||
myCurve2d->SetValue(1, TC);
|
||||
CError->SetValue(1, 1, 0.);
|
||||
CError->SetValue(2, 1, 0.);
|
||||
}
|
||||
|
||||
if (! myLoc->HasLastRestriction()) {
|
||||
gp_Dir2d D(0., 1.);
|
||||
gp_Pnt2d P(UKnots(UKnots.Upper()), 0);
|
||||
Handle(Geom2d_Line) LC = new (Geom2d_Line) (P, D);
|
||||
Handle(Geom2d_TrimmedCurve) TC =
|
||||
new (Geom2d_TrimmedCurve) (LC, First, Last);
|
||||
myCurve2d->SetValue(myCurve2d->Length(), TC);
|
||||
CError->SetValue(1, myCurve2d->Length(), 0.);
|
||||
CError->SetValue(2, myCurve2d->Length(), 0.);
|
||||
}
|
||||
} //if (myCurve2d.IsNull())
|
||||
}
|
||||
return Ok;
|
||||
}
|
||||
|
33
tests/bugs/modalg_5/bug23824_1
Executable file
33
tests/bugs/modalg_5/bug23824_1
Executable file
@ -0,0 +1,33 @@
|
||||
puts "============"
|
||||
puts "OCC23824"
|
||||
puts "============"
|
||||
puts ""
|
||||
#######################################################################
|
||||
# Bad results of sweep operation when a path curve has unpredictable torsion along its way.
|
||||
#######################################################################
|
||||
|
||||
set BugNumber OCC23824
|
||||
|
||||
restore [locate_data_file bug23824_AXE.brep] spine
|
||||
restore [locate_data_file bug23824_profil.brep] profile
|
||||
|
||||
wire spine spine
|
||||
|
||||
mksweep spine
|
||||
setsweep -DT
|
||||
addsweep profile
|
||||
buildsweep result
|
||||
|
||||
set square 516.633
|
||||
|
||||
set nb_v_good 8
|
||||
set nb_e_good 10
|
||||
set nb_w_good 3
|
||||
set nb_f_good 3
|
||||
set nb_sh_good 1
|
||||
set nb_sol_good 0
|
||||
set nb_compsol_good 0
|
||||
set nb_compound_good 0
|
||||
set nb_shape_good 25
|
||||
|
||||
set 2dviewer 1
|
34
tests/bugs/modalg_5/bug23824_2
Executable file
34
tests/bugs/modalg_5/bug23824_2
Executable file
@ -0,0 +1,34 @@
|
||||
puts "============"
|
||||
puts "OCC23824"
|
||||
puts "============"
|
||||
puts ""
|
||||
#######################################################################
|
||||
# Bad results of sweep operation when a path curve has unpredictable torsion along its way.
|
||||
#######################################################################
|
||||
|
||||
set BugNumber OCC23824
|
||||
|
||||
restore [locate_data_file bug23824_Case1_Path.brep] spine
|
||||
restore [locate_data_file bug23824_Case1_Profile.brep] profile
|
||||
|
||||
wire spine spine
|
||||
wire profile profile
|
||||
|
||||
mksweep spine
|
||||
setsweep -DT
|
||||
addsweep profile
|
||||
buildsweep result
|
||||
|
||||
set square 8997.97
|
||||
|
||||
set nb_v_good 2
|
||||
set nb_e_good 3
|
||||
set nb_w_good 1
|
||||
set nb_f_good 1
|
||||
set nb_sh_good 1
|
||||
set nb_sol_good 0
|
||||
set nb_compsol_good 0
|
||||
set nb_compound_good 0
|
||||
set nb_shape_good 8
|
||||
|
||||
set 2dviewer 1
|
35
tests/bugs/modalg_5/bug23824_3
Executable file
35
tests/bugs/modalg_5/bug23824_3
Executable file
@ -0,0 +1,35 @@
|
||||
puts "============"
|
||||
puts "OCC23824"
|
||||
puts "============"
|
||||
puts ""
|
||||
#######################################################################
|
||||
# Bad results of sweep operation when a path curve has unpredictable torsion along its way.
|
||||
#######################################################################
|
||||
|
||||
set BugNumber OCC23824
|
||||
|
||||
restore [locate_data_file bug23824_Case2_Path.brep] spine
|
||||
restore [locate_data_file bug23824_Case2_Profile.brep] profile
|
||||
|
||||
wire spine spine
|
||||
wire profile profile
|
||||
|
||||
mksweep spine
|
||||
setsweep -DT
|
||||
addsweep profile
|
||||
|
||||
buildsweep result
|
||||
|
||||
set square 848.989
|
||||
|
||||
set nb_v_good 2
|
||||
set nb_e_good 3
|
||||
set nb_w_good 1
|
||||
set nb_f_good 1
|
||||
set nb_sh_good 1
|
||||
set nb_sol_good 0
|
||||
set nb_compsol_good 0
|
||||
set nb_compound_good 0
|
||||
set nb_shape_good 8
|
||||
|
||||
set 2dviewer 1
|
35
tests/bugs/modalg_5/bug23824_4
Executable file
35
tests/bugs/modalg_5/bug23824_4
Executable file
@ -0,0 +1,35 @@
|
||||
puts "============"
|
||||
puts "OCC23824"
|
||||
puts "============"
|
||||
puts ""
|
||||
#######################################################################
|
||||
# Bad results of sweep operation when a path curve has unpredictable torsion along its way.
|
||||
#######################################################################
|
||||
|
||||
set BugNumber OCC23824
|
||||
|
||||
restore [locate_data_file bug23824_Case3_Path.brep] spine
|
||||
restore [locate_data_file bug23824_Case3_Profile.brep] profile
|
||||
|
||||
wire profile profile
|
||||
explode spine
|
||||
wire spine spine_1
|
||||
|
||||
mksweep spine
|
||||
setsweep -DT
|
||||
addsweep profile
|
||||
buildsweep result
|
||||
|
||||
set square 38260.5
|
||||
|
||||
set nb_v_good 2
|
||||
set nb_e_good 3
|
||||
set nb_w_good 1
|
||||
set nb_f_good 1
|
||||
set nb_sh_good 1
|
||||
set nb_sol_good 0
|
||||
set nb_compsol_good 0
|
||||
set nb_compound_good 0
|
||||
set nb_shape_good 8
|
||||
|
||||
set 2dviewer 1
|
Loading…
x
Reference in New Issue
Block a user