1 // Created by: Peter KURNEV
2 // Copyright (c) 2010-2014 OPEN CASCADE SAS
3 // Copyright (c) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE
4 // Copyright (c) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, CEDRAT,
5 // EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
7 // This file is part of Open CASCADE Technology software library.
9 // This library is free software; you can redistribute it and/or modify it under
10 // the terms of the GNU Lesser General Public License version 2.1 as published
11 // by the Free Software Foundation, with special exception defined in the file
12 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
13 // distribution for complete text of the license and disclaimer of any warranty.
15 // Alternatively, this file may be used under the terms of Open CASCADE
16 // commercial license or contractual agreement.
18 #include <BOPAlgo_PaveFiller.ixx>
20 #include <Precision.hxx>
22 #include <NCollection_IncAllocator.hxx>
24 #include <gp_Pnt2d.hxx>
25 #include <gp_Lin2d.hxx>
28 #include <IntRes2d_IntersectionPoint.hxx>
30 #include <Geom2d_Curve.hxx>
31 #include <Geom2d_TrimmedCurve.hxx>
32 #include <Geom2d_Line.hxx>
33 #include <Geom2dAdaptor_Curve.hxx>
34 #include <Geom2dInt_GInter.hxx>
36 #include <TopoDS_Edge.hxx>
37 #include <TopoDS_Face.hxx>
38 #include <TopoDS_Vertex.hxx>
40 #include <BRep_Tool.hxx>
41 #include <BRep_Builder.hxx>
43 #include <BOPCol_ListOfInteger.hxx>
45 #include <BOPDS_ShapeInfo.hxx>
46 #include <BOPDS_DS.hxx>
47 #include <BOPDS_FaceInfo.hxx>
48 #include <BOPDS_MapOfPaveBlock.hxx>
49 #include <BOPDS_PaveBlock.hxx>
50 #include <BOPDS_Pave.hxx>
53 void MakeSplitEdge1 (const TopoDS_Edge& aE,
54 const TopoDS_Face& aF,
55 const TopoDS_Vertex& aV1,
56 const Standard_Real aP1,
57 const TopoDS_Vertex& aV2,
58 const Standard_Real aP2,
59 TopoDS_Edge& aNewEdge);
61 //=======================================================================
62 //function : ProcessDE
64 //=======================================================================
65 void BOPAlgo_PaveFiller::ProcessDE()
67 Standard_Integer nF, aNb, nE, nV, nVSD, aNbPB;
68 Handle(NCollection_IncAllocator) aAllocator;
69 Handle(BOPDS_PaveBlock) aPBD;
70 BOPCol_ListIteratorOfListOfInteger aItLI;
74 // 1. Find degnerated edges
75 //-----------------------------------------------------scope f
77 aAllocator=new NCollection_IncAllocator();
78 BOPDS_ListOfPaveBlock aLPBOut(aAllocator);
80 aNb=myDS->NbSourceShapes();
81 for (nE=0; nE<aNb; ++nE) {
82 const BOPDS_ShapeInfo& aSIE=myDS->ShapeInfo(nE);
83 if (aSIE.ShapeType()==TopAbs_EDGE) {
84 if (aSIE.HasFlag(nF)) {
85 const BOPDS_ShapeInfo& aSIF=myDS->ShapeInfo(nF);
86 nV=aSIE.SubShapes().First();
87 if (myDS->HasShapeSD(nV, nVSD)) {
92 if (aSIF.ShapeType() == TopAbs_FACE) {
93 // 1. Find PaveBlocks that are go through nV for nF
94 FindPaveBlocks(nV, nF, aLPBOut);
95 aNbPB=aLPBOut.Extent();
101 BOPDS_ListOfPaveBlock& aLPBD=myDS->ChangePaveBlocks(nE);
104 FillPaves(nV, nE, nF, aLPBOut, aPBD);
106 myDS->UpdatePaveBlock(aPBD);
108 MakeSplitEdge(nE, nF);
112 if (aSIF.ShapeType() == TopAbs_EDGE) {
113 Standard_Real aTol=1.e-7;
114 Standard_Integer nEn;
116 const TopoDS_Edge& aDE=(*(TopoDS_Edge *)(&myDS->Shape(nE)));
117 const TopoDS_Vertex& aVn = (*(TopoDS_Vertex *)(&myDS->Shape(nV)));
122 BB.Degenerated(aE, Standard_True);
123 BB.UpdateEdge(aE, aTol);
125 aSI.SetShapeType(TopAbs_EDGE);
127 nEn=myDS->Append(aSI);
128 BOPDS_ListOfPaveBlock& aLPBD=myDS->ChangePaveBlocks(nE);
137 //=======================================================================
138 //function : FindPaveBlocks
140 //=======================================================================
141 void BOPAlgo_PaveFiller::FindPaveBlocks(const Standard_Integer nV,
142 const Standard_Integer nF,
143 BOPDS_ListOfPaveBlock& aLPBOut)
145 Standard_Integer nV1, nV2;
146 BOPDS_MapIteratorOfMapOfPaveBlock aItMPB;
148 const BOPDS_FaceInfo& aFI=myDS->ChangeFaceInfo(nF);
150 const BOPDS_IndexedMapOfPaveBlock& aMPBIn=aFI.PaveBlocksIn();
151 aItMPB.Initialize(aMPBIn);
152 for(; aItMPB.More(); aItMPB.Next()) {
153 const Handle(BOPDS_PaveBlock)& aPB=aItMPB.Value();
154 aPB->Indices(nV1, nV2);
155 if (nV==nV1 || nV==nV2) {
160 const BOPDS_IndexedMapOfPaveBlock& aMPBOn=aFI.PaveBlocksOn();
161 aItMPB.Initialize(aMPBOn);
162 for(; aItMPB.More(); aItMPB.Next()) {
163 const Handle(BOPDS_PaveBlock)& aPB=aItMPB.Value();
164 aPB->Indices(nV1, nV2);
165 if (nV==nV1 || nV==nV2) {
170 const BOPDS_IndexedMapOfPaveBlock& aMPBSc=aFI.PaveBlocksSc();
171 aItMPB.Initialize(aMPBSc);
172 for(; aItMPB.More(); aItMPB.Next()) {
173 const Handle(BOPDS_PaveBlock)& aPB=aItMPB.Value();
174 aPB->Indices(nV1, nV2);
175 if (nV==nV1 || nV==nV2) {
181 //=======================================================================
182 //function : MakeSplitEdge
184 //=======================================================================
185 void BOPAlgo_PaveFiller::MakeSplitEdge (const Standard_Integer nDE,
186 const Standard_Integer nDF)
188 Standard_Integer nSp, nV1, nV2, aNbPB;
189 Standard_Real aT1, aT2;
190 TopoDS_Edge aDE, aSp;
191 TopoDS_Vertex aV1, aV2;
192 BOPDS_ListIteratorOfListOfPaveBlock aItLPB;
195 aSI.SetShapeType(TopAbs_EDGE);
197 aDE=(*(TopoDS_Edge *)(&myDS->Shape(nDE)));
198 aDE.Orientation(TopAbs_FORWARD);
200 const TopoDS_Face& aDF=(*(TopoDS_Face *)(&myDS->Shape(nDF)));
202 BOPDS_ListOfPaveBlock& aLPB=myDS->ChangePaveBlocks(nDE);
205 aItLPB.Initialize(aLPB);
206 for (; aItLPB.More(); aItLPB.Next()) {
207 Handle(BOPDS_PaveBlock)& aPB=aItLPB.ChangeValue();
209 const BOPDS_Pave& aPave1=aPB->Pave1();
210 aPave1.Contents(nV1, aT1);
212 const BOPDS_Pave& aPave2=aPB->Pave2();
213 aPave2.Contents(nV2, aT2);
215 if (myDS->IsNewShape(nV1) || aNbPB>1) {
216 aV1=(*(TopoDS_Vertex *)(&myDS->Shape(nV1)));
217 aV1.Orientation(TopAbs_FORWARD);
219 aV2=(*(TopoDS_Vertex *)(&myDS->Shape(nV2)));
220 aV2.Orientation(TopAbs_REVERSED);
222 MakeSplitEdge1(aDE, aDF, aV1, aT1, aV2, aT2, aSp);
225 nSp=myDS->Append(aSI);
236 //=======================================================================
237 //function : FillPaves
239 //=======================================================================
240 void BOPAlgo_PaveFiller::FillPaves(const Standard_Integer nVD,
241 const Standard_Integer nED,
242 const Standard_Integer nFD,
243 const BOPDS_ListOfPaveBlock& aLPBOut,
244 const Handle(BOPDS_PaveBlock)& aPBD)
246 Standard_Boolean bXDir, bIsDone;
247 Standard_Integer nE, aNbPoints, j;
248 Standard_Real aTD1, aTD2, aT1, aT2, aTolInter, aX, aDT;
249 Standard_Real aTolCmp;
250 gp_Pnt2d aP2d1, aP2d2, aP2D;
252 Handle(Geom2d_Line) aCLDE;
253 Handle(Geom2d_Curve) aC2DDE1, aC2D;
254 Handle(Geom2d_TrimmedCurve)aC2DDE;
255 BOPDS_ListIteratorOfListOfPaveBlock aItLPB;
258 aDT=Precision::PConfusion();
262 const TopoDS_Edge& aDE=(*(TopoDS_Edge *)(&myDS->Shape(nED)));
263 const TopoDS_Face& aDF=(*(TopoDS_Face *)(&myDS->Shape(nFD)));
265 aC2DDE1=BRep_Tool::CurveOnSurface(aDE, aDF, aTD1, aTD2);
266 aC2DDE=new Geom2d_TrimmedCurve(aC2DDE1, aTD1, aTD2);
268 Handle(Geom2d_TrimmedCurve) aCLDET1=Handle(Geom2d_TrimmedCurve)::DownCast(aC2DDE1);
269 if (aCLDET1.IsNull()) {
270 aCLDE=Handle(Geom2d_Line)::DownCast(aC2DDE1);
273 Handle(Geom2d_Curve) aBasisCurve=aCLDET1->BasisCurve();
274 aCLDE=Handle(Geom2d_Line)::DownCast(aBasisCurve);
277 // Choose direction for degenerated edge
278 aC2DDE->D0(aTD1, aP2d1);
279 aC2DDE->D0(aTD2, aP2d2);
281 bXDir=Standard_False;
282 if (fabs(aP2d1.Y()-aP2d2.Y()) < aDT){
286 aItLPB.Initialize(aLPBOut);
287 for (; aItLPB.More(); aItLPB.Next()) {
288 const Handle(BOPDS_PaveBlock)& aPB=aItLPB.Value();
290 const TopoDS_Edge& aE=(*(TopoDS_Edge *)(&myDS->Shape(nE)));
291 aC2D=BRep_Tool::CurveOnSurface(aE, aDF, aT1, aT2);
297 Geom2dAdaptor_Curve aGAC1, aGAC2;
298 aGAC1.Load(aC2DDE, aTD1, aTD2);
300 Handle(Geom2d_Line) aL2D= Handle(Geom2d_Line)::DownCast(aC2D);
301 if (!aL2D.IsNull()) {
305 aGAC2.Load(aC2D, aT1, aT2);
309 aTolCmp=1.414213562*aTolInter+aDT;
310 Geom2dInt_GInter aGInter(aGAC1, aGAC2, aTolInter, aTolInter);
311 bIsDone=aGInter.IsDone();
316 aNbPoints=aGInter.NbPoints();
321 for (j=1; j<=aNbPoints; ++j) {
322 aP2D=aGInter.Point(j).Value();
323 aX=aGInter.Point(j).ParamOnFirst();
325 if (fabs (aX-aTD1) < aTolCmp || fabs (aX-aTD2) < aTolCmp) {
328 if (aX < aTD1 || aX > aTD2) {
332 if (aPBD->ContainsParameter(aX, aDT)) {
335 aPave.SetParameter(aX);
336 aPBD->AppendExtPave1(aPave);
338 }//for (; aItLPB.More(); aItLPB.Next()) {
340 myDS->UpdatePaveBlock(aPBD);
342 //=======================================================================
343 // function: MakeSplitEdge1
345 //=======================================================================
346 void MakeSplitEdge1 (const TopoDS_Edge& aE,
347 const TopoDS_Face& aF,
348 const TopoDS_Vertex& aV1,
349 const Standard_Real aP1,
350 const TopoDS_Vertex& aV2,
351 const Standard_Real aP2,
352 TopoDS_Edge& aNewEdge)
354 Standard_Real aTol=1.e-7;
363 BB.Range(E, aF, aP1, aP2);
365 BB.Degenerated(E, Standard_True);
367 BB.UpdateEdge(E, aTol);