diff --git a/src/BRepBuilderAPI/BRepBuilderAPI_BndBoxTreeSelector.hxx b/src/BRepBuilderAPI/BRepBuilderAPI_BndBoxTreeSelector.hxx new file mode 100644 index 0000000000..681c2a8feb --- /dev/null +++ b/src/BRepBuilderAPI/BRepBuilderAPI_BndBoxTreeSelector.hxx @@ -0,0 +1,77 @@ +// File: BRepBuilderAPI_BndBoxTreeSelector.hxx +// Created: Nov 29 17:47:12 2011 +// Author: ANNA MASALSKAYA +// Copyright: Open CASCADE SAS 2011 + +#ifndef _BRepBuilderAPI_BndBoxTreeSelector_Header +#define _BRepBuilderAPI_BndBoxTreeSelector_Header + +#ifndef _TColStd_ListOfInteger_HeaderFile +#include +#endif +#ifndef _Bnd_Box_HeaderFile +#include +#endif +#ifndef NCollection_UBTree_HeaderFile +#include +#endif + +typedef NCollection_UBTree BRepBuilderAPI_BndBoxTree; + +//======================================================================= +//! Class BRepBuilderAPI_BndBoxTreeSelector +//! derived from UBTree::Selector +//! This class is used to select overlapping boxes, stored in +//! NCollection::UBTree; contains methods to maintain the selection +//! condition and to retrieve selected objects after search. +//======================================================================= + +class BRepBuilderAPI_BndBoxTreeSelector : public BRepBuilderAPI_BndBoxTree::Selector +{ +public: + //! Constructor; calls the base class constructor + BRepBuilderAPI_BndBoxTreeSelector() : BRepBuilderAPI_BndBoxTree::Selector() {} + + //! Implementation of rejection method + //! @return + //! True if the bounding box does not intersect with the current + Standard_Boolean Reject (const Bnd_Box& theBox) const + { + return (myBox.IsOut (theBox)); + } + + //! Implementation of acceptance method + //! This method is called when the bounding box intersect with the current. + //! It stores the object - the index of box in the list of accepted objects. + //! @return + //! True, because the object is accepted + Standard_Boolean Accept (const Standard_Integer& theObj) + { + myResInd.Append (theObj); + return Standard_True; + } + + //! Clear the list of intersecting boxes + void ClearResList() + { + myResInd.Clear(); + } + + //! Set current box to search for overlapping with him + void SetCurrent (const Bnd_Box& theBox) + { + myBox = theBox; + } + + //! Get list of indexes of boxes intersecting with the current box + const TColStd_ListOfInteger& ResInd() + { + return myResInd; + } + +private: + TColStd_ListOfInteger myResInd; + Bnd_Box myBox; +}; + +#endif diff --git a/src/BRepBuilderAPI/BRepBuilderAPI_CellFilter.hxx b/src/BRepBuilderAPI/BRepBuilderAPI_CellFilter.hxx new file mode 100644 index 0000000000..7db85f2541 --- /dev/null +++ b/src/BRepBuilderAPI/BRepBuilderAPI_CellFilter.hxx @@ -0,0 +1,24 @@ +// File: BRepBuilderAPI_CellFilter.hxx +// Created: Nov 24 16:48:12 2011 +// Author: ANNA MASALSKAYA +// Copyright: Open CASCADE SAS 2011 + +#ifndef _BRepBuilderAPI_CellFilter_HeaderFile +#define _BRepBuilderAPI_CellFilter_HeaderFile + +#ifndef _gp_XYZ_HeaderFile +#include +#endif +#ifndef _gp_XY_HeaderFile +#include +#endif +#ifndef NCollection_CellFilter_HeaderFile +#include +#endif +#ifndef _BRepBuilderAPI_VertexInspector_HeaderFile +#include +#endif + +typedef NCollection_CellFilter BRepBuilderAPI_CellFilter; + +#endif diff --git a/src/BRepBuilderAPI/BRepBuilderAPI_Sewing.cxx b/src/BRepBuilderAPI/BRepBuilderAPI_Sewing.cxx index 8c60fbe53e..6bb580eadf 100755 --- a/src/BRepBuilderAPI/BRepBuilderAPI_Sewing.cxx +++ b/src/BRepBuilderAPI/BRepBuilderAPI_Sewing.cxx @@ -108,6 +108,10 @@ #include #include #include +#include +#include +#include +#include static void SortBox (const Handle(Bnd_HArray1OfBox) hSetBoxes, const Bnd_Box& aBox, @@ -2725,6 +2729,8 @@ static Standard_Boolean GlueVertices(TopTools_IndexedDataMapOfShapeShape& aVerte Standard_Integer i, nbVertices = aVertexNode.Extent(); // Create map of node -> vertices TopTools_IndexedDataMapOfShapeListOfShape NodeVertices; + BRepBuilderAPI_CellFilter aFilter (Tolerance); + BRepBuilderAPI_VertexInspector anInspector (Tolerance); for (i = 1; i <= nbVertices; i++) { TopoDS_Shape vertex = aVertexNode.FindKey(i); TopoDS_Vertex node = TopoDS::Vertex(aVertexNode(i)); @@ -2735,38 +2741,34 @@ static Standard_Boolean GlueVertices(TopTools_IndexedDataMapOfShapeShape& aVerte TopTools_ListOfShape vlist; vlist.Append(vertex); NodeVertices.Add(node,vlist); + gp_Pnt aPnt = BRep_Tool::Pnt (TopoDS::Vertex (node)); + aFilter.Add (NodeVertices.FindIndex (node), aPnt.XYZ()); + anInspector.Add (aPnt.XYZ()); } } Standard_Integer nbNodes = NodeVertices.Extent(); #ifdef DEB cout << "Glueing " << nbNodes << " nodes..." << endl; #endif - // Create array of boxes with nodes - Handle(Bnd_HArray1OfBox) hSetBoxes = new Bnd_HArray1OfBox(1,nbNodes); - Bnd_Box aBox; - Standard_Real eps = Tolerance*0.5; - for (i = 1; i <= nbNodes; i++) { - gp_Pnt pt = BRep_Tool::Pnt(TopoDS::Vertex(NodeVertices.FindKey(i))); - aBox.Set(pt); - aBox.Enlarge(eps); - hSetBoxes->SetValue(i,aBox); - } // Merge nearest nodes TopTools_IndexedDataMapOfShapeShape NodeNearestNode; Message_ProgressSentry aPS (theProgress, "Glueing nodes", 0, nbNodes, 1, Standard_True); for (i = 1; i <= nbNodes && aPS.More(); i++, aPS.Next()) { TopoDS_Vertex node1 = TopoDS::Vertex(NodeVertices.FindKey(i)); // Find near nodes - TColStd_ListOfInteger listIndex; - SortBox(hSetBoxes,hSetBoxes->Value(i),listIndex); - if (listIndex.IsEmpty()) continue; + gp_Pnt pt1 = BRep_Tool::Pnt (node1); + anInspector.SetCurrent (pt1.XYZ()); + gp_XYZ aPntMin = anInspector.Shift (pt1.XYZ(), -Tolerance); + gp_XYZ aPntMax = anInspector.Shift (pt1.XYZ(), Tolerance); + aFilter.Inspect (aPntMin, aPntMax, anInspector); + if (anInspector.ResInd().IsEmpty()) continue; // Retrieve list of edges for the first node const TopTools_ListOfShape& ledges1 = aNodeEdges(node1); // Explore list of near nodes and fill the sequence of glued nodes TopTools_SequenceOfShape SeqNodes; TopTools_ListOfShape listNodesSameEdge; - gp_Pnt pt1 = BRep_Tool::Pnt(node1); - TColStd_ListIteratorOfListOfInteger iter1(listIndex); + //gp_Pnt pt1 = BRep_Tool::Pnt(node1); + TColStd_ListIteratorOfListOfInteger iter1(anInspector.ResInd()); for (; iter1.More(); iter1.Next()) { TopoDS_Vertex node2 = TopoDS::Vertex(NodeVertices.FindKey(iter1.Value())); if (node1 == node2) continue; @@ -2874,11 +2876,11 @@ static Standard_Boolean GlueVertices(TopTools_IndexedDataMapOfShapeShape& aVerte if (SeqNodes.Length()) NodeNearestNode.Add(node1,SeqNodes.First()); } + anInspector.ClearResList(); } // Create new nodes for chained nearest nodes if (NodeNearestNode.IsEmpty()) return Standard_False; - hSetBoxes.Nullify(); return CreateNewNodes(NodeNearestNode,NodeVertices,aVertexNode,aNodeEdges); } @@ -3580,16 +3582,20 @@ void BRepBuilderAPI_Sewing::Cutting(const Handle(Message_ProgressIndicator)& the { Standard_Integer i, nbVertices = myVertexNode.Extent(); if (!nbVertices) return; - // Create a sort box with vertices + // Create a box tree with vertices Standard_Real eps = myTolerance*0.5; - Handle(Bnd_HArray1OfBox) hSetBoxes = new Bnd_HArray1OfBox(1,nbVertices); + BRepBuilderAPI_BndBoxTree aTree; + NCollection_UBTreeFiller aTreeFiller (aTree); + BRepBuilderAPI_BndBoxTreeSelector aSelector; for (i = 1; i <= nbVertices; i++) { gp_Pnt pt = BRep_Tool::Pnt(TopoDS::Vertex(myVertexNode.FindKey(i))); Bnd_Box aBox; aBox.Set(pt); aBox.Enlarge(eps); - hSetBoxes->ChangeValue(i) = aBox; + aTreeFiller.Add (i, aBox); } + aTreeFiller.Fill(); + Handle(Geom_Curve) c3d; TopLoc_Location loc; Standard_Real first, last; @@ -3618,16 +3624,16 @@ void BRepBuilderAPI_Sewing::Cutting(const Handle(Message_ProgressIndicator)& the GeomAdaptor_Curve adptC(c3d,first,last); BndLib_Add3dCurve::Add(adptC,myTolerance,aGlobalBox); // Sort vertices to find candidates - TColStd_ListOfInteger listIndex; - SortBox(hSetBoxes,aGlobalBox,listIndex); + aSelector.SetCurrent (aGlobalBox); + aTree.Select (aSelector); // Skip bound if no node is in the boundind box - if (!listIndex.Extent()) continue; + if (!aSelector.ResInd().Extent()) continue; // Retrieve bound nodes TopExp::Vertices(bound,V1,V2); const TopoDS_Shape& Node1 = myVertexNode.FindFromKey(V1); const TopoDS_Shape& Node2 = myVertexNode.FindFromKey(V2); // Fill map of candidate vertices - TColStd_ListIteratorOfListOfInteger itl(listIndex); + TColStd_ListIteratorOfListOfInteger itl(aSelector.ResInd()); for (; itl.More(); itl.Next()) { const Standard_Integer index = itl.Value(); const TopoDS_Shape& Node = myVertexNode.FindFromIndex(index); @@ -3636,6 +3642,7 @@ void BRepBuilderAPI_Sewing::Cutting(const Handle(Message_ProgressIndicator)& the CandidateVertices.Add(vertex); } } + aSelector.ClearResList(); } Standard_Integer nbCandidates = CandidateVertices.Extent(); if (!nbCandidates) continue; @@ -4672,3 +4679,25 @@ void BRepBuilderAPI_Sewing::SameParameterShape() } } } + +//======================================================================= +//function : Inspect +//purpose : Used for selection and storage of coinciding points +//======================================================================= + +NCollection_CellFilter_Action BRepBuilderAPI_VertexInspector::Inspect (const Standard_Integer theTarget) +{ + /*gp_Pnt aPnt = gp_Pnt (myPoints.Value (theTarget - 1)); + if (aPnt.SquareDistance (gp_Pnt (myCurrent)) <= myTol) + myResInd.Append (theTarget);*/ + + const gp_XYZ& aPnt = myPoints.Value (theTarget - 1); + Standard_Real aDx, aDy, aDz; + aDx = myCurrent.X() - aPnt.X(); + aDy = myCurrent.Y() - aPnt.Y(); + aDz = myCurrent.Z() - aPnt.Z(); + + if ((aDx*aDx <= myTol) && (aDy*aDy <= myTol) && (aDz*aDz <= myTol)) + myResInd.Append (theTarget); + return CellFilter_Keep; +} diff --git a/src/BRepBuilderAPI/BRepBuilderAPI_VertexInspector.hxx b/src/BRepBuilderAPI/BRepBuilderAPI_VertexInspector.hxx new file mode 100644 index 0000000000..92b5a83279 --- /dev/null +++ b/src/BRepBuilderAPI/BRepBuilderAPI_VertexInspector.hxx @@ -0,0 +1,79 @@ +// File: BRepBuilderAPI_VertexInspector.hxx +// Created: Nov 24 16:48:12 2011 +// Author: ANNA MASALSKAYA +// Copyright: Open CASCADE SAS 2011 + +#ifndef _BRepBuilderAPI_VertexInspector_Header +#define _BRepBuilderAPI_VertexInspector_Header + +#ifndef _TColStd_ListOfInteger_HeaderFile +#include +#endif +#ifndef NCollection_Vector_HeaderFile +#include +#endif +#ifndef _gp_XY_HeaderFile +#include +#endif +#ifndef _gp_XYZ_HeaderFile +#include +#endif + +#ifndef NCollection_CellFilter_HeaderFile +#include +#endif + +typedef NCollection_Vector VectorOfPoint; + +//======================================================================= +//! Class BRepBuilderAPI_VertexInspector +//! derived from NCollection_CellFilter_InspectorXYZ +//! This class define the Inspector interface for CellFilter algorithm, +//! working with gp_XYZ points in 3d space. +//! Used in search of coincidence points with a certain tolerance. +//======================================================================= + +class BRepBuilderAPI_VertexInspector : public NCollection_CellFilter_InspectorXYZ +{ +public: + typedef Standard_Integer Target; + //! Constructor; remembers the tolerance + BRepBuilderAPI_VertexInspector (const Standard_Real theTol) + : myTol(theTol*theTol) + {} + + //! Keep the points used for comparison + void Add (const gp_XYZ& thePnt) + { + myPoints.Append (thePnt); + } + + //! Clear the list of adjacent points + void ClearResList() + { + myResInd.Clear(); + } + + //! Set current point to search for coincidence + void SetCurrent (const gp_XYZ& theCurPnt) + { + myCurrent = theCurPnt; + } + + //! Get list of indexes of points adjacent with the current + const TColStd_ListOfInteger& ResInd() + { + return myResInd; + } + + //! Implementation of inspection method + NCollection_CellFilter_Action Inspect (const Standard_Integer theTarget); + +private: + Standard_Real myTol; + TColStd_ListOfInteger myResInd; + VectorOfPoint myPoints; + gp_XYZ myCurrent; +}; + +#endif diff --git a/src/BRepBuilderAPI/FILES b/src/BRepBuilderAPI/FILES new file mode 100644 index 0000000000..73da8c6755 --- /dev/null +++ b/src/BRepBuilderAPI/FILES @@ -0,0 +1,4 @@ +BRepBuilderAPI_VertexInspector.hxx +BRepBuilderAPI_CellFilter.hxx +BRepBuilderAPI_BndBoxTreeSelector.hxx +