1 // Created on: 1994-06-07
2 // Created by: Bruno DUMORTIER
3 // Copyright (c) 1994-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
6 // This file is part of Open CASCADE Technology software library.
8 // This library is free software; you can redistribute it and/or modify it under
9 // the terms of the GNU Lesser General Public License version 2.1 as published
10 // by the Free Software Foundation, with special exception defined in the file
11 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12 // distribution for complete text of the license and disclaimer of any warranty.
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
18 #include <Adaptor3d_CurveOnSurface.hxx>
19 #include <BRep_Builder.hxx>
20 #include <BRep_Tool.hxx>
21 #include <BRepBuilderAPI_Copy.hxx>
22 #include <BRepBuilderAPI_Transform.hxx>
23 #include <BRepClass3d_SolidClassifier.hxx>
24 #include <BRepFill_Edge3DLaw.hxx>
25 #include <BRepFill_LocationLaw.hxx>
26 #include <BRepFill_Pipe.hxx>
27 #include <BRepFill_SectionPlacement.hxx>
28 #include <BRepFill_ShapeLaw.hxx>
29 #include <BRepFill_Sweep.hxx>
30 #include <BRepLib.hxx>
31 #include <BRepLib_MakeVertex.hxx>
32 #include <BRepTools_Substitution.hxx>
33 #include <Geom2dAdaptor_HCurve.hxx>
34 #include <Geom_BSplineCurve.hxx>
35 #include <Geom_OffsetCurve.hxx>
36 #include <Geom_TrimmedCurve.hxx>
37 #include <GeomAbs_Shape.hxx>
38 #include <GeomAdaptor_HSurface.hxx>
39 #include <GeomFill_CorrectedFrenet.hxx>
40 #include <GeomFill_CurveAndTrihedron.hxx>
41 #include <GeomFill_DiscreteTrihedron.hxx>
42 #include <GeomFill_Frenet.hxx>
44 #include <Precision.hxx>
45 #include <ShapeUpgrade_RemoveLocations.hxx>
46 #include <Standard_DomainError.hxx>
47 #include <Standard_ErrorHandler.hxx>
48 #include <Standard_NotImplemented.hxx>
49 #include <StdFail_NotDone.hxx>
50 #include <TColStd_DataMapIteratorOfDataMapOfIntegerInteger.hxx>
51 #include <TColStd_DataMapOfIntegerInteger.hxx>
52 #include <TopAbs_ShapeEnum.hxx>
55 #include <TopoDS_Compound.hxx>
56 #include <TopoDS_Edge.hxx>
57 #include <TopoDS_Face.hxx>
58 #include <TopoDS_Iterator.hxx>
59 #include <TopoDS_Shape.hxx>
60 #include <TopoDS_Shell.hxx>
61 #include <TopoDS_Solid.hxx>
62 #include <TopoDS_Vertex.hxx>
63 #include <TopoDS_Wire.hxx>
64 #include <TopTools_DataMapOfShapeInteger.hxx>
65 #include <TopTools_ListIteratorOfListOfShape.hxx>
66 #include <TopTools_SequenceOfShape.hxx>
70 static Standard_Boolean Affich = 0;
73 // ---------------------------------------------------------------------------------
74 // static function: UpdateMap
76 // ---------------------------------------------------------------------------------
77 static Standard_Boolean UpdateMap(const TopoDS_Shape& theKey,
78 const TopoDS_Shape& theValue,
79 TopTools_DataMapOfShapeListOfShape& theMap)
81 if(!theMap.IsBound(theKey))
83 TopTools_ListOfShape thelist;
84 theMap.Bind(theKey, thelist);
86 TopTools_ListOfShape& aList = theMap.ChangeFind(theKey);
87 TopTools_ListIteratorOfListOfShape anIt(aList);
88 Standard_Boolean found = Standard_False;
90 for(; anIt.More(); anIt.Next())
92 if(theValue.IsSame(anIt.Value()))
94 found = Standard_True;
100 aList.Append(theValue);
105 static void ReverseModifiedEdges(TopoDS_Shape& aShape,
106 TopTools_MapOfShape& Emap)
108 TopExp_Explorer Explo(aShape, TopAbs_FACE);
111 for (; Explo.More(); Explo.Next())
113 TopoDS_Shape aFace = Explo.Current();
114 TopoDS_Iterator itf(aFace);
115 for (; itf.More(); itf.Next())
117 TopoDS_Shape aWire = itf.Value();
118 TopTools_ListOfShape Ledges;
119 TopoDS_Iterator itw(aWire);
120 for (; itw.More(); itw.Next())
121 Ledges.Append(itw.Value());
123 aWire.Free(Standard_True);
124 TopTools_ListIteratorOfListOfShape itl(Ledges);
125 for (; itl.More(); itl.Next())
126 BB.Remove(aWire, itl.Value());
128 for (itl.Initialize(Ledges); itl.More(); itl.Next())
130 TopoDS_Shape anEdge = itl.Value();
131 if (Emap.Contains(anEdge))
133 BB.Add(aWire, anEdge);
139 static void UpdateTolFromTopOrBottomPCurve(const TopoDS_Face& aFace,
142 Standard_Real fpar, lpar;
143 Handle(Geom2d_Curve) aPCurve = BRep_Tool::CurveOnSurface(anEdge, aFace, fpar, lpar);
144 if (aPCurve.IsNull())
147 Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, fpar, lpar);
151 Handle(Geom2dAdaptor_HCurve) GAHC2d = new Geom2dAdaptor_HCurve(aPCurve, fpar, lpar);
152 Handle(Geom_Surface) aSurf = BRep_Tool::Surface(aFace);
153 Handle(GeomAdaptor_HSurface) GAHS = new GeomAdaptor_HSurface(aSurf);
154 Adaptor3d_CurveOnSurface ConS(GAHC2d, GAHS);
156 Standard_Real Tol = BRep_Tool::Tolerance(anEdge);
157 Standard_Real InitTol = Tol;
158 Standard_Real TolTol = Tol*Tol;
159 const Standard_Integer NCONTROL = 22;
160 Standard_Real delta = (lpar - fpar)/NCONTROL;
161 for (Standard_Integer i = 0; i <= NCONTROL; i++)
163 Standard_Real par = fpar + i*delta;
164 gp_Pnt pnt = aCurve->Value(par);
165 gp_Pnt prj = ConS.Value(par);
166 Standard_Real sqdist = pnt.SquareDistance(prj);
170 Tol = 1.00005 * Sqrt(TolTol);
174 BB.UpdateEdge(anEdge, Tol);
175 TopoDS_Iterator itv(anEdge);
176 for (; itv.More(); itv.Next())
178 TopoDS_Vertex aVertex = TopoDS::Vertex(itv.Value());
179 BB.UpdateVertex(aVertex, Tol);
184 //=======================================================================
185 //function : BRepFill_Pipe
187 //=======================================================================
189 BRepFill_Pipe::BRepFill_Pipe()
193 myContinuity = GeomAbs_C2;
194 myMode = GeomFill_IsCorrectedFrenet;
195 myForceApproxC1 = Standard_False;
197 myCurIndexOfSectionEdge = 1;
201 //=======================================================================
202 //function : BRepFill_Pipe
204 //=======================================================================
206 BRepFill_Pipe::BRepFill_Pipe(const TopoDS_Wire& Spine,
207 const TopoDS_Shape& Profile,
208 const GeomFill_Trihedron aMode,
209 const Standard_Boolean ForceApproxC1,
210 const Standard_Boolean KPart)
216 myMode = GeomFill_IsCorrectedFrenet;
217 if (aMode == GeomFill_IsFrenet ||
218 aMode == GeomFill_IsCorrectedFrenet ||
219 aMode == GeomFill_IsDiscreteTrihedron)
222 myContinuity = GeomAbs_C2;
223 if (myMode == GeomFill_IsDiscreteTrihedron)
224 myContinuity = GeomAbs_C0;
226 myForceApproxC1 = ForceApproxC1;
228 myCurIndexOfSectionEdge = 1;
230 Perform(Spine, Profile, KPart);
234 //=======================================================================
237 //=======================================================================
239 void BRepFill_Pipe::Perform(const TopoDS_Wire& Spine,
240 const TopoDS_Shape& Profile,
241 const Standard_Boolean /*KPart*/)
244 mySections.Nullify();
253 BRepTools_WireExplorer wexp;
254 TopoDS_Shape TheProf;
256 Handle(GeomFill_TrihedronLaw) TLaw;
259 case GeomFill_IsFrenet:
260 TLaw = new GeomFill_Frenet();
262 case GeomFill_IsCorrectedFrenet:
263 TLaw = new GeomFill_CorrectedFrenet();
265 case GeomFill_IsDiscreteTrihedron:
266 TLaw = new GeomFill_DiscreteTrihedron();
271 Handle(GeomFill_CurveAndTrihedron) Loc =
272 new (GeomFill_CurveAndTrihedron) (TLaw);
273 myLoc = new (BRepFill_Edge3DLaw) (mySpine, Loc);
274 if (myLoc->NbLaw() == 0) {
275 return; // Degenerated case
277 myLoc->TransformInG0Law(); // Set into continuity
279 BRepFill_SectionPlacement Place(myLoc, Profile);
280 myTrsf = Place.Transformation();
282 TopLoc_Location Loc2(myTrsf), Loc1;
283 Loc1 = Profile.Location();
286 TheProf.Location(Loc2.Multiplied(Loc1));
288 // Construct First && Last Shape
289 Handle(GeomFill_LocationLaw) law;
294 Standard_Real first, last;
295 myLoc->Law(1)->GetDomain(first, last);
296 myLoc->Law(1)->D0(first, M, V);
297 fila.SetValues(M(1,1), M(1,2), M(1,3), V.X(),
298 M(2,1), M(2,2), M(2,3), V.Y(),
299 M(3,1), M(3,2), M(3,3), V.Z());
301 fila.Multiply(myTrsf);
302 TopLoc_Location LocFirst(fila);
304 if ( ! LocFirst.IsIdentity()) {
305 //myFirst.Location( LocFirst.Multiplied(myProfile.Location()) );
306 myFirst = BRepBuilderAPI_Transform(myProfile, fila, Standard_True); //copy
309 ShapeUpgrade_RemoveLocations RemLoc;
310 RemLoc.SetRemoveLevel(TopAbs_COMPOUND);
311 RemLoc.Remove(myFirst);
312 myFirst = RemLoc.GetResult();
314 myLoc->Law(myLoc->NbLaw())->GetDomain(first, last);
315 myLoc->Law(myLoc->NbLaw())->D0(last,M, V);
316 // try { // Not good, but there are no other means to test SetValues
317 fila.SetValues(M(1,1), M(1,2), M(1,3), V.X(),
318 M(2,1), M(2,2), M(2,3), V.Y(),
319 M(3,1), M(3,2), M(3,3), V.Z());
320 fila.Multiply(myTrsf);
321 TopLoc_Location LocLast(fila);
322 if (! myLoc->IsClosed() || LocFirst != LocLast) {
324 if ( ! LocLast.IsIdentity()) {
325 //myLast.Location(LocLast.Multiplied(myProfile.Location()) );
326 myLast = BRepBuilderAPI_Transform(myProfile, fila, Standard_True); //copy
333 RemLoc.Remove(myLast);
334 myLast = RemLoc.GetResult();
338 DBRep::Set("theprof", TheProf);
339 DBRep::Set("thefirst", myFirst);
340 DBRep::Set("thelast" , myLast);
344 myShape = MakeShape(TheProf, myFirst, myLast);
348 //=======================================================================
351 //=======================================================================
353 const TopoDS_Shape& BRepFill_Pipe::Spine() const
358 //=======================================================================
361 //=======================================================================
363 const TopoDS_Shape& BRepFill_Pipe::Profile() const
368 //=======================================================================
371 //=======================================================================
373 const TopoDS_Shape& BRepFill_Pipe::Shape() const
378 //=======================================================================
379 //function : ErrorOnSurface
381 //=======================================================================
383 Standard_Real BRepFill_Pipe::ErrorOnSurface() const
385 return myErrorOnSurf;
389 //=======================================================================
390 //function : FirstShape
392 //=======================================================================
394 const TopoDS_Shape& BRepFill_Pipe::FirstShape() const
400 //=======================================================================
401 //function : LastShape
403 //=======================================================================
405 const TopoDS_Shape& BRepFill_Pipe::LastShape() const
410 //=======================================================================
411 //function : Generated
413 //=======================================================================
414 void BRepFill_Pipe::Generated(const TopoDS_Shape& theShape,
415 TopTools_ListOfShape& theList)
419 if (theShape.IsSame(myProfile))
420 theList.Append(myShape);
423 if (theShape.ShapeType() == TopAbs_FACE ||
424 theShape.ShapeType() == TopAbs_WIRE)
426 if(myGenMap.IsBound(theShape))
427 theList = myGenMap.Find(theShape);
429 else if (theShape.ShapeType() == TopAbs_EDGE)
431 TopoDS_Iterator itw(mySpine);
432 for (; itw.More(); itw.Next())
434 const TopoDS_Edge& aSpineEdge = TopoDS::Edge(itw.Value());
435 const TopoDS_Shape& aFace = Face(aSpineEdge, TopoDS::Edge(theShape));
436 theList.Append(aFace);
439 else if (theShape.ShapeType() == TopAbs_VERTEX)
441 TopoDS_Iterator itw(mySpine);
442 for (; itw.More(); itw.Next())
444 const TopoDS_Edge& aSpineEdge = TopoDS::Edge(itw.Value());
445 const TopoDS_Shape& anEdge = Edge(aSpineEdge, TopoDS::Vertex(theShape));
446 theList.Append(anEdge);
452 //=======================================================================
455 //=======================================================================
457 TopoDS_Face BRepFill_Pipe::Face(const TopoDS_Edge& ESpine,
458 const TopoDS_Edge& EProfile)
462 if ( BRep_Tool::Degenerated(EProfile))
465 Standard_Integer ii, ispin = 0, iprof = 0, count = 0;
467 // *************************************************
468 // Search if EProfile is an edge of myProfile
469 // *************************************************
470 iprof = FindEdge(myProfile, EProfile, count);
472 if (!iprof) Standard_DomainError::Raise(
473 "BRepFill_Pipe::Face : Edge not in the Profile");
476 // *************************************************
477 // Search if ESpine is an edge of mySpine and find
478 // the index of the corresponding Filler
479 // *************************************************
480 for (ii=1; ii<=myLoc->NbLaw() && (!ispin); ii++)
481 if (ESpine.IsSame(myLoc->Edge(ii))) ispin = ii;
483 if (!ispin) Standard_DomainError::Raise(
484 "BRepFill_Pipe::Edge : Edge not in the Spine");
486 theFace = TopoDS::Face(myFaces->Value(iprof, ispin));
491 //=======================================================================
494 //=======================================================================
495 TopoDS_Edge BRepFill_Pipe::Edge(const TopoDS_Edge& ESpine,
496 const TopoDS_Vertex& VProfile)
498 Standard_Integer ii, ispin = 0, iprof = 0, count = 0;;
500 // *************************************************
501 // Search if VProfile is a Vertex of myProfile
502 // *************************************************
503 iprof = FindVertex(myProfile, VProfile, count);
504 if (!iprof) Standard_DomainError::Raise(
505 "BRepFill_Pipe::Edge : Vertex not in the Profile");
508 // *************************************************
509 // Search if ESpine is an edge of mySpine and find
510 // the index of the corresponding Filler
511 // *************************************************
513 for (ii=1; ii<=myLoc->NbLaw() && (!ispin); ii++)
514 if (ESpine.IsSame(myLoc->Edge(ii))) ispin = ii;
516 if (!ispin) Standard_DomainError::Raise(
517 "BRepFill_Pipe::Edge : Edge not in the Spine");
520 // *************************************************
521 // Generate the corresponding Shape
522 // *************************************************
524 theEdge = TopoDS::Edge(myEdges->Value(iprof, ispin));
531 //=======================================================================
534 //=======================================================================
536 TopoDS_Shape BRepFill_Pipe::Section(const TopoDS_Vertex& VSpine) const
538 TopoDS_Iterator it, itv;
540 Standard_Integer ii, ispin = 0;
542 TopoDS_Shape curSect = myProfile;
544 // *************************************************
545 // Search if ESpine is an edge of mySpine and find
546 // the index of the corresponding Filler
547 // *************************************************
549 // iterate on all the edges of mySpine
550 for (ii=1; ii<=myLoc->NbLaw()+1 && (!ispin); ii++)
551 if (VSpine.IsSame(myLoc->Vertex(ii))) ispin = ii;
553 if (!ispin) Standard_DomainError::Raise(
554 "BRepFill_Pipe::Section : Vertex not in the Spine");
557 TopoDS_Compound Comp;
558 B.MakeCompound(Comp);
559 for (ii=1; ii<=mySections->ColLength(); ii++)
560 B.Add(Comp, mySections->Value(ii, ispin));
565 //=======================================================================
566 //function : PipeLine
567 //purpose : Construct a wire by sweeping of a point
568 //=======================================================================
570 TopoDS_Wire BRepFill_Pipe::PipeLine(const gp_Pnt& Point)
577 BRepLib_MakeVertex MkV(P);
578 Handle(BRepFill_ShapeLaw) Section =
579 new (BRepFill_ShapeLaw) (MkV.Vertex());
582 BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
583 MkSw.SetForceApproxC1(myForceApproxC1);
584 MkSw.Build( myReversedEdges, myTapes, myRails,
585 BRepFill_Modified, myContinuity, GeomFill_Location, myDegmax, mySegmax );
586 TopoDS_Shape aLocalShape = MkSw.Shape();
587 myErrorOnSurf = MkSw.ErrorOnSurface();
588 return TopoDS::Wire(aLocalShape);
589 // return TopoDS::Wire(MkSw.Shape());
592 //=======================================================================
593 //function : MakeShape
595 //=======================================================================
597 TopoDS_Shape BRepFill_Pipe::MakeShape(const TopoDS_Shape& S,
598 const TopoDS_Shape& FirstShape,
599 const TopoDS_Shape& LastShape)
603 Standard_Boolean explode = Standard_False;
604 TopoDS_Shape TheS, TheFirst, TheLast;
605 Standard_Integer InitialLength = 0;
607 TheFirst = FirstShape;
609 if (! myFaces.IsNull()) InitialLength = myFaces->ColLength();
611 // there are two kinds of generation
612 // 1. generate with S from each Filler (Vertex, Edge)
613 // 2. call MakeShape recursively on the subshapes of S
615 // explode is True in the second case
617 // create the result empty
619 switch (S.ShapeType()) {
623 B.MakeWire(TopoDS::Wire(result));
630 B.MakeShell(TopoDS::Shell(result));
633 W.Closed(BRep_Tool::IsClosed(S));
635 if (!FirstShape.IsNull()) {
637 B.Add(W, FirstShape);
638 W.Closed(BRep_Tool::IsClosed(FirstShape));
641 if (!LastShape.IsNull()) {
644 W.Closed(BRep_Tool::IsClosed(LastShape));
647 result.Closed (BRep_Tool::IsClosed (result));
652 B.MakeShell(TopoDS::Shell(result));
657 B.MakeShell(TopoDS::Shell(result));
658 explode = Standard_True;
659 if ( !mySpine.Closed() && !TheFirst.IsNull()) {
660 B.Add(result, TheFirst.Reversed());
662 result.Closed (BRep_Tool::IsClosed (result));
668 B.MakeCompSolid(TopoDS::CompSolid(result));
669 explode = Standard_True;
674 case TopAbs_COMPSOLID :
675 Standard_DomainError::Raise("BRepFill_Pipe::profile contains solids");
678 case TopAbs_COMPOUND :
680 B.MakeCompound(TopoDS::Compound(result));
681 explode = Standard_True;
690 TopoDS_Iterator itFirst, itLast;
691 TopoDS_Shape first, last;
692 if (!TheFirst.IsNull()) itFirst.Initialize(TheFirst);
693 if (!TheLast.IsNull()) itLast.Initialize(TheLast);
695 for (TopoDS_Iterator it(S); it.More(); it.Next()) {
696 if (!TheFirst.IsNull()) first = itFirst.Value();
697 if (!TheLast.IsNull()) last = itLast.Value();
698 if (TheS.ShapeType() == TopAbs_FACE )
699 MakeShape(it.Value(), first, last);
701 B.Add(result,MakeShape(it.Value(), first, last));
703 if (!TheFirst.IsNull()) itFirst.Next();
704 if (!TheLast.IsNull()) itLast.Next();
709 if (TheS.ShapeType() == TopAbs_VERTEX ) {
710 Handle(BRepFill_ShapeLaw) Section =
711 new (BRepFill_ShapeLaw) (TopoDS::Vertex(TheS));
712 BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
713 MkSw.SetForceApproxC1(myForceApproxC1);
714 MkSw.Build( myReversedEdges, myTapes, myRails,
715 BRepFill_Modified, myContinuity, GeomFill_Location, myDegmax, mySegmax );
716 result = MkSw.Shape();
717 UpdateMap(TheS.Located(myProfile.Location()), result, myGenMap);
718 myErrorOnSurf = MkSw.ErrorOnSurface();
720 Handle(TopTools_HArray2OfShape) aSections = MkSw.Sections();
722 if (aSections.IsNull() == Standard_False) {
723 const Standard_Integer aVLast = aSections->UpperCol();
725 myFirst = aSections->Value(1, 1);
726 myLast = aSections->Value(1, aVLast);
730 if (TheS.ShapeType() == TopAbs_WIRE ) {
731 Handle(BRepFill_ShapeLaw) Section =
732 new (BRepFill_ShapeLaw) (TopoDS::Wire(TheS));
733 BRepFill_Sweep MkSw(Section, myLoc, Standard_True);
734 MkSw.SetBounds(TopoDS::Wire(TheFirst),
735 TopoDS::Wire(TheLast));
736 MkSw.SetForceApproxC1(myForceApproxC1);
737 MkSw.Build( myReversedEdges, myTapes, myRails,
738 BRepFill_Modified, myContinuity, GeomFill_Location, myDegmax, mySegmax );
739 result = MkSw.Shape();
740 UpdateMap(TheS.Located(myProfile.Location()), result, myGenMap);
741 myErrorOnSurf = MkSw.ErrorOnSurface();
742 //Correct <myFirst> and <myLast>
743 ReverseModifiedEdges(myFirst, myReversedEdges);
744 ReverseModifiedEdges(myLast, myReversedEdges);
746 // Labeling of elements
747 if (mySections.IsNull()) {
748 myFaces = MkSw.SubShape();
749 mySections = MkSw.Sections();
750 myEdges = MkSw.InterFaces();
753 Handle(TopTools_HArray2OfShape) Aux, Somme;
754 Standard_Integer length;
755 Standard_Integer ii, jj, kk;
757 Aux = MkSw.SubShape();
758 length = Aux->ColLength() + myFaces->ColLength();
759 Somme = new (TopTools_HArray2OfShape) (1, length, 1,
761 for (jj=1; jj<=myFaces->RowLength(); jj++) {
762 for (ii=1; ii<=myFaces->ColLength(); ii++)
763 Somme->SetValue(ii, jj, myFaces->Value(ii, jj));
765 for (kk=1, ii=myFaces->ColLength()+1;
766 kk <=Aux->ColLength(); kk++, ii++)
767 Somme->SetValue(ii, jj, Aux->Value(kk, jj));
771 Aux = MkSw.Sections();
772 length = Aux->ColLength() + mySections->ColLength();
773 Somme = new (TopTools_HArray2OfShape) (1, length, 1,
775 for (jj=1; jj<=mySections->RowLength(); jj++) {
776 for (ii=1; ii<=mySections->ColLength(); ii++)
777 Somme->SetValue(ii, jj, mySections->Value(ii, jj));
779 myCurIndexOfSectionEdge = mySections->ColLength()+1;
781 for (kk=1, ii=mySections->ColLength()+1;
782 kk <=Aux->ColLength(); kk++, ii++)
783 Somme->SetValue(ii, jj, Aux->Value(kk, jj));
787 Aux = MkSw.InterFaces();
788 length = Aux->ColLength() + myEdges->ColLength();
789 Somme = new (TopTools_HArray2OfShape) (1, length, 1,
791 for (jj=1; jj<=myEdges->RowLength(); jj++) {
792 for (ii=1; ii<=myEdges->ColLength(); ii++)
793 Somme->SetValue(ii, jj, myEdges->Value(ii, jj));
795 for (kk=1, ii=myEdges->ColLength()+1;
796 kk <=Aux->ColLength(); kk++, ii++)
797 Somme->SetValue(ii, jj, Aux->Value(kk, jj));
805 if ( TheS.ShapeType() == TopAbs_FACE ) {
806 Standard_Integer ii, jj;
808 TopExp_Explorer Explo(result, TopAbs_FACE);
809 for (; Explo.More(); Explo.Next())
811 TopoDS_Shape aFace = Explo.Current();
812 RebuildTopOrBottomFace(aFace.Reversed(), Standard_True); //top face was reversed
816 for (ii=InitialLength+1; ii<=myFaces->ColLength(); ii++) {
817 for (jj=1; jj<=myFaces->RowLength(); jj++) {
818 F = TopoDS::Face(myFaces->Value(ii, jj));
819 if (!F.IsNull()) B.Add(result, F);
823 if ( !mySpine.Closed()) {
824 // if Spine is not closed
825 // add the last face of the solid
828 RebuildTopOrBottomFace(TheLast, Standard_False); //bottom face
830 B.Add(result, TopoDS::Face(TheLast));
837 result.Closed(Standard_True);
838 BS.Add(solid,TopoDS::Shell(result));
840 BRepClass3d_SolidClassifier SC(solid);
841 SC.PerformInfinitePoint(Precision::Confusion());
842 if ( SC.State() == TopAbs_IN) {
844 TopoDS_Shape aLocalShape = result.Reversed();
845 BS.Add(solid,TopoDS::Shell(aLocalShape));
846 // BS.Add(solid,TopoDS::Shell(result.Reversed()));
848 UpdateMap(TheS.Located(myProfile.Location()), solid, myGenMap);
856 //============================================================================
857 //function : FindEdge
858 //purpose : Find the number of edge corresponding to the edge of the profile.
859 //============================================================================
861 Standard_Integer BRepFill_Pipe::FindEdge(const TopoDS_Shape& S,
862 const TopoDS_Edge& E,
863 Standard_Integer& InitialLength) const
865 Standard_Integer result = 0;
867 switch (S.ShapeType()) {
872 if (S.IsSame(E)) result = InitialLength;
878 Handle(BRepFill_ShapeLaw) Section =
879 new (BRepFill_ShapeLaw) (TopoDS::Wire(S), Standard_False);
880 Standard_Integer NbLaw = Section->NbLaw();
882 for (Standard_Integer ii = 1; (ii<=NbLaw) && (!result); ii++) {
883 if (E.IsSame(Section->Edge(ii)) ) result = InitialLength + ii;
885 InitialLength += NbLaw;
891 case TopAbs_COMPOUND :
893 for (TopoDS_Iterator it(S); it.More() && (!result); it.Next())
894 result = FindEdge(it.Value(), E, InitialLength );
899 case TopAbs_COMPSOLID :
900 Standard_DomainError::Raise("BRepFill_Pipe::SOLID or COMPSOLID");
909 //=======================================================================
910 //function : FindVertex
911 //purpose : Find the number of edge corresponding to an edge of the profile.
912 //=======================================================================
914 Standard_Integer BRepFill_Pipe::FindVertex(const TopoDS_Shape& S,
915 const TopoDS_Vertex& V,
916 Standard_Integer& InitialLength) const
918 Standard_Integer result = 0;
920 switch (S.ShapeType()) {
924 if (S.IsSame(V)) result = InitialLength;
930 TopoDS_Vertex VF, VL;
931 TopExp::Vertices(TopoDS::Edge(S), VF, VL);
932 if (S.Orientation() == TopAbs_REVERSED) {
934 aux = VF; VF = VL; VL = aux;
936 if (VF.IsSame(V)) result = InitialLength+1;
937 else if (VL.IsSame(V)) result = InitialLength+2;
944 Standard_Integer ii = InitialLength+1;
945 Handle(BRepFill_ShapeLaw) Section =
946 new (BRepFill_ShapeLaw) (TopoDS::Wire(S), Standard_False);
947 InitialLength += Section->NbLaw()+1;
949 for (; (ii<=InitialLength) && (!result); ii++) {
950 if (V.IsSame(Section->Vertex(ii, 0.)) ) result = ii;
957 case TopAbs_COMPOUND :
959 for (TopoDS_Iterator it(S); it.More() && (!result); it.Next())
960 result = FindVertex(it.Value(), V, InitialLength);
965 case TopAbs_COMPSOLID :
966 Standard_DomainError::Raise("BRepFill_Pipe::SOLID or COMPSOLID");
975 //=======================================================================
976 //function : DefineRealSegmax
977 //purpose : Defines the real number of segments
978 // required in the case of bspline spine
979 //=======================================================================
981 void BRepFill_Pipe::DefineRealSegmax()
983 Standard_Integer RealSegmax = 0;
985 TopoDS_Iterator iter(mySpine);
986 for (; iter.More(); iter.Next())
988 TopoDS_Edge E = TopoDS::Edge(iter.Value());
989 Standard_Real first, last;
990 Handle(Geom_Curve) C = BRep_Tool::Curve( E, first, last );
993 while (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve) ||
994 C->DynamicType() == STANDARD_TYPE(Geom_OffsetCurve))
996 if (C->DynamicType() == STANDARD_TYPE(Geom_TrimmedCurve))
997 C = Handle(Geom_TrimmedCurve)::DownCast (C)->BasisCurve();
998 if (C->DynamicType() == STANDARD_TYPE(Geom_OffsetCurve))
999 C = Handle(Geom_OffsetCurve)::DownCast (C)->BasisCurve();
1001 if (C->DynamicType() == STANDARD_TYPE(Geom_BSplineCurve))
1003 Handle(Geom_BSplineCurve) BC (Handle(Geom_BSplineCurve)::DownCast (C));
1004 Standard_Integer NbKnots = BC->NbKnots();
1005 Standard_Integer RealNbKnots = NbKnots;
1006 if (first > BC->FirstParameter())
1008 Standard_Integer I1, I2;
1009 BC->LocateU( first, Precision::PConfusion(), I1, I2 );
1010 RealNbKnots -= I1-1;
1012 if (last < BC->LastParameter())
1014 Standard_Integer I1, I2;
1015 BC->LocateU( last, Precision::PConfusion(), I1, I2 );
1016 RealNbKnots -= NbKnots-I2;
1018 RealSegmax += RealNbKnots-1;
1022 if (mySegmax < RealSegmax)
1023 mySegmax = RealSegmax;
1026 //=======================================================================
1027 //function : RebuildTopOrBottomFace
1028 //purpose : Correct orientation of v-iso edges
1029 // according to new 3d and 2d curves taken from swept surfaces
1030 //=======================================================================
1032 void BRepFill_Pipe::RebuildTopOrBottomFace(const TopoDS_Shape& aFace,
1033 const Standard_Boolean IsTop) const
1035 Standard_Integer IndexOfSection =
1036 (IsTop)? 1 : mySections->RowLength();
1038 Standard_Integer ii;
1040 TopoDS_Iterator itf(aFace);
1041 for (; itf.More(); itf.Next())
1043 TopoDS_Shape aWire = itf.Value();
1044 TopTools_SequenceOfShape InitEdges;
1045 TopTools_SequenceOfShape ResEdges;
1046 TopoDS_Iterator itw(aWire);
1047 for (; itw.More(); itw.Next())
1049 TopoDS_Shape anEdge = itw.Value();
1050 for (ii = myCurIndexOfSectionEdge; ii <= mySections->ColLength(); ii++)
1052 TopoDS_Shape aVisoEdge = mySections->Value(ii, IndexOfSection);
1053 if (anEdge.IsSame(aVisoEdge))
1055 InitEdges.Append(anEdge);
1056 ResEdges.Append(aVisoEdge);
1061 aWire.Free(Standard_True);
1062 for (ii = 1; ii <= InitEdges.Length(); ii++)
1064 BB.Remove(aWire, InitEdges(ii));
1065 UpdateTolFromTopOrBottomPCurve(TopoDS::Face(aFace), TopoDS::Edge(ResEdges(ii)));
1066 BB.Add(aWire, ResEdges(ii));