1
0
mirror of https://git.dev.opencascade.org/repos/occt.git synced 2025-04-04 18:06:22 +03:00
occt/src/IntTools/IntTools_EdgeEdge_1.cxx
bugmaster 6aca4d3977 0024516: Copyright information has been corrupted within some headers
Update incorrectly modified header files
2014-01-09 12:05:23 +04:00

919 lines
20 KiB
C++

// Created on: 2012-11-29
// Created by: Peter KURNEV
// Copyright (c) 2012-2014 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and / or modify it
// under the terms of the GNU Lesser General Public version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <IntTools_EdgeEdge.ixx>
#include <gp_Elips.hxx>
#include <gp_Ax1.hxx>
#include <gp_Dir.hxx>
#include <gp_XYZ.hxx>
#include <gp_Ax2.hxx>
#include <gp_Pnt.hxx>
//
#include <Geom_Curve.hxx>
#include <Geom_Line.hxx>
#include <Geom_Circle.hxx>
#include <Geom_Ellipse.hxx>
#include <Geom_Parabola.hxx>
#include <Geom_Hyperbola.hxx>
#include <Geom_BezierCurve.hxx>
#include <Geom_BSplineCurve.hxx>
#include <Geom_TrimmedCurve.hxx>
#include <Geom_OffsetCurve.hxx>
//
#include <GeomAPI_ProjectPointOnCurve.hxx>
//
#include <BRep_Tool.hxx>
//=======================================================================
//class : IntTools_ComparatorCurve
//purpose :
//=======================================================================
class IntTools_ComparatorCurve {
public:
IntTools_ComparatorCurve() {
myT11=0.;
myT12=0.;
myT21=0.;
myT22=0.;
myIsSame=Standard_False;
};
//
virtual ~IntTools_ComparatorCurve(){
};
//
void SetCurve1(const BRepAdaptor_Curve& aBC3D) {
myBC1=aBC3D;
};
//
const BRepAdaptor_Curve& Curve1()const {
return myBC1;
};
//
void SetRange1(const Standard_Real aT1,
const Standard_Real aT2) {
myT11=aT1;
myT12=aT2;
};
//
void Range1(Standard_Real& aT1, Standard_Real& aT2)const {
aT1=myT11;
aT2=myT12;
};
//
void SetCurve2(const BRepAdaptor_Curve& aBC3D){
myBC2=aBC3D;
};
//
const BRepAdaptor_Curve& Curve2()const{
return myBC2;
};
//
void SetRange2(const Standard_Real aT1,
const Standard_Real aT2){
myT21=aT1;
myT22=aT2;
};
//
void Range2(Standard_Real& aT1,
Standard_Real& aT2)const {
aT1=myT21;
aT2=myT22;
};
//
Standard_Boolean IsSame()const {
return myIsSame;
};
//
void Perform();
//
//--------------------------------------
protected:
//
void IsSameElipse();
//
void IsSameBSplineCurve();
//
static
Standard_Boolean
IsSameReal(const Standard_Real aR1,
const Standard_Real aR2);
//
static
Standard_Boolean
IsSameAx2(const gp_Ax2& aAx21,
const gp_Ax2& aAx22);
//
static
Standard_Boolean
IsSameAx1(const gp_Ax1& aAx1,
const gp_Ax1& aAx2);
//
static
Standard_Boolean
IsSamePnt(const gp_Pnt& aP1,
const gp_Pnt& aP2);
static
Standard_Boolean
IsSameDir(const gp_Dir& aDir1,
const gp_Dir& aDir2);
//
static
Standard_Boolean
IsSameXYZ(const gp_XYZ& aXYZ1,
const gp_XYZ& aXYZ2);
//
static
void GetCurveBase(const Handle(Geom_Curve)& aC3D,
GeomAbs_CurveType& aTypeBase,
Handle(Geom_Curve)& aCurveBase);
//
static
Standard_Boolean
IsTypeBase(const Handle(Geom_Curve)& aC,
GeomAbs_CurveType& aTypeB);
//
protected:
BRepAdaptor_Curve myBC1;
Standard_Real myT11;
Standard_Real myT12;
//
BRepAdaptor_Curve myBC2;
Standard_Real myT21;
Standard_Real myT22;
//
Standard_Boolean myIsSame;
};
//
//=======================================================================
//function : Perform
//purpose :
//=======================================================================
void IntTools_ComparatorCurve::Perform()
{
GeomAbs_CurveType aCurveType1, aCurveType2;
//
myIsSame=Standard_False;
//
aCurveType1=myBC1.GetType();
aCurveType2=myBC2.GetType();
//
myIsSame=(aCurveType1==aCurveType2);
if (!myIsSame) {
return;
}
//
myIsSame=IsSameReal(myT11, myT21);
if (!myIsSame) {
return;
}
//
myIsSame=IsSameReal(myT12, myT22);
if (!myIsSame) {
return;
}
//
if (aCurveType1==GeomAbs_Ellipse) {
IsSameElipse();
return;
}
else if (aCurveType1==GeomAbs_BSplineCurve) {
IsSameBSplineCurve();
return ;
}
else {
myIsSame=Standard_False;
return;
}
}
//=======================================================================
//function : IsSameBSplineCurve
//purpose :
//=======================================================================
void IntTools_ComparatorCurve::IsSameBSplineCurve()
{
Standard_Boolean bIsRational, bIsPreiodic;
Standard_Integer iNbPoles, iNbKnots, iDegree;
//
bIsRational=myBC1.IsRational();
myIsSame=(bIsRational==myBC2.IsRational());
if (!myIsSame) {
return;
}
//
iNbPoles=myBC1.NbPoles();
myIsSame=(iNbPoles==myBC2.NbPoles());
if (!myIsSame) {
return;
}
//
iNbKnots=myBC1.NbKnots();
myIsSame=(iNbKnots==myBC2.NbKnots());
if (!myIsSame) {
return;
}
//
iDegree=myBC1.Degree();
myIsSame=(iDegree==myBC2.Degree());
if (!myIsSame) {
return;
}
//
bIsPreiodic=myBC1.IsPeriodic();
myIsSame=(bIsPreiodic==myBC2.IsPeriodic());
if (!myIsSame) {
return;
}
//-------------------------------------------
Standard_Integer i, j, aM[2];
Standard_Real aT1, aT2, aX0[4], aX1[4];
GeomAbs_CurveType aTypeBase;
gp_Pnt aP;
Handle(Geom_Curve) aC;
Handle(Geom_BSplineCurve) aBSp[2];
TopoDS_Edge aE1, aE2;
//
aE1=myBC1.Edge();
aE2=myBC2.Edge();
//
aC=BRep_Tool::Curve (aE1, aT1, aT2);
GetCurveBase(aC, aTypeBase, aBSp[0]);
//
aC=BRep_Tool::Curve (aE2, aT1, aT2);
GetCurveBase(aC, aTypeBase, aBSp[1]);
//
// Poles / Weights
for(i=1; i<=iNbPoles; ++i) {
aP=aBSp[0]->Pole(i);
aP.Coord(aX0[0], aX0[1], aX0[2]);
aX0[3]=aBSp[0]->Weight(i);
//
aP=aBSp[1]->Pole(i);
aP.Coord(aX1[0], aX1[1], aX1[2]);
aX1[3]=aBSp[1]->Weight(i);
//
for (j=0; j<4; ++j) {
myIsSame=IsSameReal(aX0[j], aX1[j]);
if(!myIsSame) {
return;
}
}
}//for(i=1; i<iNbPoles; ++i) {
//
// Knots / Multiplicities
for(i=1; i<=iNbKnots; ++i) {
aX0[0]=aBSp[0]->Knot(i);
aX0[1]=aBSp[1]->Knot(i);
myIsSame=IsSameReal(aX0[0], aX0[1]);
if(!myIsSame) {
return;
}
//
aM[0]=aBSp[0]->Multiplicity(i);
aM[1]=aBSp[1]->Multiplicity(i);
myIsSame=(aM[0]==aM[1]);
if(!myIsSame) {
return;
}
}
}
//=======================================================================
//function : GetCurveBase
//purpose :
//=======================================================================
void IntTools_ComparatorCurve::GetCurveBase(const Handle(Geom_Curve)& aC3D,
GeomAbs_CurveType& aTypeBase,
Handle(Geom_Curve)& aCurveBase)
{
Standard_Boolean bIsTypeBase;
Standard_Integer iTrimmed, iOffset;
Standard_Real aOffsetBase;
GeomAbs_CurveType aTypeB;
Handle(Geom_Curve) aC3DB;
Handle(Geom_TrimmedCurve) aCT3D;
Handle(Geom_OffsetCurve) aCF3D;
//
aTypeBase=GeomAbs_OtherCurve;
aOffsetBase=0.;
//
aC3DB=aC3D;
bIsTypeBase=IsTypeBase(aC3DB, aTypeB);
if (bIsTypeBase) {
aTypeBase=aTypeB;
aCurveBase=aC3D;
return;
}
//
for(;;) {
iTrimmed=0;
iOffset=0;
aCT3D=Handle(Geom_TrimmedCurve)::DownCast(aC3DB);
if (!aCT3D.IsNull()) {
aC3DB=aCT3D->BasisCurve();
++iTrimmed;
}
//
aCF3D=Handle(Geom_OffsetCurve)::DownCast(aC3DB);
if (!aCF3D.IsNull()) {
Standard_Real aOffset;
//
aOffset=aCF3D->Offset();
aOffsetBase=aOffsetBase+aOffset;
//
aC3DB=aCF3D->BasisCurve();
++iOffset;
}
//
if (!(iTrimmed || iOffset)) {
break;
}
//
bIsTypeBase=IsTypeBase(aC3DB, aTypeB);
if (bIsTypeBase) {
aTypeBase=aTypeB;
aCurveBase=aC3DB;
return;
}
}
}
//=======================================================================
//function : IsTypeBase
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsTypeBase(const Handle(Geom_Curve)& aC,
GeomAbs_CurveType& aTypeB)
{
Standard_Boolean bRet;
Handle(Standard_Type) aType;
//
bRet=Standard_True;
//
aType=aC->DynamicType();
if (aType==STANDARD_TYPE(Geom_Line)) {
aTypeB=GeomAbs_Line;
}
else if (aType==STANDARD_TYPE(Geom_Circle)) {
aTypeB=GeomAbs_Circle;
}
else if (aType==STANDARD_TYPE(Geom_Ellipse)) {
aTypeB=GeomAbs_Ellipse;
}
else if (aType==STANDARD_TYPE(Geom_Parabola)) {
aTypeB=GeomAbs_Parabola;
}
else if (aType==STANDARD_TYPE(Geom_Hyperbola)) {
aTypeB=GeomAbs_Hyperbola;
}
else if (aType==STANDARD_TYPE(Geom_BezierCurve)) {
aTypeB=GeomAbs_BezierCurve;
}
else if (aType==STANDARD_TYPE(Geom_BSplineCurve)) {
aTypeB=GeomAbs_BSplineCurve;
}
else {
aTypeB=GeomAbs_OtherCurve;
bRet=!bRet;
}
return bRet;
}
//=======================================================================
//function : IsSameElipse
//purpose :
//=======================================================================
void IntTools_ComparatorCurve::IsSameElipse()
{
Standard_Real aR1, aR2;
gp_Elips aElips1, aElips2;
//
myIsSame=Standard_False;
//
aElips1=myBC1.Ellipse();
aElips2=myBC2.Ellipse();
//
aR1=aElips1.MajorRadius();
aR2=aElips2.MajorRadius();
myIsSame=IsSameReal(aR1, aR2);
if (!myIsSame) {
return;
}
//
aR1=aElips1.MinorRadius();
aR2=aElips2.MinorRadius();
myIsSame=IsSameReal(aR1, aR2);
if (!myIsSame) {
return;
}
//
const gp_Ax2& aAx21=aElips1.Position();
const gp_Ax2& aAx22=aElips2.Position();
myIsSame=IsSameAx2(aAx21, aAx22);
}
//=======================================================================
//function : IsSameAx2
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSameAx2(const gp_Ax2& aAx21,
const gp_Ax2& aAx22)
{
Standard_Boolean bRet;
//
const gp_Ax1& aAx1=aAx21.Axis();
const gp_Ax1& aAx2=aAx22.Axis();
//
bRet=IsSameAx1(aAx1, aAx2);
if (!bRet) {
return bRet;
}
//
const gp_Dir& aDirX1=aAx21.XDirection();
const gp_Dir& aDirX2=aAx22.XDirection();
//
bRet=IsSameDir(aDirX1, aDirX2);
if (!bRet) {
return bRet;
}
//
//
const gp_Dir& aDirY1=aAx21.YDirection();
const gp_Dir& aDirY2=aAx22.YDirection();
//
bRet=IsSameDir(aDirY1, aDirY2);
//
return bRet;
}
//=======================================================================
//function : IsSamePnt
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSamePnt(const gp_Pnt& aP1,
const gp_Pnt& aP2)
{
const gp_XYZ& aXYZ1=aP1.XYZ();
const gp_XYZ& aXYZ2=aP2.XYZ();
return IsSameXYZ(aXYZ1, aXYZ2);
}
//=======================================================================
//function : IsSameAx1
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSameAx1(const gp_Ax1& aAx1,
const gp_Ax1& aAx2)
{
Standard_Boolean bRet;
//
const gp_Pnt& aP1=aAx1.Location();
const gp_Pnt& aP2=aAx2.Location();
//
bRet=IsSamePnt(aP1, aP2);
if (!bRet) {
return bRet;
}
//
const gp_Dir& aDir1=aAx1.Direction();
const gp_Dir& aDir2=aAx2.Direction();
//
bRet=IsSameDir(aDir1, aDir2);
return bRet;
}
//=======================================================================
//function : IsSameDir
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSameDir(const gp_Dir& aDir1,
const gp_Dir& aDir2)
{
const gp_XYZ& aXYZ1=aDir1.XYZ();
const gp_XYZ& aXYZ2=aDir2.XYZ();
return IsSameXYZ(aXYZ1, aXYZ2);
}
//=======================================================================
//function : IsSameXYZ
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSameXYZ(const gp_XYZ& aXYZ1,
const gp_XYZ& aXYZ2)
{
Standard_Boolean bRet = Standard_False;
Standard_Integer i;
Standard_Real aX1[3], aX2[3];
aXYZ1.Coord(aX1[0], aX1[1], aX1[2]);
aXYZ2.Coord(aX2[0], aX2[1], aX2[2]);
//
for (i=0; i<3; ++i) {
bRet=IsSameReal(aX1[i], aX2[i]);
if(!bRet) {
break;
}
}
return bRet;
}
//=======================================================================
//function : IsSameReal
//purpose :
//=======================================================================
Standard_Boolean
IntTools_ComparatorCurve::IsSameReal(const Standard_Real aR1,
const Standard_Real aR2)
{
Standard_Boolean bRet;
Standard_Real aEpsilon;
//
aEpsilon=Epsilon(aR1);
bRet=(fabs(aR1-aR2)<aEpsilon);
return bRet;
}
//
//modified by NIZNHY-PKV Tue Jan 15 07:44:33 2013f
//=======================================================================
// class: IntTools_DistCC
// purpose :
//=======================================================================
class IntTools_DistCC {
public:
IntTools_DistCC() {
myT11=0.;
myT12=0.;
myT21=0.;
myT22=0.;
myErrorStatus=1;
myThreshold=1.e-7;
myDx=0.;
myTx=0.;
myNbP=10;
myIndent=0.3;
myEps=0.001;
};
//
~IntTools_DistCC() {
};
//-------- 1
void SetCurve1(const Handle(Geom_Curve)& aC1) {
myC1=aC1;
};
//
const Handle(Geom_Curve)& Curve1()const {
return myC1;
};
//
void SetRange1(const Standard_Real aT11,
const Standard_Real aT12) {
myT11=aT11;
myT12=aT12;
};
//
void Range1(Standard_Real& aT11,
Standard_Real& aT12)const {
aT11=myT11;
aT12=myT12;
};
//-------- 2
void SetCurve2(const Handle(Geom_Curve)& aC2) {
myC2=aC2;
};
//
const Handle(Geom_Curve)& Curve2()const {
return myC2;
};
//
void SetRange2(const Standard_Real aT21,
const Standard_Real aT22) {
myT21=aT21;
myT22=aT22;
};
//
void Range2(Standard_Real& aT21,
Standard_Real& aT22)const {
aT21=myT21;
aT22=myT22;
};
//
void SetThreshold(const Standard_Real aD) {
myThreshold=aD;
}
//
Standard_Real Threshold() const {
return myThreshold;
}
//
void Perform();
//
Standard_Integer ErrorStatus()const {
return myErrorStatus;
};
//
Standard_Real MaxDeviation()const {
return myDx;
}
//
Standard_Real MaxParameter()const {
return myTx;
}
//-----------------------------------------------------
protected :
//
void Init();
//
void CheckData();
//
Standard_Real Distance(const Standard_Real aT);
//
void FindMaxDeviation();
//
void FindMaxLocal (const Standard_Real aT11,
const Standard_Real aT12,
const Standard_Real aEps,
Standard_Real& aDx,
Standard_Real& aTx);
//
protected :
Standard_Real myT11;
Standard_Real myT12;
Handle(Geom_Curve) myC1;
Standard_Real myT21;
Standard_Real myT22;
Handle(Geom_Curve) myC2;
//
Standard_Real myThreshold;
Standard_Integer myErrorStatus;
//
Standard_Real myDx;
Standard_Real myTx;
//
Standard_Integer myNbP;
Standard_Real myIndent;
Standard_Real myEps;
GeomAPI_ProjectPointOnCurve myPPC2;
};
//=======================================================================
//function : Perform
//purpose :
//=======================================================================
void IntTools_DistCC::Perform()
{
myErrorStatus=0;
//
CheckData();
if (myErrorStatus){
return;
}
// Init
myPPC2.Init(myC2, myT21, myT22);
//
FindMaxDeviation();
if (myErrorStatus){
return;
}
}
//=======================================================================
//function : CheckData
//purpose :
//=======================================================================
void IntTools_DistCC::CheckData()
{
myErrorStatus=0;
//
if (myC1.IsNull()) {
myErrorStatus=2;
return;
}
//
if (myC2.IsNull()) {
myErrorStatus=3;
return;
}
}
//
//=======================================================================
//function : FindMaxDeviation
//purpose :
//=======================================================================
void IntTools_DistCC::FindMaxDeviation()
{
Standard_Integer i, aNbP1, aNbP2;
Standard_Real aTmax, aT, aT1, aT2, dT, aDmax, aEps, aD;
//
myErrorStatus=0;
myDx=0.;
myTx=0.;
//
aTmax=0;
aDmax=0.;
aEps=myEps*(myT12-myT11);
//
aNbP1=myNbP-1;
aNbP2=aNbP1-1;
dT=(myT12-myT11)/aNbP1;
for (i=0; i<aNbP1; ++i) {
aT1=myT11+i*dT;
aT2=aT1+dT;
//
if (!i) {
aT1=aT1+myIndent*dT;
}
else if (i==aNbP2) {
aT2=aT2-myIndent*dT;
if (aT2>myT12) {
aT2=myT12;
}
}
//
FindMaxLocal(aT1, aT2, aEps, aD, aT);
if (myErrorStatus) {
return ;
}
//
if (aD>aDmax) {
aDmax=aD;
aTmax=aT;
}
}
//
myTx=aTmax;
myDx=aDmax;
}
//=======================================================================
//function : FindMaxLocal
//purpose : Solver: Golden Mean
//=======================================================================
void IntTools_DistCC::FindMaxLocal(const Standard_Real aT11,
const Standard_Real aT12,
const Standard_Real aEps,
Standard_Real& aDx,
Standard_Real& aTx)
{
Standard_Integer iErr;
Standard_Real aA, aB, aCf, aX1, aX2, aF1, aF2, aX, aF;
//
myErrorStatus=0;
iErr=0;
aDx=0.;
aTx=0.;
//
aCf=1.6180339887498948482045868343656;// =0.5*(1.+sqrt(5.));
//
aA=aT11;
aB=aT12;
//
aX1=aB-(aB-aA)/aCf;
aF1=Distance(aX1);
if (myErrorStatus) {
return ;
}
//
aX2=aA+(aB-aA)/aCf;
aF2=Distance(aX2);
if (myErrorStatus) {
return;
}
//
for(;;) {
if (fabs(aA-aB)<aEps) {
aX=0.5*(aA+aB);
aF=Distance(aX);
if (myErrorStatus) {
return;
}
//
break;
}
if (aF1<aF2){
aA=aX1;
aX1=aX2;
aF1=aF2;
aX2=aA+(aB-aA)/aCf;
aF2=Distance(aX2);
if (myErrorStatus) {
return ;
}
}
else {
aB=aX2;
aX2=aX1;
aF2=aF1;
aX1=aB-(aB-aA)/aCf;
aF1=Distance(aX1);
if (myErrorStatus) {
return;
}
}
}
//
aDx=aF;
aTx=aX;
}
//=======================================================================
//function : Distance
//purpose :
//=======================================================================
Standard_Real IntTools_DistCC::Distance(const Standard_Real aT)
{
Standard_Integer aNbP2;
Standard_Real aD;
gp_Pnt aP1;
//
aD=0.;
if (myErrorStatus) {
return aD;
}
//
myC1->D0(aT, aP1);
myPPC2.Perform(aP1);
//
aNbP2=myPPC2.NbPoints();
if (!aNbP2) {
myErrorStatus=4;
return aD;
}
//
aD=myPPC2.LowerDistance();
if (aD>myThreshold) {
myErrorStatus=10;
}
return aD;
}
//modified by NIZNHY-PKV Tue Jan 15 07:44:44 2013t
//
//=======================================================================
//function : IsSameCurves
//purpose :
//=======================================================================
Standard_Boolean IntTools_EdgeEdge::IsSameCurves()
{
Standard_Boolean bRet, bIsBC;
GeomAbs_CurveType aCT1, aCT2;
IntTools_ComparatorCurve aICC;
//
// 1. Check letter
aICC.SetCurve1(myCFrom);
aICC.SetRange1(myTminFrom, myTmaxFrom);
//
aICC.SetCurve2(myCTo);
aICC.SetRange2(myTminTo, myTmaxTo);
//
aICC.Perform();
bRet=aICC.IsSame();
if (bRet) {
return bRet;
}
//
// 2. Check inwards
aCT1=myCFrom.GetType();
aCT2=myCTo.GetType();
bIsBC=(aCT1==GeomAbs_BSplineCurve ||
aCT1==GeomAbs_BezierCurve ||
aCT2==GeomAbs_BSplineCurve ||
aCT2==GeomAbs_BezierCurve);
//
if (bIsBC) {
Standard_Integer iErr;
Standard_Real aT11, aT12, aT21, aT22;
Handle(Geom_Curve) aC1, aC2;
IntTools_DistCC aDistCC;
//
const TopoDS_Edge& aE1=myCFrom.Edge();
aC1=BRep_Tool::Curve(aE1, aT11, aT12);
//
const TopoDS_Edge& aE2=myCTo.Edge();
aC2=BRep_Tool::Curve(aE2, aT21, aT22);
//
aDistCC.SetCurve1(aC1);
aDistCC.SetRange1(myTminFrom, myTmaxFrom);
aDistCC.SetCurve2(aC2);
aDistCC.SetRange2(myTminTo, myTmaxTo);
aDistCC.SetThreshold(myCriteria);
//
aDistCC.Perform();
//
iErr=aDistCC.ErrorStatus();
//
bRet=(!iErr);
//
}
return bRet;
}