0028599: Replacement of old Boolean operations with new ones in BRepProj_Projection...
[occt.git] / src / BRepProj / BRepProj_Projection.cxx
old mode 100755 (executable)
new mode 100644 (file)
index eec6ad2..b08f085
@@ -1,60 +1,54 @@
 // Copyright (c) 1998-1999 Matra Datavision
-// Copyright (c) 1999-2012 OPEN CASCADE SAS
+// Copyright (c) 1999-2014 OPEN CASCADE SAS
 //
-// The content of this file is subject to the Open CASCADE Technology Public
-// License Version 6.5 (the "License"). You may not use the content of this file
-// except in compliance with the License. Please obtain a copy of the License
-// at http://www.opencascade.org and read it completely before using this file.
+// This file is part of Open CASCADE Technology software library.
 //
-// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
-// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
+// 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.
 //
-// The Original Code and all software distributed under the License is
-// distributed on an "AS IS" basis, without warranty of any kind, and the
-// Initial Developer hereby disclaims all such warranties, including without
-// limitation, any warranties of merchantability, fitness for a particular
-// purpose or non-infringement. Please see the License for the specific terms
-// and conditions governing the rights and limitations under the License.
+// Alternatively, this file may be used under the terms of Open CASCADE
+// commercial license or contractual agreement.
 
-#include <BRepProj_Projection.ixx>
 
-#include <BRepAlgo_Section.hxx>
-
-#include <Precision.hxx>
+#include <Bnd_Box.hxx>
+#include <BRep_Builder.hxx>
+#include <BRep_Tool.hxx>
+#include <BRepAlgoAPI_Section.hxx>
 #include <BRepBndLib.hxx>
-#include <BRepTools_TrsfModification.hxx>
-#include <BRepTools_Modifier.hxx>
+#include <BRepFill_Generator.hxx>
 #include <BRepLib_MakeEdge.hxx>
+#include <BRepLib_MakeVertex.hxx>
 #include <BRepLib_MakeWire.hxx>
-#include <BRep_Tool.hxx>
-#include <Bnd_Box.hxx>
-
+#include <BRepProj_Projection.hxx>
 #include <BRepSweep_Prism.hxx>
-#include <BRepFill_Generator.hxx>
-#include <TopExp.hxx>
-#include <TopExp_Explorer.hxx>
-#include <TopLoc_Location.hxx>
+#include <BRepTools_Modifier.hxx>
+#include <BRepTools_TrsfModification.hxx>
 #include <gp_Dir.hxx>
 #include <gp_Pnt.hxx>
-#include <gp_Vec.hxx>
 #include <gp_Trsf.hxx>
+#include <gp_Vec.hxx>
+#include <Precision.hxx>
+#include <ShapeAnalysis_FreeBounds.hxx>
+#include <Standard_ConstructionError.hxx>
+#include <Standard_NoSuchObject.hxx>
+#include <Standard_NullObject.hxx>
+#include <TopExp.hxx>
+#include <TopExp_Explorer.hxx>
+#include <TopLoc_Location.hxx>
 #include <TopoDS.hxx>
 #include <TopoDS_Iterator.hxx>
 #include <TopoDS_Shape.hxx>
-#include <TopTools_ListOfShape.hxx>
 #include <TopTools_ListIteratorOfListOfShape.hxx>
-#include <BRep_Builder.hxx>
-#include <ShapeAnalysis_FreeBounds.hxx>
-
-#include <Standard_NullObject.hxx>
-#include <Standard_ConstructionError.hxx>
+#include <TopTools_ListOfShape.hxx>
 
 //=======================================================================
 //function : DistanceOut
 //purpose  : Compute the minimum distance between input shapes 
 //           (using Bounding Boxes of each Shape)
 //=======================================================================
-
 static Standard_Real DistanceOut (const TopoDS_Shape& S1, const TopoDS_Shape& S2) 
 {
   Bnd_Box BBox1, BBox2;
@@ -129,17 +123,19 @@ void BRepProj_Projection::BuildSection (const TopoDS_Shape& theShape,
     aShape = C;
   }
   if ( aShape.IsNull() )
-    Standard_ConstructionError::Raise(__FILE__": target shape has no faces");
-
-  // build section computing pcurves on the shape
-//  BRepAlgoAPI_Section aSectionTool (aShape, theTool, Standard_False);
-  BRepAlgo_Section aSectionTool (aShape, theTool, Standard_False);
-  aSectionTool.Approximation (Standard_True);
-  aSectionTool.ComputePCurveOn1 (Standard_True);
+    throw Standard_ConstructionError(__FILE__": target shape has no faces");
+
+  // build section computing p-curves on both shapes to get higher precision
+  BRepAlgoAPI_Section aSectionTool(aShape, theTool, Standard_False);
+  aSectionTool.Approximation(Standard_True);
+  aSectionTool.ComputePCurveOn1(Standard_True);
+  aSectionTool.ComputePCurveOn2(Standard_True);
+  // Use Oriented Bounding Boxes inside Booleans to speed up calculation of the section
+  aSectionTool.SetUseOBB(Standard_True);
   aSectionTool.Build();
 
   // check for successful work of the section tool
-  if (! aSectionTool.IsDone()) 
+  if (!aSectionTool.IsDone())
     return;
 
   // get edges of the result
@@ -184,7 +180,7 @@ BRepProj_Projection::BRepProj_Projection(const TopoDS_Shape& Wire,
   Standard_NullObject_Raise_if((Wire.IsNull() || Shape.IsNull()),__FILE__": null input shape");
   if (Wire.ShapeType() != TopAbs_EDGE && 
       Wire.ShapeType() != TopAbs_WIRE ) 
-    Standard_ConstructionError::Raise(__FILE__": projected shape is neither wire nor edge");
+    throw Standard_ConstructionError(__FILE__": projected shape is neither wire nor edge");
 
   // compute the "length" of the cylindrical surface to build
   Standard_Real mdis = DistanceIn(Wire, Shape);
@@ -220,7 +216,7 @@ BRepProj_Projection::BRepProj_Projection (const TopoDS_Shape& Wire,
   Standard_NullObject_Raise_if((Wire.IsNull() || Shape.IsNull()),__FILE__": null input shape");
   if (Wire.ShapeType() != TopAbs_EDGE && 
       Wire.ShapeType() != TopAbs_WIRE ) 
-    Standard_ConstructionError::Raise(__FILE__": projected shape is neither wire nor edge");
+    throw Standard_ConstructionError(__FILE__": projected shape is neither wire nor edge");
 
   // if Wire is only an edge, transform it into a Wire
   TopoDS_Wire aWire;
@@ -246,27 +242,33 @@ BRepProj_Projection::BRepProj_Projection (const TopoDS_Shape& Wire,
   // compute the ratio of the scale transformation
   Standard_Real Scale = PC.Distance(P);
   if ( Abs (Scale) < Precision::Confusion() ) 
-    Standard_ConstructionError::Raise("Projection");
+    throw Standard_ConstructionError("Projection");
   Scale = 1. + mdis / Scale;
   
   // move the base of the conical surface by scaling it with ratio Scale
-  // then we do a symmetric relative to a point. So we have two generators
-  // for building a "semi-infinite" conic surface
   gp_Trsf T;
   T.SetScale(P, Scale);
   Handle(BRepTools_TrsfModification) Tsca = new BRepTools_TrsfModification(T);
   BRepTools_Modifier ModifScale(aWire,Tsca);
   TopoDS_Shape ShapeGen1 = ModifScale.ModifiedShape(aWire);
 
-  T.SetMirror(P);
-  Handle(BRepTools_TrsfModification) Tmir = new BRepTools_TrsfModification(T);
-  BRepTools_Modifier ModifMirror(ShapeGen1,Tmir);
-  TopoDS_Shape ShapeGen2 = ModifMirror.ModifiedShape(ShapeGen1);
+  TopoDS_Vertex aVertex = BRepLib_MakeVertex(P);
+  TopoDS_Edge DegEdge;
+  BRep_Builder BB;
+  BB.MakeEdge( DegEdge );
+  BB.Add( DegEdge, aVertex.Oriented(TopAbs_FORWARD) );
+  BB.Add( DegEdge, aVertex.Oriented(TopAbs_REVERSED) );
+  BB.Degenerated( DegEdge, Standard_True );
+
+  TopoDS_Wire DegWire;
+  BB.MakeWire( DegWire );
+  BB.Add( DegWire, DegEdge );
+  DegWire.Closed( Standard_True );
 
   // Build the Ruled surface based shape
   BRepFill_Generator RuledSurf;
+  RuledSurf.AddWire(DegWire);
   RuledSurf.AddWire(TopoDS::Wire(ShapeGen1));
-  RuledSurf.AddWire(TopoDS::Wire(ShapeGen2));
   RuledSurf.Perform();
   TopoDS_Shell SurfShell = RuledSurf.Shell();