1
0
mirror of https://git.dev.opencascade.org/repos/occt.git synced 2025-04-04 18:06:22 +03:00
occt/src/BOPAlgo/BOPAlgo_PaveFiller_8.cxx
emv 1155d05a06 0025609: Clean up the duplicate classes in TKBO project
1. The package BOPCol has been fully removed:
- *BOPCol_BaseAllocator* is replaced with *Handle(NCollection_BaseAllocator)*;
- *BOPCol_BoxBndTree* is replaced with *BOPTools_BoxBndTree*;
- *BOPCol_Box2DBndTree* is removed as unused;
- *BOPCol_DataMapOfIntegerInteger* is replaced with *TColStd_DataMapOfIntegerInteger*;
- *BOPCol_DataMapOfIntegerListOfInteger* is replaced with *TColStd_DataMapOfIntegerListOfInteger*;
- *BOPCol_DataMapOfIntegerListOfShape* is replaced with *TopTools_DataMapOfIntegerListOfShape*;
- *BOPCol_DataMapOfIntegerMapOfInteger.hxx* is removed as unused;
- *BOPCol_DataMapOfIntegerReal* is replaced with *TColStd_DataMapOfIntegerReal*;
- *BOPCol_DataMapOfIntegerShape* is replaced with *TopTools_DataMapOfIntegerShape*;
- *BOPCol_DataMapOfShapeBox* is replaced with *TopTools_DataMapOfShapeBox*;
- *BOPCol_DataMapOfShapeInteger* is replaced with *TopTools_DataMapOfShapeInteger*;
- *BOPCol_DataMapOfShapeListOfShape* is replaced with *TopTools_DataMapOfShapeListOfShape*;
- *BOPCol_DataMapOfShapeReal* is replaced with *TopTools_DataMapOfShapeReal*;
- *BOPCol_DataMapOfShapeShape* is replaced with *TopTools_DataMapOfShapeShape*;
- *BOPCol_DataMapOfTransientAddress* is removed as unused;
- *BOPCol_IndexedDataMapOfIntegerListOfInteger* is removed as unused;
- *BOPCol_IndexedDataMapOfShapeBox* is removed as unused;
- *BOPCol_IndexedDataMapOfShapeInteger* is removed as unused;
- *BOPCol_IndexedDataMapOfShapeListOfShape* is replaced with *TopTools_IndexedDataMapOfShapeListOfShape*;
- *BOPCol_IndexedDataMapOfShapeReal* is removed as unused;
- *BOPCol_IndexedDataMapOfShapeShape* is replaced with *TopTools_IndexedDataMapOfShapeShape*;
- *BOPCol_IndexedMapOfInteger* is replaced with *TColStd_IndexedMapOfInteger*;
- *BOPCol_IndexedMapOfOrientedShape* is replaced with *TopTools_IndexedMapOfOrientedShape*;
- *BOPCol_IndexedMapOfShape* is replaced with *TopTools_IndexedMapOfShape*;
- *BOPCol_ListOfInteger* is replaced with *TColStd_ListOfInteger*;
- *BOPCol_ListOfListOfShape* is replaced with *TopTools_ListOfListOfShape*;
- *BOPCol_ListOfShape* is replaced with *TopTools_ListOfShape*;
- *BOPCol_MapOfInteger* is replaced with *TColStd_MapOfInteger*;
- *BOPCol_MapOfOrientedShape* is replaced with *TopTools_MapOfOrientedShape*;
- *BOPCol_MapOfShape* is replaced with *TopTools_MapOfShape*;
- *BOPCol_PListOfInteger* is removed as unused;
- *BOPCol_PInteger* is removed as unused
- *BOPCol_SequenceOfPnt2d* is replaced with *TColgp_SequenceOfPnt2d*;
- *BOPCol_SequenceOfReal* is replaced with *TColStd_SequenceOfReal*;
- *BOPCol_SequenceOfShape* is replaced with *TopTools_SequenceOfShape*;
- *BOPCol_Parallel* is replaced with *BOPTools_Parallel*;
- *BOPCol_NCVector* is replaced with *NCollection_Vector*;

2. The class *BOPDS_PassKey* and containers for it have been removed as unused;

3. The unused containers from *IntTools* package have been removed:
- *IntTools_DataMapOfShapeAddress* is removed as unused;
- *IntTools_IndexedDataMapOfTransientAddress* is removed as unused;

4. The container *BiTgte_DataMapOfShapeBox* is replaced with *TopTools_DataMapOfShapeBox*;

5. The class *BOPTools* has been removed as duplicate of the class *TopExp*;
2017-11-30 12:11:15 +03:00

399 lines
14 KiB
C++

// Created by: Peter KURNEV
// Copyright (c) 2010-2014 OPEN CASCADE SAS
// Copyright (c) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE
// Copyright (c) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, CEDRAT,
// EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
//
// 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 License 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 <BOPAlgo_PaveFiller.hxx>
#include <BOPAlgo_SectionAttribute.hxx>
#include <BOPDS_Curve.hxx>
#include <BOPDS_DS.hxx>
#include <BOPDS_FaceInfo.hxx>
#include <BOPDS_MapOfPaveBlock.hxx>
#include <BOPDS_Pave.hxx>
#include <BOPDS_PaveBlock.hxx>
#include <BOPDS_ShapeInfo.hxx>
#include <BRep_Builder.hxx>
#include <BRep_Tool.hxx>
#include <ElCLib.hxx>
#include <Geom2d_Curve.hxx>
#include <Geom2d_Line.hxx>
#include <Geom2d_TrimmedCurve.hxx>
#include <Geom2dAdaptor_Curve.hxx>
#include <Geom2dAPI_ProjectPointOnCurve.hxx>
#include <Geom2dInt_GInter.hxx>
#include <gp_Lin2d.hxx>
#include <gp_Pnt.hxx>
#include <gp_Pnt2d.hxx>
#include <IntRes2d_IntersectionPoint.hxx>
#include <IntTools_Context.hxx>
#include <Precision.hxx>
#include <TColStd_ListOfInteger.hxx>
#include <TopoDS_Edge.hxx>
#include <TopoDS_Face.hxx>
#include <TopoDS_Vertex.hxx>
static
void MakeSplitEdge1 (const TopoDS_Edge& aE,
const TopoDS_Face& aF,
const TopoDS_Vertex& aV1,
const Standard_Real aP1,
const TopoDS_Vertex& aV2,
const Standard_Real aP2,
TopoDS_Edge& aNewEdge);
static
Standard_Boolean AddSplitPoint(const Handle(BOPDS_PaveBlock)& thePBD,
const BOPDS_Pave& thePave,
const Standard_Real theTol);
//=======================================================================
//function : ProcessDE
//purpose :
//=======================================================================
void BOPAlgo_PaveFiller::ProcessDE()
{
Standard_Integer nF, aNb, nE, nV, nVSD, aNbPB;
Handle(NCollection_BaseAllocator) aAllocator;
Handle(BOPDS_PaveBlock) aPBD;
TColStd_ListIteratorOfListOfInteger aItLI;
//
// 1. Find degnerated edges
//-----------------------------------------------------scope f
//
aAllocator=
NCollection_BaseAllocator::CommonBaseAllocator();
BOPDS_ListOfPaveBlock aLPBOut(aAllocator);
//
aNb=myDS->NbSourceShapes();
for (nE=0; nE<aNb; ++nE) {
const BOPDS_ShapeInfo& aSIE=myDS->ShapeInfo(nE);
if (aSIE.ShapeType()==TopAbs_EDGE) {
if (aSIE.HasFlag(nF)) {
const BOPDS_ShapeInfo& aSIF=myDS->ShapeInfo(nF);
nV=aSIE.SubShapes().First();
if (myDS->HasShapeSD(nV, nVSD)) {
nV=nVSD;
}
//nV,nE,nF
//
if (aSIF.ShapeType() == TopAbs_FACE) {
// 1. Find PaveBlocks that are go through nV for nF
FindPaveBlocks(nV, nF, aLPBOut);
aNbPB=aLPBOut.Extent();
if (aNbPB) {
//
// 2.
BOPDS_ListOfPaveBlock& aLPBD = myDS->ChangePaveBlocks(nE);
Standard_ASSERT_VOID(!aLPBD.IsEmpty(), "ListOfPaveBlock is unexpectedly empty");
if (aLPBD.IsEmpty())
continue;
aPBD = aLPBD.First();
//
FillPaves(nV, nE, nF, aLPBOut, aPBD);
//
myDS->UpdatePaveBlock(aPBD);
}
//
MakeSplitEdge(nE, nF);
//
aLPBOut.Clear();
}
if (aSIF.ShapeType() == TopAbs_EDGE) {
Standard_Real aTol=1.e-7;
Standard_Integer nEn;
BRep_Builder BB;
const TopoDS_Edge& aDE=(*(TopoDS_Edge *)(&myDS->Shape(nE)));
const TopoDS_Vertex& aVn = (*(TopoDS_Vertex *)(&myDS->Shape(nV)));
//
TopoDS_Edge aE=aDE;
aE.EmptyCopy();
BB.Add(aE, aVn);
BB.Degenerated(aE, Standard_True);
BB.UpdateEdge(aE, aTol);
BOPDS_ShapeInfo aSI;
aSI.SetShapeType(TopAbs_EDGE);
aSI.SetShape(aE);
nEn=myDS->Append(aSI);
BOPDS_ListOfPaveBlock& aLPBD=myDS->ChangePaveBlocks(nE);
aPBD=aLPBD.First();
aPBD->SetEdge(nEn);
}
}
}
}
}
//=======================================================================
//function : FindPaveBlocks
//purpose :
//=======================================================================
void BOPAlgo_PaveFiller::FindPaveBlocks(const Standard_Integer nV,
const Standard_Integer nF,
BOPDS_ListOfPaveBlock& aLPBOut)
{
Standard_Integer i, aNbPBOn, aNbPBIn, aNbPBSc, nV1, nV2;
//
const BOPDS_FaceInfo& aFI=myDS->ChangeFaceInfo(nF);
// In
const BOPDS_IndexedMapOfPaveBlock& aMPBIn=aFI.PaveBlocksIn();
aNbPBIn = aMPBIn.Extent();
for (i = 1; i <= aNbPBIn; ++i) {
const Handle(BOPDS_PaveBlock)& aPB = aMPBIn(i);
aPB->Indices(nV1, nV2);
if (nV==nV1 || nV==nV2) {
aLPBOut.Append(aPB);
}
}
// On
const BOPDS_IndexedMapOfPaveBlock& aMPBOn=aFI.PaveBlocksOn();
aNbPBOn = aMPBOn.Extent();
for (i = 1; i <= aNbPBOn; ++i) {
const Handle(BOPDS_PaveBlock)& aPB = aMPBOn(i);
aPB->Indices(nV1, nV2);
if (nV==nV1 || nV==nV2) {
aLPBOut.Append(aPB);
}
}
// Sections
const BOPDS_IndexedMapOfPaveBlock& aMPBSc=aFI.PaveBlocksSc();
aNbPBSc = aMPBSc.Extent();
for (i = 1; i <= aNbPBSc; ++i) {
const Handle(BOPDS_PaveBlock)& aPB = aMPBSc(i);
aPB->Indices(nV1, nV2);
if (nV==nV1 || nV==nV2) {
aLPBOut.Append(aPB);
}
}
}
//=======================================================================
//function : MakeSplitEdge
//purpose :
//=======================================================================
void BOPAlgo_PaveFiller::MakeSplitEdge (const Standard_Integer nDE,
const Standard_Integer nDF)
{
Standard_Integer nSp, nV1, nV2, aNbPB;
Standard_Real aT1, aT2;
TopoDS_Edge aDE, aSp;
TopoDS_Vertex aV1, aV2;
BOPDS_ListIteratorOfListOfPaveBlock aItLPB;
BOPDS_ShapeInfo aSI;
//
aSI.SetShapeType(TopAbs_EDGE);
//
aDE=(*(TopoDS_Edge *)(&myDS->Shape(nDE)));
aDE.Orientation(TopAbs_FORWARD);
//
const TopoDS_Face& aDF=(*(TopoDS_Face *)(&myDS->Shape(nDF)));
//
BOPDS_ListOfPaveBlock& aLPB=myDS->ChangePaveBlocks(nDE);
aNbPB=aLPB.Extent();
//
aItLPB.Initialize(aLPB);
for (; aItLPB.More(); aItLPB.Next()) {
Handle(BOPDS_PaveBlock)& aPB=aItLPB.ChangeValue();
//
const BOPDS_Pave& aPave1=aPB->Pave1();
aPave1.Contents(nV1, aT1);
//
const BOPDS_Pave& aPave2=aPB->Pave2();
aPave2.Contents(nV2, aT2);
//
if (myDS->IsNewShape(nV1) || aNbPB>1) {
aV1=(*(TopoDS_Vertex *)(&myDS->Shape(nV1)));
aV1.Orientation(TopAbs_FORWARD);
//
aV2=(*(TopoDS_Vertex *)(&myDS->Shape(nV2)));
aV2.Orientation(TopAbs_REVERSED);
//
MakeSplitEdge1(aDE, aDF, aV1, aT1, aV2, aT2, aSp);
//
aSI.SetShape(aSp);
nSp=myDS->Append(aSI);
aPB->SetEdge(nSp);
}
else {
myDS->ChangeShapeInfo(nDE).SetReference(-1);
aLPB.Clear();
break;
}
}
}
//=======================================================================
//function : FillPaves
//purpose : Find all pave blocks passing through the vertex <nVD> and
// intersecting the 2D curve of the degenerated edge
// somewhere in the middle. Save intersection points into
// Extra paves of the pave block of degenerated edge for future
// splitting.
//=======================================================================
void BOPAlgo_PaveFiller::FillPaves(const Standard_Integer nVD,
const Standard_Integer nED,
const Standard_Integer nFD,
const BOPDS_ListOfPaveBlock& aLPBOut,
const Handle(BOPDS_PaveBlock)& aPBD)
{
// Prepare pave to put to pave block as an Extra pave
BOPDS_Pave aPave;
aPave.SetIndex(nVD);
//
const TopoDS_Vertex& aDV = (*(TopoDS_Vertex *)(&myDS->Shape(nVD)));
const TopoDS_Edge& aDE = (*(TopoDS_Edge *)(&myDS->Shape(nED)));
const TopoDS_Face& aDF = (*(TopoDS_Face *)(&myDS->Shape(nFD)));
//
Standard_Real aTolV = BRep_Tool::Tolerance(aDV);
const BRepAdaptor_Surface& aBAS = myContext->SurfaceAdaptor(aDF);
//
// 2D intersection tolerance should be computed as a resolution
// from the tolerance of vertex to resolve the touching cases
Standard_Real aTolInt = Precision::PConfusion();
// UResolution from the tolerance of the vertex
Standard_Real aURes = aBAS.UResolution(aTolV);
// VResolution from the tolerance of the vertex
Standard_Real aVRes = aBAS.VResolution(aTolV);
//
aTolInt = Max(aTolInt, Max(aURes, aVRes));
//
// Parametric tolerance to compare intersection point with boundaries
// should be computed as a resolution from the tolerance of vertex
// in the direction of the 2D curve of degenerated edge
Standard_Real aTolCmp = Precision::PConfusion();
// Get 2D curve
Standard_Real aTD1, aTD2;
Handle(Geom2d_Curve) aC2DDE = BRep_Tool::CurveOnSurface(aDE, aDF, aTD1, aTD2);
// Get direction of the curve
Standard_Boolean bUDir = Abs(aC2DDE->Value(aTD1).Y() - aC2DDE->Value(aTD2).Y()) < Precision::PConfusion();
//
aTolCmp = Max(aTolCmp, (bUDir ? aURes : aVRes));
//
// Prepare adaptor for the degenerated edge for intersection
Geom2dAdaptor_Curve aGAC1;
aGAC1.Load(aC2DDE, aTD1, aTD2);
//
BOPDS_ListIteratorOfListOfPaveBlock aItLPB(aLPBOut);
for (; aItLPB.More(); aItLPB.Next()) {
const Handle(BOPDS_PaveBlock)& aPB = aItLPB.Value();
Standard_Integer nE = aPB->Edge();
if (nE < 0) {
continue;
}
const TopoDS_Edge& aE = (*(TopoDS_Edge *)(&myDS->Shape(nE)));
Standard_Real aT1, aT2;
Handle(Geom2d_Curve) aC2D = BRep_Tool::CurveOnSurface(aE, aDF, aT1, aT2);
if (aC2D.IsNull()) {
continue;
}
//
// Prepare adaptor for the passing edge for intersection
Geom2dAdaptor_Curve aGAC2;
//
Handle(Geom2d_Line) aL2D = Handle(Geom2d_Line)::DownCast(aC2D);
if (!aL2D.IsNull()) {
aGAC2.Load(aC2D);
}
else {
aGAC2.Load(aC2D, aT1, aT2);
}
// Intersection
Geom2dInt_GInter aGInter(aGAC1, aGAC2, aTolInt, aTolInt);
if (aGInter.IsDone() && aGInter.NbPoints())
{
// Analyze intersection points
Standard_Integer i, aNbPoints = aGInter.NbPoints();
for (i = 1; i <= aNbPoints; ++i) {
Standard_Real aX = aGInter.Point(i).ParamOnFirst();
aPave.SetParameter(aX);
AddSplitPoint(aPBD, aPave, aTolCmp);
}
}
else
{
// If the intersection did not succeed, try the projection of the end point
// of the curve corresponding to the vertex of degenerated edge
Standard_Real aT = (nVD == aPB->Pave1().Index() ?
aPB->Pave1().Parameter() : aPB->Pave2().Parameter());
gp_Pnt2d aP2d = aC2D->Value(aT);
Geom2dAPI_ProjectPointOnCurve aProj2d(aP2d, aC2DDE, aTD1, aTD2);
if (aProj2d.NbPoints())
{
Standard_Real aX = aProj2d.LowerDistanceParameter();
aPave.SetParameter(aX);
AddSplitPoint(aPBD, aPave, aTolCmp);
}
}
}
}
//=======================================================================
// function: MakeSplitEdge1
// purpose:
//=======================================================================
void MakeSplitEdge1 (const TopoDS_Edge& aE,
const TopoDS_Face& aF,
const TopoDS_Vertex& aV1,
const Standard_Real aP1,
const TopoDS_Vertex& aV2,
const Standard_Real aP2,
TopoDS_Edge& aNewEdge)
{
Standard_Real aTol=1.e-7;
TopoDS_Edge E=aE;
E.EmptyCopy();
BRep_Builder BB;
BB.Add (E, aV1);
BB.Add (E, aV2);
BB.Range(E, aF, aP1, aP2);
BB.Degenerated(E, Standard_True);
BB.UpdateEdge(E, aTol);
aNewEdge=E;
}
//=======================================================================
// function: AddSplitPoint
// purpose: Validates the point represented by the pave <thePave>
// for the Pave Block <thePBD>.
// In case the point passes the checks it is added as an
// Extra Pave to the Pave Block for further splitting of the latter.
// Returns TRUE if the point is added, otherwise returns FALSE.
//=======================================================================
Standard_Boolean AddSplitPoint(const Handle(BOPDS_PaveBlock)& thePBD,
const BOPDS_Pave& thePave,
const Standard_Real theTol)
{
Standard_Real aTD1, aTD2;
thePBD->Range(aTD1, aTD2);
Standard_Real aT = thePave.Parameter();
// Check that the parameter is inside the Pave Block
if (aT - aTD1 < theTol || aTD2 - aT < theTol)
return Standard_False;
// Check that the pave block does not contain the same parameter
Standard_Integer anInd;
if (thePBD->ContainsParameter(aT, theTol, anInd))
return Standard_False;
// Add the point as an Extra pave to the Pave Block for further
// splitting of the latter
thePBD->AppendExtPave1(thePave);
return Standard_True;
}