1 // Copyright (C) 2005 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
2 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
4 // This library is free software; you can redistribute it and/or
5 // modify it under the terms of the GNU Lesser General Public
6 // License as published by the Free Software Foundation; either
7 // version 2.1 of the License.
9 // This library is distributed in the hope that it will be useful
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 // Lesser General Public License for more details.
14 // You should have received a copy of the GNU Lesser General Public
15 // License along with this library; if not, write to the Free Software
16 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 // See http://www.salome-platform.org/
20 #include <Standard_Stream.hxx>
22 #include <BRepOffsetAPI_MakeFilling.hxx>
24 #include <GEOMImpl_Block6Explorer.hxx>
26 #include "utilities.h"
28 #include <BRep_Tool.hxx>
29 #include <BRep_TFace.hxx>
30 #include <BRep_Builder.hxx>
31 #include <BRepLib.hxx>
32 #include <BRepLib_FindSurface.hxx>
33 #include <BRepTools.hxx>
34 #include <BRepTools_WireExplorer.hxx>
35 #include <BRepOffsetAPI_ThruSections.hxx>
36 #include <BRepBuilderAPI_Copy.hxx>
37 #include <BRepBuilderAPI_MakeEdge.hxx>
38 #include <BRepBuilderAPI_MakeWire.hxx>
39 #include <BRepBuilderAPI_MakeFace.hxx>
40 #include <BRepBuilderAPI_Transform.hxx>
44 #include <TopoDS_Shape.hxx>
45 #include <TopoDS_Edge.hxx>
46 #include <TopoDS_Wire.hxx>
47 #include <TopoDS_Solid.hxx>
49 #include <TopExp_Explorer.hxx>
50 #include <TopTools_MapOfShape.hxx>
51 #include <TopTools_ListOfShape.hxx>
52 #include <TopTools_ListIteratorOfListOfShape.hxx>
53 #include <TopTools_IndexedMapOfShape.hxx>
54 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
56 #include <Geom_Curve.hxx>
57 #include <Geom_TrimmedCurve.hxx>
58 #include <GeomFill_Generator.hxx>
60 #include <Precision.hxx>
62 #include <TColgp_Array1OfPnt.hxx>
64 #include <StdFail_NotDone.hxx>
65 #include <Standard_NullObject.hxx>
66 #include <Standard_TypeMismatch.hxx>
67 #include <Standard_ConstructionError.hxx>
68 #include <Standard_NoSuchObject.hxx>
74 static Standard_Integer mod4 (Standard_Integer nb)
76 if (nb <= 0) return nb + 4;
77 if (nb > 4) return nb - 4;
81 static Standard_Integer edge_id (const Standard_Integer theFaceID,
82 const Standard_Integer theEdgeNB)
84 static Standard_Integer edge_ids[NBFACES][4] = {
85 { 1, 2, 3, 4 }, // face 1
86 { 5, 6, 7, 8 }, // face 2
87 { 9, 5, 10, 1 }, // face 3
88 { 12, 7, 11, 3 }, // face 4
89 { 4, 12, 8, 9 }, // face 5
90 { 2, 11, 6, 10 } }; // face 6
92 return edge_ids[theFaceID - 1][theEdgeNB - 1];
95 static Standard_Integer side_edge_id (const Standard_Integer theEdgeNB)
97 static Standard_Integer side_edge_ids[4] = {9, 10, 11, 12};
99 return side_edge_ids[theEdgeNB - 1];
102 static Standard_Integer vertex_id (const Standard_Integer theFaceID,
103 const Standard_Integer theVertexNB)
105 static Standard_Integer vertex_ids[NBFACES][4] = {
106 { 1, 2, 3, 4 }, // face 1
107 { 5, 6, 7, 8 }, // face 2
108 { 1, 5, 6, 2 }, // face 3
109 { 4, 8, 7, 3 }, // face 4
110 { 1, 4, 8, 5 }, // face 5
111 { 2, 3, 7, 6 } }; // face 6
113 return vertex_ids[theFaceID - 1][theVertexNB - 1];
116 static Standard_Integer vertex_id_edge (const Standard_Integer theEdgeID, // [1,12]
117 const Standard_Integer theVertexNB) // [1,2]
119 static Standard_Integer vertex_ids_edge[NBEDGES][2] = {
133 return vertex_ids_edge[theEdgeID - 1][theVertexNB - 1];
136 static Standard_Integer face_id_edges (const Standard_Integer theEdge1ID, // [1,12]
137 const Standard_Integer theEdge2ID) // [1,12]
139 static Standard_Integer face_ids_edges[NBEDGES][NBEDGES] = {
140 // 1 2 3 4 5 6 7 8 9 10 11 12
141 { 0, 1, 1, 1, 3, 0, 0, 0, 3, 3, 0, 0 }, // edge 1
142 { 1, 0, 1, 1, 0, 6, 0, 0, 0, 6, 6, 0 }, // edge 2
143 { 1, 1, 0, 1, 0, 0, 4, 0, 0, 0, 4, 4 }, // edge 3
144 { 1, 1, 1, 0, 0, 0, 0, 5, 5, 0, 0, 5 }, // edge 4
145 { 3, 0, 0, 0, 0, 2, 2, 2, 3, 3, 0, 0 }, // edge 5
146 { 0, 6, 0, 0, 2, 0, 2, 2, 0, 6, 6, 0 }, // edge 6
147 { 0, 0, 4, 0, 2, 2, 0, 2, 0, 0, 4, 4 }, // edge 7
148 { 0, 0, 0, 5, 2, 2, 2, 0, 5, 0, 0, 5 }, // edge 8
149 { 3, 0, 0, 5, 3, 0, 0, 5, 0, 3, 0, 5 }, // edge 9
150 { 3, 6, 0, 0, 3, 6, 0, 0, 3, 0, 6, 0 }, // edge 10
151 { 0, 6, 4, 0, 0, 6, 4, 0, 0, 6, 0, 4 }, // edge 11
152 { 0, 0, 4, 5, 0, 0, 4, 5, 5, 0, 4, 0 } }; // edge 12
154 return face_ids_edges[theEdge1ID - 1][theEdge2ID - 1];
157 static Standard_Integer edge_id_vertices (const Standard_Integer theVertex1ID, // [1,8]
158 const Standard_Integer theVertex2ID) // [1,8]
160 static Standard_Integer edge_ids_vertices[NBVERTS][NBVERTS] = {
162 { 0, 1, 0, 4, 9, 0, 0, 0}, // vertex 1
163 { 1, 0, 2, 0, 0, 10, 0, 0}, // vertex 2
164 { 0, 2, 0, 3, 0, 0, 11, 0}, // vertex 3
165 { 4, 0, 3, 0, 0, 0, 0, 12}, // vertex 4
166 { 9, 0, 0, 0, 0, 5, 0, 8}, // vertex 5
167 { 0, 10, 0, 0, 5, 0, 6, 0}, // vertex 6
168 { 0, 0, 11, 0, 0, 6, 0, 7}, // vertex 7
169 { 0, 0, 0, 12, 8, 0, 7, 0} }; // vertex 8
171 return edge_ids_vertices[theVertex1ID - 1][theVertex2ID - 1];
174 static Standard_Integer edge_id_faces (const Standard_Integer theFace1ID, // [1,6]
175 const Standard_Integer theFace2ID) // [1,6]
177 static Standard_Integer edge_ids_faces[NBFACES][NBFACES] = {
179 { 0, 0, 1, 3, 4, 2 }, // face 1
180 { 0, 0, 5, 7, 8, 6 }, // face 2
181 { 1, 5, 0, 0, 9, 10 }, // face 3
182 { 3, 7, 0, 0, 12, 11 }, // face 4
183 { 4, 8, 9, 12, 0, 0 }, // face 5
184 { 2, 6, 10, 11, 0, 0 } }; // face 6
186 return edge_ids_faces[theFace1ID - 1][theFace2ID - 1];
189 //=======================================================================
190 //function : GEOMImpl_Block6Explorer
191 //purpose : Constructor
192 //=======================================================================
193 GEOMImpl_Block6Explorer::GEOMImpl_Block6Explorer ()
194 : myFaces(1,NBFACES), myEdges(1,NBEDGES), myVertices(1,NBVERTS)
198 //=======================================================================
199 //function : GetVertex
201 //=======================================================================
202 TopoDS_Shape GEOMImpl_Block6Explorer::GetVertex (const Standard_Integer theVertexID)
204 TopoDS_Shape aNullShape;
205 if (theVertexID < 1 || theVertexID > NBVERTS) return aNullShape;
206 return myVertices(theVertexID);
209 //=======================================================================
210 //function : GetVertexID
212 //=======================================================================
213 Standard_Integer GEOMImpl_Block6Explorer::GetVertexID (const TopoDS_Shape& theVertex)
215 for (Standard_Integer id = 1; id <= NBVERTS; id++) {
216 if (theVertex.IsSame(myVertices(id))) return id;
218 Standard_NoSuchObject::Raise("The Vertex does not belong to the Block");
222 //=======================================================================
223 //function : GetVertexID
225 //=======================================================================
226 Standard_Integer GEOMImpl_Block6Explorer::GetVertexID (const Standard_Integer theFaceID,
227 const Standard_Integer theVertexNB)
229 return vertex_id(theFaceID, theVertexNB);
232 //=======================================================================
233 //function : GetVertexOnEdgeID
235 //=======================================================================
236 Standard_Integer GEOMImpl_Block6Explorer::GetVertexOnEdgeID
237 (const Standard_Integer theEdgeID,
238 const Standard_Integer theVertexNB)
240 return vertex_id_edge(theEdgeID, theVertexNB);
243 //=======================================================================
246 //=======================================================================
247 TopoDS_Shape GEOMImpl_Block6Explorer::GetEdge (const Standard_Integer theEdgeID,
248 const Standard_Boolean doMake)
250 TopoDS_Shape aNullShape;
251 if (theEdgeID < 1 || theEdgeID > NBEDGES) return aNullShape;
252 if (myEdges(theEdgeID).IsNull() && doMake) {
253 // Create the required edge as a linear segment between
254 // corresponding vertices and put it in the Block's edges
255 BRepBuilderAPI_MakeEdge ME (TopoDS::Vertex(myVertices(vertex_id_edge(theEdgeID, 1))),
256 TopoDS::Vertex(myVertices(vertex_id_edge(theEdgeID, 2))));
258 Standard_ConstructionError::Raise("Edge construction failed");
260 myEdges(theEdgeID) = ME.Shape();
263 return myEdges(theEdgeID);
266 //=======================================================================
267 //function : GetEdgeID
269 //=======================================================================
270 Standard_Integer GEOMImpl_Block6Explorer::GetEdgeID (const TopoDS_Shape& theEdge)
272 for (Standard_Integer id = 1; id <= NBEDGES; id++) {
273 if (theEdge.IsSame(myEdges(id))) return id;
275 Standard_NoSuchObject::Raise("The Edge does not belong to the Block");
279 //=======================================================================
280 //function : GetEdgeID
282 //=======================================================================
283 Standard_Integer GEOMImpl_Block6Explorer::GetEdgeID (const Standard_Integer theFaceID,
284 const Standard_Integer theEdgeNB)
286 return edge_id(theFaceID, theEdgeNB);
289 //=======================================================================
290 //function : FindEdgeID
292 //=======================================================================
293 Standard_Integer GEOMImpl_Block6Explorer::FindEdgeID (const Standard_Integer theVertex1ID,
294 const Standard_Integer theVertex2ID)
296 return edge_id_vertices(theVertex1ID, theVertex2ID);
299 //=======================================================================
300 //function : FindCommonEdgeID
302 //=======================================================================
303 Standard_Integer GEOMImpl_Block6Explorer::FindCommonEdgeID
304 (const Standard_Integer theFace1ID,
305 const Standard_Integer theFace2ID)
307 return edge_id_faces(theFace1ID, theFace2ID);
310 //=======================================================================
313 //=======================================================================
314 TopoDS_Shape GEOMImpl_Block6Explorer::GetFace (const Standard_Integer theFaceID,
315 const Standard_Boolean doMake)
317 TopoDS_Shape aNullShape;
318 if (theFaceID < 1 || theFaceID > NBFACES) return aNullShape;
320 if (myFaces(theFaceID).IsNull() && doMake) {
322 // Create the required face between
323 // corresponding edges and put it in the Block's faces
325 TopoDS_Shape E1 = GetEdge(edge_id(theFaceID, 1), doMake);
326 TopoDS_Shape E2 = GetEdge(edge_id(theFaceID, 2), doMake);
327 TopoDS_Shape E3 = GetEdge(edge_id(theFaceID, 3), doMake);
328 TopoDS_Shape E4 = GetEdge(edge_id(theFaceID, 4), doMake);
330 BRepBuilderAPI_MakeWire MW (TopoDS::Edge(E1),
335 Standard_ConstructionError::Raise("Wire construction failed");
338 MakeFace(MW, Standard_False, aFace);
339 if (aFace.IsNull()) {
340 Standard_ConstructionError::Raise("Face construction failed");
342 myFaces(theFaceID) = aFace;
345 return myFaces(theFaceID);
348 //=======================================================================
349 //function : GetFaceID
351 //=======================================================================
352 Standard_Integer GEOMImpl_Block6Explorer::GetFaceID (const TopoDS_Shape& theFace)
354 for (Standard_Integer id = 1; id <= NBFACES; id++) {
355 if (theFace.IsSame(myFaces(id))) return id;
357 Standard_NoSuchObject::Raise("The Face does not belong to the Block");
361 //=======================================================================
362 //function : FindFaceID
364 //=======================================================================
365 Standard_Integer GEOMImpl_Block6Explorer::FindFaceID (const Standard_Integer theEdge1ID,
366 const Standard_Integer theEdge2ID)
368 return face_id_edges(theEdge1ID, theEdge2ID);
371 //=======================================================================
372 //function : GetOppositeFaceID
374 //=======================================================================
375 Standard_Integer GEOMImpl_Block6Explorer::GetOppositeFaceID (const Standard_Integer theFaceID)
377 Standard_Integer opp_face_id[NBFACES + 1] = {
386 return opp_face_id[theFaceID];
389 //=======================================================================
390 //function : IsSimilarFaces
392 //=======================================================================
393 Standard_Boolean GEOMImpl_Block6Explorer::IsSimilarFaces (const Standard_Integer theFace1ID,
394 const Standard_Integer theFace2ID,
395 const gp_Trsf theTransformation)
397 Standard_Integer common_edge_id = FindCommonEdgeID(theFace1ID, theFace2ID);
399 if (common_edge_id == 0) { // opposite faces
400 for (Standard_Integer id = 1; id <= 4; id++) {
401 TopoDS_Shape E1 = GetEdge(edge_id(theFace1ID, id));
402 TopoDS_Shape E2 = GetEdge(edge_id(theFace2ID, id));
404 BRepBuilderAPI_Transform aTrsf (E1, theTransformation, Standard_False);
405 if (!IsSimilarEdges(aTrsf.Shape(), E2))
406 return Standard_False;
408 } else { // the faces have common edge
409 TopTools_Array1OfShape aVerts1 (1,4);
410 TopTools_Array1OfShape aVerts2 (1,4);
412 Standard_Integer common_vertex1 = GetVertexOnEdgeID(common_edge_id, 1);
413 Standard_Integer common_vertex2 = GetVertexOnEdgeID(common_edge_id, 2);
414 aVerts1(1) = myVertices(common_vertex1);
415 aVerts1(2) = myVertices(common_vertex2);
416 aVerts2(1) = myVertices(common_vertex1);
417 aVerts2(2) = myVertices(common_vertex2);
419 Standard_Integer not_common_v11 = 0, not_common_v12 = 0;
420 Standard_Integer vnb, vid;
421 for (vnb = 1; vnb <= 4; vnb++) {
422 vid = GetVertexID(theFace1ID, vnb);
423 if (vid != common_vertex1 && FindEdgeID(vid, common_vertex1) == 0) {
424 not_common_v12 = vid;
426 if (vid != common_vertex2 && FindEdgeID(vid, common_vertex2) == 0) {
427 not_common_v11 = vid;
432 Standard_Integer not_common_v21 = 0, not_common_v22 = 0;
433 for (vnb = 1; vnb <= 4; vnb++) {
434 vid = GetVertexID(theFace2ID, vnb);
435 if (vid != common_vertex1 && FindEdgeID(vid, common_vertex1) == 0) {
436 not_common_v22 = vid;
438 if (vid != common_vertex2 && FindEdgeID(vid, common_vertex2) == 0) {
439 not_common_v21 = vid;
443 aVerts1(3) = myVertices(not_common_v11);
444 aVerts1(4) = myVertices(not_common_v12);
445 aVerts2(3) = myVertices(not_common_v21);
446 aVerts2(4) = myVertices(not_common_v22);
448 for (Standard_Integer id = 1; id <= 4; id++) {
449 BRepBuilderAPI_Transform aTrsf (aVerts1(id), theTransformation, Standard_False);
450 TopoDS_Vertex V1 = TopoDS::Vertex(aTrsf.Shape());
451 TopoDS_Vertex V2 = TopoDS::Vertex(aVerts2(id));
452 if (!BRepTools::Compare(V1, V2)) {
453 return Standard_False;
458 return Standard_True;
461 //============ Initialization methods ===================================
463 //=======================================================================
464 //function : InitByBlock
466 //=======================================================================
467 void GEOMImpl_Block6Explorer::InitByBlock (const TopoDS_Shape& theBlock)
469 // 1. Find any one face of the block
470 TopExp_Explorer faces (theBlock, TopAbs_FACE);
472 Standard_ConstructionError::Raise("The block has no faces");
474 TopoDS_Shape aFirstFace = faces.Current();
476 // 2. Store all elements of the block relatively aFirstFace
477 InitByBlockAndFace(theBlock, aFirstFace);
480 //=======================================================================
481 //function : InitByBlockAndFace
483 //=======================================================================
484 void GEOMImpl_Block6Explorer::InitByBlockAndFace (const TopoDS_Shape& theBlock,
485 const TopoDS_Shape& theFace)
487 myFaces(1) = theFace;
489 // 2. Get wire of the first face
490 TopExp_Explorer wires (myFaces(1), TopAbs_WIRE);
492 Standard_ConstructionError::Raise("A face of the block has no wires");
494 TopoDS_Shape aWire = wires.Current();
497 Standard_ConstructionError::Raise("A face of the block has more than one wires");
500 // 3. Explore wire to init edges and vertices of the first face
501 BRepTools_WireExplorer aWE (TopoDS::Wire(aWire), TopoDS::Face(myFaces(1)));
502 Standard_Integer nb = 1;
503 for (; aWE.More(); aWE.Next(), nb++) {
505 Standard_ConstructionError::Raise("A face of the block has more than four edges");
507 myEdges(edge_id(1, nb)) = aWE.Current();
508 myVertices(vertex_id(1, nb)) = aWE.CurrentVertex();
511 Standard_ConstructionError::Raise("A face of the block has less than four edges");
514 // 2. Store all other elements of the block
515 InitByBlockAndVertices (theBlock,
516 myVertices(vertex_id(1,1)),
517 myVertices(vertex_id(1,2)),
518 myVertices(vertex_id(1,3)));
521 //=======================================================================
522 //function : InitByBlockAndEdges
524 //=======================================================================
525 void GEOMImpl_Block6Explorer::InitByBlockAndEdges (const TopoDS_Shape& theBlock,
526 const TopoDS_Shape& theEdge1,
527 const TopoDS_Shape& theEdge3)
529 // 1. Store vertices and edges of the first face
531 // 1.1. Store two given edges
532 myEdges(edge_id(1, 1)) = theEdge1;
533 myEdges(edge_id(1, 3)) = theEdge3;
535 // 1.2. Find and store the first face
536 TopTools_IndexedDataMapOfShapeListOfShape MEF;
537 MapShapesAndAncestors(theBlock, TopAbs_EDGE, TopAbs_FACE, MEF);
538 if (MEF.Extent() != NBEDGES) {
539 Standard_TypeMismatch::Raise("Block has wrong number of edges");
541 const TopTools_ListOfShape& aFacesOfE1 = MEF.FindFromKey(theEdge1);
542 const TopTools_ListOfShape& aFacesOfE3 = MEF.FindFromKey(theEdge3);
544 Standard_Boolean isFound = Standard_False;
545 TopTools_ListIteratorOfListOfShape anIterF1 (aFacesOfE1);
546 for (; anIterF1.More() && !isFound; anIterF1.Next()) {
548 TopTools_ListIteratorOfListOfShape anIterF3 (aFacesOfE3);
549 for (; anIterF3.More() && !isFound; anIterF3.Next()) {
551 if (anIterF1.Value().IsSame(anIterF3.Value())) {
552 isFound = Standard_True;
554 // Store the face, defined by two opposite edges
555 myFaces(1) = anIterF1.Value();
560 Standard_ConstructionError::Raise
561 ("Edges 1 and 2 do not belong to one face of the block");
564 // 1.3. Make vertices of the first edge the first and the
565 // second vertices of the first face. Order is free.
566 TopoDS_Edge E = TopoDS::Edge(theEdge1);
567 TopoDS_Vertex V1, V2;
568 TopExp::Vertices(E, V1, V2, Standard_True);
569 myVertices(vertex_id(1,1)) = V1;
570 myVertices(vertex_id(1,2)) = V2;
572 // Init maps vertex->list_of_edges for the face
573 TopTools_IndexedDataMapOfShapeListOfShape M1;
574 MapShapesAndAncestors(myFaces(1), TopAbs_VERTEX, TopAbs_EDGE, M1);
575 if (M1.Extent() != 4) {
576 Standard_TypeMismatch::Raise("The first face of block has wrong number of vertices");
579 // 1.4. Find and store others elements of the first face
581 // edges of the first vertex
582 TopoDS_Shape E1_f = M1.FindFromKey(V1).First();
583 TopoDS_Shape E1_l = M1.FindFromKey(V1).Last();
585 if (E1_f.IsSame(theEdge1)) {
586 myEdges(edge_id(1, 4)) = E1_l;
588 myEdges(edge_id(1, 4)) = E1_f;
592 TopoDS_Edge E4 = TopoDS::Edge(myEdges(edge_id(1, 4)));
593 TopoDS_Vertex V41, V42;
594 TopExp::Vertices(E4, V41, V42, Standard_True);
595 if (V41.IsSame(V1)) {
596 myVertices(vertex_id(1,4)) = V42;
598 myVertices(vertex_id(1,4)) = V41;
601 // edges of the second vertex
602 TopoDS_Shape E2_f = M1.FindFromKey(V2).First();
603 TopoDS_Shape E2_l = M1.FindFromKey(V2).Last();
605 if (E2_f.IsSame(theEdge1)) {
606 myEdges(edge_id(1, 2)) = E2_l;
608 myEdges(edge_id(1, 2)) = E2_f;
612 TopoDS_Edge E2 = TopoDS::Edge(myEdges(edge_id(1, 2)));
613 TopoDS_Vertex V21, V22;
614 TopExp::Vertices(E2, V21, V22, Standard_True);
615 if (V21.IsSame(V2)) {
616 myVertices(vertex_id(1,3)) = V22;
618 myVertices(vertex_id(1,3)) = V21;
621 // 2. Store all other elements of the block
622 InitByBlockAndVertices (theBlock,
623 myVertices(vertex_id(1,1)),
624 myVertices(vertex_id(1,2)),
625 myVertices(vertex_id(1,3)));
628 //=======================================================================
629 //function : InitByBlockAndVertices
631 //=======================================================================
632 void GEOMImpl_Block6Explorer::InitByBlockAndVertices (const TopoDS_Shape& theBlock,
633 const TopoDS_Shape& theVertex1,
634 const TopoDS_Shape& theVertex2,
635 const TopoDS_Shape& theVertex3)
637 // Here we suppose, that vertices are ordered, i.e. exists edge between
638 // theVertex1 and theVertex2 and edge between theVertex2 and theVertex3
640 // 1. Store vertices and edges of the first face.
641 // If the first face is initialized, it means, that this
642 // method is called from another initialization method, and all
643 // vertices and edges of the first face are also initialized
644 if (myFaces(1).IsNull()) {
646 // 1.1. Store first three vertices
647 myVertices(vertex_id(1, 1)) = theVertex1;
648 myVertices(vertex_id(1, 2)) = theVertex2;
649 myVertices(vertex_id(1, 3)) = theVertex3;
651 // 1.2. Find and store the first face
652 TopTools_IndexedDataMapOfShapeListOfShape MVF;
653 MapShapesAndAncestors(theBlock, TopAbs_VERTEX, TopAbs_FACE, MVF);
654 if (MVF.Extent() != NBVERTS) {
655 Standard_TypeMismatch::Raise("Block has wrong number of vertices");
657 const TopTools_ListOfShape& aFacesOfV1 = MVF.FindFromKey(theVertex1);
658 const TopTools_ListOfShape& aFacesOfV3 = MVF.FindFromKey(theVertex3);
660 Standard_Boolean isFound = Standard_False;
661 TopTools_ListIteratorOfListOfShape anIterF1 (aFacesOfV1);
662 for (; anIterF1.More() && !isFound; anIterF1.Next()) {
664 TopTools_ListIteratorOfListOfShape anIterF3 (aFacesOfV3);
665 for (; anIterF3.More() && !isFound; anIterF3.Next()) {
667 if (anIterF1.Value().IsSame(anIterF3.Value())) {
668 isFound = Standard_True;
670 // Store the face, defined by two opposite vertices
671 myFaces(1) = anIterF1.Value();
676 Standard_ConstructionError::Raise
677 ("Vertices 1 and 3 do not belong to one face of the block");
680 // Init maps vertex->list_of_edges for the face
681 TopTools_IndexedDataMapOfShapeListOfShape M1;
682 MapShapesAndAncestors(myFaces(1), TopAbs_VERTEX, TopAbs_EDGE, M1);
683 if (M1.Extent() != 4) {
684 Standard_TypeMismatch::Raise("The first face of block has wrong number of vertices");
687 // 1.3. Find and store edges and last vertex of the first face
688 const TopTools_ListOfShape& anEdgesOfV1 = M1.FindFromKey(theVertex1);
689 const TopTools_ListOfShape& anEdgesOfV2 = M1.FindFromKey(theVertex2);
690 const TopTools_ListOfShape& anEdgesOfV3 = M1.FindFromKey(theVertex3);
692 TopTools_ListIteratorOfListOfShape anIterE2 (anEdgesOfV2);
693 for (; anIterE2.More(); anIterE2.Next()) {
695 TopTools_ListIteratorOfListOfShape anIterE1 (anEdgesOfV1);
696 for (; anIterE1.More(); anIterE1.Next()) {
698 if (anIterE1.Value().IsSame(anIterE2.Value())) {
699 // Store the first edge, defined by two vertices
700 myEdges(edge_id(1,1)) = anIterE1.Value();
703 // Store the last edge
704 myEdges(edge_id(1,4)) = anIterE1.Value();
706 // Find and store the last vertex
707 TopoDS_Edge E = TopoDS::Edge(myEdges(4));
708 TopoDS_Vertex V1, V2;
709 TopExp::Vertices(E, V1, V2, Standard_True);
711 if (V1.IsSame(theVertex1)) {
712 myVertices(vertex_id(1,4)) = V2;
714 myVertices(vertex_id(1,4)) = V1;
719 TopTools_ListIteratorOfListOfShape anIterE3 (anEdgesOfV3);
720 for (; anIterE3.More(); anIterE3.Next()) {
722 if (anIterE3.Value().IsSame(anIterE2.Value())) {
723 // Store the second edge, defined by two vertices
724 myEdges(edge_id(1,2)) = anIterE3.Value();
727 // Store the fird edge
728 myEdges(edge_id(1,3)) = anIterE3.Value();
734 // Init map vertex->list_of_edges for the block
735 TopTools_IndexedDataMapOfShapeListOfShape MB;
736 MapShapesAndAncestors(theBlock, TopAbs_VERTEX, TopAbs_EDGE, MB);
737 if (MB.Extent() != NBVERTS) {
738 Standard_TypeMismatch::Raise("Block has wrong number of vertices");
741 // 2. Store edges, linking the first face with the second one
742 // and vertices of the second face
743 TopTools_IndexedMapOfShape aFaceEdges;
744 TopExp::MapShapes(myFaces(1), TopAbs_EDGE, aFaceEdges);
746 Standard_Integer i = 1;
747 for (; i <= 4; i++) {
748 // Get i-th vertex of the face 1
749 TopoDS_Shape Vi = myVertices(vertex_id(1, i));
750 if (!MB.Contains(Vi)) {
751 Standard_ConstructionError::Raise("Face does not belong to the block");
754 // Get list of block's edges, sharing this Vertex
755 const TopTools_ListOfShape& anEdgesOfVi = MB.FindFromKey(Vi);
756 TopTools_ListIteratorOfListOfShape anEdgesIter (anEdgesOfVi);
758 // Get Edge (from the List), not belonging to the face 1
759 Standard_Boolean isFound = Standard_False;
760 for (; anEdgesIter.More() && !isFound; anEdgesIter.Next()) {
761 if (!aFaceEdges.Contains(anEdgesIter.Value())) {
762 isFound = Standard_True;
764 // Store the linking edge
765 TopoDS_Shape aLinkEdge = anEdgesIter.Value();
766 myEdges(side_edge_id(i)) = aLinkEdge;
768 // Get another vertex of the linking edge
769 TopoDS_Edge E = TopoDS::Edge(aLinkEdge);
770 TopoDS_Vertex V1, V2;
771 TopExp::Vertices(E, V1, V2, Standard_True);
773 // Store the i-th vertex of the second (opposite to the first) face
775 myVertices(vertex_id(2, i)) = V2;
777 myVertices(vertex_id(2, i)) = V1;
783 // 3. Store edges of the second (opposite to the first) face
784 for (i = 1; i <= 4; i++) {
785 // Get i-th and (i+1)-th vertices of the face 2
786 TopoDS_Shape Vi = myVertices(vertex_id(2, i));
787 TopoDS_Shape Vj = myVertices(vertex_id(2, mod4(i + 1)));
789 // Get list of block's edges, sharing Vi
790 const TopTools_ListOfShape& anEdgesOfVi = MB.FindFromKey(Vi);
791 // Get list of block's edges, sharing Vj
792 const TopTools_ListOfShape& anEdgesOfVj = MB.FindFromKey(Vj);
794 // Get Edge (from the List), linking this vertex with the next one
795 Standard_Boolean isFound = Standard_False;
796 TopTools_ListIteratorOfListOfShape anEdgesIteri (anEdgesOfVi);
797 for (; anEdgesIteri.More() && !isFound; anEdgesIteri.Next()) {
799 TopTools_ListIteratorOfListOfShape anEdgesIterj (anEdgesOfVj);
800 for (; anEdgesIterj.More() && !isFound; anEdgesIterj.Next()) {
802 if (anEdgesIteri.Value().IsSame(anEdgesIterj.Value())) {
803 isFound = Standard_True;
805 // Store the linking edge
806 myEdges(edge_id(2, i)) = anEdgesIteri.Value();
812 // 4. Store faces of the block
813 TopTools_IndexedDataMapOfShapeListOfShape MBE;
814 MapShapesAndAncestors(theBlock, TopAbs_EDGE, TopAbs_FACE, MBE);
815 if (MBE.Extent() != NBEDGES) {
816 Standard_TypeMismatch::Raise("Block has wrong number of edges");
819 for (i = 2; i <= NBFACES; i++) {
820 TopoDS_Shape Ei1 = myEdges(edge_id(i, 1));
821 TopoDS_Shape Ei2 = myEdges(edge_id(i, 2));
822 const TopTools_ListOfShape& aFacesOfEi1 = MBE.FindFromKey(Ei1);
823 const TopTools_ListOfShape& aFacesOfEi2 = MBE.FindFromKey(Ei2);
825 Standard_Boolean isFound = Standard_False;
826 TopTools_ListIteratorOfListOfShape anIterEi1 (aFacesOfEi1);
827 for (; anIterEi1.More() && !isFound; anIterEi1.Next()) {
829 TopTools_ListIteratorOfListOfShape anIterEi2 (aFacesOfEi2);
830 for (; anIterEi2.More() && !isFound; anIterEi2.Next()) {
832 if (anIterEi1.Value().IsSame(anIterEi2.Value())) {
833 isFound = Standard_True;
835 // Store the face, defined by two edges
836 myFaces(i) = anIterEi1.Value();
843 //=======================================================================
844 //function : InitByTwoFaces
846 //=======================================================================
847 void GEOMImpl_Block6Explorer::InitByTwoFaces (const TopoDS_Shape& theFace1,
848 const TopoDS_Shape& theFace2)
850 if (theFace1.IsSame(theFace2)) {
851 Standard_ConstructionError::Raise("The faces must be different");
854 // Add two given faces in the structure
855 myFaces(1) = theFace1;
856 myFaces(2) = theFace2;
858 // Step 1. Order vertices (and edges)
860 // 1.1. Ordered vertices and edges of the first face we put in <myVertices>
862 // Get wire of the first face
863 TopExp_Explorer wires1 (myFaces(1), TopAbs_WIRE);
864 if (!wires1.More()) {
865 Standard_ConstructionError::Raise("A face for the block has no wires");
867 TopoDS_Shape aWire1 = wires1.Current();
870 Standard_ConstructionError::Raise("A face for the block has more than one wire");
873 BRepTools_WireExplorer aWE1 (TopoDS::Wire(aWire1), TopoDS::Face(myFaces(1)));
875 for (nb = 1; aWE1.More(); aWE1.Next(), nb++) {
877 Standard_ConstructionError::Raise("A face for the block has more than four edges");
879 myEdges(edge_id(1, nb)) = aWE1.Current();
880 myVertices(vertex_id(1, nb)) = aWE1.CurrentVertex();
883 Standard_ConstructionError::Raise("A face for the block has less than four edges");
886 // 1.2. Ordered vertices and edges of the second face we temporarily store
887 // in arrays, to find for them rigth location in <myVertices> on the Step 2.
890 TopTools_Array1OfShape aVertis2(1,4); // ordered vertices of the second face
891 TopTools_Array1OfShape anEdges2(1,4); // anEdges2(i) links aVertis2(i) and aVertis2(i+1)
893 // Get wire of the second face
894 TopExp_Explorer wires2 (myFaces(2), TopAbs_WIRE);
895 if (!wires2.More()) {
896 Standard_ConstructionError::Raise("A face for the block has no wires");
898 TopoDS_Shape aWire2 = wires2.Current();
901 Standard_ConstructionError::Raise("A face for the block has more than one wire");
904 BRepTools_WireExplorer aWE2 (TopoDS::Wire(aWire2), TopoDS::Face(myFaces(2)));
905 for (nb = 1; aWE2.More(); aWE2.Next(), nb++) {
907 Standard_ConstructionError::Raise("A face for the block has more than four edges");
909 anEdges2(nb) = aWE2.Current();
910 aVertis2(nb) = aWE2.CurrentVertex();
913 Standard_ConstructionError::Raise("A face for the block has less than four edges");
916 // Step 2. Find right place in <myVertices> for the <aVertis2>,
917 // so as to minimize common length of linking edges
918 // between face 1 and face 2.
919 // Each linking edge (of four) will link vertices of the
920 // faces 1 and 2 with equal local numbers.
921 // The right place is defined by:
922 // - vertex <aVertis2(i_min)>, which will become the first vertex
923 // of the second face <myVertices(vertex_id(2,1))>
924 // - orientation of <aVertis2> relatively their future location
925 // in <myVertices> (s_min = 1 if direct, s_min = -1 if reversed)
926 Standard_Integer i_min = 0, s_min = 0;
928 TColgp_Array1OfPnt aPnts1 (1,4); // points of the first face
929 aPnts1(1) = BRep_Tool::Pnt(TopoDS::Vertex(myVertices(vertex_id(1, 1))));
930 aPnts1(2) = BRep_Tool::Pnt(TopoDS::Vertex(myVertices(vertex_id(1, 2))));
931 aPnts1(3) = BRep_Tool::Pnt(TopoDS::Vertex(myVertices(vertex_id(1, 3))));
932 aPnts1(4) = BRep_Tool::Pnt(TopoDS::Vertex(myVertices(vertex_id(1, 4))));
934 TColgp_Array1OfPnt aPnts2 (1,4); // points of the second face
935 aPnts2(1) = BRep_Tool::Pnt(TopoDS::Vertex(aVertis2(1)));
936 aPnts2(2) = BRep_Tool::Pnt(TopoDS::Vertex(aVertis2(2)));
937 aPnts2(3) = BRep_Tool::Pnt(TopoDS::Vertex(aVertis2(3)));
938 aPnts2(4) = BRep_Tool::Pnt(TopoDS::Vertex(aVertis2(4)));
940 Standard_Real Dist_min = RealLast();
941 // try all possible locations to find the best (with minimum sum distance)
942 Standard_Integer i = 1;
943 for (; i <= 4; i++) {
944 // try direct orientation
945 Standard_Real Dist_plus = aPnts1(1).Distance(aPnts2(i)) +
946 aPnts1(2).Distance(aPnts2(mod4(i + 1))) +
947 aPnts1(3).Distance(aPnts2(mod4(i + 2))) +
948 aPnts1(4).Distance(aPnts2(mod4(i + 3)));
949 if (Dist_plus < Dist_min) {
950 Dist_min = Dist_plus;
955 // try reversed orientation
956 Standard_Real Dist_minus = aPnts1(1).Distance(aPnts2(i)) +
957 aPnts1(2).Distance(aPnts2(mod4(i - 1))) +
958 aPnts1(3).Distance(aPnts2(mod4(i - 2))) +
959 aPnts1(4).Distance(aPnts2(mod4(i - 3)));
960 if (Dist_minus < Dist_min) {
961 Dist_min = Dist_minus;
967 // 3. Put vertices and edges of the second face to they
968 // permanent location in <myVertices> and <myEdges>
969 for (i = 1; i <= 4; i++) {
970 Standard_Integer nb = mod4(i_min + s_min*(i - 1));
972 if (aPnts1(i).Distance(aPnts2(nb)) < Precision::Confusion()) {
973 Standard_ConstructionError::Raise("The faces are too close");
976 myVertices(vertex_id(2, i)) = aVertis2(nb);
978 if (s_min == -1) nb = mod4(nb - 1);
979 myEdges(edge_id(2, i)) = anEdges2(nb);
982 // 4. Generate side surface
983 if (!aWire1.Closed() || !aWire2.Closed()) {
984 // BRepOffsetAPI_ThruSections is not applicable on not closed wires
985 GetFace(3, Standard_True);
986 GetFace(4, Standard_True);
987 GetFace(5, Standard_True);
988 GetFace(6, Standard_True);
990 // try to build faces on native surfaces of edges or planar
991 Standard_Boolean tryThru = Standard_False;
992 for (Standard_Integer i = 3; i <= 6 && !tryThru; i++) {
993 Standard_Boolean doMake = Standard_True;
994 TopoDS_Shape E1 = GetEdge(edge_id(i, 1), doMake);
995 TopoDS_Shape E2 = GetEdge(edge_id(i, 2), doMake);
996 TopoDS_Shape E3 = GetEdge(edge_id(i, 3), doMake);
997 TopoDS_Shape E4 = GetEdge(edge_id(i, 4), doMake);
999 BRepBuilderAPI_MakeWire MW (TopoDS::Edge(E1),
1004 Standard_ConstructionError::Raise("Wire construction failed");
1007 BRepBuilderAPI_MakeFace MF (MW, Standard_False);
1009 myFaces(i) = MF.Shape();
1011 tryThru = Standard_True;
1015 // Build side surface by ThruSections algorithm
1017 BRepOffsetAPI_ThruSections THS;
1018 THS.AddWire(TopoDS::Wire(aWire1));
1019 THS.AddWire(TopoDS::Wire(aWire2));
1021 if (!THS.IsDone()) {
1022 StdFail_NotDone::Raise("Side surface generation failed");
1024 for (Standard_Integer i = 1; i <= 4; i++) {
1026 myFaces(i+2) = THS.GeneratedFace(myEdges(i));
1029 Standard_Integer ee = side_edge_id(i);
1030 TopTools_IndexedDataMapOfShapeListOfShape MVE;
1031 MapShapesAndAncestors(myFaces(i+2), TopAbs_VERTEX, TopAbs_EDGE, MVE);
1032 FindEdge(myEdges(ee),
1033 myVertices(vertex_id_edge(ee, 1)),
1034 myVertices(vertex_id_edge(ee, 2)),
1041 //=======================================================================
1042 //function : MapShapesAndAncestors
1044 //=======================================================================
1045 void GEOMImpl_Block6Explorer::MapShapesAndAncestors (const TopoDS_Shape& S,
1046 const TopAbs_ShapeEnum TS,
1047 const TopAbs_ShapeEnum TA,
1048 TopTools_IndexedDataMapOfShapeListOfShape& M)
1050 TopTools_ListOfShape empty;
1051 TopTools_MapOfShape mapA;
1054 TopExp_Explorer exa (S,TA);
1055 for (; exa.More(); exa.Next()) {
1057 const TopoDS_Shape& anc = exa.Current();
1058 if (mapA.Add(anc)) {
1059 TopExp_Explorer exs (anc,TS);
1060 TopTools_MapOfShape mapS;
1061 for (; exs.More(); exs.Next()) {
1062 if (mapS.Add(exs.Current())) {
1063 Standard_Integer index = M.FindIndex(exs.Current());
1064 if (index == 0) index = M.Add(exs.Current(),empty);
1065 M(index).Append(anc);
1071 // visit shapes not under ancestors
1072 TopExp_Explorer ex (S,TS,TA);
1073 for (; ex.More(); ex.Next()) {
1074 Standard_Integer index = M.FindIndex(ex.Current());
1075 if (index == 0) index = M.Add(ex.Current(),empty);
1079 //=======================================================================
1080 //function : IsSimilarEdges
1082 //=======================================================================
1083 Standard_Boolean GEOMImpl_Block6Explorer::IsSimilarEdges (const TopoDS_Shape& E1,
1084 const TopoDS_Shape& E2)
1086 TopoDS_Edge E1e = TopoDS::Edge(E1);
1087 TopoDS_Edge E2e = TopoDS::Edge(E2);
1088 TopoDS_Vertex V11, V12, V21, V22;
1089 TopExp::Vertices(E1e, V11, V12, Standard_True);
1090 TopExp::Vertices(E2e, V21, V22, Standard_True);
1091 if (BRepTools::Compare(V11, V21) && BRepTools::Compare(V12, V22))
1092 return Standard_True;
1093 if (BRepTools::Compare(V11, V22) && BRepTools::Compare(V12, V21))
1094 return Standard_True;
1096 return Standard_False;
1099 //=======================================================================
1100 //function : FindEdge
1102 //=======================================================================
1103 Standard_Integer GEOMImpl_Block6Explorer::FindEdge
1104 (TopoDS_Shape& theResult,
1105 const TopoDS_Shape& V1,
1106 const TopoDS_Shape& V2,
1107 const TopTools_IndexedDataMapOfShapeListOfShape& MVE,
1108 const Standard_Boolean findAll)
1110 Standard_Integer isFound = 0;
1112 const TopTools_ListOfShape& anEdgesOfV1 = MVE.FindFromKey(V1);
1113 const TopTools_ListOfShape& anEdgesOfV2 = MVE.FindFromKey(V2);
1115 TopTools_ListIteratorOfListOfShape it1 (anEdgesOfV1);
1116 for (; it1.More(); it1.Next()) {
1117 TopTools_ListIteratorOfListOfShape it2 (anEdgesOfV2);
1118 for (; it2.More(); it2.Next()) {
1119 if (it1.Value().IsSame(it2.Value())) {
1121 theResult = it1.Value();
1122 if (!findAll) return isFound;
1130 //=======================================================================
1131 //function : FindFace
1133 //=======================================================================
1134 Standard_Integer GEOMImpl_Block6Explorer::FindFace
1135 (TopoDS_Shape& theResult,
1136 const TopoDS_Shape& V1,
1137 const TopoDS_Shape& V2,
1138 const TopoDS_Shape& V3,
1139 const TopoDS_Shape& V4,
1140 const TopTools_IndexedDataMapOfShapeListOfShape& MVF,
1141 const Standard_Boolean findAll)
1143 Standard_Integer isFound = Standard_False;
1145 const TopTools_ListOfShape& aFacesOfV1 = MVF.FindFromKey(V1);
1146 const TopTools_ListOfShape& aFacesOfV2 = MVF.FindFromKey(V2);
1147 const TopTools_ListOfShape& aFacesOfV3 = MVF.FindFromKey(V3);
1148 const TopTools_ListOfShape& aFacesOfV4 = MVF.FindFromKey(V4);
1150 TopTools_ListIteratorOfListOfShape it1 (aFacesOfV1);
1151 for (; it1.More(); it1.Next()) {
1152 TopTools_ListIteratorOfListOfShape it2 (aFacesOfV2);
1153 for (; it2.More(); it2.Next()) {
1154 if (it1.Value().IsSame(it2.Value())) {
1155 TopTools_ListIteratorOfListOfShape it3 (aFacesOfV3);
1156 for (; it3.More(); it3.Next()) {
1157 if (it1.Value().IsSame(it3.Value())) {
1158 TopTools_ListIteratorOfListOfShape it4 (aFacesOfV4);
1159 for (; it4.More(); it4.Next()) {
1160 if (it1.Value().IsSame(it4.Value())) {
1162 theResult = it1.Value();
1163 if (!findAll) return isFound;
1175 //=======================================================================
1176 //function : MakeFace
1178 //=======================================================================
1179 void GEOMImpl_Block6Explorer::MakeFace (const TopoDS_Wire& theWire,
1180 const Standard_Boolean isPlanarWanted,
1181 TopoDS_Shape& theResult)
1183 // try to build face on plane or on any surface under the edges of the wire
1184 BRepBuilderAPI_MakeFace MK (theWire, isPlanarWanted);
1186 theResult = MK.Shape();
1190 if (!isPlanarWanted) {
1191 // try to construct filling surface
1192 BRepOffsetAPI_MakeFilling MF;
1194 Standard_Integer nbEdges = 0;
1195 BRepTools_WireExplorer aWE (theWire);
1196 for (; aWE.More(); aWE.Next(), nbEdges++) {
1197 MF.Add(TopoDS::Edge(aWE.Current()), GeomAbs_C0);
1202 // Result of filling
1203 TopoDS_Shape aFace = MF.Shape();
1206 Standard_Real aTol = MF.G0Error();
1208 TColgp_Array1OfPnt aPnts (1,nbEdges); // points of the given wire
1209 BRepTools_WireExplorer aWE1 (theWire);
1210 Standard_Integer vi = 1;
1211 for (; aWE1.More() && vi <= nbEdges; aWE1.Next(), vi++) {
1212 aPnts(vi) = BRep_Tool::Pnt(TopoDS::Vertex(aWE1.CurrentVertex()));
1215 // Find maximum deviation in vertices
1216 TopExp_Explorer exp (aFace, TopAbs_VERTEX);
1217 TopTools_MapOfShape mapShape;
1218 for (; exp.More(); exp.Next()) {
1219 if (mapShape.Add(exp.Current())) {
1220 TopoDS_Vertex aV = TopoDS::Vertex(exp.Current());
1221 Standard_Real aTolV = BRep_Tool::Tolerance(aV);
1222 gp_Pnt aP = BRep_Tool::Pnt(aV);
1223 Standard_Real min_dist = aP.Distance(aPnts(1));
1224 for (vi = 2; vi <= nbEdges; vi++) {
1225 min_dist = Min(min_dist, aP.Distance(aPnts(vi)));
1227 aTol = Max(aTol, aTolV);
1228 aTol = Max(aTol, min_dist);
1232 if ((*((Handle(BRep_TFace)*)&aFace.TShape()))->Tolerance() < aTol) {
1233 (*((Handle(BRep_TFace)*)&aFace.TShape()))->Tolerance(aTol);
1238 // try to update wire tolerances to build a planar face
1240 // With OCCT6.0 or lower
1243 Standard_Real aToleranceReached, aTol;
1244 BRepLib_FindSurface aFS;
1245 aFS.Init(theWire, -1., isPlanarWanted);
1246 aToleranceReached = aFS.ToleranceReached();
1247 aTol = aFS.Tolerance();
1250 aFS.Init(theWire, aToleranceReached, isPlanarWanted);
1251 if (!aFS.Found()) return;
1252 aToleranceReached = aFS.ToleranceReached();
1253 aTol = aFS.Tolerance();
1255 aTol = Max(1.2 * aToleranceReached, aTol);
1257 // Copy the wire, bacause it can be updated with very-very big tolerance here
1258 BRepBuilderAPI_Copy aMC (theWire);
1259 if (!aMC.IsDone()) return;
1260 TopoDS_Wire aWire = TopoDS::Wire(aMC.Shape());
1261 // Update tolerances to <aTol>
1263 for (TopExp_Explorer expE (aWire, TopAbs_EDGE); expE.More(); expE.Next()) {
1264 TopoDS_Edge anE = TopoDS::Edge(expE.Current());
1265 B.UpdateEdge(anE, aTol);
1267 for (TopExp_Explorer expV (aWire, TopAbs_VERTEX); expV.More(); expV.Next()) {
1268 TopoDS_Vertex aV = TopoDS::Vertex(expV.Current());
1269 B.UpdateVertex(aV, aTol);
1271 //BRepLib::UpdateTolerances(aWire);
1273 BRepBuilderAPI_MakeFace MK1 (aWire, isPlanarWanted);
1275 theResult = MK1.Shape();
1279 // After migration on OCCT version higher than 6.0
1280 //BRepLib_MakeFace aBMF;
1281 //aBMF.Init(theWire, isPlanarWanted, Standard_True);
1282 //if (aBMF.Error() == BRepLib_FaceDone) {
1283 // theResult = aBMF.Shape();