]> OCCT Git - occt-copy.git/commitdiff
1) The option to remove INTERNAL edges from the faces of the result of Offset operati...
authormsv <msv@opencascade.com>
Wed, 28 Oct 2015 09:05:26 +0000 (12:05 +0300)
committermsv <msv@opencascade.com>
Fri, 22 Apr 2016 12:48:04 +0000 (15:48 +0300)
By default these edges will be kept in the result.
To remove these edges make sure to set the corresponding flag to TRUE when initializing the Offset algo.

void BRepOffset_MakeOffset::Initialize(const TopoDS_Shape&    S,
                                       const Standard_Real    Offset,
                                       const Standard_Real    Tol,
                                       const BRepOffset_Mode  Mode,
                                       const Standard_Boolean Inter,
                                       const Standard_Boolean SelfInter,
                                       const GeomAbs_JoinType Join,
                                       const Standard_Boolean RemoveIntEdges,
                                       const Standard_Boolean Thickening)

2) Due to the small inaccuracy of the calculation of the bi-normal direction (direction inside the face on the edge) the criterion on the coincidence of these directions has been weakened.

3) Make the possibility to produce empty result in case of any invalidity (spikes, self-intersections, faces inversion) optional.

src/BRepOffset/BRepOffset_MakeOffset.cdl
src/BRepOffset/BRepOffset_MakeOffset.cxx
src/BRepOffsetAPI/BRepOffsetAPI_MakeOffsetShape.cdl
src/BRepOffsetAPI/BRepOffsetAPI_MakeOffsetShape.cxx
src/BRepOffsetAPI/BRepOffsetAPI_MakeThickSolid.cdl
src/BRepOffsetAPI/BRepOffsetAPI_MakeThickSolid.cxx
src/BRepTest/BRepTest_FeatureCommands.cxx

index ca16ccca38eb56a2ea05e3b2a052ef61f53b3081..250c0de2fe64028b7d1bcd4f4e0128f5cbfe8b19 100644 (file)
@@ -45,27 +45,31 @@ is
 
     Create;
     
-    Create ( S            : Shape    from TopoDS;
-             Offset       : Real     from Standard;
-             Tol          : Real     from Standard;
-             Mode         : Mode     from BRepOffset = BRepOffset_Skin;
-                 Intersection : Boolean  from Standard   = Standard_False;
-             SelfInter    : Boolean  from Standard   = Standard_False;
-             Join         : JoinType from GeomAbs    = GeomAbs_Arc;
-             Thickening   : Boolean  from Standard   = Standard_False)
+    Create ( S              : Shape    from TopoDS;
+             Offset         : Real     from Standard;
+             Tol            : Real     from Standard;
+             Mode           : Mode     from BRepOffset = BRepOffset_Skin;
+             Intersection   : Boolean  from Standard   = Standard_False;
+             SelfInter      : Boolean  from Standard   = Standard_False;
+             Join           : JoinType from GeomAbs    = GeomAbs_Arc; 
+             RemoveIntEdges : Boolean  from Standard   = Standard_False;
+             Thickening     : Boolean  from Standard   = Standard_False; 
+             RemoveInvalidFaces: Boolean from Standard = Standard_False)
     returns MakeOffset from BRepOffset;             
              
 ---Category: Initialization.
 
     Initialize (me : in out;
-                    S            : Shape    from TopoDS;
-                Offset       : Real     from Standard;
-                Tol          : Real     from Standard;
-                Mode         : Mode     from BRepOffset = BRepOffset_Skin;
-                    Intersection : Boolean  from Standard   = Standard_False;
-                SelfInter    : Boolean  from Standard   = Standard_False;
-                Join         : JoinType from GeomAbs    = GeomAbs_Arc; 
-                Thickening   : Boolean  from Standard   = Standard_False)
+                S              : Shape    from TopoDS;
+                Offset         : Real     from Standard;
+                Tol            : Real     from Standard;
+                Mode           : Mode     from BRepOffset = BRepOffset_Skin;
+                Intersection   : Boolean  from Standard   = Standard_False;
+                SelfInter      : Boolean  from Standard   = Standard_False;
+                Join           : JoinType from GeomAbs    = GeomAbs_Arc; 
+                RemoveIntEdges : Boolean  from Standard   = Standard_False;
+                Thickening     : Boolean  from Standard   = Standard_False;
+                RemoveInvalidFaces: Boolean from Standard = Standard_False)
     is static;
     
     Clear (me : in out) 
@@ -209,7 +213,11 @@ is
 
     MakeMissingWalls (me: in out)
         ---Purpose: Private method used to build walls for thickening the shell
-    is static private; 
+    is static private;  
+     
+    RemoveInternalEdges (me: in out)
+        ---Purpose: Removes INTERNAL edges from the faces
+    is static private;  
 
 fields
 
@@ -219,9 +227,11 @@ fields
     myMode           : Mode       from BRepOffset;
     myInter          : Boolean    from Standard;
     mySelfInter      : Boolean    from Standard;
-    myJoin           : JoinType   from GeomAbs; 
+    myJoin           : JoinType   from GeomAbs;  
+    myRemoveIntEdges : Boolean    from Standard;
     myThickening     : Boolean    from Standard;
-     
+    myRemoveInvalidFaces : Boolean from Standard;
+    
     myFaceOffset     : DataMapOfShapeReal from TopTools;
     
     myFaces          : IndexedMapOfShape from TopTools;
index 702116d382b70565367af656a0df8058adabc457..b08858fdf14444300878aa27181b0af3e252dccb 100644 (file)
@@ -330,13 +330,15 @@ static
                                   const TopTools_IndexedDataMapOfShapeListOfShape& theOrigins,
                                   const TopTools_MapOfShape& theMFence,
                                   Standard_Boolean& bKeep,
-                                  Standard_Boolean& bRem);
+                                  Standard_Boolean& bRem,
+                                  const Standard_Boolean RemoveInvalidFaces);
 
 static 
   void CheckBiNormals(TopTools_ListOfShape&  theLFImages,
                       const TopoDS_Face& theF,
                       const TopTools_IndexedDataMapOfShapeListOfShape& theOrigins,
-                      TopTools_ListOfShape& theLFKeep);
+                      TopTools_ListOfShape& theLFKeep,
+                      const Standard_Boolean RemoveInvalidFaces);
 
 static 
   Standard_Boolean CheckNormals(const TopoDS_Face& theFIm,
@@ -348,6 +350,10 @@ static
                         const TopoDS_Shape&     myOffsetShape,
                         const TopAbs_ShapeEnum &theShapeType);
 
+static 
+  void RemoveShapes(TopoDS_Shape& theS,
+                    const TopTools_ListOfShape& theLS);
+
 //=======================================================================
 
 
@@ -371,17 +377,21 @@ BRepOffset_MakeOffset::BRepOffset_MakeOffset(const TopoDS_Shape&    S,
                                              const Standard_Boolean Inter, 
                                              const Standard_Boolean SelfInter, 
                                              const GeomAbs_JoinType Join,
-                                             const Standard_Boolean Thickening)
+                                             const Standard_Boolean RemoveIntEdges,
+                                             const Standard_Boolean Thickening,
+                                             const Standard_Boolean RemInvFaces)
 : 
-myOffset     (Offset),
-myTol        (Tol),
-myShape      (S),
-myMode       (Mode),
-myInter      (Inter),
-mySelfInter  (SelfInter),
-myJoin       (Join),
-myThickening (Thickening),
-myDone     (Standard_False)
+myOffset        (Offset),
+myTol           (Tol),
+myShape         (S),
+myMode          (Mode),
+myInter         (Inter),
+mySelfInter     (SelfInter),
+myJoin          (Join),
+myRemoveIntEdges(RemoveIntEdges),
+myThickening    (Thickening),
+myRemoveInvalidFaces(RemInvFaces),
+myDone          (Standard_False)
 
 {
   myAsDes = new BRepAlgo_AsDes();
@@ -399,17 +409,21 @@ void BRepOffset_MakeOffset::Initialize(const TopoDS_Shape&    S,
                                        const Standard_Boolean Inter,
                                        const Standard_Boolean SelfInter,
                                        const GeomAbs_JoinType Join,
-                                       const Standard_Boolean Thickening)
+                                       const Standard_Boolean RemoveIntEdges,
+                                       const Standard_Boolean Thickening,
+                                       const Standard_Boolean RemInvFaces)
 {
-  myOffset     = Offset;
-  myShape      = S;
-  myTol        = Tol;
-  myMode       = Mode;
-  myInter      = Inter;
-  mySelfInter  = SelfInter;
-  myJoin       = Join;
-  myThickening = Thickening;
-  myDone     = Standard_False;
+  myOffset         = Offset;
+  myShape          = S;
+  myTol            = Tol;
+  myMode           = Mode;
+  myInter          = Inter;
+  mySelfInter      = SelfInter;
+  myJoin           = Join;
+  myRemoveIntEdges = RemoveIntEdges;
+  myThickening     = Thickening;
+  myRemoveInvalidFaces = RemInvFaces;
+  myDone           = Standard_False;
   Clear();
 }
 
@@ -538,6 +552,12 @@ void BRepOffset_MakeOffset::MakeOffsetShape()
   //--------------
   SelectShells ();
   //----------------------------------
+  // Remove INTERNAL edges if necessasry
+  //----------------------------------
+  if (myRemoveIntEdges) {
+    RemoveInternalEdges();
+  }
+  //----------------------------------
   // Coding of regularities.
   //----------------------------------
   EncodeRegularity();
@@ -1411,7 +1431,7 @@ void BRepOffset_MakeOffset::BuildSplitsOfFaces
         //
         // check offset faces on the coincidence of the 
         // bi-normal directions with the original faces
-        CheckBiNormals(aLFImages, aF, theOrigins, aLFKeep);
+        CheckBiNormals(aLFImages, aF, theOrigins, aLFKeep, myRemoveInvalidFaces);
         //
         // limit the face
         if (aLFImages.Extent() > 1) {
@@ -2964,14 +2984,16 @@ void BRepOffset_MakeOffset::MakeShells()
           //
           // check the result
           Standard_Boolean bGood = Standard_True;
-          BOPCol_ListIteratorOfListOfShape aItLSF(aLSF);
-          for (; aItLSF.More(); aItLSF.Next()) {
-            const TopoDS_Shape& aFx = aItLSF.Value();
-            if (!aMFResult.Contains(aFx)) {
-              const TopTools_ListOfShape& aLFMx = aMV1.Modified(aFx);
-              if (aLFMx.IsEmpty()) {
-                bGood = Standard_False;
-                break;
+          if (myRemoveInvalidFaces) {
+            BOPCol_ListIteratorOfListOfShape aItLSF(aLSF);
+            for (; aItLSF.More(); aItLSF.Next()) {
+              const TopoDS_Shape& aFx = aItLSF.Value();
+              if (!aMFResult.Contains(aFx)) {
+                const TopTools_ListOfShape& aLFMx = aMV1.Modified(aFx);
+                if (aLFMx.IsEmpty()) {
+                  bGood = Standard_False;
+                  break;
+                }
               }
             }
           }
@@ -3407,11 +3429,88 @@ void BRepOffset_MakeOffset::EncodeRegularity ()
 #endif
 }
 
+//=======================================================================
+//function : RemoveInternalEdges
+//purpose  : 
+//=======================================================================
+void BRepOffset_MakeOffset::RemoveInternalEdges()
+{
+  Standard_Boolean bRemoveWire, bRemoveEdge;
+  TopExp_Explorer aExpF, aExpW, aExpE;
+  TopTools_IndexedDataMapOfShapeListOfShape aDMELF;
+  //
+  TopExp::MapShapesAndAncestors(myOffsetShape, TopAbs_EDGE, TopAbs_FACE, aDMELF);
+  //
+  aExpF.Init(myOffsetShape, TopAbs_FACE);
+  for (; aExpF.More(); aExpF.Next()) {
+    TopoDS_Face& aF = *(TopoDS_Face*)&aExpF.Current();
+    //
+    TopTools_ListOfShape aLIW;
+    //
+    aExpW.Init(aF, TopAbs_WIRE);
+    for (; aExpW.More(); aExpW.Next()) {
+      TopoDS_Wire& aW = *(TopoDS_Wire*)&aExpW.Current();
+      //
+      bRemoveWire = Standard_True;
+      TopTools_ListOfShape aLIE;
+      //
+      aExpE.Init(aW, TopAbs_EDGE);
+      for (; aExpE.More(); aExpE.Next()) {
+        const TopoDS_Edge& aE = *(TopoDS_Edge*)&aExpE.Current();
+        if (aE.Orientation() != TopAbs_INTERNAL) {
+          bRemoveWire = Standard_False;
+          continue;
+        }
+        //
+        const TopTools_ListOfShape& aLF = aDMELF.FindFromKey(aE);
+        bRemoveEdge = (aLF.Extent() == 1);
+        if (bRemoveEdge) {
+          aLIE.Append(aE);
+        }
+        else {
+          bRemoveWire = Standard_False;
+        }
+      }
+      //
+      if (bRemoveWire) {
+        aLIW.Append(aW);
+      }
+      else if (aLIE.Extent()) {
+        RemoveShapes(aW, aLIE);
+      }
+    }
+    //
+    if (aLIW.Extent()) {
+      RemoveShapes(aF, aLIW);
+    }
+  }
+}
 
 //=======================================================================
 // static methods implementation
 //=======================================================================
 
+//=======================================================================
+//function : RemoveShapes
+//purpose  : Removes the shapes <theLS> from the shape <theS>
+//=======================================================================
+void RemoveShapes(TopoDS_Shape& theS,
+                  const TopTools_ListOfShape& theLS)
+{
+  BRep_Builder aBB;
+  //
+  Standard_Boolean bFree = theS.Free();
+  theS.Free(Standard_True);
+  //
+  TopTools_ListIteratorOfListOfShape aIt(theLS);
+  for (; aIt.More(); aIt.Next()) {
+    const TopoDS_Shape& aSI = aIt.Value();
+    aBB.Remove(theS, aSI);
+  }
+  //
+  theS.Free(bFree);
+}
+
 //=======================================================================
 //function : UpDateTolerance
 //purpose  : 
@@ -4151,12 +4250,13 @@ Standard_Boolean CheckBiNormals
    const TopTools_IndexedDataMapOfShapeListOfShape& theOrigins,
    const TopTools_MapOfShape& theMFence,
    Standard_Boolean& bKeep,
-   Standard_Boolean& bRemove)
+   Standard_Boolean& bRemove,
+   const Standard_Boolean RemoveInvalidFaces)
 {
   Standard_Boolean bChecked;
   Standard_Integer aNbEdgesChecked;
   Standard_Real anAngle;
-  TopTools_ListOfShape aLEInv;
+  TopTools_IndexedMapOfShape aMEInv;
   //
   aNbEdgesChecked = 0;
   //
@@ -4203,6 +4303,15 @@ Standard_Boolean CheckBiNormals
       }
     }
     //
+    if (!RemoveInvalidFaces) {
+      if (theMFence.Contains(aEIm)) {
+        bChecked = Standard_True;
+        bKeep = Standard_True;
+        bRemove = Standard_False;
+        return bChecked;
+      }
+    }
+    //
     const TopoDS_Edge& aEOr = *(TopoDS_Edge*)&aLEOr.First();
     //
     TopoDS_Edge aEOrF;
@@ -4225,8 +4334,8 @@ Standard_Boolean CheckBiNormals
     ++aNbEdgesChecked;
     //
     anAngle = aDB1.Angle(aDB2);
-    if (Abs(anAngle - M_PI) < Precision::Confusion()) {
-      aLEInv.Append(aEIm);
+    if (Abs(anAngle - M_PI) < 1.e-4) {
+      aMEInv.Add(aEIm);
     }
   }
   //
@@ -4239,24 +4348,24 @@ Standard_Boolean CheckBiNormals
   bKeep = Standard_True;
   bRemove = Standard_False;
   //
-  if (aLEInv.IsEmpty()) {
+  Standard_Integer  aNb = aMEInv.Extent();
+  if (aNb == 0) {
     return bChecked;
   }
   //
-  TopTools_ListIteratorOfListOfShape aItLS(aLEInv);
-  for (; aItLS.More(); aItLS.Next()) {
-    const TopoDS_Shape& aE = aItLS.Value();
-    if (theMFence.Contains(aE)) {
-      bKeep = Standard_False;
-      bRemove = Standard_True;
-      break;
-    }
+  if (aNb == aNbEdgesChecked) {
+    bKeep = Standard_False;
+    bRemove = Standard_True;
   }
   //
   if (!bRemove) {
-    if (aNbEdgesChecked == aLEInv.Extent()) {
-      bKeep = Standard_False;
-      bRemove = Standard_True;
+    for (Standard_Integer i = 1; i <= aNb; ++i) {
+      const TopoDS_Shape& aE = aMEInv(i);
+      if (theMFence.Contains(aE)) {
+        bKeep = Standard_False;
+        bRemove = Standard_True;
+        break;
+      }
     }
   }
   //
@@ -4271,7 +4380,8 @@ void CheckBiNormals
   (TopTools_ListOfShape&  theLFImages,
    const TopoDS_Face& theF,
    const TopTools_IndexedDataMapOfShapeListOfShape& theOrigins,
-   TopTools_ListOfShape& theLFKeep)
+   TopTools_ListOfShape& theLFKeep,
+   const Standard_Boolean RemoveInvalidFaces)
 {
   Standard_Boolean bChecked, bKeep, bRem;
   Standard_Integer i, aNb;
@@ -4302,7 +4412,7 @@ void CheckBiNormals
   for (; aItLF.More(); ) {
     const TopoDS_Face& aFIm = *(TopoDS_Face*)&aItLF.Value();
     //
-    bChecked = CheckBiNormals(aFIm, aFOr, theOrigins, aMEToKeep, bKeep, bRem);
+    bChecked = CheckBiNormals(aFIm, aFOr, theOrigins, aMEToKeep, bKeep, bRem, RemoveInvalidFaces);
     //
     if (bChecked) {
       if (bRem) {
index a8a97f7277a9341fd6a30ec754a3cc43e7a9729c..c41af537226740812957d1c803eb2b0cd7784aae 100644 (file)
@@ -46,7 +46,8 @@ is
             Mode         : Mode     from BRepOffset = BRepOffset_Skin;
             Intersection : Boolean  from Standard   = Standard_False;
             SelfInter    : Boolean  from Standard   = Standard_False;
-             Join         : JoinType from GeomAbs    = GeomAbs_Arc)
+             Join         : JoinType from GeomAbs    = GeomAbs_Arc;
+             RemoveIntEdges:Boolean  from Standard   = Standard_False)
        ---Purpose: Constructs a shape parallel to the shape S, where
        -- - S may be a face, a shell, a solid or a compound of these shape kinds;
        -- - Offset is the offset value. The offset shape is constructed:
@@ -82,6 +83,8 @@ is
        -- - if Join is equal to GeomAbs_Intersection, then the parallels to the
        -- two adjacent faces are enlarged and intersected,
        -- so that there are no free edges on parallels to faces.
+        -- RemoveIntEdges flag defines whether to remove the INTERNAL edges 
+        -- from the result or not.
        --   Warnings
        -- 1. All the faces of the shape S should be based on the surfaces
        -- with continuity at least C1.
index f4245d5bb77523a7b9de25f8079196579a78bacf..9b1d0b73b06f97b70538725f75f51f02d03844d4 100644 (file)
@@ -43,9 +43,11 @@ BRepOffsetAPI_MakeOffsetShape::BRepOffsetAPI_MakeOffsetShape
  const BRepOffset_Mode  Mode, 
  const Standard_Boolean Intersection,
  const Standard_Boolean SelfInter,
- const GeomAbs_JoinType Join)
+ const GeomAbs_JoinType Join,
+ const Standard_Boolean RemoveIntEdges)
 {
-  myOffsetShape.Initialize (S,Offset,Tol,Mode,Intersection,SelfInter,Join);
+  myOffsetShape.Initialize (S,Offset,Tol,Mode,Intersection,SelfInter,
+                            Join, RemoveIntEdges);
   Build();
 }
 
index ec8a6a4bec6e33756cdfcca5ab2c3c288b43523d..516429d56c2555b49d30ca6aace7818a36b918b8 100644 (file)
@@ -53,7 +53,8 @@ is
             Mode         : Mode        from BRepOffset = BRepOffset_Skin;
             Intersection : Boolean     from Standard   = Standard_False;
             SelfInter    : Boolean     from Standard   = Standard_False;
-             Join         : JoinType    from GeomAbs    = GeomAbs_Arc)
+             Join         : JoinType    from GeomAbs    = GeomAbs_Arc;
+             RemoveIntEdges : Boolean   from Standard   = Standard_False)
        ---Purpose:  Constructs a hollowed solid from
        -- the solid S by removing the set of faces ClosingFaces from S, where:
        --       Offset defines the thickness of the walls. Its sign indicates
index e8d865274605c3ad09c5c49cf5c7b6978c7c2026..5f645ab0805ad21c16c72dbb95c72f7c041a9158 100644 (file)
@@ -44,9 +44,11 @@ BRepOffsetAPI_MakeThickSolid::BRepOffsetAPI_MakeThickSolid
  const BRepOffset_Mode       Mode,
  const Standard_Boolean      Intersection,
  const Standard_Boolean      SelfInter,
- const GeomAbs_JoinType      Join)
+ const GeomAbs_JoinType      Join,
+ const Standard_Boolean      RemoveIntEdges)
 {
-  myOffsetShape.Initialize (S,Offset,Tol,Mode,Intersection,SelfInter,Join);
+  myOffsetShape.Initialize (S,Offset,Tol,Mode,Intersection,SelfInter,
+                            Join, RemoveIntEdges);
   TopTools_ListIteratorOfListOfShape it(ClosingFaces);
   for (; it.More(); it.Next()) {
     myOffsetShape.AddFace(TopoDS::Face(it.Value()));
index 97acc216d067368dece91cdadfaa99e3442876ae..80338cf7398a5885321eb7aca1b6e362dd6aad69 100644 (file)
@@ -803,7 +803,7 @@ static Standard_Integer SPLS(Draw_Interpretor& ,
 //=======================================================================
 
 Standard_Integer thickshell(Draw_Interpretor& ,
-                           Standard_Integer n, const char** a)
+                            Standard_Integer n, const char** a)
 {
 
   //OSD_Chronometer Clock;
@@ -818,9 +818,9 @@ Standard_Integer thickshell(Draw_Interpretor& ,
   if (n > 4)
     {
       if (!strcmp(a[4],"i"))
-       JT = GeomAbs_Intersection;
+        JT = GeomAbs_Intersection;
       if (!strcmp(a[4],"t"))
-       JT = GeomAbs_Tangent;
+        JT = GeomAbs_Tangent;
     }
   
   Standard_Boolean Inter = Standard_False; //Standard_True;
@@ -829,7 +829,7 @@ Standard_Integer thickshell(Draw_Interpretor& ,
     Tol = Draw::Atof(a[5]);
 
   BRepOffset_MakeOffset B;
-  B.Initialize(S,Of,Tol,BRepOffset_Skin,Inter,0,JT, Standard_True);
+  B.Initialize(S,Of,Tol,BRepOffset_Skin,Inter,0,JT, Standard_False, Standard_True);
 
 //  Clock.Start();
 
@@ -907,53 +907,64 @@ static Standard_Boolean      theYaBouchon;
 static Standard_Real         TheTolerance = Precision::Confusion();
 static Standard_Boolean      TheInter     = Standard_False;
 static GeomAbs_JoinType      TheJoin      = GeomAbs_Arc;
+static Standard_Boolean      RemoveIntEdges = Standard_False;
+static Standard_Boolean      RemoveInvalidFaces = Standard_False;
 
 Standard_Integer offsetparameter(Draw_Interpretor& di,
-                                Standard_Integer n, const char** a)
+                                 Standard_Integer n, const char** a)
 {
   if ( n == 1 ) { 
-    //cout << " OffsetParameter Tol Inter(c/p) JoinType(a/i)" << endl;
-    //cout << " Current Values" << endl;
-    //cout << "   --> Tolerance :" << TheTolerance << endl;
-    //cout << "   --> TheInter  :";
-    di << " OffsetParameter Tol Inter(c/p) JoinType(a/i)" << "\n";
+    di << " OffsetParameter Tol Inter(c/p) JoinType(a/i/t) [RemoveInternalEdges(r/k) RemoveInvalidFaces(r/k)] " << "\n";
     di << " Current Values" << "\n";
-    di << "   --> Tolerance :" << TheTolerance << "\n";
-    di << "   --> TheInter  :";
+    di << "   --> Tolerance : " << TheTolerance << "\n";
+    di << "   --> TheInter  : ";
     if ( TheInter) {
-      //cout << "Complet" ;
       di << "Complet" ;
     } else {
-      //cout << "Partial";
       di << "Partial";
     }
-    //cout << endl << "   --> TheJoin   :";
-    di << "\n" << "   --> TheJoin   :";
+    di << "\n" << "   --> TheJoin   : ";
     
     switch (TheJoin) {
-    //case GeomAbs_Arc:          cout << " Arc";          break;
-    //case GeomAbs_Intersection: cout << " Intersection"; break;
-    case GeomAbs_Arc:          di << " Arc";          break;
-    case GeomAbs_Intersection: di << " Intersection"; break;
+    case GeomAbs_Arc:          di << "Arc";          break;
+    case GeomAbs_Intersection: di << "Intersection"; break;
     default:
       break ;
     }
-    //cout << endl;
+    //
+    di << "\n" << "   --> Internal Edges : ";
+    if (RemoveIntEdges) {
+      di << "Remove";
+    }
+    else {
+      di << "Keep";
+    }
+    //
+    di << "\n" << "   --> Invalid Faces : ";
+    if (RemoveInvalidFaces) {
+      di << "Remove";
+    }
+    else {
+      di << "Keep";
+    }
     di << "\n";
-
+    //
     return 0;
   }
 
   if ( n < 4 ) return 1;
-  
+  //
   TheTolerance = Draw::Atof(a[1]);
   TheInter     = strcmp(a[2],"p");
-  
+  //
   if      ( !strcmp(a[3],"a")) TheJoin = GeomAbs_Arc;
   else if ( !strcmp(a[3],"i")) TheJoin = GeomAbs_Intersection;
   else if ( !strcmp(a[3],"t")) TheJoin = GeomAbs_Tangent;
-    
-  return 0;    
+  //
+  RemoveIntEdges = (n >= 5) ? !strcmp(a[4], "r") : Standard_False;
+  RemoveInvalidFaces = (n == 6) ? !strcmp(a[5], "r") : Standard_False;
+  //
+  return 0;
 }
 
 
@@ -963,7 +974,7 @@ Standard_Integer offsetparameter(Draw_Interpretor& di,
 //=======================================================================
 
 Standard_Integer offsetload(Draw_Interpretor& ,
-                           Standard_Integer n, const char** a)
+                            Standard_Integer n, const char** a)
 {
   if ( n < 2) return 1;
   TopoDS_Shape  S  = DBRep::Get(a[1]);
@@ -973,7 +984,8 @@ Standard_Integer offsetload(Draw_Interpretor& ,
   TheRadius = Of;
 //  Standard_Boolean Inter = Standard_True;
   
-  TheOffset.Initialize(S,Of,TheTolerance,BRepOffset_Skin,TheInter,0,TheJoin);
+  TheOffset.Initialize(S,Of,TheTolerance,BRepOffset_Skin,TheInter,0,TheJoin,
+                       RemoveIntEdges,Standard_False,RemoveInvalidFaces);
   //------------------------------------------
   // recuperation et chargement des bouchons.
   //----------------------------------------