1 // SMESH SMDS : implementaion of Salome mesh data structure
3 // Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
23 #pragma warning(disable:4786)
26 #include "utilities.h"
27 #include "SMDS_Mesh.hxx"
28 #include "SMDS_VolumeOfNodes.hxx"
29 #include "SMDS_VolumeOfFaces.hxx"
30 #include "SMDS_FaceOfNodes.hxx"
31 #include "SMDS_FaceOfEdges.hxx"
32 #include "SMDS_PolyhedralVolumeOfNodes.hxx"
33 #include "SMDS_PolygonalFaceOfNodes.hxx"
34 #include "SMDS_QuadraticEdge.hxx"
35 #include "SMDS_QuadraticFaceOfNodes.hxx"
36 #include "SMDS_QuadraticVolumeOfNodes.hxx"
43 #include <sys/sysinfo.h>
47 //================================================================================
49 * \brief Raise an exception if free memory (ram+swap) too low
50 * \param doNotRaise - if true, suppres exception, just return free memory size
51 * \retval int - amount of available memory in MB or negative number in failure case
53 //================================================================================
55 int SMDS_Mesh::CheckMemory(const bool doNotRaise) throw (std::bad_alloc)
59 int err = sysinfo( &si );
63 static int limit = -1;
65 int status = system("SMDS_MemoryLimit"); // it returns lower limit of free RAM
67 limit = WEXITSTATUS(status);
72 limit = int( limit * 1.5 );
74 cout << "SMDS_Mesh::CheckMemory() memory limit = " << limit << " MB" << endl;
78 const unsigned long Mbyte = 1024 * 1024;
79 // compute separately to avoid overflow
81 ( si.freeram * si.mem_unit ) / Mbyte +
82 ( si.freeswap * si.mem_unit ) / Mbyte;
85 return freeMb - limit;
90 cout<<"SMDS_Mesh::CheckMemory() throws as free memory too low: " << freeMb <<" MB" << endl;
92 throw std::bad_alloc();
98 ///////////////////////////////////////////////////////////////////////////////
99 /// Create a new mesh object
100 ///////////////////////////////////////////////////////////////////////////////
101 SMDS_Mesh::SMDS_Mesh()
103 myNodeIDFactory(new SMDS_MeshElementIDFactory()),
104 myElementIDFactory(new SMDS_MeshElementIDFactory()),
105 myHasConstructionEdges(false), myHasConstructionFaces(false),
106 myHasInverseElements(true)
110 ///////////////////////////////////////////////////////////////////////////////
111 /// Create a new child mesh
112 /// Note that the tree structure of SMDS_Mesh seems to be unused in this version
113 /// (2003-09-08) of SMESH
114 ///////////////////////////////////////////////////////////////////////////////
115 SMDS_Mesh::SMDS_Mesh(SMDS_Mesh * parent)
116 :myParent(parent), myNodeIDFactory(parent->myNodeIDFactory),
117 myElementIDFactory(parent->myElementIDFactory),
118 myHasConstructionEdges(false), myHasConstructionFaces(false),
119 myHasInverseElements(true)
123 ///////////////////////////////////////////////////////////////////////////////
124 ///Create a submesh and add it to the current mesh
125 ///////////////////////////////////////////////////////////////////////////////
127 SMDS_Mesh *SMDS_Mesh::AddSubMesh()
129 SMDS_Mesh *submesh = new SMDS_Mesh(this);
130 myChildren.insert(myChildren.end(), submesh);
134 ///////////////////////////////////////////////////////////////////////////////
135 ///create a MeshNode and add it to the current Mesh
136 ///An ID is automatically assigned to the node.
137 ///@return : The created node
138 ///////////////////////////////////////////////////////////////////////////////
140 SMDS_MeshNode * SMDS_Mesh::AddNode(double x, double y, double z)
142 return SMDS_Mesh::AddNodeWithID(x,y,z,myNodeIDFactory->GetFreeID());
145 ///////////////////////////////////////////////////////////////////////////////
146 ///create a MeshNode and add it to the current Mesh
147 ///@param ID : The ID of the MeshNode to create
148 ///@return : The created node or NULL if a node with this ID already exists
149 ///////////////////////////////////////////////////////////////////////////////
150 SMDS_MeshNode * SMDS_Mesh::AddNodeWithID(double x, double y, double z, int ID)
152 // find the MeshNode corresponding to ID
153 const SMDS_MeshElement *node = myNodeIDFactory->MeshElement(ID);
156 SMDS_MeshNode * node=new SMDS_MeshNode(x, y, z);
158 myNodeIDFactory->BindID(ID,node);
165 ///////////////////////////////////////////////////////////////////////////////
166 /// create a MeshEdge and add it to the current Mesh
167 /// @return : The created MeshEdge
168 ///////////////////////////////////////////////////////////////////////////////
170 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(int idnode1, int idnode2, int ID)
172 SMDS_MeshNode * node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
173 SMDS_MeshNode * node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
174 if(!node1 || !node2) return NULL;
175 return SMDS_Mesh::AddEdgeWithID(node1, node2, ID);
178 ///////////////////////////////////////////////////////////////////////////////
179 /// create a MeshEdge and add it to the current Mesh
180 /// @return : The created MeshEdge
181 ///////////////////////////////////////////////////////////////////////////////
183 SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode * node1,
184 const SMDS_MeshNode * node2)
186 return SMDS_Mesh::AddEdgeWithID(node1, node2, myElementIDFactory->GetFreeID());
189 ///////////////////////////////////////////////////////////////////////////////
190 /// Create a new edge and at it to the mesh
191 /// @param idnode1 ID of the first node
192 /// @param idnode2 ID of the second node
193 /// @param ID ID of the edge to create
194 /// @return The created edge or NULL if an element with this ID already exists or
195 /// if input nodes are not found.
196 ///////////////////////////////////////////////////////////////////////////////
198 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(const SMDS_MeshNode * n1,
199 const SMDS_MeshNode * n2,
202 if ( !n1 || !n2 ) return 0;
205 SMDS_MeshEdge * edge=new SMDS_MeshEdge(n1,n2);
206 if(myElementIDFactory->BindID(ID, edge)) {
207 SMDS_MeshNode *node1,*node2;
208 node1=const_cast<SMDS_MeshNode*>(n1);
209 node2=const_cast<SMDS_MeshNode*>(n2);
210 node1->AddInverseElement(edge);
211 node2->AddInverseElement(edge);
222 ///////////////////////////////////////////////////////////////////////////////
223 /// Add a triangle defined by its nodes. An ID is automatically affected to the
225 ///////////////////////////////////////////////////////////////////////////////
227 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
228 const SMDS_MeshNode * n2,
229 const SMDS_MeshNode * n3)
231 return SMDS_Mesh::AddFaceWithID(n1,n2,n3, myElementIDFactory->GetFreeID());
234 ///////////////////////////////////////////////////////////////////////////////
235 /// Add a triangle defined by its nodes IDs
236 ///////////////////////////////////////////////////////////////////////////////
238 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int idnode1, int idnode2, int idnode3, int ID)
240 SMDS_MeshNode * node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
241 SMDS_MeshNode * node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
242 SMDS_MeshNode * node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
243 if(!node1 || !node2 || !node3) return NULL;
244 return SMDS_Mesh::AddFaceWithID(node1, node2, node3, ID);
247 ///////////////////////////////////////////////////////////////////////////////
248 /// Add a triangle defined by its nodes
249 ///////////////////////////////////////////////////////////////////////////////
251 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
252 const SMDS_MeshNode * n2,
253 const SMDS_MeshNode * n3,
256 SMDS_MeshFace * face=createTriangle(n1, n2, n3);
258 if (face && !registerElement(ID, face)) {
259 RemoveElement(face, false);
265 ///////////////////////////////////////////////////////////////////////////////
266 /// Add a quadrangle defined by its nodes. An ID is automatically affected to the
268 ///////////////////////////////////////////////////////////////////////////////
270 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
271 const SMDS_MeshNode * n2,
272 const SMDS_MeshNode * n3,
273 const SMDS_MeshNode * n4)
275 return SMDS_Mesh::AddFaceWithID(n1,n2,n3, n4, myElementIDFactory->GetFreeID());
278 ///////////////////////////////////////////////////////////////////////////////
279 /// Add a quadrangle defined by its nodes IDs
280 ///////////////////////////////////////////////////////////////////////////////
282 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int idnode1,
288 SMDS_MeshNode *node1, *node2, *node3, *node4;
289 node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
290 node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
291 node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
292 node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
293 if(!node1 || !node2 || !node3 || !node4) return NULL;
294 return SMDS_Mesh::AddFaceWithID(node1, node2, node3, node4, ID);
297 ///////////////////////////////////////////////////////////////////////////////
298 /// Add a quadrangle defined by its nodes
299 ///////////////////////////////////////////////////////////////////////////////
301 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
302 const SMDS_MeshNode * n2,
303 const SMDS_MeshNode * n3,
304 const SMDS_MeshNode * n4,
307 SMDS_MeshFace * face=createQuadrangle(n1, n2, n3, n4);
309 if (face && !registerElement(ID, face)) {
310 RemoveElement(face, false);
316 ///////////////////////////////////////////////////////////////////////////////
317 /// Add a triangle defined by its edges. An ID is automatically assigned to the
319 ///////////////////////////////////////////////////////////////////////////////
321 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshEdge * e1,
322 const SMDS_MeshEdge * e2,
323 const SMDS_MeshEdge * e3)
325 if (!hasConstructionEdges())
327 return AddFaceWithID(e1,e2,e3, myElementIDFactory->GetFreeID());
330 ///////////////////////////////////////////////////////////////////////////////
331 /// Add a triangle defined by its edges
332 ///////////////////////////////////////////////////////////////////////////////
334 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshEdge * e1,
335 const SMDS_MeshEdge * e2,
336 const SMDS_MeshEdge * e3,
339 if (!hasConstructionEdges())
341 if ( !e1 || !e2 || !e3 ) return 0;
344 SMDS_MeshFace * face = new SMDS_FaceOfEdges(e1,e2,e3);
346 myInfo.myNbTriangles++;
348 if (!registerElement(ID, face)) {
349 RemoveElement(face, false);
355 ///////////////////////////////////////////////////////////////////////////////
356 /// Add a quadrangle defined by its edges. An ID is automatically assigned to the
358 ///////////////////////////////////////////////////////////////////////////////
360 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshEdge * e1,
361 const SMDS_MeshEdge * e2,
362 const SMDS_MeshEdge * e3,
363 const SMDS_MeshEdge * e4)
365 if (!hasConstructionEdges())
367 return AddFaceWithID(e1,e2,e3,e4, myElementIDFactory->GetFreeID());
370 ///////////////////////////////////////////////////////////////////////////////
371 /// Add a quadrangle defined by its edges
372 ///////////////////////////////////////////////////////////////////////////////
374 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshEdge * e1,
375 const SMDS_MeshEdge * e2,
376 const SMDS_MeshEdge * e3,
377 const SMDS_MeshEdge * e4,
380 if (!hasConstructionEdges())
382 if ( !e1 || !e2 || !e3 || !e4 ) return 0;
384 SMDS_MeshFace * face = new SMDS_FaceOfEdges(e1,e2,e3,e4);
386 myInfo.myNbQuadrangles++;
388 if (!registerElement(ID, face))
390 RemoveElement(face, false);
396 ///////////////////////////////////////////////////////////////////////////////
397 ///Create a new tetrahedron and add it to the mesh.
398 ///@return The created tetrahedron
399 ///////////////////////////////////////////////////////////////////////////////
401 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
402 const SMDS_MeshNode * n2,
403 const SMDS_MeshNode * n3,
404 const SMDS_MeshNode * n4)
406 int ID = myElementIDFactory->GetFreeID();
407 SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, ID);
408 if(v==NULL) myElementIDFactory->ReleaseID(ID);
412 ///////////////////////////////////////////////////////////////////////////////
413 ///Create a new tetrahedron and add it to the mesh.
414 ///@param ID The ID of the new volume
415 ///@return The created tetrahedron or NULL if an element with this ID already exists
416 ///or if input nodes are not found.
417 ///////////////////////////////////////////////////////////////////////////////
419 SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
425 SMDS_MeshNode *node1, *node2, *node3, *node4;
426 node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
427 node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
428 node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
429 node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
430 if(!node1 || !node2 || !node3 || !node4) return NULL;
431 return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, ID);
434 ///////////////////////////////////////////////////////////////////////////////
435 ///Create a new tetrahedron and add it to the mesh.
436 ///@param ID The ID of the new volume
437 ///@return The created tetrahedron
438 ///////////////////////////////////////////////////////////////////////////////
440 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
441 const SMDS_MeshNode * n2,
442 const SMDS_MeshNode * n3,
443 const SMDS_MeshNode * n4,
446 SMDS_MeshVolume* volume = 0;
447 if ( !n1 || !n2 || !n3 || !n4) return volume;
449 if(hasConstructionFaces()) {
450 SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3);
451 SMDS_MeshFace * f2=FindFaceOrCreate(n1,n2,n4);
452 SMDS_MeshFace * f3=FindFaceOrCreate(n1,n3,n4);
453 SMDS_MeshFace * f4=FindFaceOrCreate(n2,n3,n4);
454 volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4);
455 myVolumes.Add(volume);
458 else if(hasConstructionEdges()) {
459 MESSAGE("Error : Not implemented");
463 volume=new SMDS_VolumeOfNodes(n1,n2,n3,n4);
464 myVolumes.Add(volume);
468 if (!registerElement(ID, volume)) {
469 RemoveElement(volume, false);
475 ///////////////////////////////////////////////////////////////////////////////
476 ///Create a new pyramid and add it to the mesh.
477 ///Nodes 1,2,3 and 4 define the base of the pyramid
478 ///@return The created pyramid
479 ///////////////////////////////////////////////////////////////////////////////
481 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
482 const SMDS_MeshNode * n2,
483 const SMDS_MeshNode * n3,
484 const SMDS_MeshNode * n4,
485 const SMDS_MeshNode * n5)
487 int ID = myElementIDFactory->GetFreeID();
488 SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, ID);
489 if(v==NULL) myElementIDFactory->ReleaseID(ID);
493 ///////////////////////////////////////////////////////////////////////////////
494 ///Create a new pyramid and add it to the mesh.
495 ///Nodes 1,2,3 and 4 define the base of the pyramid
496 ///@param ID The ID of the new volume
497 ///@return The created pyramid or NULL if an element with this ID already exists
498 ///or if input nodes are not found.
499 ///////////////////////////////////////////////////////////////////////////////
501 SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
508 SMDS_MeshNode *node1, *node2, *node3, *node4, *node5;
509 node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
510 node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
511 node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
512 node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
513 node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
514 if(!node1 || !node2 || !node3 || !node4 || !node5) return NULL;
515 return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, ID);
518 ///////////////////////////////////////////////////////////////////////////////
519 ///Create a new pyramid and add it to the mesh.
520 ///Nodes 1,2,3 and 4 define the base of the pyramid
521 ///@param ID The ID of the new volume
522 ///@return The created pyramid
523 ///////////////////////////////////////////////////////////////////////////////
525 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
526 const SMDS_MeshNode * n2,
527 const SMDS_MeshNode * n3,
528 const SMDS_MeshNode * n4,
529 const SMDS_MeshNode * n5,
532 SMDS_MeshVolume* volume = 0;
533 if ( !n1 || !n2 || !n3 || !n4 || !n5) return volume;
535 if(hasConstructionFaces()) {
536 SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3,n4);
537 SMDS_MeshFace * f2=FindFaceOrCreate(n1,n2,n5);
538 SMDS_MeshFace * f3=FindFaceOrCreate(n2,n3,n5);
539 SMDS_MeshFace * f4=FindFaceOrCreate(n3,n4,n5);
540 volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4);
541 myVolumes.Add(volume);
542 myInfo.myNbPyramids++;
544 else if(hasConstructionEdges()) {
545 MESSAGE("Error : Not implemented");
549 volume=new SMDS_VolumeOfNodes(n1,n2,n3,n4,n5);
550 myVolumes.Add(volume);
551 myInfo.myNbPyramids++;
554 if (!registerElement(ID, volume)) {
555 RemoveElement(volume, false);
561 ///////////////////////////////////////////////////////////////////////////////
562 ///Create a new prism and add it to the mesh.
563 ///Nodes 1,2,3 is a triangle and 1,2,5,4 a quadrangle.
564 ///@return The created prism
565 ///////////////////////////////////////////////////////////////////////////////
567 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
568 const SMDS_MeshNode * n2,
569 const SMDS_MeshNode * n3,
570 const SMDS_MeshNode * n4,
571 const SMDS_MeshNode * n5,
572 const SMDS_MeshNode * n6)
574 int ID = myElementIDFactory->GetFreeID();
575 SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, ID);
576 if(v==NULL) myElementIDFactory->ReleaseID(ID);
580 ///////////////////////////////////////////////////////////////////////////////
581 ///Create a new prism and add it to the mesh.
582 ///Nodes 1,2,3 is a triangle and 1,2,5,4 a quadrangle.
583 ///@param ID The ID of the new volume
584 ///@return The created prism or NULL if an element with this ID already exists
585 ///or if input nodes are not found.
586 ///////////////////////////////////////////////////////////////////////////////
588 SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
596 SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6;
597 node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
598 node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
599 node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
600 node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
601 node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
602 node6 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode6);
603 if(!node1 || !node2 || !node3 || !node4 || !node5 || !node6) return NULL;
604 return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, node6, ID);
607 ///////////////////////////////////////////////////////////////////////////////
608 ///Create a new prism and add it to the mesh.
609 ///Nodes 1,2,3 is a triangle and 1,2,5,4 a quadrangle.
610 ///@param ID The ID of the new volume
611 ///@return The created prism
612 ///////////////////////////////////////////////////////////////////////////////
614 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
615 const SMDS_MeshNode * n2,
616 const SMDS_MeshNode * n3,
617 const SMDS_MeshNode * n4,
618 const SMDS_MeshNode * n5,
619 const SMDS_MeshNode * n6,
622 SMDS_MeshVolume* volume = 0;
623 if ( !n1 || !n2 || !n3 || !n4 || !n5 || !n6) return volume;
625 if(hasConstructionFaces()) {
626 SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3);
627 SMDS_MeshFace * f2=FindFaceOrCreate(n4,n5,n6);
628 SMDS_MeshFace * f3=FindFaceOrCreate(n1,n4,n5,n2);
629 SMDS_MeshFace * f4=FindFaceOrCreate(n2,n5,n6,n3);
630 SMDS_MeshFace * f5=FindFaceOrCreate(n3,n6,n4,n1);
631 volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5);
632 myVolumes.Add(volume);
635 else if(hasConstructionEdges()) {
636 MESSAGE("Error : Not implemented");
640 volume=new SMDS_VolumeOfNodes(n1,n2,n3,n4,n5,n6);
641 myVolumes.Add(volume);
645 if (!registerElement(ID, volume)) {
646 RemoveElement(volume, false);
652 ///////////////////////////////////////////////////////////////////////////////
653 ///Create a new hexahedron and add it to the mesh.
654 ///Nodes 1,2,3,4 and 5,6,7,8 are quadrangle and 5,1 and 7,3 are an edges.
655 ///@return The created hexahedron
656 ///////////////////////////////////////////////////////////////////////////////
658 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
659 const SMDS_MeshNode * n2,
660 const SMDS_MeshNode * n3,
661 const SMDS_MeshNode * n4,
662 const SMDS_MeshNode * n5,
663 const SMDS_MeshNode * n6,
664 const SMDS_MeshNode * n7,
665 const SMDS_MeshNode * n8)
667 int ID = myElementIDFactory->GetFreeID();
668 SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, ID);
669 if(v==NULL) myElementIDFactory->ReleaseID(ID);
673 ///////////////////////////////////////////////////////////////////////////////
674 ///Create a new hexahedron and add it to the mesh.
675 ///Nodes 1,2,3,4 and 5,6,7,8 are quadrangle and 5,1 and 7,3 are an edges.
676 ///@param ID The ID of the new volume
677 ///@return The created hexahedron or NULL if an element with this ID already
678 ///exists or if input nodes are not found.
679 ///////////////////////////////////////////////////////////////////////////////
681 SMDS_MeshVolume * SMDS_Mesh::AddVolumeWithID(int idnode1,
691 SMDS_MeshNode *node1, *node2, *node3, *node4, *node5, *node6, *node7, *node8;
692 node1 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode1);
693 node2 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode2);
694 node3 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode3);
695 node4 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode4);
696 node5 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode5);
697 node6 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode6);
698 node7 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode7);
699 node8 = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(idnode8);
700 if(!node1 || !node2 || !node3 || !node4 || !node5 || !node6 || !node7 || !node8)
702 return SMDS_Mesh::AddVolumeWithID(node1, node2, node3, node4, node5, node6,
706 ///////////////////////////////////////////////////////////////////////////////
707 ///Create a new hexahedron and add it to the mesh.
708 ///Nodes 1,2,3,4 and 5,6,7,8 are quadrangle and 5,1 and 7,3 are an edges.
709 ///@param ID The ID of the new volume
710 ///@return The created prism or NULL if an element with this ID already exists
711 ///or if input nodes are not found.
712 ///////////////////////////////////////////////////////////////////////////////
714 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
715 const SMDS_MeshNode * n2,
716 const SMDS_MeshNode * n3,
717 const SMDS_MeshNode * n4,
718 const SMDS_MeshNode * n5,
719 const SMDS_MeshNode * n6,
720 const SMDS_MeshNode * n7,
721 const SMDS_MeshNode * n8,
724 SMDS_MeshVolume* volume = 0;
725 if ( !n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n7 || !n8) return volume;
727 if(hasConstructionFaces()) {
728 SMDS_MeshFace * f1=FindFaceOrCreate(n1,n2,n3,n4);
729 SMDS_MeshFace * f2=FindFaceOrCreate(n5,n6,n7,n8);
730 SMDS_MeshFace * f3=FindFaceOrCreate(n1,n4,n8,n5);
731 SMDS_MeshFace * f4=FindFaceOrCreate(n1,n2,n6,n5);
732 SMDS_MeshFace * f5=FindFaceOrCreate(n2,n3,n7,n6);
733 SMDS_MeshFace * f6=FindFaceOrCreate(n3,n4,n8,n7);
734 volume=new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5,f6);
735 myVolumes.Add(volume);
738 else if(hasConstructionEdges()) {
739 MESSAGE("Error : Not implemented");
743 // volume=new SMDS_HexahedronOfNodes(n1,n2,n3,n4,n5,n6,n7,n8);
744 volume=new SMDS_VolumeOfNodes(n1,n2,n3,n4,n5,n6,n7,n8);
745 myVolumes.Add(volume);
749 if (!registerElement(ID, volume)) {
750 RemoveElement(volume, false);
756 ///////////////////////////////////////////////////////////////////////////////
757 ///Create a new tetrahedron defined by its faces and add it to the mesh.
758 ///@return The created tetrahedron
759 ///////////////////////////////////////////////////////////////////////////////
761 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
762 const SMDS_MeshFace * f2,
763 const SMDS_MeshFace * f3,
764 const SMDS_MeshFace * f4)
766 if (!hasConstructionFaces())
768 return AddVolumeWithID(f1,f2,f3,f4, myElementIDFactory->GetFreeID());
771 ///////////////////////////////////////////////////////////////////////////////
772 ///Create a new tetrahedron defined by its faces and add it to the mesh.
773 ///@param ID The ID of the new volume
774 ///@return The created tetrahedron
775 ///////////////////////////////////////////////////////////////////////////////
777 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
778 const SMDS_MeshFace * f2,
779 const SMDS_MeshFace * f3,
780 const SMDS_MeshFace * f4,
783 if (!hasConstructionFaces())
785 if ( !f1 || !f2 || !f3 || !f4) return 0;
787 SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4);
788 myVolumes.Add(volume);
791 if (!registerElement(ID, volume)) {
792 RemoveElement(volume, false);
798 ///////////////////////////////////////////////////////////////////////////////
799 ///Create a new pyramid defined by its faces and add it to the mesh.
800 ///@return The created pyramid
801 ///////////////////////////////////////////////////////////////////////////////
803 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
804 const SMDS_MeshFace * f2,
805 const SMDS_MeshFace * f3,
806 const SMDS_MeshFace * f4,
807 const SMDS_MeshFace * f5)
809 if (!hasConstructionFaces())
811 return AddVolumeWithID(f1,f2,f3,f4,f5, myElementIDFactory->GetFreeID());
814 ///////////////////////////////////////////////////////////////////////////////
815 ///Create a new pyramid defined by its faces and add it to the mesh.
816 ///@param ID The ID of the new volume
817 ///@return The created pyramid
818 ///////////////////////////////////////////////////////////////////////////////
820 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
821 const SMDS_MeshFace * f2,
822 const SMDS_MeshFace * f3,
823 const SMDS_MeshFace * f4,
824 const SMDS_MeshFace * f5,
827 if (!hasConstructionFaces())
829 if ( !f1 || !f2 || !f3 || !f4 || !f5) return 0;
831 SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5);
832 myVolumes.Add(volume);
833 myInfo.myNbPyramids++;
835 if (!registerElement(ID, volume)) {
836 RemoveElement(volume, false);
842 ///////////////////////////////////////////////////////////////////////////////
843 ///Create a new prism defined by its faces and add it to the mesh.
844 ///@return The created prism
845 ///////////////////////////////////////////////////////////////////////////////
847 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshFace * f1,
848 const SMDS_MeshFace * f2,
849 const SMDS_MeshFace * f3,
850 const SMDS_MeshFace * f4,
851 const SMDS_MeshFace * f5,
852 const SMDS_MeshFace * f6)
854 if (!hasConstructionFaces())
856 return AddVolumeWithID(f1,f2,f3,f4,f5,f6, myElementIDFactory->GetFreeID());
859 ///////////////////////////////////////////////////////////////////////////////
860 ///Create a new prism defined by its faces and add it to the mesh.
861 ///@param ID The ID of the new volume
862 ///@return The created prism
863 ///////////////////////////////////////////////////////////////////////////////
865 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshFace * f1,
866 const SMDS_MeshFace * f2,
867 const SMDS_MeshFace * f3,
868 const SMDS_MeshFace * f4,
869 const SMDS_MeshFace * f5,
870 const SMDS_MeshFace * f6,
873 if (!hasConstructionFaces())
875 if ( !f1 || !f2 || !f3 || !f4 || !f5 || !f6) return 0;
877 SMDS_MeshVolume * volume = new SMDS_VolumeOfFaces(f1,f2,f3,f4,f5,f6);
878 myVolumes.Add(volume);
881 if (!registerElement(ID, volume)) {
882 RemoveElement(volume, false);
888 ///////////////////////////////////////////////////////////////////////////////
889 /// Add a polygon defined by its nodes IDs
890 ///////////////////////////////////////////////////////////////////////////////
892 SMDS_MeshFace* SMDS_Mesh::AddPolygonalFaceWithID (std::vector<int> nodes_ids,
895 int nbNodes = nodes_ids.size();
896 std::vector<const SMDS_MeshNode*> nodes (nbNodes);
897 for (int i = 0; i < nbNodes; i++) {
898 nodes[i] = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nodes_ids[i]);
899 if (!nodes[i]) return NULL;
901 return SMDS_Mesh::AddPolygonalFaceWithID(nodes, ID);
904 ///////////////////////////////////////////////////////////////////////////////
905 /// Add a polygon defined by its nodes
906 ///////////////////////////////////////////////////////////////////////////////
908 SMDS_MeshFace* SMDS_Mesh::AddPolygonalFaceWithID
909 (std::vector<const SMDS_MeshNode*> nodes,
912 SMDS_MeshFace * face;
915 if (hasConstructionEdges())
917 MESSAGE("Error : Not implemented");
922 for ( int i = 0; i < nodes.size(); ++i )
923 if ( !nodes[ i ] ) return 0;
924 face = new SMDS_PolygonalFaceOfNodes(nodes);
926 myInfo.myNbPolygons++;
929 if (!registerElement(ID, face)) {
930 RemoveElement(face, false);
936 ///////////////////////////////////////////////////////////////////////////////
937 /// Add a polygon defined by its nodes.
938 /// An ID is automatically affected to the created face.
939 ///////////////////////////////////////////////////////////////////////////////
941 SMDS_MeshFace* SMDS_Mesh::AddPolygonalFace (std::vector<const SMDS_MeshNode*> nodes)
943 return SMDS_Mesh::AddPolygonalFaceWithID(nodes, myElementIDFactory->GetFreeID());
946 ///////////////////////////////////////////////////////////////////////////////
947 /// Create a new polyhedral volume and add it to the mesh.
948 /// @param ID The ID of the new volume
949 /// @return The created volume or NULL if an element with this ID already exists
950 /// or if input nodes are not found.
951 ///////////////////////////////////////////////////////////////////////////////
953 SMDS_MeshVolume * SMDS_Mesh::AddPolyhedralVolumeWithID
954 (std::vector<int> nodes_ids,
955 std::vector<int> quantities,
958 int nbNodes = nodes_ids.size();
959 std::vector<const SMDS_MeshNode*> nodes (nbNodes);
960 for (int i = 0; i < nbNodes; i++) {
961 nodes[i] = (SMDS_MeshNode *)myNodeIDFactory->MeshElement(nodes_ids[i]);
962 if (!nodes[i]) return NULL;
964 return SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
967 ///////////////////////////////////////////////////////////////////////////////
968 /// Create a new polyhedral volume and add it to the mesh.
969 /// @param ID The ID of the new volume
970 /// @return The created volume
971 ///////////////////////////////////////////////////////////////////////////////
973 SMDS_MeshVolume* SMDS_Mesh::AddPolyhedralVolumeWithID
974 (std::vector<const SMDS_MeshNode*> nodes,
975 std::vector<int> quantities,
978 SMDS_MeshVolume* volume;
980 if (hasConstructionFaces()) {
981 MESSAGE("Error : Not implemented");
983 } else if (hasConstructionEdges()) {
984 MESSAGE("Error : Not implemented");
987 for ( int i = 0; i < nodes.size(); ++i )
988 if ( !nodes[ i ] ) return 0;
989 volume = new SMDS_PolyhedralVolumeOfNodes(nodes, quantities);
990 myVolumes.Add(volume);
991 myInfo.myNbPolyhedrons++;
994 if (!registerElement(ID, volume)) {
995 RemoveElement(volume, false);
1001 ///////////////////////////////////////////////////////////////////////////////
1002 /// Create a new polyhedral volume and add it to the mesh.
1003 /// @return The created volume
1004 ///////////////////////////////////////////////////////////////////////////////
1006 SMDS_MeshVolume* SMDS_Mesh::AddPolyhedralVolume
1007 (std::vector<const SMDS_MeshNode*> nodes,
1008 std::vector<int> quantities)
1010 int ID = myElementIDFactory->GetFreeID();
1011 SMDS_MeshVolume * v = SMDS_Mesh::AddPolyhedralVolumeWithID(nodes, quantities, ID);
1012 if (v == NULL) myElementIDFactory->ReleaseID(ID);
1016 ///////////////////////////////////////////////////////////////////////////////
1017 /// Registers element with the given ID, maintains inverse connections
1018 ///////////////////////////////////////////////////////////////////////////////
1019 bool SMDS_Mesh::registerElement(int ID, SMDS_MeshElement * element)
1021 if (myElementIDFactory->BindID(ID, element)) {
1022 SMDS_ElemIteratorPtr it = element->nodesIterator();
1023 while (it->more()) {
1024 SMDS_MeshNode *node = static_cast<SMDS_MeshNode*>
1025 (const_cast<SMDS_MeshElement*>(it->next()));
1026 node->AddInverseElement(element);
1033 ///////////////////////////////////////////////////////////////////////////////
1034 /// Return the node whose ID is 'ID'.
1035 ///////////////////////////////////////////////////////////////////////////////
1036 const SMDS_MeshNode * SMDS_Mesh::FindNode(int ID) const
1038 return (const SMDS_MeshNode *)myNodeIDFactory->MeshElement(ID);
1041 ///////////////////////////////////////////////////////////////////////////////
1042 ///Create a triangle and add it to the current mesh. This methode do not bind a
1043 ///ID to the create triangle.
1044 ///////////////////////////////////////////////////////////////////////////////
1045 SMDS_MeshFace * SMDS_Mesh::createTriangle(const SMDS_MeshNode * node1,
1046 const SMDS_MeshNode * node2,
1047 const SMDS_MeshNode * node3)
1049 if ( !node1 || !node2 || !node3) return 0;
1051 if(hasConstructionEdges())
1053 SMDS_MeshEdge *edge1, *edge2, *edge3;
1054 edge1=FindEdgeOrCreate(node1,node2);
1055 edge2=FindEdgeOrCreate(node2,node3);
1056 edge3=FindEdgeOrCreate(node3,node1);
1058 SMDS_MeshFace * face = new SMDS_FaceOfEdges(edge1,edge2,edge3);
1060 myInfo.myNbTriangles++;
1065 SMDS_MeshFace * face = new SMDS_FaceOfNodes(node1,node2,node3);
1067 myInfo.myNbTriangles++;
1072 ///////////////////////////////////////////////////////////////////////////////
1073 ///Create a quadrangle and add it to the current mesh. This methode do not bind
1074 ///a ID to the create triangle.
1075 ///////////////////////////////////////////////////////////////////////////////
1076 SMDS_MeshFace * SMDS_Mesh::createQuadrangle(const SMDS_MeshNode * node1,
1077 const SMDS_MeshNode * node2,
1078 const SMDS_MeshNode * node3,
1079 const SMDS_MeshNode * node4)
1081 if ( !node1 || !node2 || !node3 || !node4 ) return 0;
1083 if(hasConstructionEdges())
1085 SMDS_MeshEdge *edge1, *edge2, *edge3, *edge4;
1086 edge1=FindEdgeOrCreate(node1,node2);
1087 edge2=FindEdgeOrCreate(node2,node3);
1088 edge3=FindEdgeOrCreate(node3,node4);
1089 edge4=FindEdgeOrCreate(node4,node1);
1091 SMDS_MeshFace * face = new SMDS_FaceOfEdges(edge1,edge2,edge3,edge4);
1093 myInfo.myNbQuadrangles++;
1098 SMDS_MeshFace * face = new SMDS_FaceOfNodes(node1,node2,node3,node4);
1100 myInfo.myNbQuadrangles++;
1105 ///////////////////////////////////////////////////////////////////////////////
1106 /// Remove a node and all the elements which own this node
1107 ///////////////////////////////////////////////////////////////////////////////
1109 void SMDS_Mesh::RemoveNode(const SMDS_MeshNode * node)
1111 RemoveElement(node, true);
1114 ///////////////////////////////////////////////////////////////////////////////
1115 /// Remove an edge and all the elements which own this edge
1116 ///////////////////////////////////////////////////////////////////////////////
1118 void SMDS_Mesh::RemoveEdge(const SMDS_MeshEdge * edge)
1120 RemoveElement(edge,true);
1123 ///////////////////////////////////////////////////////////////////////////////
1124 /// Remove an face and all the elements which own this face
1125 ///////////////////////////////////////////////////////////////////////////////
1127 void SMDS_Mesh::RemoveFace(const SMDS_MeshFace * face)
1129 RemoveElement(face, true);
1132 ///////////////////////////////////////////////////////////////////////////////
1134 ///////////////////////////////////////////////////////////////////////////////
1136 void SMDS_Mesh::RemoveVolume(const SMDS_MeshVolume * volume)
1138 RemoveElement(volume, true);
1141 //=======================================================================
1142 //function : RemoveFromParent
1144 //=======================================================================
1146 bool SMDS_Mesh::RemoveFromParent()
1148 if (myParent==NULL) return false;
1149 else return (myParent->RemoveSubMesh(this));
1152 //=======================================================================
1153 //function : RemoveSubMesh
1155 //=======================================================================
1157 bool SMDS_Mesh::RemoveSubMesh(const SMDS_Mesh * aMesh)
1161 list<SMDS_Mesh *>::iterator itmsh=myChildren.begin();
1162 for (; itmsh!=myChildren.end() && !found; itmsh++)
1164 SMDS_Mesh * submesh = *itmsh;
1165 if (submesh == aMesh)
1168 myChildren.erase(itmsh);
1175 //=======================================================================
1176 //function : ChangeElementNodes
1178 //=======================================================================
1180 bool SMDS_Mesh::ChangeElementNodes(const SMDS_MeshElement * elem,
1181 const SMDS_MeshNode * nodes[],
1184 // keep current nodes of elem
1185 set<const SMDS_MeshElement*> oldNodes;
1186 SMDS_ElemIteratorPtr itn = elem->nodesIterator();
1188 oldNodes.insert( itn->next() );
1192 switch ( elem->GetType() )
1194 case SMDSAbs_Edge: {
1195 if ( nbnodes == 2 ) {
1196 const SMDS_MeshEdge* edge = dynamic_cast<const SMDS_MeshEdge*>( elem );
1198 Ok = const_cast<SMDS_MeshEdge*>( edge )->ChangeNodes( nodes[0], nodes[1] );
1200 else if ( nbnodes == 3 ) {
1201 const SMDS_QuadraticEdge* edge = dynamic_cast<const SMDS_QuadraticEdge*>( elem );
1203 Ok = const_cast<SMDS_QuadraticEdge*>( edge )->ChangeNodes( nodes[0], nodes[1], nodes[2] );
1207 case SMDSAbs_Face: {
1208 const SMDS_FaceOfNodes* face = dynamic_cast<const SMDS_FaceOfNodes*>( elem );
1210 Ok = const_cast<SMDS_FaceOfNodes*>( face )->ChangeNodes( nodes, nbnodes );
1213 const SMDS_QuadraticFaceOfNodes* QF =
1214 dynamic_cast<const SMDS_QuadraticFaceOfNodes*>( elem );
1216 Ok = const_cast<SMDS_QuadraticFaceOfNodes*>( QF )->ChangeNodes( nodes, nbnodes );
1220 const SMDS_PolygonalFaceOfNodes* face = dynamic_cast<const SMDS_PolygonalFaceOfNodes*>(elem);
1222 Ok = const_cast<SMDS_PolygonalFaceOfNodes*>(face)->ChangeNodes(nodes, nbnodes);
1229 //case SMDSAbs_PolygonalFace: {
1230 // const SMDS_PolygonalFaceOfNodes* face = dynamic_cast<const SMDS_PolygonalFaceOfNodes*>(elem);
1232 // Ok = const_cast<SMDS_PolygonalFaceOfNodes*>(face)->ChangeNodes(nodes, nbnodes);
1236 case SMDSAbs_Volume: {
1237 const SMDS_VolumeOfNodes* vol = dynamic_cast<const SMDS_VolumeOfNodes*>( elem );
1239 Ok = const_cast<SMDS_VolumeOfNodes*>( vol )->ChangeNodes( nodes, nbnodes );
1242 const SMDS_QuadraticVolumeOfNodes* QV = dynamic_cast<const SMDS_QuadraticVolumeOfNodes*>( elem );
1244 Ok = const_cast<SMDS_QuadraticVolumeOfNodes*>( QV )->ChangeNodes( nodes, nbnodes );
1250 MESSAGE ( "WRONG ELEM TYPE");
1253 if ( Ok ) { // update InverseElements
1255 // AddInverseElement to new nodes
1256 for ( int i = 0; i < nbnodes; i++ )
1257 if ( oldNodes.find( nodes[i] ) == oldNodes.end() )
1259 const_cast<SMDS_MeshNode*>( nodes[i] )->AddInverseElement( elem );
1261 // remove from oldNodes a node that remains in elem
1262 oldNodes.erase( nodes[i] );
1265 // RemoveInverseElement from the nodes removed from elem
1266 set<const SMDS_MeshElement*>::iterator it;
1267 for ( it = oldNodes.begin(); it != oldNodes.end(); it++ )
1269 SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
1270 (const_cast<SMDS_MeshElement *>( *it ));
1271 n->RemoveInverseElement( elem );
1275 //MESSAGE ( "::ChangeNodes() Ok = " << Ok);
1280 //=======================================================================
1281 //function : ChangePolyhedronNodes
1282 //purpose : to change nodes of polyhedral volume
1283 //=======================================================================
1284 bool SMDS_Mesh::ChangePolyhedronNodes (const SMDS_MeshElement * elem,
1285 std::vector<const SMDS_MeshNode*> nodes,
1286 std::vector<int> quantities)
1288 if (elem->GetType() != SMDSAbs_Volume) {
1289 MESSAGE("WRONG ELEM TYPE");
1293 const SMDS_PolyhedralVolumeOfNodes* vol = dynamic_cast<const SMDS_PolyhedralVolumeOfNodes*>(elem);
1298 // keep current nodes of elem
1299 set<const SMDS_MeshElement*> oldNodes;
1300 SMDS_ElemIteratorPtr itn = elem->nodesIterator();
1301 while (itn->more()) {
1302 oldNodes.insert(itn->next());
1306 bool Ok = const_cast<SMDS_PolyhedralVolumeOfNodes*>(vol)->ChangeNodes(nodes, quantities);
1311 // update InverseElements
1313 // AddInverseElement to new nodes
1314 int nbnodes = nodes.size();
1315 for (int i = 0; i < nbnodes; i++) {
1316 if (oldNodes.find(nodes[i]) == oldNodes.end()) {
1318 const_cast<SMDS_MeshNode*>(nodes[i])->AddInverseElement(elem);
1320 // remove from oldNodes a node that remains in elem
1321 oldNodes.erase(nodes[i]);
1325 // RemoveInverseElement from the nodes removed from elem
1326 set<const SMDS_MeshElement*>::iterator it;
1327 for (it = oldNodes.begin(); it != oldNodes.end(); it++) {
1328 SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
1329 (const_cast<SMDS_MeshElement *>( *it ));
1330 n->RemoveInverseElement(elem);
1337 //=======================================================================
1338 //function : FindEdge
1340 //=======================================================================
1342 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(int idnode1, int idnode2) const
1344 const SMDS_MeshNode * node1=FindNode(idnode1);
1345 const SMDS_MeshNode * node2=FindNode(idnode2);
1346 if((node1==NULL)||(node2==NULL)) return NULL;
1347 return FindEdge(node1,node2);
1350 //#include "Profiler.h"
1351 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
1352 const SMDS_MeshNode * node2)
1354 if ( !node1 ) return 0;
1355 const SMDS_MeshEdge * toReturn=NULL;
1358 SMDS_ElemIteratorPtr it1=node1->GetInverseElementIterator(SMDSAbs_Edge);
1361 while(it1->more()) {
1362 const SMDS_MeshElement * e = it1->next();
1363 if ( e->NbNodes() == 2 && e->GetNodeIndex( node2 ) >= 0 ) {
1364 toReturn = static_cast<const SMDS_MeshEdge*>( e );
1373 //=======================================================================
1374 //function : FindEdgeOrCreate
1376 //=======================================================================
1378 SMDS_MeshEdge* SMDS_Mesh::FindEdgeOrCreate(const SMDS_MeshNode * node1,
1379 const SMDS_MeshNode * node2)
1381 if ( !node1 || !node2) return 0;
1382 SMDS_MeshEdge * toReturn=NULL;
1383 toReturn=const_cast<SMDS_MeshEdge*>(FindEdge(node1,node2));
1384 if(toReturn==NULL) {
1386 toReturn=new SMDS_MeshEdge(node1,node2);
1387 myEdges.Add(toReturn);
1394 //=======================================================================
1395 //function : FindEdge
1397 //=======================================================================
1399 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(int idnode1, int idnode2,
1402 const SMDS_MeshNode * node1=FindNode(idnode1);
1403 const SMDS_MeshNode * node2=FindNode(idnode2);
1404 const SMDS_MeshNode * node3=FindNode(idnode3);
1405 return FindEdge(node1,node2,node3);
1408 const SMDS_MeshEdge* SMDS_Mesh::FindEdge(const SMDS_MeshNode * node1,
1409 const SMDS_MeshNode * node2,
1410 const SMDS_MeshNode * node3)
1412 if ( !node1 ) return 0;
1413 SMDS_ElemIteratorPtr it1 = node1->GetInverseElementIterator(SMDSAbs_Edge);
1414 while(it1->more()) {
1415 const SMDS_MeshElement * e = it1->next();
1416 if ( e->NbNodes() == 3 ) {
1417 SMDS_ElemIteratorPtr it2 = e->nodesIterator();
1418 while(it2->more()) {
1419 const SMDS_MeshElement* n = it2->next();
1429 return static_cast<const SMDS_MeshEdge *> (e);
1436 //=======================================================================
1437 //function : FindFace
1439 //=======================================================================
1441 const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
1444 const SMDS_MeshNode * node1=FindNode(idnode1);
1445 const SMDS_MeshNode * node2=FindNode(idnode2);
1446 const SMDS_MeshNode * node3=FindNode(idnode3);
1447 return FindFace(node1, node2, node3);
1450 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
1451 const SMDS_MeshNode *node2,
1452 const SMDS_MeshNode *node3)
1454 if ( !node1 ) return 0;
1455 SMDS_ElemIteratorPtr it1 = node1->GetInverseElementIterator(SMDSAbs_Face);
1456 while(it1->more()) {
1457 const SMDS_MeshElement * e = it1->next();
1458 if ( e->NbNodes() == 3 ) {
1459 SMDS_ElemIteratorPtr it2 = e->nodesIterator();
1460 while(it2->more()) {
1461 const SMDS_MeshElement* n = it2->next();
1471 return static_cast<const SMDS_MeshFace *> (e);
1477 SMDS_MeshFace* SMDS_Mesh::FindFaceOrCreate(const SMDS_MeshNode *node1,
1478 const SMDS_MeshNode *node2,
1479 const SMDS_MeshNode *node3)
1481 SMDS_MeshFace * toReturn=NULL;
1482 toReturn = const_cast<SMDS_MeshFace*>(FindFace(node1,node2,node3));
1483 if(toReturn==NULL) {
1484 toReturn = createTriangle(node1,node2,node3);
1490 //=======================================================================
1491 //function : FindFace
1493 //=======================================================================
1495 const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
1496 int idnode3, int idnode4) const
1498 const SMDS_MeshNode * node1=FindNode(idnode1);
1499 const SMDS_MeshNode * node2=FindNode(idnode2);
1500 const SMDS_MeshNode * node3=FindNode(idnode3);
1501 const SMDS_MeshNode * node4=FindNode(idnode4);
1502 return FindFace(node1, node2, node3, node4);
1505 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
1506 const SMDS_MeshNode *node2,
1507 const SMDS_MeshNode *node3,
1508 const SMDS_MeshNode *node4)
1510 if ( !node1 ) return 0;
1511 SMDS_ElemIteratorPtr it1 = node1->GetInverseElementIterator(SMDSAbs_Face);
1512 while(it1->more()) {
1513 const SMDS_MeshElement * e = it1->next();
1514 if ( e->NbNodes() == 4 ) {
1515 SMDS_ElemIteratorPtr it2 = e->nodesIterator();
1516 while(it2->more()) {
1517 const SMDS_MeshElement* n = it2->next();
1528 return static_cast<const SMDS_MeshFace *> (e);
1534 SMDS_MeshFace* SMDS_Mesh::FindFaceOrCreate(const SMDS_MeshNode *node1,
1535 const SMDS_MeshNode *node2,
1536 const SMDS_MeshNode *node3,
1537 const SMDS_MeshNode *node4)
1539 SMDS_MeshFace * toReturn=NULL;
1540 toReturn=const_cast<SMDS_MeshFace*>(FindFace(node1,node2,node3,node4));
1541 if(toReturn==NULL) {
1542 toReturn=createQuadrangle(node1,node2,node3,node4);
1548 //=======================================================================
1549 //function : FindFace
1550 //purpose :quadratic triangle
1551 //=======================================================================
1553 const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
1554 int idnode3, int idnode4,
1555 int idnode5, int idnode6) const
1557 const SMDS_MeshNode * node1 = FindNode(idnode1);
1558 const SMDS_MeshNode * node2 = FindNode(idnode2);
1559 const SMDS_MeshNode * node3 = FindNode(idnode3);
1560 const SMDS_MeshNode * node4 = FindNode(idnode4);
1561 const SMDS_MeshNode * node5 = FindNode(idnode5);
1562 const SMDS_MeshNode * node6 = FindNode(idnode6);
1563 return FindFace(node1, node2, node3, node4, node5, node6);
1566 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
1567 const SMDS_MeshNode *node2,
1568 const SMDS_MeshNode *node3,
1569 const SMDS_MeshNode *node4,
1570 const SMDS_MeshNode *node5,
1571 const SMDS_MeshNode *node6)
1573 if ( !node1 ) return 0;
1574 SMDS_ElemIteratorPtr it1 = node1->GetInverseElementIterator(SMDSAbs_Face);
1575 while(it1->more()) {
1576 const SMDS_MeshElement * e = it1->next();
1577 if ( e->NbNodes() == 6 ) {
1578 SMDS_ElemIteratorPtr it2 = e->nodesIterator();
1579 while(it2->more()) {
1580 const SMDS_MeshElement* n = it2->next();
1593 return static_cast<const SMDS_MeshFace *> (e);
1600 //=======================================================================
1601 //function : FindFace
1602 //purpose : quadratic quadrangle
1603 //=======================================================================
1605 const SMDS_MeshFace* SMDS_Mesh::FindFace(int idnode1, int idnode2,
1606 int idnode3, int idnode4,
1607 int idnode5, int idnode6,
1608 int idnode7, int idnode8) const
1610 const SMDS_MeshNode * node1 = FindNode(idnode1);
1611 const SMDS_MeshNode * node2 = FindNode(idnode2);
1612 const SMDS_MeshNode * node3 = FindNode(idnode3);
1613 const SMDS_MeshNode * node4 = FindNode(idnode4);
1614 const SMDS_MeshNode * node5 = FindNode(idnode5);
1615 const SMDS_MeshNode * node6 = FindNode(idnode6);
1616 const SMDS_MeshNode * node7 = FindNode(idnode7);
1617 const SMDS_MeshNode * node8 = FindNode(idnode8);
1618 return FindFace(node1, node2, node3, node4, node5, node6, node7, node8);
1621 const SMDS_MeshFace* SMDS_Mesh::FindFace(const SMDS_MeshNode *node1,
1622 const SMDS_MeshNode *node2,
1623 const SMDS_MeshNode *node3,
1624 const SMDS_MeshNode *node4,
1625 const SMDS_MeshNode *node5,
1626 const SMDS_MeshNode *node6,
1627 const SMDS_MeshNode *node7,
1628 const SMDS_MeshNode *node8)
1630 if ( !node1 ) return 0;
1631 SMDS_ElemIteratorPtr it1 = node1->GetInverseElementIterator(SMDSAbs_Face);
1632 while(it1->more()) {
1633 const SMDS_MeshElement * e = it1->next();
1634 if ( e->NbNodes() == 8 ) {
1635 SMDS_ElemIteratorPtr it2 = e->nodesIterator();
1636 while(it2->more()) {
1637 const SMDS_MeshElement* n = it2->next();
1652 return static_cast<const SMDS_MeshFace *> (e);
1659 //=======================================================================
1660 //function : FindElement
1662 //=======================================================================
1664 const SMDS_MeshElement* SMDS_Mesh::FindElement(int IDelem) const
1666 return myElementIDFactory->MeshElement(IDelem);
1669 //=======================================================================
1670 //function : FindFace
1671 //purpose : find polygon
1672 //=======================================================================
1674 const SMDS_MeshFace* SMDS_Mesh::FindFace (std::vector<int> nodes_ids) const
1676 int nbnodes = nodes_ids.size();
1677 std::vector<const SMDS_MeshNode *> poly_nodes (nbnodes);
1678 for (int inode = 0; inode < nbnodes; inode++) {
1679 const SMDS_MeshNode * node = FindNode(nodes_ids[inode]);
1680 if (node == NULL) return NULL;
1682 return FindFace(poly_nodes);
1685 const SMDS_MeshFace* SMDS_Mesh::FindFace (std::vector<const SMDS_MeshNode *> nodes)
1687 if ( nodes.size() > 2 && nodes[0] ) {
1688 SMDS_ElemIteratorPtr itF = nodes[0]->GetInverseElementIterator(SMDSAbs_Face);
1689 while (itF->more()) {
1690 const SMDS_MeshElement* f = itF->next();
1691 if ( f->NbNodes() == nodes.size() ) {
1692 SMDS_ElemIteratorPtr it2 = f->nodesIterator();
1693 while(it2->more()) {
1694 if ( find( nodes.begin(), nodes.end(), it2->next() ) == nodes.end() ) {
1700 return static_cast<const SMDS_MeshFace *> (f);
1707 //=======================================================================
1708 //function : DumpNodes
1710 //=======================================================================
1712 void SMDS_Mesh::DumpNodes() const
1714 MESSAGE("dump nodes of mesh : ");
1715 SMDS_NodeIteratorPtr itnode=nodesIterator();
1716 while(itnode->more()) MESSAGE(itnode->next());
1719 //=======================================================================
1720 //function : DumpEdges
1722 //=======================================================================
1724 void SMDS_Mesh::DumpEdges() const
1726 MESSAGE("dump edges of mesh : ");
1727 SMDS_EdgeIteratorPtr itedge=edgesIterator();
1728 while(itedge->more()) MESSAGE(itedge->next());
1731 //=======================================================================
1732 //function : DumpFaces
1734 //=======================================================================
1736 void SMDS_Mesh::DumpFaces() const
1738 MESSAGE("dump faces of mesh : ");
1739 SMDS_FaceIteratorPtr itface=facesIterator();
1740 while(itface->more()) MESSAGE(itface->next());
1743 //=======================================================================
1744 //function : DumpVolumes
1746 //=======================================================================
1748 void SMDS_Mesh::DumpVolumes() const
1750 MESSAGE("dump volumes of mesh : ");
1751 SMDS_VolumeIteratorPtr itvol=volumesIterator();
1752 while(itvol->more()) MESSAGE(itvol->next());
1755 //=======================================================================
1756 //function : DebugStats
1758 //=======================================================================
1760 void SMDS_Mesh::DebugStats() const
1762 MESSAGE("Debug stats of mesh : ");
1764 MESSAGE("===== NODES ====="<<NbNodes());
1765 MESSAGE("===== EDGES ====="<<NbEdges());
1766 MESSAGE("===== FACES ====="<<NbFaces());
1767 MESSAGE("===== VOLUMES ====="<<NbVolumes());
1769 MESSAGE("End Debug stats of mesh ");
1773 SMDS_NodeIteratorPtr itnode=nodesIterator();
1774 int sizeofnodes = 0;
1775 int sizeoffaces = 0;
1777 while(itnode->more())
1779 const SMDS_MeshNode *node = itnode->next();
1781 sizeofnodes += sizeof(*node);
1783 SMDS_ElemIteratorPtr it = node->GetInverseElementIterator();
1786 const SMDS_MeshElement *me = it->next();
1787 sizeofnodes += sizeof(me);
1792 SMDS_FaceIteratorPtr itface=facesIterator();
1793 while(itface->more())
1795 const SMDS_MeshElement *face = itface->next();
1796 sizeoffaces += sizeof(*face);
1799 MESSAGE("total size of node elements = " << sizeofnodes);;
1800 MESSAGE("total size of face elements = " << sizeoffaces);;
1805 ///////////////////////////////////////////////////////////////////////////////
1806 /// Return the number of nodes
1807 ///////////////////////////////////////////////////////////////////////////////
1808 int SMDS_Mesh::NbNodes() const
1810 return myNodes.Size();
1813 ///////////////////////////////////////////////////////////////////////////////
1814 /// Return the number of edges (including construction edges)
1815 ///////////////////////////////////////////////////////////////////////////////
1816 int SMDS_Mesh::NbEdges() const
1818 return myEdges.Size();
1821 ///////////////////////////////////////////////////////////////////////////////
1822 /// Return the number of faces (including construction faces)
1823 ///////////////////////////////////////////////////////////////////////////////
1824 int SMDS_Mesh::NbFaces() const
1826 return myFaces.Size();
1829 ///////////////////////////////////////////////////////////////////////////////
1830 /// Return the number of volumes
1831 ///////////////////////////////////////////////////////////////////////////////
1832 int SMDS_Mesh::NbVolumes() const
1834 return myVolumes.Size();
1837 ///////////////////////////////////////////////////////////////////////////////
1838 /// Return the number of child mesh of this mesh.
1839 /// Note that the tree structure of SMDS_Mesh seems to be unused in this version
1840 /// (2003-09-08) of SMESH
1841 ///////////////////////////////////////////////////////////////////////////////
1842 int SMDS_Mesh::NbSubMesh() const
1844 return myChildren.size();
1847 ///////////////////////////////////////////////////////////////////////////////
1848 /// Destroy the mesh and all its elements
1849 /// All pointer on elements owned by this mesh become illegals.
1850 ///////////////////////////////////////////////////////////////////////////////
1851 SMDS_Mesh::~SMDS_Mesh()
1853 list<SMDS_Mesh*>::iterator itc=myChildren.begin();
1854 while(itc!=myChildren.end())
1860 SetOfNodes::Iterator itn(myNodes);
1861 for (; itn.More(); itn.Next())
1864 SetOfEdges::Iterator ite(myEdges);
1865 for (; ite.More(); ite.Next())
1867 SMDS_MeshElement* elem = ite.Value();
1869 myElementIDFactory->ReleaseID(elem->GetID());
1873 SetOfFaces::Iterator itf(myFaces);
1874 for (; itf.More(); itf.Next())
1876 SMDS_MeshElement* elem = itf.Value();
1878 myElementIDFactory->ReleaseID(elem->GetID());
1882 SetOfVolumes::Iterator itv(myVolumes);
1883 for (; itv.More(); itv.Next())
1885 SMDS_MeshElement* elem = itv.Value();
1887 myElementIDFactory->ReleaseID(elem->GetID());
1893 delete myNodeIDFactory;
1894 delete myElementIDFactory;
1898 ///////////////////////////////////////////////////////////////////////////////
1899 /// Return true if this mesh create faces with edges.
1900 /// A false returned value mean that faces are created with nodes. A concequence
1901 /// is, iteration on edges (SMDS_Element::edgesIterator) will be unavailable.
1902 ///////////////////////////////////////////////////////////////////////////////
1903 bool SMDS_Mesh::hasConstructionEdges()
1905 return myHasConstructionEdges;
1908 ///////////////////////////////////////////////////////////////////////////////
1909 /// Return true if this mesh create volumes with faces
1910 /// A false returned value mean that volumes are created with nodes or edges.
1911 /// (see hasConstructionEdges)
1912 /// A concequence is, iteration on faces (SMDS_Element::facesIterator) will be
1914 ///////////////////////////////////////////////////////////////////////////////
1915 bool SMDS_Mesh::hasConstructionFaces()
1917 return myHasConstructionFaces;
1920 ///////////////////////////////////////////////////////////////////////////////
1921 /// Return true if nodes are linked to the finit elements, they are belonging to.
1922 /// Currently, It always return true.
1923 ///////////////////////////////////////////////////////////////////////////////
1924 bool SMDS_Mesh::hasInverseElements()
1926 return myHasInverseElements;
1929 ///////////////////////////////////////////////////////////////////////////////
1930 /// Make this mesh creating construction edges (see hasConstructionEdges)
1931 /// @param b true to have construction edges, else false.
1932 ///////////////////////////////////////////////////////////////////////////////
1933 void SMDS_Mesh::setConstructionEdges(bool b)
1935 myHasConstructionEdges=b;
1938 ///////////////////////////////////////////////////////////////////////////////
1939 /// Make this mesh creating construction faces (see hasConstructionFaces)
1940 /// @param b true to have construction faces, else false.
1941 ///////////////////////////////////////////////////////////////////////////////
1942 void SMDS_Mesh::setConstructionFaces(bool b)
1944 myHasConstructionFaces=b;
1947 ///////////////////////////////////////////////////////////////////////////////
1948 /// Make this mesh creating link from nodes to elements (see hasInverseElements)
1949 /// @param b true to link nodes to elements, else false.
1950 ///////////////////////////////////////////////////////////////////////////////
1951 void SMDS_Mesh::setInverseElements(bool b)
1953 if(!b) MESSAGE("Error : inverseElement=false not implemented");
1954 myHasInverseElements=b;
1957 ///////////////////////////////////////////////////////////////////////////////
1958 /// Return an iterator on nodes of the current mesh factory
1959 ///////////////////////////////////////////////////////////////////////////////
1960 class SMDS_Mesh_MyNodeIterator:public SMDS_NodeIterator
1962 SMDS_ElemIteratorPtr myIterator;
1964 SMDS_Mesh_MyNodeIterator(const SMDS_ElemIteratorPtr& it):myIterator(it)
1969 return myIterator->more();
1972 const SMDS_MeshNode* next()
1974 return static_cast<const SMDS_MeshNode*>(myIterator->next());
1978 SMDS_NodeIteratorPtr SMDS_Mesh::nodesIterator() const
1980 return SMDS_NodeIteratorPtr
1981 (new SMDS_Mesh_MyNodeIterator(myNodeIDFactory->elementsIterator()));
1984 ///////////////////////////////////////////////////////////////////////////////
1985 /// Return an iterator on elements of the current mesh factory
1986 ///////////////////////////////////////////////////////////////////////////////
1987 SMDS_ElemIteratorPtr SMDS_Mesh::elementsIterator() const
1989 return myElementIDFactory->elementsIterator();
1992 ///////////////////////////////////////////////////////////////////////////////
1993 ///Return an iterator on edges of the current mesh.
1994 ///////////////////////////////////////////////////////////////////////////////
1995 class SMDS_Mesh_MyEdgeIterator:public SMDS_EdgeIterator
1997 typedef SMDS_Mesh::SetOfEdges SetOfEdges;
1998 SetOfEdges::Iterator myIterator;
2000 SMDS_Mesh_MyEdgeIterator(const SetOfEdges& s):myIterator(s)
2005 while(myIterator.More())
2007 if(myIterator.Value()->GetID()!=-1)
2014 const SMDS_MeshEdge* next()
2016 const SMDS_MeshEdge* current = myIterator.Value();
2022 SMDS_EdgeIteratorPtr SMDS_Mesh::edgesIterator() const
2024 return SMDS_EdgeIteratorPtr(new SMDS_Mesh_MyEdgeIterator(myEdges));
2027 ///////////////////////////////////////////////////////////////////////////////
2028 ///Return an iterator on faces of the current mesh.
2029 ///////////////////////////////////////////////////////////////////////////////
2030 class SMDS_Mesh_MyFaceIterator:public SMDS_FaceIterator
2032 typedef SMDS_Mesh::SetOfFaces SetOfFaces;
2033 SetOfFaces::Iterator myIterator;
2035 SMDS_Mesh_MyFaceIterator(const SetOfFaces& s):myIterator(s)
2040 while(myIterator.More())
2042 if(myIterator.Value()->GetID()!=-1)
2049 const SMDS_MeshFace* next()
2051 const SMDS_MeshFace* current = myIterator.Value();
2057 SMDS_FaceIteratorPtr SMDS_Mesh::facesIterator() const
2059 return SMDS_FaceIteratorPtr(new SMDS_Mesh_MyFaceIterator(myFaces));
2062 ///////////////////////////////////////////////////////////////////////////////
2063 ///Return an iterator on volumes of the current mesh.
2064 ///////////////////////////////////////////////////////////////////////////////
2065 class SMDS_Mesh_MyVolumeIterator:public SMDS_VolumeIterator
2067 typedef SMDS_Mesh::SetOfVolumes SetOfVolumes;
2068 SetOfVolumes::Iterator myIterator;
2070 SMDS_Mesh_MyVolumeIterator(const SetOfVolumes& s):myIterator(s)
2075 return myIterator.More() != Standard_False;
2078 const SMDS_MeshVolume* next()
2080 const SMDS_MeshVolume* current = myIterator.Value();
2086 SMDS_VolumeIteratorPtr SMDS_Mesh::volumesIterator() const
2088 return SMDS_VolumeIteratorPtr(new SMDS_Mesh_MyVolumeIterator(myVolumes));
2091 ///////////////////////////////////////////////////////////////////////////////
2092 /// Do intersection of sets (more than 2)
2093 ///////////////////////////////////////////////////////////////////////////////
2094 static set<const SMDS_MeshElement*> * intersectionOfSets(
2095 set<const SMDS_MeshElement*> vs[], int numberOfSets)
2097 set<const SMDS_MeshElement*>* rsetA=new set<const SMDS_MeshElement*>(vs[0]);
2098 set<const SMDS_MeshElement*>* rsetB;
2100 for(int i=0; i<numberOfSets-1; i++)
2102 rsetB=new set<const SMDS_MeshElement*>();
2104 rsetA->begin(), rsetA->end(),
2105 vs[i+1].begin(), vs[i+1].end(),
2106 inserter(*rsetB, rsetB->begin()));
2113 ///////////////////////////////////////////////////////////////////////////////
2114 /// Return the list of finit elements owning the given element
2115 ///////////////////////////////////////////////////////////////////////////////
2116 static set<const SMDS_MeshElement*> * getFinitElements(const SMDS_MeshElement * element)
2118 int numberOfSets=element->NbNodes();
2119 set<const SMDS_MeshElement*> *initSet = new set<const SMDS_MeshElement*>[numberOfSets];
2121 SMDS_ElemIteratorPtr itNodes=element->nodesIterator();
2124 while(itNodes->more())
2126 const SMDS_MeshNode * n=static_cast<const SMDS_MeshNode*>(itNodes->next());
2127 SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator();
2129 //initSet[i]=set<const SMDS_MeshElement*>();
2131 initSet[i].insert(itFe->next());
2135 set<const SMDS_MeshElement*> *retSet=intersectionOfSets(initSet, numberOfSets);
2140 ///////////////////////////////////////////////////////////////////////////////
2141 /// Return the list of nodes used only by the given elements
2142 ///////////////////////////////////////////////////////////////////////////////
2143 static set<const SMDS_MeshElement*> * getExclusiveNodes(
2144 set<const SMDS_MeshElement*>& elements)
2146 set<const SMDS_MeshElement*> * toReturn=new set<const SMDS_MeshElement*>();
2147 set<const SMDS_MeshElement*>::iterator itElements=elements.begin();
2149 while(itElements!=elements.end())
2151 SMDS_ElemIteratorPtr itNodes = (*itElements)->nodesIterator();
2154 while(itNodes->more())
2156 const SMDS_MeshNode * n=static_cast<const SMDS_MeshNode*>(itNodes->next());
2157 SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator();
2158 set<const SMDS_MeshElement*> s;
2160 s.insert(itFe->next());
2161 if(s==elements) toReturn->insert(n);
2167 ///////////////////////////////////////////////////////////////////////////////
2168 ///Find the children of an element that are made of given nodes
2169 ///@param setOfChildren The set in which matching children will be inserted
2170 ///@param element The element were to search matching children
2171 ///@param nodes The nodes that the children must have to be selected
2172 ///////////////////////////////////////////////////////////////////////////////
2173 void SMDS_Mesh::addChildrenWithNodes(set<const SMDS_MeshElement*>& setOfChildren,
2174 const SMDS_MeshElement * element, set<const SMDS_MeshElement*>& nodes)
2177 switch(element->GetType())
2180 MESSAGE("Internal Error: This should not append");
2184 SMDS_ElemIteratorPtr itn=element->nodesIterator();
2187 const SMDS_MeshElement * e=itn->next();
2188 if(nodes.find(e)!=nodes.end())
2190 setOfChildren.insert(element);
2197 SMDS_ElemIteratorPtr itn=element->nodesIterator();
2200 const SMDS_MeshElement * e=itn->next();
2201 if(nodes.find(e)!=nodes.end())
2203 setOfChildren.insert(element);
2207 if(hasConstructionEdges())
2209 SMDS_ElemIteratorPtr ite=element->edgesIterator();
2211 addChildrenWithNodes(setOfChildren, ite->next(), nodes);
2214 case SMDSAbs_Volume:
2216 if(hasConstructionFaces())
2218 SMDS_ElemIteratorPtr ite=element->facesIterator();
2220 addChildrenWithNodes(setOfChildren, ite->next(), nodes);
2222 else if(hasConstructionEdges())
2224 SMDS_ElemIteratorPtr ite=element->edgesIterator();
2226 addChildrenWithNodes(setOfChildren, ite->next(), nodes);
2232 ///////////////////////////////////////////////////////////////////////////////
2233 ///@param elem The element to delete
2234 ///@param removenodes if true remaining nodes will be removed
2235 ///////////////////////////////////////////////////////////////////////////////
2236 void SMDS_Mesh::RemoveElement(const SMDS_MeshElement * elem,
2237 const bool removenodes)
2239 list<const SMDS_MeshElement *> removedElems;
2240 list<const SMDS_MeshElement *> removedNodes;
2241 RemoveElement( elem, removedElems, removedNodes, removenodes );
2244 ///////////////////////////////////////////////////////////////////////////////
2245 ///@param elem The element to delete
2246 ///@param removedElems contains all removed elements
2247 ///@param removedNodes contains all removed nodes
2248 ///@param removenodes if true remaining nodes will be removed
2249 ///////////////////////////////////////////////////////////////////////////////
2250 void SMDS_Mesh::RemoveElement(const SMDS_MeshElement * elem,
2251 list<const SMDS_MeshElement *>& removedElems,
2252 list<const SMDS_MeshElement *>& removedNodes,
2255 // get finite elements built on elem
2256 set<const SMDS_MeshElement*> * s1;
2257 if (!hasConstructionEdges() && elem->GetType() == SMDSAbs_Edge ||
2258 !hasConstructionFaces() && elem->GetType() == SMDSAbs_Face ||
2259 elem->GetType() == SMDSAbs_Volume)
2261 s1 = new set<const SMDS_MeshElement*>();
2265 s1 = getFinitElements(elem);
2267 // get exclusive nodes (which would become free afterwards)
2268 set<const SMDS_MeshElement*> * s2;
2269 if (elem->GetType() == SMDSAbs_Node) // a node is removed
2271 // do not remove nodes except elem
2272 s2 = new set<const SMDS_MeshElement*>();
2277 s2 = getExclusiveNodes(*s1);
2279 // form the set of finite and construction elements to remove
2280 set<const SMDS_MeshElement*> s3;
2281 set<const SMDS_MeshElement*>::iterator it=s1->begin();
2282 while(it!=s1->end())
2284 addChildrenWithNodes(s3, *it ,*s2);
2288 if(elem->GetType()!=SMDSAbs_Node) s3.insert(elem);
2290 // remove finite and construction elements
2294 // Remove element from <InverseElements> of its nodes
2295 SMDS_ElemIteratorPtr itn=(*it)->nodesIterator();
2298 SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
2299 (const_cast<SMDS_MeshElement *>(itn->next()));
2300 n->RemoveInverseElement( (*it) );
2303 switch((*it)->GetType())
2306 MESSAGE("Internal Error: This should not happen");
2309 myEdges.Remove(static_cast<SMDS_MeshEdge*>
2310 (const_cast<SMDS_MeshElement*>(*it)));
2311 myInfo.RemoveEdge(*it);
2314 myFaces.Remove(static_cast<SMDS_MeshFace*>
2315 (const_cast<SMDS_MeshElement*>(*it)));
2316 myInfo.RemoveFace(*it);
2318 case SMDSAbs_Volume:
2319 myVolumes.Remove(static_cast<SMDS_MeshVolume*>
2320 (const_cast<SMDS_MeshElement*>(*it)));
2321 myInfo.RemoveVolume(*it);
2324 //MESSAGE( "SMDS: RM elem " << (*it)->GetID() );
2325 removedElems.push_back( (*it) );
2326 myElementIDFactory->ReleaseID((*it)->GetID());
2331 // remove exclusive (free) nodes
2335 while(it!=s2->end())
2337 //MESSAGE( "SMDS: RM node " << (*it)->GetID() );
2338 myNodes.Remove(static_cast<SMDS_MeshNode*>
2339 (const_cast<SMDS_MeshElement*>(*it)));
2341 myNodeIDFactory->ReleaseID((*it)->GetID());
2342 removedNodes.push_back( (*it) );
2353 ///////////////////////////////////////////////////////////////////////////////
2354 ///@param elem The element to delete
2355 ///////////////////////////////////////////////////////////////////////////////
2356 void SMDS_Mesh::RemoveFreeElement(const SMDS_MeshElement * elem)
2358 SMDSAbs_ElementType aType = elem->GetType();
2359 if (aType == SMDSAbs_Node) {
2360 // only free node can be removed by this method
2361 const SMDS_MeshNode* n = static_cast<const SMDS_MeshNode*>(elem);
2362 SMDS_ElemIteratorPtr itFe = n->GetInverseElementIterator();
2363 if (!itFe->more()) { // free node
2364 myNodes.Remove(const_cast<SMDS_MeshNode*>(n));
2366 myNodeIDFactory->ReleaseID(elem->GetID());
2370 if (hasConstructionEdges() || hasConstructionFaces())
2371 // this methods is only for meshes without descendants
2374 // Remove element from <InverseElements> of its nodes
2375 SMDS_ElemIteratorPtr itn = elem->nodesIterator();
2376 while (itn->more()) {
2377 SMDS_MeshNode * n = static_cast<SMDS_MeshNode *>
2378 (const_cast<SMDS_MeshElement *>(itn->next()));
2379 n->RemoveInverseElement(elem);
2382 // in meshes without descendants elements are always free
2385 myEdges.Remove(static_cast<SMDS_MeshEdge*>
2386 (const_cast<SMDS_MeshElement*>(elem)));
2387 myInfo.RemoveEdge(elem);
2390 myFaces.Remove(static_cast<SMDS_MeshFace*>
2391 (const_cast<SMDS_MeshElement*>(elem)));
2392 myInfo.RemoveFace(elem);
2394 case SMDSAbs_Volume:
2395 myVolumes.Remove(static_cast<SMDS_MeshVolume*>
2396 (const_cast<SMDS_MeshElement*>(elem)));
2397 myInfo.RemoveVolume(elem);
2402 myElementIDFactory->ReleaseID(elem->GetID());
2408 * Checks if the element is present in mesh.
2409 * Useful to determine dead pointers.
2411 bool SMDS_Mesh::Contains (const SMDS_MeshElement* elem) const
2413 // we should not imply on validity of *elem, so iterate on containers
2414 // of all types in the hope of finding <elem> somewhere there
2415 SMDS_NodeIteratorPtr itn = nodesIterator();
2417 if (elem == itn->next())
2419 SMDS_EdgeIteratorPtr ite = edgesIterator();
2421 if (elem == ite->next())
2423 SMDS_FaceIteratorPtr itf = facesIterator();
2425 if (elem == itf->next())
2427 SMDS_VolumeIteratorPtr itv = volumesIterator();
2429 if (elem == itv->next())
2434 //=======================================================================
2435 //function : MaxNodeID
2437 //=======================================================================
2439 int SMDS_Mesh::MaxNodeID() const
2441 return myNodeIDFactory->GetMaxID();
2444 //=======================================================================
2445 //function : MinNodeID
2447 //=======================================================================
2449 int SMDS_Mesh::MinNodeID() const
2451 return myNodeIDFactory->GetMinID();
2454 //=======================================================================
2455 //function : MaxElementID
2457 //=======================================================================
2459 int SMDS_Mesh::MaxElementID() const
2461 return myElementIDFactory->GetMaxID();
2464 //=======================================================================
2465 //function : MinElementID
2467 //=======================================================================
2469 int SMDS_Mesh::MinElementID() const
2471 return myElementIDFactory->GetMinID();
2474 //=======================================================================
2475 //function : Renumber
2476 //purpose : Renumber all nodes or elements.
2477 //=======================================================================
2479 void SMDS_Mesh::Renumber (const bool isNodes, const int startID, const int deltaID)
2484 SMDS_MeshElementIDFactory * idFactory =
2485 isNodes ? myNodeIDFactory : myElementIDFactory;
2487 // get existing elements in the order of ID increasing
2488 map<int,SMDS_MeshElement*> elemMap;
2489 SMDS_ElemIteratorPtr idElemIt = idFactory->elementsIterator();
2490 while ( idElemIt->more() ) {
2491 SMDS_MeshElement* elem = const_cast<SMDS_MeshElement*>(idElemIt->next());
2492 int id = elem->GetID();
2493 elemMap.insert(map<int,SMDS_MeshElement*>::value_type(id, elem));
2495 // release their ids
2496 map<int,SMDS_MeshElement*>::iterator elemIt = elemMap.begin();
2497 for ( ; elemIt != elemMap.end(); elemIt++ )
2499 int id = (*elemIt).first;
2500 idFactory->ReleaseID( id );
2504 elemIt = elemMap.begin();
2505 for ( ; elemIt != elemMap.end(); elemIt++ )
2507 idFactory->BindID( ID, (*elemIt).second );
2512 //=======================================================================
2513 //function : GetElementType
2514 //purpose : Return type of element or node with id
2515 //=======================================================================
2517 SMDSAbs_ElementType SMDS_Mesh::GetElementType( const int id, const bool iselem ) const
2519 SMDS_MeshElement* elem = 0;
2521 elem = myElementIDFactory->MeshElement( id );
2523 elem = myNodeIDFactory->MeshElement( id );
2527 //throw SALOME_Exception(LOCALIZED ("this element isn't exist"));
2531 return elem->GetType();
2536 //********************************************************************
2537 //********************************************************************
2538 //******** *********
2539 //***** Methods for addition of quadratic elements ******
2540 //******** *********
2541 //********************************************************************
2542 //********************************************************************
2544 //=======================================================================
2545 //function : AddEdgeWithID
2547 //=======================================================================
2548 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(int n1, int n2, int n12, int ID)
2550 return SMDS_Mesh::AddEdgeWithID
2551 ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1),
2552 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2),
2553 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
2557 //=======================================================================
2558 //function : AddEdge
2560 //=======================================================================
2561 SMDS_MeshEdge* SMDS_Mesh::AddEdge(const SMDS_MeshNode* n1,
2562 const SMDS_MeshNode* n2,
2563 const SMDS_MeshNode* n12)
2565 return SMDS_Mesh::AddEdgeWithID(n1, n2, n12, myElementIDFactory->GetFreeID());
2568 //=======================================================================
2569 //function : AddEdgeWithID
2571 //=======================================================================
2572 SMDS_MeshEdge* SMDS_Mesh::AddEdgeWithID(const SMDS_MeshNode * n1,
2573 const SMDS_MeshNode * n2,
2574 const SMDS_MeshNode * n12,
2577 if ( !n1 || !n2 || !n12 ) return 0;
2578 SMDS_QuadraticEdge* edge = new SMDS_QuadraticEdge(n1,n2,n12);
2579 if(myElementIDFactory->BindID(ID, edge)) {
2580 SMDS_MeshNode *node1,*node2, *node12;
2581 node1 = const_cast<SMDS_MeshNode*>(n1);
2582 node2 = const_cast<SMDS_MeshNode*>(n2);
2583 node12 = const_cast<SMDS_MeshNode*>(n12);
2584 node1->AddInverseElement(edge);
2585 node2->AddInverseElement(edge);
2586 node12->AddInverseElement(edge);
2588 myInfo.myNbQuadEdges++;
2598 //=======================================================================
2599 //function : AddFace
2601 //=======================================================================
2602 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
2603 const SMDS_MeshNode * n2,
2604 const SMDS_MeshNode * n3,
2605 const SMDS_MeshNode * n12,
2606 const SMDS_MeshNode * n23,
2607 const SMDS_MeshNode * n31)
2609 return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n12,n23,n31,
2610 myElementIDFactory->GetFreeID());
2613 //=======================================================================
2614 //function : AddFaceWithID
2616 //=======================================================================
2617 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3,
2618 int n12,int n23,int n31, int ID)
2620 return SMDS_Mesh::AddFaceWithID
2621 ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
2622 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
2623 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
2624 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
2625 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
2626 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n31),
2630 //=======================================================================
2631 //function : AddFaceWithID
2633 //=======================================================================
2634 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
2635 const SMDS_MeshNode * n2,
2636 const SMDS_MeshNode * n3,
2637 const SMDS_MeshNode * n12,
2638 const SMDS_MeshNode * n23,
2639 const SMDS_MeshNode * n31,
2642 if ( !n1 || !n2 || !n3 || !n12 || !n23 || !n31) return 0;
2643 if(hasConstructionEdges()) {
2644 // creation quadratic edges - not implemented
2647 SMDS_QuadraticFaceOfNodes* face =
2648 new SMDS_QuadraticFaceOfNodes(n1,n2,n3,n12,n23,n31);
2650 myInfo.myNbQuadTriangles++;
2652 if (!registerElement(ID, face)) {
2653 RemoveElement(face, false);
2660 //=======================================================================
2661 //function : AddFace
2663 //=======================================================================
2664 SMDS_MeshFace* SMDS_Mesh::AddFace(const SMDS_MeshNode * n1,
2665 const SMDS_MeshNode * n2,
2666 const SMDS_MeshNode * n3,
2667 const SMDS_MeshNode * n4,
2668 const SMDS_MeshNode * n12,
2669 const SMDS_MeshNode * n23,
2670 const SMDS_MeshNode * n34,
2671 const SMDS_MeshNode * n41)
2673 return SMDS_Mesh::AddFaceWithID(n1,n2,n3,n4,n12,n23,n34,n41,
2674 myElementIDFactory->GetFreeID());
2677 //=======================================================================
2678 //function : AddFaceWithID
2680 //=======================================================================
2681 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(int n1, int n2, int n3, int n4,
2682 int n12,int n23,int n34,int n41, int ID)
2684 return SMDS_Mesh::AddFaceWithID
2685 ((SMDS_MeshNode *)myNodeIDFactory->MeshElement(n1) ,
2686 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n2) ,
2687 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n3) ,
2688 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n4) ,
2689 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n12),
2690 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n23),
2691 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n34),
2692 (SMDS_MeshNode *)myNodeIDFactory->MeshElement(n41),
2696 //=======================================================================
2697 //function : AddFaceWithID
2699 //=======================================================================
2700 SMDS_MeshFace* SMDS_Mesh::AddFaceWithID(const SMDS_MeshNode * n1,
2701 const SMDS_MeshNode * n2,
2702 const SMDS_MeshNode * n3,
2703 const SMDS_MeshNode * n4,
2704 const SMDS_MeshNode * n12,
2705 const SMDS_MeshNode * n23,
2706 const SMDS_MeshNode * n34,
2707 const SMDS_MeshNode * n41,
2710 if ( !n1 || !n2 || !n3 || !n4 || !n12 || !n23 || !n34 || !n41) return 0;
2711 if(hasConstructionEdges()) {
2712 // creation quadratic edges - not implemented
2714 SMDS_QuadraticFaceOfNodes* face =
2715 new SMDS_QuadraticFaceOfNodes(n1,n2,n3,n4,n12,n23,n34,n41);
2717 myInfo.myNbQuadQuadrangles++;
2719 if (!registerElement(ID, face)) {
2720 RemoveElement(face, false);
2727 //=======================================================================
2728 //function : AddVolume
2730 //=======================================================================
2731 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
2732 const SMDS_MeshNode * n2,
2733 const SMDS_MeshNode * n3,
2734 const SMDS_MeshNode * n4,
2735 const SMDS_MeshNode * n12,
2736 const SMDS_MeshNode * n23,
2737 const SMDS_MeshNode * n31,
2738 const SMDS_MeshNode * n14,
2739 const SMDS_MeshNode * n24,
2740 const SMDS_MeshNode * n34)
2742 int ID = myElementIDFactory->GetFreeID();
2743 SMDS_MeshVolume * v = SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n12, n23,
2744 n31, n14, n24, n34, ID);
2745 if(v==NULL) myElementIDFactory->ReleaseID(ID);
2749 //=======================================================================
2750 //function : AddVolumeWithID
2752 //=======================================================================
2753 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4,
2754 int n12,int n23,int n31,
2755 int n14,int n24,int n34, int ID)
2757 return SMDS_Mesh::AddVolumeWithID
2758 ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
2759 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
2760 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
2761 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
2762 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
2763 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
2764 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n31),
2765 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n14),
2766 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n24),
2767 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
2771 //=======================================================================
2772 //function : AddVolumeWithID
2773 //purpose : 2d order tetrahedron of 10 nodes
2774 //=======================================================================
2775 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
2776 const SMDS_MeshNode * n2,
2777 const SMDS_MeshNode * n3,
2778 const SMDS_MeshNode * n4,
2779 const SMDS_MeshNode * n12,
2780 const SMDS_MeshNode * n23,
2781 const SMDS_MeshNode * n31,
2782 const SMDS_MeshNode * n14,
2783 const SMDS_MeshNode * n24,
2784 const SMDS_MeshNode * n34,
2787 if ( !n1 || !n2 || !n3 || !n4 || !n12 || !n23 || !n31 || !n14 || !n24 || !n34)
2789 if(hasConstructionFaces()) {
2790 // creation quadratic faces - not implemented
2793 SMDS_QuadraticVolumeOfNodes * volume =
2794 new SMDS_QuadraticVolumeOfNodes(n1,n2,n3,n4,n12,n23,n31,n14,n24,n34);
2795 myVolumes.Add(volume);
2796 myInfo.myNbQuadTetras++;
2798 if (!registerElement(ID, volume)) {
2799 RemoveElement(volume, false);
2806 //=======================================================================
2807 //function : AddVolume
2809 //=======================================================================
2810 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
2811 const SMDS_MeshNode * n2,
2812 const SMDS_MeshNode * n3,
2813 const SMDS_MeshNode * n4,
2814 const SMDS_MeshNode * n5,
2815 const SMDS_MeshNode * n12,
2816 const SMDS_MeshNode * n23,
2817 const SMDS_MeshNode * n34,
2818 const SMDS_MeshNode * n41,
2819 const SMDS_MeshNode * n15,
2820 const SMDS_MeshNode * n25,
2821 const SMDS_MeshNode * n35,
2822 const SMDS_MeshNode * n45)
2824 int ID = myElementIDFactory->GetFreeID();
2825 SMDS_MeshVolume * v =
2826 SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n12, n23, n34, n41,
2827 n15, n25, n35, n45, ID);
2828 if(v==NULL) myElementIDFactory->ReleaseID(ID);
2832 //=======================================================================
2833 //function : AddVolumeWithID
2835 //=======================================================================
2836 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4, int n5,
2837 int n12,int n23,int n34,int n41,
2838 int n15,int n25,int n35,int n45, int ID)
2840 return SMDS_Mesh::AddVolumeWithID
2841 ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
2842 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
2843 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
2844 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
2845 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5) ,
2846 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
2847 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
2848 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
2849 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n41),
2850 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n15),
2851 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n25),
2852 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n35),
2853 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n45),
2857 //=======================================================================
2858 //function : AddVolumeWithID
2859 //purpose : 2d order pyramid of 13 nodes
2860 //=======================================================================
2861 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
2862 const SMDS_MeshNode * n2,
2863 const SMDS_MeshNode * n3,
2864 const SMDS_MeshNode * n4,
2865 const SMDS_MeshNode * n5,
2866 const SMDS_MeshNode * n12,
2867 const SMDS_MeshNode * n23,
2868 const SMDS_MeshNode * n34,
2869 const SMDS_MeshNode * n41,
2870 const SMDS_MeshNode * n15,
2871 const SMDS_MeshNode * n25,
2872 const SMDS_MeshNode * n35,
2873 const SMDS_MeshNode * n45,
2876 if (!n1 || !n2 || !n3 || !n4 || !n5 || !n12 || !n23 ||
2877 !n34 || !n41 || !n15 || !n25 || !n35 || !n45)
2879 if(hasConstructionFaces()) {
2880 // creation quadratic faces - not implemented
2883 SMDS_QuadraticVolumeOfNodes * volume =
2884 new SMDS_QuadraticVolumeOfNodes(n1,n2,n3,n4,n5,n12,n23,
2885 n34,n41,n15,n25,n35,n45);
2886 myVolumes.Add(volume);
2887 myInfo.myNbQuadPyramids++;
2889 if (!registerElement(ID, volume)) {
2890 RemoveElement(volume, false);
2897 //=======================================================================
2898 //function : AddVolume
2900 //=======================================================================
2901 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
2902 const SMDS_MeshNode * n2,
2903 const SMDS_MeshNode * n3,
2904 const SMDS_MeshNode * n4,
2905 const SMDS_MeshNode * n5,
2906 const SMDS_MeshNode * n6,
2907 const SMDS_MeshNode * n12,
2908 const SMDS_MeshNode * n23,
2909 const SMDS_MeshNode * n31,
2910 const SMDS_MeshNode * n45,
2911 const SMDS_MeshNode * n56,
2912 const SMDS_MeshNode * n64,
2913 const SMDS_MeshNode * n14,
2914 const SMDS_MeshNode * n25,
2915 const SMDS_MeshNode * n36)
2917 int ID = myElementIDFactory->GetFreeID();
2918 SMDS_MeshVolume * v =
2919 SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n12, n23, n31,
2920 n45, n56, n64, n14, n25, n36, ID);
2921 if(v==NULL) myElementIDFactory->ReleaseID(ID);
2925 //=======================================================================
2926 //function : AddVolumeWithID
2928 //=======================================================================
2929 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3,
2930 int n4, int n5, int n6,
2931 int n12,int n23,int n31,
2932 int n45,int n56,int n64,
2933 int n14,int n25,int n36, int ID)
2935 return SMDS_Mesh::AddVolumeWithID
2936 ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1) ,
2937 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2) ,
2938 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3) ,
2939 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4) ,
2940 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5) ,
2941 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6) ,
2942 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
2943 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
2944 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n31),
2945 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n45),
2946 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
2947 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n64),
2948 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n14),
2949 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n25),
2950 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n36),
2954 //=======================================================================
2955 //function : AddVolumeWithID
2956 //purpose : 2d order Pentahedron with 15 nodes
2957 //=======================================================================
2958 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
2959 const SMDS_MeshNode * n2,
2960 const SMDS_MeshNode * n3,
2961 const SMDS_MeshNode * n4,
2962 const SMDS_MeshNode * n5,
2963 const SMDS_MeshNode * n6,
2964 const SMDS_MeshNode * n12,
2965 const SMDS_MeshNode * n23,
2966 const SMDS_MeshNode * n31,
2967 const SMDS_MeshNode * n45,
2968 const SMDS_MeshNode * n56,
2969 const SMDS_MeshNode * n64,
2970 const SMDS_MeshNode * n14,
2971 const SMDS_MeshNode * n25,
2972 const SMDS_MeshNode * n36,
2975 if (!n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n12 || !n23 ||
2976 !n31 || !n45 || !n56 || !n64 || !n14 || !n25 || !n36)
2978 if(hasConstructionFaces()) {
2979 // creation quadratic faces - not implemented
2982 SMDS_QuadraticVolumeOfNodes * volume =
2983 new SMDS_QuadraticVolumeOfNodes(n1,n2,n3,n4,n5,n6,n12,n23,n31,
2984 n45,n56,n64,n14,n25,n36);
2985 myVolumes.Add(volume);
2986 myInfo.myNbQuadPrisms++;
2988 if (!registerElement(ID, volume)) {
2989 RemoveElement(volume, false);
2996 //=======================================================================
2997 //function : AddVolume
2999 //=======================================================================
3000 SMDS_MeshVolume* SMDS_Mesh::AddVolume(const SMDS_MeshNode * n1,
3001 const SMDS_MeshNode * n2,
3002 const SMDS_MeshNode * n3,
3003 const SMDS_MeshNode * n4,
3004 const SMDS_MeshNode * n5,
3005 const SMDS_MeshNode * n6,
3006 const SMDS_MeshNode * n7,
3007 const SMDS_MeshNode * n8,
3008 const SMDS_MeshNode * n12,
3009 const SMDS_MeshNode * n23,
3010 const SMDS_MeshNode * n34,
3011 const SMDS_MeshNode * n41,
3012 const SMDS_MeshNode * n56,
3013 const SMDS_MeshNode * n67,
3014 const SMDS_MeshNode * n78,
3015 const SMDS_MeshNode * n85,
3016 const SMDS_MeshNode * n15,
3017 const SMDS_MeshNode * n26,
3018 const SMDS_MeshNode * n37,
3019 const SMDS_MeshNode * n48)
3021 int ID = myElementIDFactory->GetFreeID();
3022 SMDS_MeshVolume * v =
3023 SMDS_Mesh::AddVolumeWithID(n1, n2, n3, n4, n5, n6, n7, n8, n12, n23, n34, n41,
3024 n56, n67, n78, n85, n15, n26, n37, n48, ID);
3025 if(v==NULL) myElementIDFactory->ReleaseID(ID);
3029 //=======================================================================
3030 //function : AddVolumeWithID
3032 //=======================================================================
3033 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(int n1, int n2, int n3, int n4,
3034 int n5, int n6, int n7, int n8,
3035 int n12,int n23,int n34,int n41,
3036 int n56,int n67,int n78,int n85,
3037 int n15,int n26,int n37,int n48, int ID)
3039 return SMDS_Mesh::AddVolumeWithID
3040 ((SMDS_MeshNode*) myNodeIDFactory->MeshElement(n1),
3041 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n2),
3042 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n3),
3043 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n4),
3044 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n5),
3045 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n6),
3046 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n7),
3047 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n8),
3048 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n12),
3049 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n23),
3050 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n34),
3051 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n41),
3052 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n56),
3053 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n67),
3054 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n78),
3055 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n85),
3056 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n15),
3057 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n26),
3058 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n37),
3059 (SMDS_MeshNode*) myNodeIDFactory->MeshElement(n48),
3063 //=======================================================================
3064 //function : AddVolumeWithID
3065 //purpose : 2d order Hexahedrons with 20 nodes
3066 //=======================================================================
3067 SMDS_MeshVolume* SMDS_Mesh::AddVolumeWithID(const SMDS_MeshNode * n1,
3068 const SMDS_MeshNode * n2,
3069 const SMDS_MeshNode * n3,
3070 const SMDS_MeshNode * n4,
3071 const SMDS_MeshNode * n5,
3072 const SMDS_MeshNode * n6,
3073 const SMDS_MeshNode * n7,
3074 const SMDS_MeshNode * n8,
3075 const SMDS_MeshNode * n12,
3076 const SMDS_MeshNode * n23,
3077 const SMDS_MeshNode * n34,
3078 const SMDS_MeshNode * n41,
3079 const SMDS_MeshNode * n56,
3080 const SMDS_MeshNode * n67,
3081 const SMDS_MeshNode * n78,
3082 const SMDS_MeshNode * n85,
3083 const SMDS_MeshNode * n15,
3084 const SMDS_MeshNode * n26,
3085 const SMDS_MeshNode * n37,
3086 const SMDS_MeshNode * n48,
3089 if (!n1 || !n2 || !n3 || !n4 || !n5 || !n6 || !n7 || !n8 || !n12 || !n23 ||
3090 !n34 || !n41 || !n56 || !n67 || !n78 || !n85 || !n15 || !n26 || !n37 || !n48)
3092 if(hasConstructionFaces()) {
3094 // creation quadratic faces - not implemented
3096 SMDS_QuadraticVolumeOfNodes * volume =
3097 new SMDS_QuadraticVolumeOfNodes(n1,n2,n3,n4,n5,n6,n7,n8,n12,n23,n34,n41,
3098 n56,n67,n78,n85,n15,n26,n37,n48);
3099 myVolumes.Add(volume);
3100 myInfo.myNbQuadHexas++;
3102 if (!registerElement(ID, volume)) {
3103 RemoveElement(volume, false);