// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
+#include <RWStepShape_RWEdgeCurve.hxx>
#include <Interface_EntityIterator.hxx>
#include <Interface_ShareTool.hxx>
#include <Precision.hxx>
-#include <RWStepShape_RWEdgeCurve.hxx>
#include <StepData_StepReaderData.hxx>
#include <StepData_StepWriter.hxx>
#include <StepGeom_CartesianPoint.hxx>
#include <StepShape_Vertex.hxx>
#include <StepShape_VertexPoint.hxx>
-RWStepShape_RWEdgeCurve::RWStepShape_RWEdgeCurve () {}
-
-void RWStepShape_RWEdgeCurve::ReadStep
- (const Handle(StepData_StepReaderData)& data,
- const Standard_Integer num,
- Handle(Interface_Check)& ach,
- const Handle(StepShape_EdgeCurve)& ent) const
+namespace
{
+ // ================================================================
+ // Function : GetSharing
+ // Purpose : Returns a step entity of a type StepShapeType that is
+ // sharing theStepEntity. If no sharing entity of
+ // required type is found, returns nullptr.
+ // ================================================================
+ template<typename StepShapeType>
+ Handle (StepShapeType) GetSharing (const Handle (Standard_Transient)& theStepEntity,
+ const Interface_ShareTool& theShareTool)
+ {
+ Interface_EntityIterator aSharedEntitiesIt = theShareTool.Sharings (theStepEntity);
+ aSharedEntitiesIt.SelectType (STANDARD_TYPE (StepShapeType), Standard_True);
+ return aSharedEntitiesIt.NbEntities() == 0
+ ? Handle (StepShapeType){}
+ : Handle (StepShapeType)::DownCast (aSharedEntitiesIt.Value());
+ }
+ // ================================================================
+ // Function : GetFaceBoundOrientation
+ // Purpose : Returns an orientation of face bound sharing
+ // theOrientedEdge. If face bound cannot be found,
+ // returns true (to preserve pre-refactoring behavior).
+ // ================================================================
+ Standard_Boolean GetFaceBoundOrientation (const Handle (StepShape_OrientedEdge)& theOrientedEdge,
+ const Interface_ShareTool& theShareTool)
+ {
+ if (!theShareTool.IsShared (theOrientedEdge))
+ {
+ return Standard_True;
+ }
- // --- Number of Parameter Control ---
-
- if (!data->CheckNbParams(num,5,ach,"edge_curve")) return;
-
- // --- inherited field : name ---
-
- Handle(TCollection_HAsciiString) aName;
- data->ReadString (num,1,"name",ach,aName);
-
- // --- inherited field : edgeStart ---
-
- Handle(StepShape_Vertex) aEdgeStart;
- data->ReadEntity(num, 2,"edge_start", ach, STANDARD_TYPE(StepShape_Vertex), aEdgeStart);
-
- // --- inherited field : edgeEnd ---
-
- Handle(StepShape_Vertex) aEdgeEnd;
- data->ReadEntity(num, 3,"edge_end", ach, STANDARD_TYPE(StepShape_Vertex), aEdgeEnd);
-
- // --- own field : edgeGeometry ---
-
- Handle(StepGeom_Curve) aEdgeGeometry;
- data->ReadEntity(num, 4,"edge_geometry", ach, STANDARD_TYPE(StepGeom_Curve), aEdgeGeometry);
-
- // --- own field : sameSense ---
+ const Handle (StepShape_EdgeLoop) anEdgeLoop = GetSharing<StepShape_EdgeLoop> (theOrientedEdge,
+ theShareTool);
+ if (!theShareTool.IsShared (anEdgeLoop))
+ {
+ return Standard_True;
+ }
- Standard_Boolean aSameSense;
- data->ReadBoolean (num,5,"same_sense",ach,aSameSense);
+ const Handle (StepShape_FaceBound) aFaceBound = GetSharing<StepShape_FaceBound> (anEdgeLoop,
+ theShareTool);
+ return aFaceBound.IsNull() ? Standard_True : aFaceBound->Orientation();
+ }
- //--- Initialisation of the read entity ---
+ // ================================================================
+ // Function : GetFaceBoundOrientation
+ // Purpose : Returns true if start and end points of theEdgeCurve
+ // are valid points of the different vertices and are
+ // equal to each other within Precision::Confusion().
+ // ================================================================
+ Standard_Boolean AreEndsMatch (const Handle (StepShape_EdgeCurve)& theEdgeCurve)
+ {
+ Handle (StepShape_VertexPoint) aStartVertex = Handle (StepShape_VertexPoint)::DownCast (
+ theEdgeCurve->EdgeStart());
+ Handle (StepShape_VertexPoint) anEndVertex = Handle (StepShape_VertexPoint)::DownCast (
+ theEdgeCurve->EdgeEnd());
+ if (aStartVertex == anEndVertex)
+ {
+ return Standard_False;
+ }
+ Handle (StepGeom_CartesianPoint) aStartPoint = Handle (StepGeom_CartesianPoint)::DownCast (
+ aStartVertex->VertexGeometry());
+ Handle (StepGeom_CartesianPoint) anEndPoint = Handle (StepGeom_CartesianPoint)::DownCast (
+ anEndVertex->VertexGeometry());
+ if (aStartPoint.IsNull() || anEndPoint.IsNull())
+ {
+ return Standard_False;
+ }
- ent->Init(aName, aEdgeStart, aEdgeEnd, aEdgeGeometry, aSameSense);
+ const Standard_Real aDistance = Sqrt (
+ (aStartPoint->CoordinatesValue (1) - anEndPoint->CoordinatesValue (1))
+ * (aStartPoint->CoordinatesValue (1) - anEndPoint->CoordinatesValue (1))
+ + (aStartPoint->CoordinatesValue (2) - anEndPoint->CoordinatesValue (2))
+ * (aStartPoint->CoordinatesValue (2) - anEndPoint->CoordinatesValue (2))
+ + (aStartPoint->CoordinatesValue (3) - anEndPoint->CoordinatesValue (3))
+ * (aStartPoint->CoordinatesValue (3) - anEndPoint->CoordinatesValue (3)));
+ return aDistance < Precision::Confusion();
+ }
}
-
-void RWStepShape_RWEdgeCurve::WriteStep
- (StepData_StepWriter& SW,
- const Handle(StepShape_EdgeCurve)& ent) const
+// ================================================================
+// Function : ReadStep
+// Purpose :
+// ================================================================
+void RWStepShape_RWEdgeCurve::ReadStep (const Handle (StepData_StepReaderData)& theStepData,
+ const Standard_Integer theRecordID,
+ Handle (Interface_Check)& theMessageTool,
+ const Handle (StepShape_EdgeCurve)& theEdgeCurve) const
{
+ // --- Number of Parameter Control ---
+ if (!theStepData->CheckNbParams (theRecordID, 5, theMessageTool, "edge_curve"))
+ {
+ return;
+ }
- // --- inherited field name ---
-
- SW.Send(ent->Name());
-
- // --- inherited field edgeStart ---
-
- SW.Send(ent->EdgeStart());
-
- // --- inherited field edgeEnd ---
+ // --- inherited field : name ---
+ Handle (TCollection_HAsciiString) aName;
+ theStepData->ReadString (theRecordID, 1, "name", theMessageTool, aName);
+
+ // --- inherited field : edgeStart ---
+ Handle (StepShape_Vertex) anEdgeStart;
+ theStepData->ReadEntity (theRecordID,
+ 2,
+ "edge_start",
+ theMessageTool,
+ STANDARD_TYPE (StepShape_Vertex),
+ anEdgeStart);
+
+ // --- inherited field : edgeEnd ---
+ Handle (StepShape_Vertex) anEdgeEnd;
+ theStepData->ReadEntity (theRecordID,
+ 3,
+ "edge_end",
+ theMessageTool,
+ STANDARD_TYPE (StepShape_Vertex),
+ anEdgeEnd);
+
+ // --- own field : edgeGeometry ---
+ Handle (StepGeom_Curve) anEdgeGeometry;
+ theStepData->ReadEntity (theRecordID,
+ 4,
+ "edge_geometry",
+ theMessageTool,
+ STANDARD_TYPE (StepGeom_Curve),
+ anEdgeGeometry);
+
+ // --- own field : sameSense ---
+ Standard_Boolean aSameSense;
+ theStepData->ReadBoolean (theRecordID, 5, "same_sense", theMessageTool, aSameSense);
+
+ //--- Initialisation of the read entity ---
+ theEdgeCurve->Init (aName, anEdgeStart, anEdgeEnd, anEdgeGeometry, aSameSense);
+}
- SW.Send(ent->EdgeEnd());
+// ================================================================
+// Function : WriteStep
+// Purpose :
+// ================================================================
+void RWStepShape_RWEdgeCurve::WriteStep (StepData_StepWriter& theStepWriter,
+ const Handle (StepShape_EdgeCurve)& theEdgeCurve) const
+{
+ // --- inherited field name ---
+ theStepWriter.Send (theEdgeCurve->Name());
- // --- own field : edgeGeometry ---
+ // --- inherited field edgeStart ---
+ theStepWriter.Send (theEdgeCurve->EdgeStart());
- SW.Send(ent->EdgeGeometry());
+ // --- inherited field edgeEnd ---
+ theStepWriter.Send (theEdgeCurve->EdgeEnd());
- // --- own field : sameSense ---
+ // --- own field : edgeGeometry ---
+ theStepWriter.Send (theEdgeCurve->EdgeGeometry());
- SW.SendBoolean(ent->SameSense());
+ // --- own field : sameSense ---
+ theStepWriter.SendBoolean (theEdgeCurve->SameSense());
}
-
-void RWStepShape_RWEdgeCurve::Share(const Handle(StepShape_EdgeCurve)& ent, Interface_EntityIterator& iter) const
+// ================================================================
+// Function : Share
+// Purpose :
+// ================================================================
+void RWStepShape_RWEdgeCurve::Share (const Handle (StepShape_EdgeCurve)& theEdgeCurve,
+ Interface_EntityIterator& theSharedEntitiesIt) const
{
+ theSharedEntitiesIt.GetOneItem (theEdgeCurve->EdgeStart());
- iter.GetOneItem(ent->EdgeStart());
-
+ theSharedEntitiesIt.GetOneItem (theEdgeCurve->EdgeEnd());
- iter.GetOneItem(ent->EdgeEnd());
-
-
- iter.GetOneItem(ent->EdgeGeometry());
+ theSharedEntitiesIt.GetOneItem (theEdgeCurve->EdgeGeometry());
}
-
-
-void RWStepShape_RWEdgeCurve::Check
- (const Handle(StepShape_EdgeCurve)& ent,
- const Interface_ShareTool& aShto,
- Handle(Interface_Check)& ach) const
+// ================================================================
+// Function : Check
+// Purpose :
+// ================================================================
+void RWStepShape_RWEdgeCurve::Check (const Handle (StepShape_EdgeCurve)& theEdgeCurve,
+ const Interface_ShareTool& theShareTool,
+ Handle (Interface_Check)& theMessageTool) const
{
-// std::cout << "------ calling CheckEdgeCurve ------" << std::endl;
-
- Handle(StepShape_OrientedEdge) theOE1, theOE2;
- Handle(StepShape_FaceBound) theFOB1, theFOB2;
- //Handle(StepShape_FaceSurface) theFS1, theFS2;
-
- Standard_Boolean theOEOri1 = Standard_True;
- Standard_Boolean theOEOri2 = Standard_True;
- Standard_Boolean theFBOri1 = Standard_True;
- Standard_Boolean theFBOri2 = Standard_True;
- //Standard_Boolean theFSOri1 = Standard_True;
- //Standard_Boolean theFSOri2 = Standard_True;
- Standard_Boolean Cumulated1, Cumulated2;
-
// 1- First Vertex != LastVertex but First VertexPoint == Last VertexPoint
- // Remark : time consuming process but useful !
- // If this append, we can drop one of the two vertices and replace it
- // everywhere it is referenced. Side effect : tolerance problem !!!
-
- Handle(StepShape_VertexPoint) StartVertex =
- Handle(StepShape_VertexPoint)::DownCast(ent->EdgeStart());
- Handle(StepShape_VertexPoint) EndVertex =
- Handle(StepShape_VertexPoint)::DownCast(ent->EdgeEnd());
-
- if (StartVertex != EndVertex) {
-
- Handle(StepGeom_CartesianPoint) StartPoint =
- Handle(StepGeom_CartesianPoint)::DownCast(StartVertex->VertexGeometry());
- Handle(StepGeom_CartesianPoint) EndPoint =
- Handle(StepGeom_CartesianPoint)::DownCast(EndVertex->VertexGeometry());
-
- // it can also be a degenerated pcurve
+ // Remark: time consuming process but useful.
+ // If this append, we can drop one of the two vertices and replace it
+ // everywhere it is referenced. Side effect: tolerance problem.
+ if (AreEndsMatch (theEdgeCurve))
+ {
+ theMessageTool->AddWarning (
+ "Two instances of Vertex have equal (within uncertainty) coordinates");
+ }
- if (!StartPoint.IsNull() && !EndPoint.IsNull()) {
- Standard_Real Dist = Sqrt
- ((StartPoint->CoordinatesValue(1) - EndPoint->CoordinatesValue(1)) *
- (StartPoint->CoordinatesValue(1) - EndPoint->CoordinatesValue(1)) +
- (StartPoint->CoordinatesValue(2) - EndPoint->CoordinatesValue(2)) *
- (StartPoint->CoordinatesValue(2) - EndPoint->CoordinatesValue(2)) +
- (StartPoint->CoordinatesValue(3) - EndPoint->CoordinatesValue(3)) *
- (StartPoint->CoordinatesValue(3) - EndPoint->CoordinatesValue(3)));
- if (Dist < Precision::Confusion() ) {
- ach->AddWarning("Two instances of Vertex have equal (within uncertainty) coordinates");
- }
- }
+ if (!theShareTool.IsShared (theEdgeCurve))
+ {
+ theMessageTool->AddFail ("ERROR: EdgeCurve not referenced");
+ return;
}
-
- // 2- Two-Manifold Topology
- Standard_Boolean sharEC = aShto.IsShared(ent);
- Standard_Integer nbRef;
- if(!sharEC){
- ach->AddFail("ERROR: EdgeCurve not referenced");
+ // 2- Two-Manifold Topology
+ Interface_EntityIterator aSharedEntitiesIt = theShareTool.Sharings (theEdgeCurve);
+ aSharedEntitiesIt.SelectType (STANDARD_TYPE (StepShape_OrientedEdge), Standard_True);
+ if (aSharedEntitiesIt.NbEntities() != 2)
+ {
+ return;
}
- else {
- Interface_EntityIterator myShRef = aShto.Sharings(ent);
- myShRef.SelectType (STANDARD_TYPE(StepShape_OrientedEdge),Standard_True);
- nbRef = myShRef.NbEntities();
- if (nbRef ==2) {
- theOE1 = Handle(StepShape_OrientedEdge)::DownCast(myShRef.Value());
- theOEOri1 = theOE1->Orientation();
- myShRef.Next();
- theOE2 = Handle(StepShape_OrientedEdge)::DownCast(myShRef.Value());
- theOEOri2 = theOE2->Orientation();
-
- // get the FaceBound orientation for theOE1
-
- Standard_Boolean sharOE1 = aShto.IsShared(theOE1);
- if(!sharOE1){
-#ifdef OCCT_DEBUG
- std::cout << "OrientedEdge1 not shared" <<std::endl;
-#endif
- }
- else {
- myShRef = aShto.Sharings(theOE1);
- myShRef.SelectType (STANDARD_TYPE(StepShape_EdgeLoop),Standard_True);
- nbRef = myShRef.NbEntities();
- if (nbRef == 1) {
- myShRef.Start();
- Handle(StepShape_EdgeLoop) theEL1 =
- Handle(StepShape_EdgeLoop)::DownCast(myShRef.Value());
- Standard_Boolean sharEL1 = aShto.IsShared(theEL1);
- if(!sharEL1) {
-#ifdef OCCT_DEBUG
- std::cout << "EdgeLoop1 not shared" <<std::endl;
-#endif
- }
- else {
- myShRef = aShto.Sharings(theEL1);
- myShRef.SelectType (STANDARD_TYPE(StepShape_FaceBound),Standard_True);
-#ifdef OCCT_DEBUG
- nbRef =
-#endif
- myShRef.NbEntities();
- myShRef.Start();
- theFOB1 = Handle(StepShape_FaceBound)::DownCast(myShRef.Value());
- if (!theFOB1.IsNull()) {
- theFBOri1 = theFOB1->Orientation();
- }
- else {
-#ifdef OCCT_DEBUG
- std::cout << "EdgeLoop not referenced by FaceBound" << std::endl;
-#endif
- }
- }
- }
- else {
- if (nbRef == 0) {
-#ifdef OCCT_DEBUG
- std::cout << "OrientedEdge not referenced" << std::endl;
-#endif
- }
- else {
- if (aShto.NbTypedSharings(theOE1,
- STANDARD_TYPE(StepShape_EdgeLoop)) > 1) {
-#ifdef OCCT_DEBUG
- std::cout << "OrientedEdge referenced more than once" << std::endl;
-#endif
- }
- }
- }
- }
- // get the FaceBound orientation for theOE2
+ const Handle (StepShape_OrientedEdge) anOrientedEdge1 =
+ Handle (StepShape_OrientedEdge)::DownCast (aSharedEntitiesIt.Value());
+ const Standard_Boolean aFaceBoundOrientation1 = GetFaceBoundOrientation (anOrientedEdge1,
+ theShareTool);
+ const Standard_Boolean anIsCumulated1 = aFaceBoundOrientation1 != anOrientedEdge1->Orientation();
- Standard_Boolean sharOE2 = aShto.IsShared(theOE2);
- if(!sharOE2){
-#ifdef OCCT_DEBUG
- std::cout << "OrientedEdge2 not shared" <<std::endl;
-#endif
- }
- else {
- myShRef = aShto.Sharings(theOE2);
-#ifdef OCCT_DEBUG
-// Standard_Integer nbRef =
-#endif
-// unused myShRef.NbEntities();
- myShRef.Start();
- Handle(StepShape_EdgeLoop) theEL2 =
- Handle(StepShape_EdgeLoop)::DownCast(myShRef.Value());
- Standard_Boolean sharEL2 = aShto.IsShared(theEL2);
- if(!sharEL2){
-#ifdef OCCT_DEBUG
- std::cout << "EdgeLoop2 not shared" <<std::endl;
-#endif
- }
- else {
- myShRef = aShto.Sharings(theEL2);
- // unused Standard_Integer nbRef = myShRef.NbEntities();
- myShRef.Start();
- theFOB2 = Handle(StepShape_FaceBound)::DownCast(myShRef.Value());
- if (!theFOB2.IsNull()) {
- theFBOri2 = theFOB2->Orientation();
- }
- else {
-#ifdef OCCT_DEBUG
- std::cout << "EdgeLoop not referenced by FaceBound" << std::endl;
-#endif
- }
- }
- }
-
- // "cumulate" the FaceBound and the OrientedEdge orientation
-
- Cumulated1 = theFBOri1 ^ theOEOri1;
- Cumulated2 = theFBOri2 ^ theOEOri2;
-
- // the orientation of the OrientedEdges must be opposite
-
- if (Cumulated1 == Cumulated2) {
- ach->AddFail("ERROR: non 2-manifold topology");
- }
- }
+ aSharedEntitiesIt.Next();
+
+ const Handle (StepShape_OrientedEdge) anOrientedEdge2 =
+ Handle (StepShape_OrientedEdge)::DownCast (aSharedEntitiesIt.Value());
+ const Standard_Boolean aFaceBoundOrientation2 = GetFaceBoundOrientation (anOrientedEdge2,
+ theShareTool);
+ const Standard_Boolean anIsCumulated2 = aFaceBoundOrientation2 != anOrientedEdge2->Orientation();
+
+ // the orientation of the OrientedEdges must be opposite
+ if (anIsCumulated1 == anIsCumulated2)
+ {
+ theMessageTool->AddFail ("ERROR: non 2-manifold topology");
}
}
-
#include <Standard.hxx>
#include <Standard_DefineAlloc.hxx>
#include <Standard_Handle.hxx>
-
#include <Standard_Integer.hxx>
+
class StepData_StepReaderData;
class Interface_Check;
class StepShape_EdgeCurve;
class Interface_EntityIterator;
class Interface_ShareTool;
-
//! Read & Write Module for EdgeCurve
//! Check added by CKY , 7-OCT-1996
-class RWStepShape_RWEdgeCurve
+class RWStepShape_RWEdgeCurve
{
public:
-
DEFINE_STANDARD_ALLOC
-
- Standard_EXPORT RWStepShape_RWEdgeCurve();
-
- Standard_EXPORT void ReadStep (const Handle(StepData_StepReaderData)& data, const Standard_Integer num, Handle(Interface_Check)& ach, const Handle(StepShape_EdgeCurve)& ent) const;
-
- Standard_EXPORT void WriteStep (StepData_StepWriter& SW, const Handle(StepShape_EdgeCurve)& ent) const;
-
- Standard_EXPORT void Share (const Handle(StepShape_EdgeCurve)& ent, Interface_EntityIterator& iter) const;
-
- Standard_EXPORT void Check (const Handle(StepShape_EdgeCurve)& ent, const Interface_ShareTool& shares, Handle(Interface_Check)& ach) const;
-
-
-
-
-protected:
-
-
-
-
-
-private:
-
+public:
+ RWStepShape_RWEdgeCurve() = default;
+ Standard_EXPORT void ReadStep (const Handle (StepData_StepReaderData)& theStepData,
+ const Standard_Integer theRecordID,
+ Handle (Interface_Check)& theMessageTool,
+ const Handle (StepShape_EdgeCurve)& theEdgeCurve) const;
+ Standard_EXPORT void WriteStep (StepData_StepWriter& theStepWriter,
+ const Handle (StepShape_EdgeCurve)& theEdgeCurve) const;
+ Standard_EXPORT void Share (const Handle (StepShape_EdgeCurve)& theEdgeCurve,
+ Interface_EntityIterator& theSharedEntitiesIt) const;
+ Standard_EXPORT void Check (const Handle (StepShape_EdgeCurve)& theEdgeCurve,
+ const Interface_ShareTool& theShareTool,
+ Handle (Interface_Check)& theMessageTool) const;
};
-
-
-
-
-
-
#endif // _RWStepShape_RWEdgeCurve_HeaderFile
// ============================================================================
static inline Standard_Boolean isReversed(const Handle(StepGeom_Surface)& theStepSurf)
{
- Handle(StepGeom_ToroidalSurface) aStepTorSur;
if(theStepSurf->IsKind(STANDARD_TYPE(StepGeom_RectangularTrimmedSurface)))
+ {
return isReversed(Handle(StepGeom_RectangularTrimmedSurface)::DownCast(theStepSurf)->BasisSurface());
-
+ }
else
- aStepTorSur = Handle(StepGeom_ToroidalSurface)::DownCast(theStepSurf);
-
- return (!aStepTorSur.IsNull() && aStepTorSur->MajorRadius() < 0 ? Standard_True : Standard_False);
+ {
+ Handle(StepGeom_ToroidalSurface) aStepTorSur =
+ Handle(StepGeom_ToroidalSurface)::DownCast(theStepSurf);
+ return !aStepTorSur.IsNull() && aStepTorSur->MajorRadius() < 0.;
+ }
}
// ============================================================================
// Method : Init
// Purpose : Init with a FaceSurface and a Tool
// ============================================================================
-void StepToTopoDS_TranslateFace::Init(const Handle(StepShape_FaceSurface)& FS,
- StepToTopoDS_Tool& aTool,
- StepToTopoDS_NMTool& NMTool,
- const StepData_Factors& theLocalFactors)
+void StepToTopoDS_TranslateFace::Init (const Handle (StepShape_FaceSurface)& theFaceSurface,
+ StepToTopoDS_Tool& theTopoDSTool,
+ StepToTopoDS_NMTool& theTopoDSToolNM,
+ const StepData_Factors& theLocalFactors)
{
done = Standard_True;
- if (aTool.IsBound(FS)) {
- myResult = TopoDS::Face(aTool.Find(FS));
- myError = StepToTopoDS_TranslateFaceDone;
- done = Standard_True;
+ if (theTopoDSTool.IsBound (theFaceSurface))
+ {
+ myResult = TopoDS::Face (theTopoDSTool.Find (theFaceSurface));
+ myError = StepToTopoDS_TranslateFaceDone;
+ done = Standard_True;
return;
}
-
- Handle(Transfer_TransientProcess) TP = aTool.TransientProcess();
-
+
+ // Within a context of this method this object is used for message handling only.
+ Handle (Transfer_TransientProcess) aMessageHandler = theTopoDSTool.TransientProcess();
+
// ----------------------------------------------
// Map the Face Geometry and create a TopoDS_Face
// ----------------------------------------------
- Handle(StepGeom_Surface) StepSurf = FS->FaceGeometry();
-
- // sln 01.10.2001 BUC61003. If corresponding entity was read with error StepSurface may be NULL. In this case we exit from function
- if ( StepSurf.IsNull() ) {
- TP->AddFail(StepSurf," Surface has not been created");
+ Handle (StepGeom_Surface) aStepGeomSurface = theFaceSurface->FaceGeometry();
+ // sln 01.10.2001 BUC61003. If corresponding entity was read with error StepSurface may be NULL.
+ // In this case we exit from function
+ if (aStepGeomSurface.IsNull())
+ {
+ aMessageHandler->AddFail (aStepGeomSurface, " Surface has not been created");
myError = StepToTopoDS_TranslateFaceOther;
- done = Standard_False;
+ done = Standard_False;
return;
}
// [BEGIN] Added to process non-manifold topology (ssv; 14.11.2010)
- if ( NMTool.IsActive() && NMTool.IsBound(StepSurf) ) {
- TopoDS_Shape existingShape = NMTool.Find(StepSurf);
+ if (theTopoDSToolNM.IsActive() && theTopoDSToolNM.IsBound (aStepGeomSurface))
+ {
+ TopoDS_Shape anExistingShape = theTopoDSToolNM.Find (aStepGeomSurface);
// Reverse shape's orientation for the next shell
- existingShape.Reverse();
- myResult = existingShape;
+ anExistingShape.Reverse();
+ myResult = anExistingShape;
myError = StepToTopoDS_TranslateFaceDone;
- done = Standard_True;
+ done = Standard_True;
return;
}
// [END] Added to process non-manifold topology (ssv; 14.11.2010)
- if (StepSurf->IsKind(STANDARD_TYPE(StepGeom_OffsetSurface))) //:d4 abv 12 Mar 98
- TP->AddWarning(StepSurf," Type OffsetSurface is out of scope of AP 214");
- Handle(Geom_Surface) GeomSurf = StepToGeom::MakeSurface (StepSurf, theLocalFactors);
- if (GeomSurf.IsNull())
+ if (aStepGeomSurface->IsKind (STANDARD_TYPE (StepGeom_OffsetSurface))) //: d4 abv 12 Mar 98
+ {
+ aMessageHandler->AddWarning (aStepGeomSurface, " Type OffsetSurface is out of scope of AP 214");
+ }
+
+ Handle (Geom_Surface) aGeomSurface = StepToGeom::MakeSurface (aStepGeomSurface, theLocalFactors);
+ if (aGeomSurface.IsNull())
{
- TP->AddFail(StepSurf," Surface has not been created");
+ aMessageHandler->AddFail (aStepGeomSurface, " Surface has not been created");
myError = StepToTopoDS_TranslateFaceOther;
- done = Standard_False;
+ done = Standard_False;
return;
}
+
// pdn to force bsplsurf to be periodic
- Handle(StepGeom_BSplineSurface) sgbss = Handle(StepGeom_BSplineSurface)::DownCast(StepSurf);
- if (!sgbss.IsNull()) {
- Handle(Geom_Surface) periodicSurf = ShapeAlgo::AlgoContainer()->ConvertToPeriodic(GeomSurf);
- if (!periodicSurf.IsNull()) {
- TP->AddWarning(StepSurf, "Surface forced to be periodic");
- GeomSurf = periodicSurf;
+ if (!Handle (StepGeom_BSplineSurface)::DownCast (aStepGeomSurface).IsNull())
+ {
+ Handle (Geom_Surface) periodicSurf = ShapeAlgo::AlgoContainer()->ConvertToPeriodic (
+ aGeomSurface);
+ if (!periodicSurf.IsNull())
+ {
+ aMessageHandler->AddWarning (aStepGeomSurface, "Surface forced to be periodic");
+ aGeomSurface = periodicSurf;
}
}
-
- Standard_Boolean sameSenseFace = FS->SameSense();
- //fix for bug 0026376 Solid Works wrote face based on toroidal surface having negative major radius
- //seems that such case is interpreted by "Solid Works" and "ProE" as face having reversed orientation.
- Standard_Boolean sameSense = (isReversed(StepSurf) ? !sameSenseFace : sameSenseFace);
-
+ // fix for bug 0026376 Solid Works wrote face based on toroidal surface having negative major radius
+ // seems that such case is interpreted by "Solid Works" and "ProE" as face having reversed orientation.
+ const Standard_Boolean aSameSense = isReversed (aStepGeomSurface) ? !theFaceSurface->SameSense()
+ : theFaceSurface->SameSense();
+
// -- Statistics --
- aTool.AddContinuity (GeomSurf);
-
- TopoDS_Face F;
- BRep_Builder B;
- B.MakeFace ( F, GeomSurf, Precision::Confusion() );
-
+ theTopoDSTool.AddContinuity (aGeomSurface);
+
+ TopoDS_Face aResultFace;
+ BRep_Builder aFaceBuilder;
+ aFaceBuilder.MakeFace (aResultFace, aGeomSurface, Precision::Confusion());
+
// ----------------------------------
// Iterate on each FaceBounds (Wires)
// ----------------------------------
- Handle(StepShape_FaceBound) FaceBound;
- Handle(StepShape_Loop) Loop;
-
- StepToTopoDS_TranslateVertexLoop myTranVL;
- StepToTopoDS_TranslatePolyLoop myTranPL;
- StepToTopoDS_TranslateEdgeLoop myTranEdgeLoop;
-
- Standard_Integer NbBnd = FS->NbBounds();
-
- // -- Critere de couture simple (CKY, JAN97)
- // surface periodique (typiquement un cylindre)
- // 2 face bounds, chacun avec un edge loop d une seule edge
- // cette edge est fermee, c-a-d vtx-deb = vtx-fin (pour les deux edges)
- // est-ce suffisant (verifier que ce sont deux outer-bounds ... ?? comment ?)
- // Alors on peut dire : face a deux bords dont la couture manque
- // La couture est entre les deux vertex
-
- for (Standard_Integer i = 1; i <= NbBnd; i ++) {
-
-#ifdef OCCT_DEBUG
- std::cout << " Processing Wire : " << i << std::endl;
-#endif
- FaceBound = FS->BoundsValue(i);
- Loop = FaceBound->Bound();
- if (Loop.IsNull())
+ // - Simple sewing criterion (CKY, Jan97)
+ // Periodic surface (typically a cylinder)
+ // 2 face bounds, each with an edge loop from a single edge.
+ // This edge is closed, c-a-d vertex-begin = vertex-end (for the two edges)
+ // Is it sufficient (check that these are two outer-bounds... ?? How?)
+ // Then we can say: face with two edges whose seam is missing
+ // The seam is between the two vertex
+ for (Standard_Integer aBoundIndex = 1; aBoundIndex <= theFaceSurface->NbBounds(); ++aBoundIndex)
+ {
+ Handle (StepShape_FaceBound) aFaceBound = theFaceSurface->BoundsValue (aBoundIndex);
+ if (aFaceBound.IsNull())
{
continue;
}
+ Handle (StepShape_Loop) aFaceLoop = aFaceBound->Bound();
+ if (aFaceLoop.IsNull())
+ {
+ continue;
+ }
+
// ------------------------
// The Loop is a VertexLoop
// ------------------------
-
- if (Loop->IsKind(STANDARD_TYPE(StepShape_VertexLoop))) {
-//:S4136 STF.Closed() = Standard_False;
-// PROBLEME si SPHERE ou TORE
-// Il faudra faire un wire complet, a condition que le point porte sur la face
-// En attendant, on ne fait rien
- Handle(StepShape_VertexLoop) VL = Handle(StepShape_VertexLoop)::DownCast(Loop);
+ if (aFaceLoop->IsKind (STANDARD_TYPE (StepShape_VertexLoop)))
+ {
+ //: S4136 STF.Closed() = Standard_False;
+ // PROBLEM if SPHERE or TORE
+ // It will be necessary to make a complete wire, provided that the point carries on the face
+ // In the meantime, we do nothing
// abv 10.07.00 pr1sy.stp: vertex_loop can be wrong; so just make natural bounds
- if (GeomSurf->IsKind (STANDARD_TYPE(Geom_SphericalSurface)) ||
- GeomSurf->IsKind (STANDARD_TYPE(Geom_BSplineSurface)) ||
- GeomSurf->IsKind (STANDARD_TYPE(Geom_SurfaceOfRevolution)))
+ if ((aGeomSurface->IsKind (STANDARD_TYPE (Geom_SphericalSurface))
+ || aGeomSurface->IsKind (STANDARD_TYPE (Geom_BSplineSurface))
+ || aGeomSurface->IsKind (STANDARD_TYPE (Geom_SurfaceOfRevolution)))
+ && (theFaceSurface->NbBounds() == 1))
{
-
- // Modification to create natural bounds for face based on the spherical and Bspline surface and having only one bound represented by Vertex loop was made.
- // According to the specification of ISO - 10303 part 42:
- // "If the face has only one bound and this is of type vertex_loop, then the interior of the face is the domain of the face_surface.face_geometry.
- // In such a case the underlying surface shall be closed (e.g. a spherical_surface.)"
- // - natural bounds are applied only in case if VertexLoop is only the one defined face bound.
- if (NbBnd == 1)
+ // Modification to create natural bounds for face based on the spherical and Bspline
+ // surface and having only one bound represented by Vertex loop was made.
+ // According to the specification of ISO - 10303 part 42:
+ // "If the face has only one bound and this is of type vertex_loop, then the interior of
+ // the face is the domain of the face_surface.face_geometry. In such a case the underlying
+ // surface shall be closed (e.g. a spherical_surface.)"
+ // - natural bounds are applied only in case if VertexLoop is only the one defined face bound.
+ BRepBuilderAPI_MakeFace anAuxiliaryFaceBuilder (aGeomSurface, Precision());
+ for (TopoDS_Iterator aFaceIt (anAuxiliaryFaceBuilder); aFaceIt.More(); aFaceIt.Next())
{
- BRepBuilderAPI_MakeFace mf(GeomSurf, Precision());
- for (TopoDS_Iterator it(mf); it.More(); it.Next())
- {
- B.Add(F, it.Value());
- }
- continue;
+ aFaceBuilder.Add (aResultFace, aFaceIt.Value());
}
+ continue;
}
- if (GeomSurf->IsKind(STANDARD_TYPE(Geom_ToroidalSurface))) {
- continue;
- }
- if (GeomSurf->IsKind(STANDARD_TYPE(Geom_Plane))) {
- TP->AddWarning(VL, "VertexLoop on plane is ignored");
- continue; //smh : BUC60809
- }
- myTranVL.SetPrecision(Precision());//gka
- myTranVL.SetMaxTol(MaxTol());
- myTranVL.Init(VL, aTool, NMTool, theLocalFactors);
- if (myTranVL.IsDone()) {
- B.Add(F, myTranVL.Value());
- }
- else {
- TP->AddWarning(VL, " a VertexLoop not mapped to TopoDS");
+ if (aGeomSurface->IsKind (STANDARD_TYPE (Geom_ToroidalSurface)))
+ {
+ continue;
+ }
+
+ Handle (StepShape_VertexLoop) aVertexLoop = Handle (StepShape_VertexLoop)::DownCast (
+ aFaceLoop);
+ if (aGeomSurface->IsKind (STANDARD_TYPE (Geom_Plane)))
+ {
+ aMessageHandler->AddWarning (aVertexLoop, "VertexLoop on plane is ignored");
+ continue; // smh : BUC60809
+ }
+
+ StepToTopoDS_TranslateVertexLoop aVertexLoopTranslator;
+ aVertexLoopTranslator.SetPrecision (Precision()); // gka
+ aVertexLoopTranslator.SetMaxTol (MaxTol());
+ aVertexLoopTranslator.Init (aVertexLoop, theTopoDSTool, theTopoDSToolNM, theLocalFactors);
+ if (aVertexLoopTranslator.IsDone())
+ {
+ aFaceBuilder.Add (aResultFace, aVertexLoopTranslator.Value());
+ }
+ else
+ {
+ aMessageHandler->AddWarning (aVertexLoop, " a VertexLoop not mapped to TopoDS");
+ }
}
- }
-
- // ----------------------
- // The Loop is a PolyLoop
- // ----------------------
- else if (Loop->IsKind(STANDARD_TYPE(StepShape_PolyLoop))) {
-//:S4136 STF.Closed() = Standard_False;
- Handle(StepShape_PolyLoop) PL = Handle(StepShape_PolyLoop)::DownCast(Loop);
- F.Orientation ( FS->SameSense() ? TopAbs_FORWARD : TopAbs_REVERSED);
- myTranPL.SetPrecision(Precision()); //gka
- myTranPL.SetMaxTol(MaxTol());
- myTranPL.Init(PL, aTool, GeomSurf, F, theLocalFactors);
- if (myTranPL.IsDone()) {
- TopoDS_Wire W = TopoDS::Wire(myTranPL.Value());
- W.Orientation(FaceBound->Orientation() ? TopAbs_FORWARD : TopAbs_REVERSED);
- B.Add(F, W);
+ // ----------------------
+ // The Loop is a PolyLoop
+ // ----------------------
+ else if (aFaceLoop->IsKind (STANDARD_TYPE (StepShape_PolyLoop)))
+ {
+ Handle (StepShape_PolyLoop) aPolyLoop = Handle (StepShape_PolyLoop)::DownCast (aFaceLoop);
+ aResultFace.Orientation (theFaceSurface->SameSense() ? TopAbs_FORWARD : TopAbs_REVERSED);
+ StepToTopoDS_TranslatePolyLoop aPolyLoopTranslator;
+ aPolyLoopTranslator.SetPrecision (Precision()); // gka
+ aPolyLoopTranslator.SetMaxTol (MaxTol());
+ aPolyLoopTranslator.Init (aPolyLoop,
+ theTopoDSTool,
+ aGeomSurface,
+ aResultFace,
+ theLocalFactors);
+ if (aPolyLoopTranslator.IsDone())
+ {
+ TopoDS_Wire aPolyLoopWire = TopoDS::Wire (aPolyLoopTranslator.Value());
+ aPolyLoopWire.Orientation (aFaceBound->Orientation() ? TopAbs_FORWARD : TopAbs_REVERSED);
+ aFaceBuilder.Add (aResultFace, aPolyLoopWire);
}
- else {
- TP->AddWarning(PL, " a PolyLoop not mapped to TopoDS");
+ else
+ {
+ aMessageHandler->AddWarning (aPolyLoop, " a PolyLoop not mapped to TopoDS");
}
}
-
// -----------------------
// The Loop is an EdgeLoop
// -----------------------
- else if (Loop->IsKind(STANDARD_TYPE(StepShape_EdgeLoop))) {
- //:S4136 if (STF.Closed()) {
- //:S4136 Handle(StepShape_EdgeLoop) EL =
- //:S4136 Handle(StepShape_EdgeLoop)::DownCast(FaceBound->Bound());
- //:S4136 if (EL->NbEdgeList() != 1) STF.Closed() = Standard_False;
- //:S4136 }
-
- TopoDS_Wire W;
- myTranEdgeLoop.SetPrecision(Precision()); //gka
- myTranEdgeLoop.SetMaxTol(MaxTol());
- myTranEdgeLoop.Init(FaceBound, F, GeomSurf, StepSurf, sameSense, aTool, NMTool, theLocalFactors);
-
- if (myTranEdgeLoop.IsDone()) {
- W = TopoDS::Wire(myTranEdgeLoop.Value());
-
- // STEP Face_Surface orientation :
- // if the topological orientation is opposite to the geometric
- // orientation of the surface => the underlying topological
- // orientation are not implicitly reversed
- // this is the case in CAS.CADE => If the face_surface is reversed,
- // the wire orientation has to be explicitly reversed
- if (FaceBound->Orientation()) {
- // *DTH* if (sameSense || GeomSurf->IsKind(STANDARD_TYPE(Geom_Plane)))
- W.Orientation(sameSense ? TopAbs_FORWARD : TopAbs_REVERSED);
- }
- else {
- // *DTH* if (sameSense || GeomSurf->IsKind(STANDARD_TYPE(Geom_Plane)))
- W.Orientation(sameSense ? TopAbs_REVERSED : TopAbs_FORWARD);
+ else if (aFaceLoop->IsKind (STANDARD_TYPE (StepShape_EdgeLoop)))
+ {
+ StepToTopoDS_TranslateEdgeLoop anEdgeLoopTranslator;
+ anEdgeLoopTranslator.SetPrecision (Precision()); // gka
+ anEdgeLoopTranslator.SetMaxTol (MaxTol());
+ anEdgeLoopTranslator.Init (aFaceBound,
+ aResultFace,
+ aGeomSurface,
+ aStepGeomSurface,
+ aSameSense,
+ theTopoDSTool,
+ theTopoDSToolNM,
+ theLocalFactors);
+
+ if (anEdgeLoopTranslator.IsDone())
+ {
+ TopoDS_Wire anEdgeLoopWire = TopoDS::Wire (anEdgeLoopTranslator.Value());
+
+ // STEP Face_Surface orientation :
+ // if the topological orientation is opposite to the geometric
+ // orientation of the surface => the underlying topological
+ // orientation are not implicitly reversed
+ // this is the case in CAS.CADE => If the face_surface is reversed,
+ // the wire orientation has to be explicitly reversed
+ if (aFaceBound->Orientation())
+ {
+ anEdgeLoopWire.Orientation (aSameSense ? TopAbs_FORWARD : TopAbs_REVERSED);
+ }
+ else
+ {
+ anEdgeLoopWire.Orientation (aSameSense ? TopAbs_REVERSED : TopAbs_FORWARD);
+ }
+ // -----------------------------
+ // The Wire is added to the Face
+ // -----------------------------
+ aFaceBuilder.Add (aResultFace, anEdgeLoopWire);
}
- // -----------------------------
- // The Wire is added to the Face
- // -----------------------------
- B.Add(F, W);
- }
- else {
- // Il y a eu un probleme dans le mapping : On perd la Face
- // (facon de parler ...) Pas de moyen aujourd hui de recuperer
- // au moins toutes les geometries (Points, Courbes 3D, Surface)
- TP->AddFail(Loop, " EdgeLoop not mapped to TopoDS");
-
- // CKY JAN-97 : un Wire manque, eh bien on continue quand meme !!
- // sauf si OuterBound : la c est quand meme pas bien normal ...
- if (FaceBound->IsKind(STANDARD_TYPE(StepShape_FaceOuterBound))) {
- TP->AddWarning(FS, "No Outer Bound : Face not done");
+ else
+ {
+ // There was a problem in the mapping: We lost Face (so to speak...).
+ // No way today to recover at least all the geometries (Points, 3D Curves, Surface).
+ aMessageHandler->AddFail (aFaceLoop, " EdgeLoop not mapped to TopoDS");
+
+ // CKY JAN-97: a Wire is missing, well we continue anyway
+ // unless OuterBound: that's still not quite normal...
+ if (aFaceBound->IsKind (STANDARD_TYPE (StepShape_FaceOuterBound)))
+ {
+ aMessageHandler->AddWarning (theFaceSurface, "No Outer Bound : Face not done");
+ }
+ continue;
}
- continue;
}
- }
- else {
+ else
+ {
// Type not yet implemented or non sens
- TP->AddFail(Loop," Type of loop not yet implemented");
-#ifdef OCCT_DEBUG
- std::cout << Loop->DynamicType() << std::endl;
-#endif
+ aMessageHandler->AddFail (aFaceLoop, " Type of loop not yet implemented");
continue;
}
}
- F.Orientation ( FS->SameSense() ? TopAbs_FORWARD : TopAbs_REVERSED);
- aTool.Bind(FS,F);
+ aResultFace.Orientation (theFaceSurface->SameSense() ? TopAbs_FORWARD : TopAbs_REVERSED);
+ theTopoDSTool.Bind (theFaceSurface, aResultFace);
// Register face in NM tool (ssv; 14.11.2010)
- if ( NMTool.IsActive() )
- NMTool.Bind(StepSurf, F);
+ if (theTopoDSToolNM.IsActive())
+ {
+ theTopoDSToolNM.Bind (aStepGeomSurface, aResultFace);
+ }
- myResult = F;
+ myResult = aResultFace;
myError = StepToTopoDS_TranslateFaceDone;
done = Standard_True;
}
StepToTopoDS_NMTool& theNMTool,
const StepData_Factors& theLocalFactors = StepData_Factors());
- Standard_EXPORT void Init (const Handle(StepShape_FaceSurface)& FS,
- StepToTopoDS_Tool& T,
- StepToTopoDS_NMTool& NMTool,
+ Standard_EXPORT void Init (const Handle(StepShape_FaceSurface)& theFaceSurface,
+ StepToTopoDS_Tool& theTopoDSTool,
+ StepToTopoDS_NMTool& theTopoDSToolNM,
const StepData_Factors& theLocalFactors = StepData_Factors());
Standard_EXPORT void Init (const Handle(StepVisual_TessellatedFace)& theTF,
--- /dev/null
+puts "# ====================================================================="
+puts "# 0033665: Data Exchange, Step Import - TransferRoots crashes for"
+puts "# invalid STEP files."
+puts "# ====================================================================="
+
+# Step entity #18 is intentionally removed from test file,
+# but it is still referenced by other step entities.
+# Parsing and root transfer should not cause crash for such invalid file.
+
+set aFilePath [locate_data_file bug33665.step]
+testreadstep "$aFilePath" aShape
+checkshape aShape