1 # Copyright (C) 2007-2016 CEA/DEN, EDF R&D, OPEN CASCADE
3 # This library is free software; you can redistribute it and/or
4 # modify it under the terms of the GNU Lesser General Public
5 # License as published by the Free Software Foundation; either
6 # version 2.1 of the License, or (at your option) any later version.
8 # This library is distributed in the hope that it will be useful,
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 # Lesser General Public License for more details.
13 # You should have received a copy of the GNU Lesser General Public
14 # License along with this library; if not, write to the Free Software
15 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 # See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
19 # File : smeshBuilder.py
20 # Author : Francis KLOSS, OCC
24 from salome.geom import geomBuilder
26 import SMESH # This is necessary for back compatibility
27 import omniORB # back compatibility
28 SMESH.MED_V2_1 = omniORB.EnumItem("MED_V2_1", 0) # back compatibility
29 SMESH.MED_V2_2 = omniORB.EnumItem("MED_V2_2", 1) # back compatibility
32 from salome.smesh.smesh_algorithm import Mesh_Algorithm
39 # In case the omniORBpy EnumItem class does not fully support Python 3
40 # (for instance in version 4.2.1-2), the comparison ordering methods must be
44 SMESH.Entity_Triangle < SMESH.Entity_Quadrangle
46 def enumitem_eq(self, other):
48 if isinstance(other, omniORB.EnumItem):
49 if other._parent_id == self._parent_id:
50 return self._v == other._v
52 return self._parent_id == other._parent_id
54 return id(self) == id(other)
56 return id(self) == id(other)
58 def enumitem_lt(self, other):
60 if isinstance(other, omniORB.EnumItem):
61 if other._parent_id == self._parent_id:
62 return self._v < other._v
64 return self._parent_id < other._parent_id
66 return id(self) < id(other)
68 return id(self) < id(other)
70 def enumitem_le(self, other):
72 if isinstance(other, omniORB.EnumItem):
73 if other._parent_id == self._parent_id:
74 return self._v <= other._v
76 return self._parent_id <= other._parent_id
78 return id(self) <= id(other)
80 return id(self) <= id(other)
82 def enumitem_gt(self, other):
84 if isinstance(other, omniORB.EnumItem):
85 if other._parent_id == self._parent_id:
86 return self._v > other._v
88 return self._parent_id > other._parent_id
90 return id(self) > id(other)
92 return id(self) > id(other)
94 def enumitem_ge(self, other):
96 if isinstance(other, omniORB.EnumItem):
97 if other._parent_id == self._parent_id:
98 return self._v >= other._v
100 return self._parent_id >= other._parent_id
102 return id(self) >= id(other)
104 return id(self) >= id(other)
106 omniORB.EnumItem.__eq__ = enumitem_eq
107 omniORB.EnumItem.__lt__ = enumitem_lt
108 omniORB.EnumItem.__le__ = enumitem_le
109 omniORB.EnumItem.__gt__ = enumitem_gt
110 omniORB.EnumItem.__ge__ = enumitem_ge
113 class MeshMeta(type):
114 """Private class used to workaround a problem that sometimes isinstance(m, Mesh) returns False
116 def __instancecheck__(cls, inst):
117 """Implement isinstance(inst, cls)."""
118 return any(cls.__subclasscheck__(c)
119 for c in {type(inst), inst.__class__})
121 def __subclasscheck__(cls, sub):
122 """Implement issubclass(sub, cls)."""
123 return type.__subclasscheck__(cls, sub) or (cls.__name__ == sub.__name__ and cls.__module__ == sub.__module__)
125 def DegreesToRadians(AngleInDegrees):
126 """Convert an angle from degrees to radians
129 return AngleInDegrees * pi / 180.0
131 import salome_notebook
132 notebook = salome_notebook.notebook
133 # Salome notebook variable separator
136 def ParseParameters(*args):
138 Return list of variable values from salome notebook.
139 The last argument, if is callable, is used to modify values got from notebook
145 if args and callable(args[-1]):
146 args, varModifFun = args[:-1], args[-1]
147 for parameter in args:
149 Parameters += str(parameter) + var_separator
151 if isinstance(parameter,str):
152 # check if there is an inexistent variable name
153 if not notebook.isVariable(parameter):
154 raise ValueError("Variable with name '" + parameter + "' doesn't exist!!!")
155 parameter = notebook.get(parameter)
158 parameter = varModifFun(parameter)
161 Result.append(parameter)
164 Parameters = Parameters[:-1]
165 Result.append( Parameters )
166 Result.append( hasVariables )
169 def ParseAngles(*args):
171 Parse parameters while converting variables to radians
173 return ParseParameters( *( args + (DegreesToRadians, )))
175 def __initPointStruct(point,*args):
177 Substitute PointStruct.__init__() to create SMESH.PointStruct using notebook variables.
178 Parameters are stored in PointStruct.parameters attribute
180 point.x, point.y, point.z, point.parameters,hasVars = ParseParameters(*args)
182 SMESH.PointStruct.__init__ = __initPointStruct
184 def __initAxisStruct(ax,*args):
186 Substitute AxisStruct.__init__() to create SMESH.AxisStruct using notebook variables.
187 Parameters are stored in AxisStruct.parameters attribute
190 raise RuntimeError("Bad nb args (%s) passed in SMESH.AxisStruct(x,y,z,dx,dy,dz)"%(len( args )))
191 ax.x, ax.y, ax.z, ax.vx, ax.vy, ax.vz, ax.parameters,hasVars = ParseParameters(*args)
193 SMESH.AxisStruct.__init__ = __initAxisStruct
195 smeshPrecisionConfusion = 1.e-07
196 def IsEqual(val1, val2, tol=smeshPrecisionConfusion):
197 """Compare real values using smeshPrecisionConfusion as tolerance
199 if abs(val1 - val2) < tol:
207 Return a name of an object
214 if isinstance(obj, SALOMEDS._objref_SObject):
218 ior = salome.orb.object_to_string(obj)
222 sobj = salome.myStudy.FindObjectIOR(ior)
224 return sobj.GetName()
225 if hasattr(obj, "GetName"):
226 # unknown CORBA object, having GetName() method
229 # unknown CORBA object, no GetName() method
232 if hasattr(obj, "GetName"):
233 # unknown non-CORBA object, having GetName() method
236 raise RuntimeError("Null or invalid object")
238 def TreatHypoStatus(status, hypName, geomName, isAlgo, mesh):
240 Print error message if a hypothesis was not assigned.
243 hypType = "algorithm"
245 hypType = "hypothesis"
248 if hasattr( status, "__getitem__" ):
249 status, reason = status[0], status[1]
250 if status == HYP_UNKNOWN_FATAL:
251 reason = "for unknown reason"
252 elif status == HYP_INCOMPATIBLE:
253 reason = "this hypothesis mismatches the algorithm"
254 elif status == HYP_NOTCONFORM:
255 reason = "a non-conform mesh would be built"
256 elif status == HYP_ALREADY_EXIST:
257 if isAlgo: return # it does not influence anything
258 reason = hypType + " of the same dimension is already assigned to this shape"
259 elif status == HYP_BAD_DIM:
260 reason = hypType + " mismatches the shape"
261 elif status == HYP_CONCURRENT :
262 reason = "there are concurrent hypotheses on sub-shapes"
263 elif status == HYP_BAD_SUBSHAPE:
264 reason = "the shape is neither the main one, nor its sub-shape, nor a valid group"
265 elif status == HYP_BAD_GEOMETRY:
266 reason = "the algorithm is not applicable to this geometry"
267 elif status == HYP_HIDDEN_ALGO:
268 reason = "it is hidden by an algorithm of an upper dimension, which generates elements of all dimensions"
269 elif status == HYP_HIDING_ALGO:
270 reason = "it hides algorithms of lower dimensions by generating elements of all dimensions"
271 elif status == HYP_NEED_SHAPE:
272 reason = "algorithm can't work without shape"
273 elif status == HYP_INCOMPAT_HYPS:
279 where = '"%s"' % geomName
281 meshName = GetName( mesh )
282 if meshName and meshName != NO_NAME:
283 where = '"%s" shape in "%s" mesh ' % ( geomName, meshName )
284 if status < HYP_UNKNOWN_FATAL and where:
285 print('"%s" was assigned to %s but %s' %( hypName, where, reason ))
287 print('"%s" was not assigned to %s : %s' %( hypName, where, reason ))
289 print('"%s" was not assigned : %s' %( hypName, reason ))
292 def AssureGeomPublished(mesh, geom, name=''):
294 Private method. Add geom (sub-shape of the main shape) into the study if not yet there
296 if not isinstance( geom, geomBuilder.GEOM._objref_GEOM_Object ):
298 if not geom.GetStudyEntry():
300 if not name and geom.GetShapeType() != geomBuilder.GEOM.COMPOUND:
301 # for all groups SubShapeName() return "Compound_-1"
302 name = mesh.geompyD.SubShapeName(geom, mesh.geom)
304 name = "%s_%s"%(geom.GetShapeType(), id(geom)%10000)
306 mesh.geompyD.addToStudyInFather( mesh.geom, geom, name )
309 def FirstVertexOnCurve(mesh, edge):
312 the first vertex of a geometrical edge by ignoring orientation
314 vv = mesh.geompyD.SubShapeAll( edge, geomBuilder.geomBuilder.ShapeType["VERTEX"])
316 raise TypeError("Given object has no vertices")
317 if len( vv ) == 1: return vv[0]
318 v0 = mesh.geompyD.MakeVertexOnCurve(edge,0.)
319 xyz = mesh.geompyD.PointCoordinates( v0 ) # coords of the first vertex
320 xyz1 = mesh.geompyD.PointCoordinates( vv[0] )
321 xyz2 = mesh.geompyD.PointCoordinates( vv[1] )
324 dist1 += abs( xyz[i] - xyz1[i] )
325 dist2 += abs( xyz[i] - xyz2[i] )
334 smeshInst is a singleton
340 class smeshBuilder( SMESH._objref_SMESH_Gen, object ):
342 This class allows to create, load or manipulate meshes.
343 It has a set of methods to create, load or copy meshes, to combine several meshes, etc.
344 It also has methods to get infos and measure meshes.
347 # MirrorType enumeration
348 POINT = SMESH_MeshEditor.POINT
349 AXIS = SMESH_MeshEditor.AXIS
350 PLANE = SMESH_MeshEditor.PLANE
352 # Smooth_Method enumeration
353 LAPLACIAN_SMOOTH = SMESH_MeshEditor.LAPLACIAN_SMOOTH
354 CENTROIDAL_SMOOTH = SMESH_MeshEditor.CENTROIDAL_SMOOTH
356 PrecisionConfusion = smeshPrecisionConfusion
358 # TopAbs_State enumeration
359 [TopAbs_IN, TopAbs_OUT, TopAbs_ON, TopAbs_UNKNOWN] = list(range(4))
361 # Methods of splitting a hexahedron into tetrahedra
362 Hex_5Tet, Hex_6Tet, Hex_24Tet, Hex_2Prisms, Hex_4Prisms = 1, 2, 3, 1, 2
364 def __new__(cls, *args):
368 #print("==== __new__", engine, smeshInst, doLcc)
370 if smeshInst is None:
371 # smesh engine is either retrieved from engine, or created
373 # Following test avoids a recursive loop
375 if smeshInst is not None:
376 # smesh engine not created: existing engine found
380 # FindOrLoadComponent called:
381 # 1. CORBA resolution of server
382 # 2. the __new__ method is called again
383 #print("==== smeshInst = lcc.FindOrLoadComponent ", engine, smeshInst, doLcc)
384 smeshInst = salome.lcc.FindOrLoadComponent( "FactoryServer", "SMESH" )
386 # FindOrLoadComponent not called
387 if smeshInst is None:
388 # smeshBuilder instance is created from lcc.FindOrLoadComponent
389 #print("==== smeshInst = super(smeshBuilder,cls).__new__(cls) ", engine, smeshInst, doLcc)
390 smeshInst = super(smeshBuilder,cls).__new__(cls)
392 # smesh engine not created: existing engine found
393 #print("==== existing ", engine, smeshInst, doLcc)
395 #print("====1 ", smeshInst)
398 #print("====2 ", smeshInst)
401 def __init__(self, *args):
403 #print("--------------- smeshbuilder __init__ ---", created)
406 SMESH._objref_SMESH_Gen.__init__(self, *args)
409 def DumpPython(self, theStudy, theIsPublished=True, theIsMultiFile=True):
411 Dump component to the Python script.
412 This method overrides IDL function to allow default values for the parameters.
415 return SMESH._objref_SMESH_Gen.DumpPython(self, theStudy, theIsPublished, theIsMultiFile)
417 def SetDumpPythonHistorical(self, isHistorical):
419 Set mode of DumpPython(), *historical* or *snapshot*.
420 In the *historical* mode, the Python Dump script includes all commands
421 performed by SMESH engine. In the *snapshot* mode, commands
422 relating to objects removed from the Study are excluded from the script
423 as well as commands not influencing the current state of meshes
426 if isHistorical: val = "true"
428 SMESH._objref_SMESH_Gen.SetOption(self, "historical_python_dump", val)
430 def init_smesh(self,geompyD = None):
432 Set Geometry component
435 self.UpdateStudy(geompyD)
436 notebook.myStudy = salome.myStudy
438 def Mesh(self, obj=0, name=0):
440 Create a mesh. This mesh can be either
442 * an empty mesh not bound to geometry, if *obj* == 0
443 * an empty mesh bound to geometry, if *obj* is GEOM.GEOM_Object
444 * a mesh wrapping a :class:`CORBA mesh <SMESH.SMESH_Mesh>` given as *obj* parameter.
449 1. a :class:`CORBA mesh <SMESH.SMESH_Mesh>` got by calling e.g.
452 salome.myStudy.FindObjectID("0:1:2:3").GetObject()
454 2. a geometrical object for meshing
456 name: the name for the new mesh.
459 an instance of class :class:`Mesh`.
462 if isinstance(obj,str):
464 return Mesh(self, self.geompyD, obj, name)
466 def EnumToLong(self,theItem):
468 Return a long value from enumeration
473 def ColorToString(self,c):
475 Convert SALOMEDS.Color to string.
476 To be used with filters.
479 c: color value (SALOMEDS.Color)
482 a string representation of the color.
486 if isinstance(c, SALOMEDS.Color):
487 val = "%s;%s;%s" % (c.R, c.G, c.B)
488 elif isinstance(c, str):
491 raise ValueError("Color value should be of string or SALOMEDS.Color type")
494 def GetPointStruct(self,theVertex):
496 Get :class:`SMESH.PointStruct` from vertex
499 theVertex (GEOM.GEOM_Object): vertex
502 :class:`SMESH.PointStruct`
505 [x, y, z] = self.geompyD.PointCoordinates(theVertex)
506 return PointStruct(x,y,z)
508 def GetDirStruct(self,theVector):
510 Get :class:`SMESH.DirStruct` from vector
513 theVector (GEOM.GEOM_Object): vector
516 :class:`SMESH.DirStruct`
519 vertices = self.geompyD.SubShapeAll( theVector, geomBuilder.geomBuilder.ShapeType["VERTEX"] )
520 if(len(vertices) != 2):
521 print("Error: vector object is incorrect.")
523 p1 = self.geompyD.PointCoordinates(vertices[0])
524 p2 = self.geompyD.PointCoordinates(vertices[1])
525 pnt = PointStruct(p2[0]-p1[0], p2[1]-p1[1], p2[2]-p1[2])
526 dirst = DirStruct(pnt)
529 def MakeDirStruct(self,x,y,z):
531 Make :class:`SMESH.DirStruct` from a triplet of floats
534 x,y,z (float): vector components
537 :class:`SMESH.DirStruct`
540 pnt = PointStruct(x,y,z)
541 return DirStruct(pnt)
543 def GetAxisStruct(self,theObj):
545 Get :class:`SMESH.AxisStruct` from a geometrical object
548 theObj (GEOM.GEOM_Object): line or plane
551 :class:`SMESH.AxisStruct`
554 edges = self.geompyD.SubShapeAll( theObj, geomBuilder.geomBuilder.ShapeType["EDGE"] )
557 vertex1, vertex2 = self.geompyD.SubShapeAll( edges[0], geomBuilder.geomBuilder.ShapeType["VERTEX"] )
558 vertex3, vertex4 = self.geompyD.SubShapeAll( edges[1], geomBuilder.geomBuilder.ShapeType["VERTEX"] )
559 vertex1 = self.geompyD.PointCoordinates(vertex1)
560 vertex2 = self.geompyD.PointCoordinates(vertex2)
561 vertex3 = self.geompyD.PointCoordinates(vertex3)
562 vertex4 = self.geompyD.PointCoordinates(vertex4)
563 v1 = [vertex2[0]-vertex1[0], vertex2[1]-vertex1[1], vertex2[2]-vertex1[2]]
564 v2 = [vertex4[0]-vertex3[0], vertex4[1]-vertex3[1], vertex4[2]-vertex3[2]]
565 normal = [ v1[1]*v2[2]-v2[1]*v1[2], v1[2]*v2[0]-v2[2]*v1[0], v1[0]*v2[1]-v2[0]*v1[1] ]
566 axis = AxisStruct(vertex1[0], vertex1[1], vertex1[2], normal[0], normal[1], normal[2])
567 axis._mirrorType = SMESH.SMESH_MeshEditor.PLANE
568 elif len(edges) == 1:
569 vertex1, vertex2 = self.geompyD.SubShapeAll( edges[0], geomBuilder.geomBuilder.ShapeType["VERTEX"] )
570 p1 = self.geompyD.PointCoordinates( vertex1 )
571 p2 = self.geompyD.PointCoordinates( vertex2 )
572 axis = AxisStruct(p1[0], p1[1], p1[2], p2[0]-p1[0], p2[1]-p1[1], p2[2]-p1[2])
573 axis._mirrorType = SMESH.SMESH_MeshEditor.AXIS
574 elif theObj.GetShapeType() == GEOM.VERTEX:
575 x,y,z = self.geompyD.PointCoordinates( theObj )
576 axis = AxisStruct( x,y,z, 1,0,0,)
577 axis._mirrorType = SMESH.SMESH_MeshEditor.POINT
580 # From SMESH_Gen interface:
581 # ------------------------
583 def SetName(self, obj, name):
585 Set the given name to an object
588 obj: the object to rename
589 name: a new object name
592 if isinstance( obj, Mesh ):
594 elif isinstance( obj, Mesh_Algorithm ):
595 obj = obj.GetAlgorithm()
596 ior = salome.orb.object_to_string(obj)
597 SMESH._objref_SMESH_Gen.SetName(self, ior, name)
599 def SetEmbeddedMode( self,theMode ):
604 SMESH._objref_SMESH_Gen.SetEmbeddedMode(self,theMode)
606 def IsEmbeddedMode(self):
611 return SMESH._objref_SMESH_Gen.IsEmbeddedMode(self)
613 def UpdateStudy( self, geompyD = None ):
615 Update the current study. Calling UpdateStudy() allows to
616 update meshes at switching GEOM->SMESH
620 from salome.geom import geomBuilder
621 geompyD = geomBuilder.geom
624 self.SetGeomEngine(geompyD)
625 SMESH._objref_SMESH_Gen.UpdateStudy(self)
626 sb = salome.myStudy.NewBuilder()
627 sc = salome.myStudy.FindComponent("SMESH")
629 sb.LoadWith(sc, self)
632 def SetEnablePublish( self, theIsEnablePublish ):
634 Sets enable publishing in the study. Calling SetEnablePublish( false ) allows to
635 switch OFF publishing in the Study of mesh objects.
637 #self.SetEnablePublish(theIsEnablePublish)
638 SMESH._objref_SMESH_Gen.SetEnablePublish(self,theIsEnablePublish)
640 notebook = salome_notebook.NoteBook( theIsEnablePublish )
643 def CreateMeshesFromUNV( self,theFileName ):
645 Create a Mesh object importing data from the given UNV file
648 an instance of class :class:`Mesh`
651 aSmeshMesh = SMESH._objref_SMESH_Gen.CreateMeshesFromUNV(self,theFileName)
652 aMesh = Mesh(self, self.geompyD, aSmeshMesh)
655 def CreateMeshesFromMED( self,theFileName ):
657 Create a Mesh object(s) importing data from the given MED file
660 a tuple ( list of class :class:`Mesh` instances,
661 :class:`SMESH.DriverMED_ReadStatus` )
664 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromMED(self,theFileName)
665 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
666 return aMeshes, aStatus
668 def CreateMeshesFromSAUV( self,theFileName ):
670 Create a Mesh object(s) importing data from the given SAUV file
673 a tuple ( list of class :class:`Mesh` instances, :class:`SMESH.DriverMED_ReadStatus` )
676 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromSAUV(self,theFileName)
677 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
678 return aMeshes, aStatus
680 def CreateMeshesFromSTL( self, theFileName ):
682 Create a Mesh object importing data from the given STL file
685 an instance of class :class:`Mesh`
688 aSmeshMesh = SMESH._objref_SMESH_Gen.CreateMeshesFromSTL(self,theFileName)
689 aMesh = Mesh(self, self.geompyD, aSmeshMesh)
692 def CreateMeshesFromCGNS( self, theFileName ):
694 Create Mesh objects importing data from the given CGNS file
697 a tuple ( list of class :class:`Mesh` instances, :class:`SMESH.DriverMED_ReadStatus` )
700 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromCGNS(self,theFileName)
701 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
702 return aMeshes, aStatus
704 def CreateMeshesFromGMF( self, theFileName ):
706 Create a Mesh object importing data from the given GMF file.
707 GMF files must have .mesh extension for the ASCII format and .meshb for
711 ( an instance of class :class:`Mesh`, :class:`SMESH.ComputeError` )
714 aSmeshMesh, error = SMESH._objref_SMESH_Gen.CreateMeshesFromGMF(self,
717 if error.comment: print("*** CreateMeshesFromGMF() errors:\n", error.comment)
718 return Mesh(self, self.geompyD, aSmeshMesh), error
720 def Concatenate( self, meshes, uniteIdenticalGroups,
721 mergeNodesAndElements = False, mergeTolerance = 1e-5, allGroups = False,
724 Concatenate the given meshes into one mesh. All groups of input meshes will be
725 present in the new mesh.
728 meshes: :class:`meshes, sub-meshes, groups or filters <SMESH.SMESH_IDSource>` to combine into one mesh
729 uniteIdenticalGroups: if True, groups with same names are united, else they are renamed
730 mergeNodesAndElements: if True, equal nodes and elements are merged
731 mergeTolerance: tolerance for merging nodes
732 allGroups: forces creation of groups corresponding to every input mesh
733 name: name of a new mesh
736 an instance of class :class:`Mesh`
739 if not meshes: return None
740 for i,m in enumerate(meshes):
741 if isinstance(m, Mesh):
742 meshes[i] = m.GetMesh()
743 mergeTolerance,Parameters,hasVars = ParseParameters(mergeTolerance)
744 meshes[0].SetParameters(Parameters)
746 aSmeshMesh = SMESH._objref_SMESH_Gen.ConcatenateWithGroups(
747 self,meshes,uniteIdenticalGroups,mergeNodesAndElements,mergeTolerance)
749 aSmeshMesh = SMESH._objref_SMESH_Gen.Concatenate(
750 self,meshes,uniteIdenticalGroups,mergeNodesAndElements,mergeTolerance)
751 aMesh = Mesh(self, self.geompyD, aSmeshMesh, name=name)
754 def CopyMesh( self, meshPart, meshName, toCopyGroups=False, toKeepIDs=False):
756 Create a mesh by copying a part of another mesh.
759 meshPart: a part of mesh to copy, either
760 :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
761 To copy nodes or elements not forming any mesh object,
762 pass result of :meth:`Mesh.GetIDSource` as *meshPart*
763 meshName: a name of the new mesh
764 toCopyGroups: to create in the new mesh groups the copied elements belongs to
765 toKeepIDs: to preserve order of the copied elements or not
768 an instance of class :class:`Mesh`
771 if (isinstance( meshPart, Mesh )):
772 meshPart = meshPart.GetMesh()
773 mesh = SMESH._objref_SMESH_Gen.CopyMesh( self,meshPart,meshName,toCopyGroups,toKeepIDs )
774 return Mesh(self, self.geompyD, mesh)
776 def GetSubShapesId( self, theMainObject, theListOfSubObjects ):
778 Return IDs of sub-shapes
781 theMainObject (GEOM.GEOM_Object): a shape
782 theListOfSubObjects: sub-shapes (list of GEOM.GEOM_Object)
784 the list of integer values
787 return SMESH._objref_SMESH_Gen.GetSubShapesId(self,theMainObject, theListOfSubObjects)
789 def GetPattern(self):
791 Create a pattern mapper.
794 an instance of :class:`SMESH.SMESH_Pattern`
796 :ref:`Example of Patterns usage <tui_pattern_mapping>`
799 return SMESH._objref_SMESH_Gen.GetPattern(self)
801 def SetBoundaryBoxSegmentation(self, nbSegments):
803 Set number of segments per diagonal of boundary box of geometry, by which
804 default segment length of appropriate 1D hypotheses is defined in GUI.
808 SMESH._objref_SMESH_Gen.SetBoundaryBoxSegmentation(self,nbSegments)
810 # Filtering. Auxiliary functions:
811 # ------------------------------
813 def GetEmptyCriterion(self):
815 Create an empty criterion
818 :class:`SMESH.Filter.Criterion`
821 Type = self.EnumToLong(FT_Undefined)
822 Compare = self.EnumToLong(FT_Undefined)
826 UnaryOp = self.EnumToLong(FT_Undefined)
827 BinaryOp = self.EnumToLong(FT_Undefined)
830 Precision = -1 ##@1e-07
831 return Filter.Criterion(Type, Compare, Threshold, ThresholdStr, ThresholdID,
832 UnaryOp, BinaryOp, Tolerance, TypeOfElement, Precision)
834 def GetCriterion(self,elementType,
836 Compare = FT_EqualTo,
838 UnaryOp=FT_Undefined,
839 BinaryOp=FT_Undefined,
842 Create a criterion by the given parameters
843 Criterion structures allow to define complex filters by combining them with logical operations (AND / OR) (see example below)
846 elementType: the :class:`type of elements <SMESH.ElementType>` (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
847 CritType: the type of criterion :class:`SMESH.FunctorType` (SMESH.FT_Taper, SMESH.FT_Area, etc.).
848 Note that the items starting from FT_LessThan are not suitable for *CritType*.
849 Compare: belongs to {SMESH.FT_LessThan, SMESH.FT_MoreThan, SMESH.FT_EqualTo}
850 Threshold: the threshold value (range of ids as string, shape, numeric)
851 UnaryOp: SMESH.FT_LogicalNOT or SMESH.FT_Undefined
852 BinaryOp: a binary logical operation SMESH.FT_LogicalAND, SMESH.FT_LogicalOR or
854 Tolerance: the tolerance used by SMESH.FT_BelongToGeom, SMESH.FT_BelongToSurface,
855 SMESH.FT_LyingOnGeom, SMESH.FT_CoplanarFaces criteria
858 :class:`SMESH.Filter.Criterion`
860 Example: :ref:`combining_filters`
863 if not CritType in SMESH.FunctorType._items:
864 raise TypeError("CritType should be of SMESH.FunctorType")
865 aCriterion = self.GetEmptyCriterion()
866 aCriterion.TypeOfElement = elementType
867 aCriterion.Type = self.EnumToLong(CritType)
868 aCriterion.Tolerance = Tolerance
870 aThreshold = Threshold
872 if Compare in [FT_LessThan, FT_MoreThan, FT_EqualTo]:
873 aCriterion.Compare = self.EnumToLong(Compare)
874 elif Compare == "=" or Compare == "==":
875 aCriterion.Compare = self.EnumToLong(FT_EqualTo)
877 aCriterion.Compare = self.EnumToLong(FT_LessThan)
879 aCriterion.Compare = self.EnumToLong(FT_MoreThan)
880 elif Compare != FT_Undefined:
881 aCriterion.Compare = self.EnumToLong(FT_EqualTo)
884 if CritType in [FT_BelongToGeom, FT_BelongToPlane, FT_BelongToGenSurface,
885 FT_BelongToCylinder, FT_LyingOnGeom]:
886 # Check that Threshold is GEOM object
887 if isinstance(aThreshold, geomBuilder.GEOM._objref_GEOM_Object):
888 aCriterion.ThresholdStr = GetName(aThreshold)
889 aCriterion.ThresholdID = aThreshold.GetStudyEntry()
890 if not aCriterion.ThresholdID:
891 name = aCriterion.ThresholdStr
893 name = "%s_%s"%(aThreshold.GetShapeType(), id(aThreshold)%10000)
894 aCriterion.ThresholdID = self.geompyD.addToStudy( aThreshold, name )
895 # or a name of GEOM object
896 elif isinstance( aThreshold, str ):
897 aCriterion.ThresholdStr = aThreshold
899 raise TypeError("The Threshold should be a shape.")
900 if isinstance(UnaryOp,float):
901 aCriterion.Tolerance = UnaryOp
902 UnaryOp = FT_Undefined
904 elif CritType == FT_BelongToMeshGroup:
905 # Check that Threshold is a group
906 if isinstance(aThreshold, SMESH._objref_SMESH_GroupBase):
907 if aThreshold.GetType() != elementType:
908 raise ValueError("Group type mismatches Element type")
909 aCriterion.ThresholdStr = aThreshold.GetName()
910 aCriterion.ThresholdID = salome.orb.object_to_string( aThreshold )
911 study = salome.myStudy
913 so = study.FindObjectIOR( aCriterion.ThresholdID )
917 aCriterion.ThresholdID = entry
919 raise TypeError("The Threshold should be a Mesh Group")
920 elif CritType == FT_RangeOfIds:
921 # Check that Threshold is string
922 if isinstance(aThreshold, str):
923 aCriterion.ThresholdStr = aThreshold
925 raise TypeError("The Threshold should be a string.")
926 elif CritType == FT_CoplanarFaces:
927 # Check the Threshold
928 if isinstance(aThreshold, int):
929 aCriterion.ThresholdID = str(aThreshold)
930 elif isinstance(aThreshold, str):
933 raise ValueError("Invalid ID of mesh face: '%s'"%aThreshold)
934 aCriterion.ThresholdID = aThreshold
936 raise TypeError("The Threshold should be an ID of mesh face and not '%s'"%aThreshold)
937 elif CritType == FT_ConnectedElements:
938 # Check the Threshold
939 if isinstance(aThreshold, geomBuilder.GEOM._objref_GEOM_Object): # shape
940 aCriterion.ThresholdID = aThreshold.GetStudyEntry()
941 if not aCriterion.ThresholdID:
942 name = aThreshold.GetName()
944 name = "%s_%s"%(aThreshold.GetShapeType(), id(aThreshold)%10000)
945 aCriterion.ThresholdID = self.geompyD.addToStudy( aThreshold, name )
946 elif isinstance(aThreshold, int): # node id
947 aCriterion.Threshold = aThreshold
948 elif isinstance(aThreshold, list): # 3 point coordinates
949 if len( aThreshold ) < 3:
950 raise ValueError("too few point coordinates, must be 3")
951 aCriterion.ThresholdStr = " ".join( [str(c) for c in aThreshold[:3]] )
952 elif isinstance(aThreshold, str):
953 if aThreshold.isdigit():
954 aCriterion.Threshold = aThreshold # node id
956 aCriterion.ThresholdStr = aThreshold # hope that it's point coordinates
958 raise TypeError("The Threshold should either a VERTEX, or a node ID, "\
959 "or a list of point coordinates and not '%s'"%aThreshold)
960 elif CritType == FT_ElemGeomType:
961 # Check the Threshold
963 aCriterion.Threshold = self.EnumToLong(aThreshold)
964 assert( aThreshold in SMESH.GeometryType._items )
966 if isinstance(aThreshold, int):
967 aCriterion.Threshold = aThreshold
969 raise TypeError("The Threshold should be an integer or SMESH.GeometryType.")
972 elif CritType == FT_EntityType:
973 # Check the Threshold
975 aCriterion.Threshold = self.EnumToLong(aThreshold)
976 assert( aThreshold in SMESH.EntityType._items )
978 if isinstance(aThreshold, int):
979 aCriterion.Threshold = aThreshold
981 raise TypeError("The Threshold should be an integer or SMESH.EntityType.")
985 elif CritType == FT_GroupColor:
986 # Check the Threshold
988 aCriterion.ThresholdStr = self.ColorToString(aThreshold)
990 raise TypeError("The threshold value should be of SALOMEDS.Color type")
992 elif CritType in [FT_FreeBorders, FT_FreeEdges, FT_FreeNodes, FT_FreeFaces,
993 FT_LinearOrQuadratic, FT_BadOrientedVolume,
994 FT_BareBorderFace, FT_BareBorderVolume,
995 FT_OverConstrainedFace, FT_OverConstrainedVolume,
996 FT_EqualNodes,FT_EqualEdges,FT_EqualFaces,FT_EqualVolumes ]:
997 # At this point the Threshold is unnecessary
998 if aThreshold == FT_LogicalNOT:
999 aCriterion.UnaryOp = self.EnumToLong(FT_LogicalNOT)
1000 elif aThreshold in [FT_LogicalAND, FT_LogicalOR]:
1001 aCriterion.BinaryOp = aThreshold
1005 aThreshold = float(aThreshold)
1006 aCriterion.Threshold = aThreshold
1008 raise TypeError("The Threshold should be a number.")
1011 if Threshold == FT_LogicalNOT or UnaryOp == FT_LogicalNOT:
1012 aCriterion.UnaryOp = self.EnumToLong(FT_LogicalNOT)
1014 if Threshold in [FT_LogicalAND, FT_LogicalOR]:
1015 aCriterion.BinaryOp = self.EnumToLong(Threshold)
1017 if UnaryOp in [FT_LogicalAND, FT_LogicalOR]:
1018 aCriterion.BinaryOp = self.EnumToLong(UnaryOp)
1020 if BinaryOp in [FT_LogicalAND, FT_LogicalOR]:
1021 aCriterion.BinaryOp = self.EnumToLong(BinaryOp)
1025 def GetFilter(self,elementType,
1026 CritType=FT_Undefined,
1029 UnaryOp=FT_Undefined,
1033 Create a filter with the given parameters
1036 elementType: the :class:`type of elements <SMESH.ElementType>` (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
1037 CritType: the :class:`type of criterion <SMESH.FunctorType>` (SMESH.FT_Taper, SMESH.FT_Area, etc.).
1038 Note that the items starting from FT_LessThan are not suitable for CritType.
1039 Compare: belongs to {SMESH.FT_LessThan, SMESH.FT_MoreThan, SMESH.FT_EqualTo}
1040 Threshold: the threshold value (range of ids as string, shape, numeric)
1041 UnaryOp: SMESH.FT_LogicalNOT or SMESH.FT_Undefined
1042 Tolerance: the tolerance used by SMESH.FT_BelongToGeom, SMESH.FT_BelongToSurface,
1043 SMESH.FT_LyingOnGeom, SMESH.FT_CoplanarFaces and SMESH.FT_EqualNodes criteria
1044 mesh: the mesh to initialize the filter with
1047 :class:`SMESH.Filter`
1050 See :doc:`Filters usage examples <tui_filters>`
1053 aCriterion = self.GetCriterion(elementType, CritType, Compare, Threshold, UnaryOp, FT_Undefined,Tolerance)
1054 aFilterMgr = self.CreateFilterManager()
1055 aFilter = aFilterMgr.CreateFilter()
1057 aCriteria.append(aCriterion)
1058 aFilter.SetCriteria(aCriteria)
1060 if isinstance( mesh, Mesh ): aFilter.SetMesh( mesh.GetMesh() )
1061 else : aFilter.SetMesh( mesh )
1062 aFilterMgr.UnRegister()
1065 def GetFilterFromCriteria(self,criteria, binOp=SMESH.FT_LogicalAND):
1067 Create a filter from criteria
1070 criteria: a list of :class:`SMESH.Filter.Criterion`
1071 binOp: binary operator used when binary operator of criteria is undefined
1074 :class:`SMESH.Filter`
1077 See :doc:`Filters usage examples <tui_filters>`
1080 for i in range( len( criteria ) - 1 ):
1081 if criteria[i].BinaryOp == self.EnumToLong( SMESH.FT_Undefined ):
1082 criteria[i].BinaryOp = self.EnumToLong( binOp )
1083 aFilterMgr = self.CreateFilterManager()
1084 aFilter = aFilterMgr.CreateFilter()
1085 aFilter.SetCriteria(criteria)
1086 aFilterMgr.UnRegister()
1089 def GetFunctor(self,theCriterion):
1091 Create a numerical functor by its type
1094 theCriterion (SMESH.FunctorType): functor type.
1095 Note that not all items correspond to numerical functors.
1098 :class:`SMESH.NumericalFunctor`
1101 if isinstance( theCriterion, SMESH._objref_NumericalFunctor ):
1103 aFilterMgr = self.CreateFilterManager()
1105 if theCriterion == FT_AspectRatio:
1106 functor = aFilterMgr.CreateAspectRatio()
1107 elif theCriterion == FT_AspectRatio3D:
1108 functor = aFilterMgr.CreateAspectRatio3D()
1109 elif theCriterion == FT_Warping:
1110 functor = aFilterMgr.CreateWarping()
1111 elif theCriterion == FT_MinimumAngle:
1112 functor = aFilterMgr.CreateMinimumAngle()
1113 elif theCriterion == FT_Taper:
1114 functor = aFilterMgr.CreateTaper()
1115 elif theCriterion == FT_Skew:
1116 functor = aFilterMgr.CreateSkew()
1117 elif theCriterion == FT_Area:
1118 functor = aFilterMgr.CreateArea()
1119 elif theCriterion == FT_Volume3D:
1120 functor = aFilterMgr.CreateVolume3D()
1121 elif theCriterion == FT_MaxElementLength2D:
1122 functor = aFilterMgr.CreateMaxElementLength2D()
1123 elif theCriterion == FT_MaxElementLength3D:
1124 functor = aFilterMgr.CreateMaxElementLength3D()
1125 elif theCriterion == FT_MultiConnection:
1126 functor = aFilterMgr.CreateMultiConnection()
1127 elif theCriterion == FT_MultiConnection2D:
1128 functor = aFilterMgr.CreateMultiConnection2D()
1129 elif theCriterion == FT_Length:
1130 functor = aFilterMgr.CreateLength()
1131 elif theCriterion == FT_Length2D:
1132 functor = aFilterMgr.CreateLength2D()
1133 elif theCriterion == FT_Deflection2D:
1134 functor = aFilterMgr.CreateDeflection2D()
1135 elif theCriterion == FT_NodeConnectivityNumber:
1136 functor = aFilterMgr.CreateNodeConnectivityNumber()
1137 elif theCriterion == FT_BallDiameter:
1138 functor = aFilterMgr.CreateBallDiameter()
1140 print("Error: given parameter is not numerical functor type.")
1141 aFilterMgr.UnRegister()
1144 def CreateHypothesis(self, theHType, theLibName="libStdMeshersEngine.so"):
1149 theHType (string): mesh hypothesis type
1150 theLibName (string): mesh plug-in library name
1153 created hypothesis instance
1155 hyp = SMESH._objref_SMESH_Gen.CreateHypothesis(self, theHType, theLibName )
1157 if isinstance( hyp, SMESH._objref_SMESH_Algo ):
1160 # wrap hypothesis methods
1161 for meth_name in dir( hyp.__class__ ):
1162 if not meth_name.startswith("Get") and \
1163 not meth_name in dir ( SMESH._objref_SMESH_Hypothesis ):
1164 method = getattr ( hyp.__class__, meth_name )
1165 if callable(method):
1166 setattr( hyp, meth_name, hypMethodWrapper( hyp, method ))
1170 def GetMeshInfo(self, obj):
1172 Get the mesh statistic.
1173 Use :meth:`smeshBuilder.EnumToLong` to get an integer from
1174 an item of :class:`SMESH.EntityType`.
1177 dictionary { :class:`SMESH.EntityType` - "count of elements" }
1180 if isinstance( obj, Mesh ):
1183 if hasattr(obj, "GetMeshInfo"):
1184 values = obj.GetMeshInfo()
1185 for i in range(SMESH.Entity_Last._v):
1186 if i < len(values): d[SMESH.EntityType._item(i)]=values[i]
1190 def MinDistance(self, src1, src2=None, id1=0, id2=0, isElem1=False, isElem2=False):
1192 Get minimum distance between two objects
1194 * If *src2* is None, and *id2* = 0, distance from *src1* / *id1* to the origin is computed.
1195 * If *src2* is None, and *id2* != 0, it is assumed that both *id1* and *id2* belong to *src1*.
1198 src1 (SMESH.SMESH_IDSource): first source object
1199 src2 (SMESH.SMESH_IDSource): second source object
1200 id1 (int): node/element id from the first source
1201 id2 (int): node/element id from the second (or first) source
1202 isElem1 (boolean): *True* if *id1* is element id, *False* if it is node id
1203 isElem2 (boolean): *True* if *id2* is element id, *False* if it is node id
1206 minimum distance value
1209 :meth:`GetMinDistance`
1212 result = self.GetMinDistance(src1, src2, id1, id2, isElem1, isElem2)
1216 result = result.value
1219 def GetMinDistance(self, src1, src2=None, id1=0, id2=0, isElem1=False, isElem2=False):
1221 Get :class:`SMESH.Measure` structure specifying minimum distance data between two objects
1223 * If *src2* is None, and *id2* = 0, distance from *src1* / *id1* to the origin is computed.
1224 * If *src2* is None, and *id2* != 0, it is assumed that both *id1* and *id2* belong to *src1*.
1227 src1 (SMESH.SMESH_IDSource): first source object
1228 src2 (SMESH.SMESH_IDSource): second source object
1229 id1 (int): node/element id from the first source
1230 id2 (int): node/element id from the second (or first) source
1231 isElem1 (boolean): *True* if **id1** is element id, *False* if it is node id
1232 isElem2 (boolean): *True* if **id2** is element id, *False* if it is node id
1235 :class:`SMESH.Measure` structure or None if input data is invalid
1240 if isinstance(src1, Mesh): src1 = src1.mesh
1241 if isinstance(src2, Mesh): src2 = src2.mesh
1242 if src2 is None and id2 != 0: src2 = src1
1243 if not hasattr(src1, "_narrow"): return None
1244 src1 = src1._narrow(SMESH.SMESH_IDSource)
1245 if not src1: return None
1246 unRegister = genObjUnRegister()
1249 e = m.GetMeshEditor()
1251 src1 = e.MakeIDSource([id1], SMESH.FACE)
1253 src1 = e.MakeIDSource([id1], SMESH.NODE)
1254 unRegister.set( src1 )
1256 if hasattr(src2, "_narrow"):
1257 src2 = src2._narrow(SMESH.SMESH_IDSource)
1258 if src2 and id2 != 0:
1260 e = m.GetMeshEditor()
1262 src2 = e.MakeIDSource([id2], SMESH.FACE)
1264 src2 = e.MakeIDSource([id2], SMESH.NODE)
1265 unRegister.set( src2 )
1268 aMeasurements = self.CreateMeasurements()
1269 unRegister.set( aMeasurements )
1270 result = aMeasurements.MinDistance(src1, src2)
1273 def BoundingBox(self, objects):
1275 Get bounding box of the specified object(s)
1278 objects (SMESH.SMESH_IDSource): single source object or list of source objects
1281 tuple of six values (minX, minY, minZ, maxX, maxY, maxZ)
1284 :meth:`GetBoundingBox`
1287 result = self.GetBoundingBox(objects)
1291 result = (result.minX, result.minY, result.minZ, result.maxX, result.maxY, result.maxZ)
1294 def GetBoundingBox(self, objects):
1296 Get :class:`SMESH.Measure` structure specifying bounding box data of the specified object(s)
1299 objects (SMESH.SMESH_IDSource): single source object or list of source objects
1302 :class:`SMESH.Measure` structure
1308 if isinstance(objects, tuple):
1309 objects = list(objects)
1310 if not isinstance(objects, list):
1314 if isinstance(o, Mesh):
1315 srclist.append(o.mesh)
1316 elif hasattr(o, "_narrow"):
1317 src = o._narrow(SMESH.SMESH_IDSource)
1318 if src: srclist.append(src)
1321 aMeasurements = self.CreateMeasurements()
1322 result = aMeasurements.BoundingBox(srclist)
1323 aMeasurements.UnRegister()
1326 def GetLength(self, obj):
1328 Get sum of lengths of all 1D elements in the mesh object.
1331 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1334 sum of lengths of all 1D elements
1337 if isinstance(obj, Mesh): obj = obj.mesh
1338 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1339 aMeasurements = self.CreateMeasurements()
1340 value = aMeasurements.Length(obj)
1341 aMeasurements.UnRegister()
1344 def GetArea(self, obj):
1346 Get sum of areas of all 2D elements in the mesh object.
1349 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1352 sum of areas of all 2D elements
1355 if isinstance(obj, Mesh): obj = obj.mesh
1356 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1357 aMeasurements = self.CreateMeasurements()
1358 value = aMeasurements.Area(obj)
1359 aMeasurements.UnRegister()
1362 def GetVolume(self, obj):
1364 Get sum of volumes of all 3D elements in the mesh object.
1367 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1370 sum of volumes of all 3D elements
1373 if isinstance(obj, Mesh): obj = obj.mesh
1374 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1375 aMeasurements = self.CreateMeasurements()
1376 value = aMeasurements.Volume(obj)
1377 aMeasurements.UnRegister()
1380 def GetGravityCenter(self, obj):
1382 Get gravity center of all nodes of the mesh object.
1385 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1388 Three components of the gravity center (x,y,z)
1390 if isinstance(obj, Mesh): obj = obj.mesh
1391 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1392 aMeasurements = self.CreateMeasurements()
1393 pointStruct = aMeasurements.GravityCenter(obj)
1394 aMeasurements.UnRegister()
1395 return pointStruct.x, pointStruct.y, pointStruct.z
1397 pass # end of class smeshBuilder
1400 omniORB.registerObjref(SMESH._objref_SMESH_Gen._NP_RepositoryId, smeshBuilder)
1401 """Registering the new proxy for SMESH.SMESH_Gen"""
1404 def New( instance=None, instanceGeom=None):
1406 Create a new smeshBuilder instance. The smeshBuilder class provides the Python
1407 interface to create or load meshes.
1412 salome.salome_init()
1413 from salome.smesh import smeshBuilder
1414 smesh = smeshBuilder.New()
1417 isPublished If False, the notebool will not be used.
1418 instance CORBA proxy of SMESH Engine. If None, the default Engine is used.
1420 :class:`smeshBuilder` instance
1428 smeshInst = smeshBuilder()
1429 assert isinstance(smeshInst,smeshBuilder), "Smesh engine class is %s but should be smeshBuilder.smeshBuilder. Import salome.smesh.smeshBuilder before creating the instance."%smeshInst.__class__
1430 smeshInst.init_smesh(instanceGeom)
1434 # Public class: Mesh
1435 # ==================
1438 class Mesh(metaclass = MeshMeta):
1440 This class allows defining and managing a mesh.
1441 It has a set of methods to build a mesh on the given geometry, including the definition of sub-meshes.
1442 It also has methods to define groups of mesh elements, to modify a mesh (by addition of
1443 new nodes and elements and by changing the existing entities), to get information
1444 about a mesh and to export a mesh in different formats.
1451 def __init__(self, smeshpyD, geompyD, obj=0, name=0):
1456 Create a mesh on the shape *obj* (or an empty mesh if *obj* is equal to 0) and
1457 sets the GUI name of this mesh to *name*.
1460 smeshpyD: an instance of smeshBuilder class
1461 geompyD: an instance of geomBuilder class
1462 obj: Shape to be meshed or :class:`SMESH.SMESH_Mesh` object
1463 name: Study name of the mesh
1466 self.smeshpyD = smeshpyD
1467 self.geompyD = geompyD
1472 if isinstance(obj, geomBuilder.GEOM._objref_GEOM_Object):
1475 # publish geom of mesh (issue 0021122)
1476 if not self.geom.GetStudyEntry():
1480 geo_name = name + " shape"
1482 geo_name = "%s_%s to mesh"%(self.geom.GetShapeType(), id(self.geom)%100)
1483 geompyD.addToStudy( self.geom, geo_name )
1484 self.SetMesh( self.smeshpyD.CreateMesh(self.geom) )
1486 elif isinstance(obj, SMESH._objref_SMESH_Mesh):
1489 self.SetMesh( self.smeshpyD.CreateEmptyMesh() )
1491 self.smeshpyD.SetName(self.mesh, name)
1493 self.smeshpyD.SetName(self.mesh, GetName(obj)) # + " mesh"
1496 self.geom = self.mesh.GetShapeToMesh()
1498 self.editor = self.mesh.GetMeshEditor()
1499 self.functors = [None] * SMESH.FT_Undefined._v
1501 # set self to algoCreator's
1502 for attrName in dir(self):
1503 attr = getattr( self, attrName )
1504 if isinstance( attr, algoCreator ):
1505 setattr( self, attrName, attr.copy( self ))
1512 Destructor. Clean-up resources
1515 #self.mesh.UnRegister()
1519 def SetMesh(self, theMesh):
1521 Initialize the Mesh object from an instance of :class:`SMESH.SMESH_Mesh` interface
1524 theMesh: a :class:`SMESH.SMESH_Mesh` object
1528 # do not call Register() as this prevents mesh servant deletion at closing study
1529 #if self.mesh: self.mesh.UnRegister()
1532 #self.mesh.Register()
1533 self.geom = self.mesh.GetShapeToMesh()
1538 Return the mesh, that is an encapsulated instance of :class:`SMESH.SMESH_Mesh` interface
1541 a :class:`SMESH.SMESH_Mesh` object
1548 Get the name of the mesh
1551 the name of the mesh as a string
1554 name = GetName(self.GetMesh())
1557 def SetName(self, name):
1559 Set a name to the mesh
1562 name: a new name of the mesh
1565 self.smeshpyD.SetName(self.GetMesh(), name)
1567 def GetSubMesh(self, geom, name):
1569 Get a sub-mesh object associated to a *geom* geometrical object.
1572 geom: a geometrical object (shape)
1573 name: a name for the sub-mesh in the Object Browser
1576 an object of type :class:`SMESH.SMESH_subMesh`, representing a part of mesh,
1577 which lies on the given shape
1580 A sub-mesh is implicitly created when a sub-shape is specified at
1581 creating an algorithm, for example::
1583 algo1D = mesh.Segment(geom=Edge_1)
1585 creates a sub-mesh on *Edge_1* and assign Wire Discretization algorithm to it.
1586 The created sub-mesh can be retrieved from the algorithm::
1588 submesh = algo1D.GetSubMesh()
1591 AssureGeomPublished( self, geom, name )
1592 submesh = self.mesh.GetSubMesh( geom, name )
1597 Return the shape associated to the mesh
1605 def SetShape(self, geom):
1607 Associate the given shape to the mesh (entails the recreation of the mesh)
1610 geom: the shape to be meshed (GEOM_Object)
1613 self.mesh = self.smeshpyD.CreateMesh(geom)
1617 Load mesh from the study after opening the study
1621 def IsReadyToCompute(self, theSubObject):
1623 Return true if the hypotheses are defined well
1626 theSubObject: a sub-shape of a mesh shape
1632 return self.smeshpyD.IsReadyToCompute(self.mesh, theSubObject)
1634 def GetAlgoState(self, theSubObject):
1636 Return errors of hypotheses definition.
1637 The list of errors is empty if everything is OK.
1640 theSubObject: a sub-shape of a mesh shape
1646 return self.smeshpyD.GetAlgoState(self.mesh, theSubObject)
1648 def GetGeometryByMeshElement(self, theElementID, theGeomName):
1650 Return a geometrical object on which the given element was built.
1651 The returned geometrical object, if not nil, is either found in the
1652 study or published by this method with the given name
1655 theElementID: the id of the mesh element
1656 theGeomName: the user-defined name of the geometrical object
1659 GEOM.GEOM_Object instance
1662 return self.smeshpyD.GetGeometryByMeshElement( self.mesh, theElementID, theGeomName )
1664 def MeshDimension(self):
1666 Return the mesh dimension depending on the dimension of the underlying shape
1667 or, if the mesh is not based on any shape, basing on deimension of elements
1670 mesh dimension as an integer value [0,3]
1673 if self.mesh.HasShapeToMesh():
1674 shells = self.geompyD.SubShapeAllIDs( self.geom, self.geompyD.ShapeType["SOLID"] )
1675 if len( shells ) > 0 :
1677 elif self.geompyD.NumberOfFaces( self.geom ) > 0 :
1679 elif self.geompyD.NumberOfEdges( self.geom ) > 0 :
1684 if self.NbVolumes() > 0: return 3
1685 if self.NbFaces() > 0: return 2
1686 if self.NbEdges() > 0: return 1
1689 def Evaluate(self, geom=0):
1691 Evaluate size of prospective mesh on a shape
1694 a list where i-th element is a number of elements of i-th :class:`SMESH.EntityType`.
1695 To know predicted number of e.g. edges, inquire it this way::
1697 Evaluate()[ smesh.EnumToLong( SMESH.Entity_Edge )]
1700 if geom == 0 or not isinstance(geom, geomBuilder.GEOM._objref_GEOM_Object):
1702 geom = self.mesh.GetShapeToMesh()
1705 return self.smeshpyD.Evaluate(self.mesh, geom)
1708 def Compute(self, geom=0, discardModifs=False, refresh=False):
1710 Compute the mesh and return the status of the computation
1713 geom: geomtrical shape on which mesh data should be computed
1714 discardModifs: if True and the mesh has been edited since
1715 a last total re-compute and that may prevent successful partial re-compute,
1716 then the mesh is cleaned before Compute()
1717 refresh: if *True*, Object Browser is automatically updated (when running in GUI)
1723 if geom == 0 or not isinstance(geom, geomBuilder.GEOM._objref_GEOM_Object):
1725 geom = self.mesh.GetShapeToMesh()
1730 if discardModifs and self.mesh.HasModificationsToDiscard(): # issue 0020693
1732 ok = self.smeshpyD.Compute(self.mesh, geom)
1733 except SALOME.SALOME_Exception as ex:
1734 print("Mesh computation failed, exception caught:")
1735 print(" ", ex.details.text)
1738 print("Mesh computation failed, exception caught:")
1739 traceback.print_exc()
1743 # Treat compute errors
1744 computeErrors = self.smeshpyD.GetComputeErrors( self.mesh, geom )
1746 for err in computeErrors:
1747 if self.mesh.HasShapeToMesh():
1748 shapeText = " on %s" % self.GetSubShapeName( err.subShapeID )
1750 stdErrors = ["OK", #COMPERR_OK
1751 "Invalid input mesh", #COMPERR_BAD_INPUT_MESH
1752 "std::exception", #COMPERR_STD_EXCEPTION
1753 "OCC exception", #COMPERR_OCC_EXCEPTION
1754 "..", #COMPERR_SLM_EXCEPTION
1755 "Unknown exception", #COMPERR_EXCEPTION
1756 "Memory allocation problem", #COMPERR_MEMORY_PB
1757 "Algorithm failed", #COMPERR_ALGO_FAILED
1758 "Unexpected geometry", #COMPERR_BAD_SHAPE
1759 "Warning", #COMPERR_WARNING
1760 "Computation cancelled",#COMPERR_CANCELED
1761 "No mesh on sub-shape"] #COMPERR_NO_MESH_ON_SHAPE
1763 if err.code < len(stdErrors): errText = stdErrors[err.code]
1765 errText = "code %s" % -err.code
1766 if errText: errText += ". "
1767 errText += err.comment
1768 if allReasons: allReasons += "\n"
1770 allReasons += '- "%s"%s - %s' %(err.algoName, shapeText, errText)
1772 allReasons += '- "%s" failed%s. Error: %s' %(err.algoName, shapeText, errText)
1776 errors = self.smeshpyD.GetAlgoState( self.mesh, geom )
1778 if err.isGlobalAlgo:
1786 reason = '%s %sD algorithm is missing' % (glob, dim)
1787 elif err.state == HYP_MISSING:
1788 reason = ('%s %sD algorithm "%s" misses %sD hypothesis'
1789 % (glob, dim, name, dim))
1790 elif err.state == HYP_NOTCONFORM:
1791 reason = 'Global "Not Conform mesh allowed" hypothesis is missing'
1792 elif err.state == HYP_BAD_PARAMETER:
1793 reason = ('Hypothesis of %s %sD algorithm "%s" has a bad parameter value'
1794 % ( glob, dim, name ))
1795 elif err.state == HYP_BAD_GEOMETRY:
1796 reason = ('%s %sD algorithm "%s" is assigned to mismatching'
1797 'geometry' % ( glob, dim, name ))
1798 elif err.state == HYP_HIDDEN_ALGO:
1799 reason = ('%s %sD algorithm "%s" is ignored due to presence of a %s '
1800 'algorithm of upper dimension generating %sD mesh'
1801 % ( glob, dim, name, glob, dim ))
1803 reason = ("For unknown reason. "
1804 "Developer, revise Mesh.Compute() implementation in smeshBuilder.py!")
1806 if allReasons: allReasons += "\n"
1807 allReasons += "- " + reason
1809 if not ok or allReasons != "":
1810 msg = '"' + GetName(self.mesh) + '"'
1811 if ok: msg += " has been computed with warnings"
1812 else: msg += " has not been computed"
1813 if allReasons != "": msg += ":"
1818 if salome.sg.hasDesktop():
1819 if not isinstance( refresh, list): # not a call from subMesh.Compute()
1820 smeshgui = salome.ImportComponentGUI("SMESH")
1822 smeshgui.SetMeshIcon( salome.ObjectToID( self.mesh ), ok, (self.NbNodes()==0) )
1823 if refresh: salome.sg.updateObjBrowser()
1827 def GetComputeErrors(self, shape=0 ):
1829 Return a list of error messages (:class:`SMESH.ComputeError`) of the last :meth:`Compute`
1833 shape = self.mesh.GetShapeToMesh()
1834 return self.smeshpyD.GetComputeErrors( self.mesh, shape )
1836 def GetSubShapeName(self, subShapeID ):
1838 Return a name of a sub-shape by its ID.
1839 Possible variants (for *subShapeID* == 3):
1841 - **"Face_12"** - published sub-shape
1842 - **FACE #3** - not published sub-shape
1843 - **sub-shape #3** - invalid sub-shape ID
1844 - **#3** - error in this function
1847 subShapeID: a unique ID of a sub-shape
1850 a string describing the sub-shape
1854 if not self.mesh.HasShapeToMesh():
1858 mainIOR = salome.orb.object_to_string( self.GetShape() )
1860 mainSO = s.FindObjectIOR(mainIOR)
1863 shapeText = '"%s"' % mainSO.GetName()
1864 subIt = s.NewChildIterator(mainSO)
1866 subSO = subIt.Value()
1868 obj = subSO.GetObject()
1869 if not obj: continue
1870 go = obj._narrow( geomBuilder.GEOM._objref_GEOM_Object )
1873 ids = self.geompyD.GetSubShapeID( self.GetShape(), go )
1876 if ids == subShapeID:
1877 shapeText = '"%s"' % subSO.GetName()
1879 shape = self.geompyD.GetSubShape( self.GetShape(), [subShapeID])
1881 shapeText = '%s #%s' % (shape.GetShapeType(), subShapeID)
1883 shapeText = 'sub-shape #%s' % (subShapeID)
1885 shapeText = "#%s" % (subShapeID)
1888 def GetFailedShapes(self, publish=False):
1890 Return a list of sub-shapes meshing of which failed, grouped into GEOM groups by
1891 error of an algorithm
1894 publish: if *True*, the returned groups will be published in the study
1897 a list of GEOM groups each named after a failed algorithm
1902 computeErrors = self.smeshpyD.GetComputeErrors( self.mesh, self.GetShape() )
1903 for err in computeErrors:
1904 shape = self.geompyD.GetSubShape( self.GetShape(), [err.subShapeID])
1905 if not shape: continue
1906 if err.algoName in algo2shapes:
1907 algo2shapes[ err.algoName ].append( shape )
1909 algo2shapes[ err.algoName ] = [ shape ]
1913 for algoName, shapes in list(algo2shapes.items()):
1915 groupType = self.smeshpyD.EnumToLong( shapes[0].GetShapeType() )
1916 otherTypeShapes = []
1918 group = self.geompyD.CreateGroup( self.geom, groupType )
1919 for shape in shapes:
1920 if shape.GetShapeType() == shapes[0].GetShapeType():
1921 sameTypeShapes.append( shape )
1923 otherTypeShapes.append( shape )
1924 self.geompyD.UnionList( group, sameTypeShapes )
1926 group.SetName( "%s %s" % ( algoName, shapes[0].GetShapeType() ))
1928 group.SetName( algoName )
1929 groups.append( group )
1930 shapes = otherTypeShapes
1933 for group in groups:
1934 self.geompyD.addToStudyInFather( self.geom, group, group.GetName() )
1937 def GetMeshOrder(self):
1939 Return sub-mesh objects list in meshing order
1942 list of lists of :class:`sub-meshes <SMESH.SMESH_subMesh>`
1945 return self.mesh.GetMeshOrder()
1947 def SetMeshOrder(self, submeshes):
1949 Set order in which concurrent sub-meshes should be meshed
1952 submeshes: list of lists of :class:`sub-meshes <SMESH.SMESH_subMesh>`
1955 return self.mesh.SetMeshOrder(submeshes)
1957 def Clear(self, refresh=False):
1959 Remove all nodes and elements generated on geometry. Imported elements remain.
1962 refresh: if *True*, Object browser is automatically updated (when running in GUI)
1966 if ( salome.sg.hasDesktop() ):
1967 smeshgui = salome.ImportComponentGUI("SMESH")
1969 smeshgui.SetMeshIcon( salome.ObjectToID( self.mesh ), False, True )
1970 if refresh: salome.sg.updateObjBrowser()
1972 def ClearSubMesh(self, geomId, refresh=False):
1974 Remove all nodes and elements of indicated shape
1977 geomId: the ID of a sub-shape to remove elements on
1978 refresh: if *True*, Object browser is automatically updated (when running in GUI)
1981 self.mesh.ClearSubMesh(geomId)
1982 if salome.sg.hasDesktop():
1983 smeshgui = salome.ImportComponentGUI("SMESH")
1985 smeshgui.SetMeshIcon( salome.ObjectToID( self.mesh ), False, True )
1986 if refresh: salome.sg.updateObjBrowser()
1988 def AutomaticTetrahedralization(self, fineness=0):
1990 Compute a tetrahedral mesh using AutomaticLength + MEFISTO + Tetrahedron
1993 fineness: [0.0,1.0] defines mesh fineness
1999 dim = self.MeshDimension()
2001 self.RemoveGlobalHypotheses()
2002 self.Segment().AutomaticLength(fineness)
2004 self.Triangle().LengthFromEdges()
2009 return self.Compute()
2011 def AutomaticHexahedralization(self, fineness=0):
2013 Compute an hexahedral mesh using AutomaticLength + Quadrangle + Hexahedron
2016 fineness: [0.0, 1.0] defines mesh fineness
2022 dim = self.MeshDimension()
2023 # assign the hypotheses
2024 self.RemoveGlobalHypotheses()
2025 self.Segment().AutomaticLength(fineness)
2032 return self.Compute()
2034 def AddHypothesis(self, hyp, geom=0):
2039 hyp: a hypothesis to assign
2040 geom: a subhape of mesh geometry
2043 :class:`SMESH.Hypothesis_Status`
2046 if isinstance( hyp, geomBuilder.GEOM._objref_GEOM_Object ):
2047 hyp, geom = geom, hyp
2048 if isinstance( hyp, Mesh_Algorithm ):
2049 hyp = hyp.GetAlgorithm()
2054 geom = self.mesh.GetShapeToMesh()
2057 if self.mesh.HasShapeToMesh():
2058 hyp_type = hyp.GetName()
2059 lib_name = hyp.GetLibName()
2060 # checkAll = ( not geom.IsSame( self.mesh.GetShapeToMesh() ))
2061 # if checkAll and geom:
2062 # checkAll = geom.GetType() == 37
2064 isApplicable = self.smeshpyD.IsApplicable(hyp_type, lib_name, geom, checkAll)
2066 AssureGeomPublished( self, geom, "shape for %s" % hyp.GetName())
2067 status = self.mesh.AddHypothesis(geom, hyp)
2069 status = HYP_BAD_GEOMETRY, ""
2070 hyp_name = GetName( hyp )
2073 geom_name = geom.GetName()
2074 isAlgo = hyp._narrow( SMESH_Algo )
2075 TreatHypoStatus( status, hyp_name, geom_name, isAlgo, self )
2078 def IsUsedHypothesis(self, hyp, geom):
2080 Return True if an algorithm or hypothesis is assigned to a given shape
2083 hyp: an algorithm or hypothesis to check
2084 geom: a subhape of mesh geometry
2090 if not hyp: # or not geom
2092 if isinstance( hyp, Mesh_Algorithm ):
2093 hyp = hyp.GetAlgorithm()
2095 hyps = self.GetHypothesisList(geom)
2097 if h.GetId() == hyp.GetId():
2101 def RemoveHypothesis(self, hyp, geom=0):
2103 Unassign a hypothesis
2106 hyp (SMESH.SMESH_Hypothesis): a hypothesis to unassign
2107 geom (GEOM.GEOM_Object): a sub-shape of mesh geometry
2110 :class:`SMESH.Hypothesis_Status`
2115 if isinstance( hyp, Mesh_Algorithm ):
2116 hyp = hyp.GetAlgorithm()
2122 if self.IsUsedHypothesis( hyp, shape ):
2123 return self.mesh.RemoveHypothesis( shape, hyp )
2124 hypName = GetName( hyp )
2125 geoName = GetName( shape )
2126 print("WARNING: RemoveHypothesis() failed as '%s' is not assigned to '%s' shape" % ( hypName, geoName ))
2129 def GetHypothesisList(self, geom):
2131 Get the list of hypotheses added on a geometry
2134 geom (GEOM.GEOM_Object): a sub-shape of mesh geometry
2137 the sequence of :class:`SMESH.SMESH_Hypothesis`
2140 return self.mesh.GetHypothesisList( geom )
2142 def RemoveGlobalHypotheses(self):
2144 Remove all global hypotheses
2147 current_hyps = self.mesh.GetHypothesisList( self.geom )
2148 for hyp in current_hyps:
2149 self.mesh.RemoveHypothesis( self.geom, hyp )
2152 def ExportMED(self, *args, **kwargs):
2154 Export the mesh in a file in MED format
2155 allowing to overwrite the file if it exists or add the exported data to its contents
2158 fileName: is the file name
2159 auto_groups (boolean): parameter for creating/not creating
2160 the groups Group_On_All_Nodes, Group_On_All_Faces, ... ;
2161 the typical use is auto_groups=False.
2162 overwrite (boolean): parameter for overwriting/not overwriting the file
2163 meshPart: a part of mesh (group, sub-mesh) to export instead of the mesh
2164 autoDimension if @c True (default), a space dimension of a MED mesh can be either
2165 - 1D if all mesh nodes lie on OX coordinate axis, or
2166 - 2D if all mesh nodes lie on XOY coordinate plane, or
2167 - 3D in the rest cases.
2168 If *autoDimension* is *False*, the space dimension is always 3.
2169 fields: list of GEOM fields defined on the shape to mesh.
2170 geomAssocFields: each character of this string means a need to export a
2171 corresponding field; correspondence between fields and characters is following:
2172 - 'v' stands for "_vertices _" field;
2173 - 'e' stands for "_edges _" field;
2174 - 'f' stands for "_faces _" field;
2175 - 's' stands for "_solids _" field.
2177 # process positional arguments
2178 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]] # backward compatibility
2180 auto_groups = args[1] if len(args) > 1 else False
2181 overwrite = args[2] if len(args) > 2 else True
2182 meshPart = args[3] if len(args) > 3 else None
2183 autoDimension = args[4] if len(args) > 4 else True
2184 fields = args[5] if len(args) > 5 else []
2185 geomAssocFields = args[6] if len(args) > 6 else ''
2186 # process keywords arguments
2187 auto_groups = kwargs.get("auto_groups", auto_groups)
2188 overwrite = kwargs.get("overwrite", overwrite)
2189 meshPart = kwargs.get("meshPart", meshPart)
2190 autoDimension = kwargs.get("autoDimension", autoDimension)
2191 fields = kwargs.get("fields", fields)
2192 geomAssocFields = kwargs.get("geomAssocFields", geomAssocFields)
2193 # invoke engine's function
2194 if meshPart or fields or geomAssocFields:
2195 unRegister = genObjUnRegister()
2196 if isinstance( meshPart, list ):
2197 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2198 unRegister.set( meshPart )
2199 self.mesh.ExportPartToMED( meshPart, fileName, auto_groups, overwrite, autoDimension,
2200 fields, geomAssocFields)
2202 self.mesh.ExportMED(fileName, auto_groups, overwrite, autoDimension)
2204 def ExportSAUV(self, f, auto_groups=0):
2206 Export the mesh in a file in SAUV format
2211 auto_groups: boolean parameter for creating/not creating
2212 the groups Group_On_All_Nodes, Group_On_All_Faces, ... ;
2213 the typical use is auto_groups=False.
2216 self.mesh.ExportSAUV(f, auto_groups)
2218 def ExportDAT(self, f, meshPart=None):
2220 Export the mesh in a file in DAT format
2224 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2228 unRegister = genObjUnRegister()
2229 if isinstance( meshPart, list ):
2230 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2231 unRegister.set( meshPart )
2232 self.mesh.ExportPartToDAT( meshPart, f )
2234 self.mesh.ExportDAT(f)
2236 def ExportUNV(self, f, meshPart=None):
2238 Export the mesh in a file in UNV format
2242 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2246 unRegister = genObjUnRegister()
2247 if isinstance( meshPart, list ):
2248 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2249 unRegister.set( meshPart )
2250 self.mesh.ExportPartToUNV( meshPart, f )
2252 self.mesh.ExportUNV(f)
2254 def ExportSTL(self, f, ascii=1, meshPart=None):
2256 Export the mesh in a file in STL format
2260 ascii: defines the file encoding
2261 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2265 unRegister = genObjUnRegister()
2266 if isinstance( meshPart, list ):
2267 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2268 unRegister.set( meshPart )
2269 self.mesh.ExportPartToSTL( meshPart, f, ascii )
2271 self.mesh.ExportSTL(f, ascii)
2273 def ExportCGNS(self, f, overwrite=1, meshPart=None, groupElemsByType=False):
2275 Export the mesh in a file in CGNS format
2279 overwrite: boolean parameter for overwriting/not overwriting the file
2280 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2281 groupElemsByType: if True all elements of same entity type are exported at ones,
2282 else elements are exported in order of their IDs which can cause creation
2283 of multiple cgns sections
2286 unRegister = genObjUnRegister()
2287 if isinstance( meshPart, list ):
2288 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2289 unRegister.set( meshPart )
2290 if isinstance( meshPart, Mesh ):
2291 meshPart = meshPart.mesh
2293 meshPart = self.mesh
2294 self.mesh.ExportCGNS(meshPart, f, overwrite, groupElemsByType)
2296 def ExportGMF(self, f, meshPart=None):
2298 Export the mesh in a file in GMF format.
2299 GMF files must have .mesh extension for the ASCII format and .meshb for
2300 the bynary format. Other extensions are not allowed.
2304 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2307 unRegister = genObjUnRegister()
2308 if isinstance( meshPart, list ):
2309 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
2310 unRegister.set( meshPart )
2311 if isinstance( meshPart, Mesh ):
2312 meshPart = meshPart.mesh
2314 meshPart = self.mesh
2315 self.mesh.ExportGMF(meshPart, f, True)
2317 def ExportToMED(self, *args, **kwargs):
2319 Deprecated, used only for compatibility! Please, use :meth:`ExportMED` method instead.
2320 Export the mesh in a file in MED format
2321 allowing to overwrite the file if it exists or add the exported data to its contents
2324 fileName: the file name
2325 opt (boolean): parameter for creating/not creating
2326 the groups Group_On_All_Nodes, Group_On_All_Faces, ...
2327 overwrite: boolean parameter for overwriting/not overwriting the file
2328 autoDimension: if *True* (default), a space dimension of a MED mesh can be either
2330 - 1D if all mesh nodes lie on OX coordinate axis, or
2331 - 2D if all mesh nodes lie on XOY coordinate plane, or
2332 - 3D in the rest cases.
2334 If **autoDimension** is *False*, the space dimension is always 3.
2337 print("WARNING: ExportToMED() is deprecated, use ExportMED() instead")
2338 # process positional arguments
2339 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]] # backward compatibility
2341 auto_groups = args[1] if len(args) > 1 else False
2342 overwrite = args[2] if len(args) > 2 else True
2343 autoDimension = args[3] if len(args) > 3 else True
2344 # process keywords arguments
2345 auto_groups = kwargs.get("opt", auto_groups) # old keyword name
2346 auto_groups = kwargs.get("auto_groups", auto_groups) # new keyword name
2347 overwrite = kwargs.get("overwrite", overwrite)
2348 autoDimension = kwargs.get("autoDimension", autoDimension)
2349 # invoke engine's function
2350 self.mesh.ExportMED(fileName, auto_groups, overwrite, autoDimension)
2352 def ExportToMEDX(self, *args, **kwargs):
2354 Deprecated, used only for compatibility! Please, use ExportMED() method instead.
2355 Export the mesh in a file in MED format
2358 fileName: the file name
2359 opt (boolean): parameter for creating/not creating
2360 the groups Group_On_All_Nodes, Group_On_All_Faces, ...
2361 overwrite: boolean parameter for overwriting/not overwriting the file
2362 autoDimension: if *True* (default), a space dimension of a MED mesh can be either
2364 - 1D if all mesh nodes lie on OX coordinate axis, or
2365 - 2D if all mesh nodes lie on XOY coordinate plane, or
2366 - 3D in the rest cases.
2368 If **autoDimension** is *False*, the space dimension is always 3.
2371 print("WARNING: ExportToMEDX() is deprecated, use ExportMED() instead")
2372 # process positional arguments
2373 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]] # backward compatibility
2375 auto_groups = args[1] if len(args) > 1 else False
2376 overwrite = args[2] if len(args) > 2 else True
2377 autoDimension = args[3] if len(args) > 3 else True
2378 # process keywords arguments
2379 auto_groups = kwargs.get("auto_groups", auto_groups)
2380 overwrite = kwargs.get("overwrite", overwrite)
2381 autoDimension = kwargs.get("autoDimension", autoDimension)
2382 # invoke engine's function
2383 self.mesh.ExportMED(fileName, auto_groups, overwrite, autoDimension)
2385 # Operations with groups:
2386 # ----------------------
2387 def CreateEmptyGroup(self, elementType, name):
2389 Create an empty mesh group
2392 elementType: the :class:`type <SMESH.ElementType>` of elements in the group;
2393 either of (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
2394 name: the name of the mesh group
2397 :class:`SMESH.SMESH_Group`
2400 return self.mesh.CreateGroup(elementType, name)
2402 def Group(self, grp, name=""):
2404 Create a mesh group based on the geometric object *grp*
2405 and give it a *name*.
2406 If *name* is not defined the name of the geometric group is used
2409 Works like :meth:`GroupOnGeom`.
2412 grp: a geometric group, a vertex, an edge, a face or a solid
2413 name: the name of the mesh group
2416 :class:`SMESH.SMESH_GroupOnGeom`
2419 return self.GroupOnGeom(grp, name)
2421 def GroupOnGeom(self, grp, name="", typ=None):
2423 Create a mesh group based on the geometrical object *grp*
2425 if *name* is not defined the name of the geometric group is used
2428 grp: a geometrical group, a vertex, an edge, a face or a solid
2429 name: the name of the mesh group
2430 typ: the type of elements in the group; either of
2431 (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME). If not set, it is
2432 automatically detected by the type of the geometry
2435 :class:`SMESH.SMESH_GroupOnGeom`
2438 AssureGeomPublished( self, grp, name )
2440 name = grp.GetName()
2442 typ = self._groupTypeFromShape( grp )
2443 return self.mesh.CreateGroupFromGEOM(typ, name, grp)
2445 def _groupTypeFromShape( self, shape ):
2447 Pivate method to get a type of group on geometry
2449 tgeo = str(shape.GetShapeType())
2450 if tgeo == "VERTEX":
2452 elif tgeo == "EDGE":
2454 elif tgeo == "FACE" or tgeo == "SHELL":
2456 elif tgeo == "SOLID" or tgeo == "COMPSOLID":
2458 elif tgeo == "COMPOUND":
2459 sub = self.geompyD.SubShapeAll( shape, self.geompyD.ShapeType["SHAPE"])
2461 raise ValueError("_groupTypeFromShape(): empty geometric group or compound '%s'" % GetName(shape))
2462 return self._groupTypeFromShape( sub[0] )
2464 raise ValueError("_groupTypeFromShape(): invalid geometry '%s'" % GetName(shape))
2467 def GroupOnFilter(self, typ, name, filter):
2469 Create a mesh group with given *name* based on the *filter* which
2470 is a special type of group dynamically updating it's contents during
2474 typ: the type of elements in the group; either of
2475 (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME).
2476 name: the name of the mesh group
2477 filter (SMESH.Filter): the filter defining group contents
2480 :class:`SMESH.SMESH_GroupOnFilter`
2483 return self.mesh.CreateGroupFromFilter(typ, name, filter)
2485 def MakeGroupByIds(self, groupName, elementType, elemIDs):
2487 Create a mesh group by the given ids of elements
2490 groupName: the name of the mesh group
2491 elementType: the type of elements in the group; either of
2492 (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME).
2493 elemIDs: either the list of ids, :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
2496 :class:`SMESH.SMESH_Group`
2499 group = self.mesh.CreateGroup(elementType, groupName)
2500 if isinstance( elemIDs, Mesh ):
2501 elemIDs = elemIDs.GetMesh()
2502 if hasattr( elemIDs, "GetIDs" ):
2503 if hasattr( elemIDs, "SetMesh" ):
2504 elemIDs.SetMesh( self.GetMesh() )
2505 group.AddFrom( elemIDs )
2513 CritType=FT_Undefined,
2516 UnaryOp=FT_Undefined,
2519 Create a mesh group by the given conditions
2522 groupName: the name of the mesh group
2523 elementType (SMESH.ElementType): the type of elements (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
2524 CritType (SMESH.FunctorType): the type of criterion (SMESH.FT_Taper, SMESH.FT_Area, etc.).
2525 Note that the items starting from FT_LessThan are not suitable for CritType.
2526 Compare (SMESH.FunctorType): belongs to {SMESH.FT_LessThan, SMESH.FT_MoreThan, SMESH.FT_EqualTo}
2527 Threshold: the threshold value (range of ids as string, shape, numeric, depending on *CritType*)
2528 UnaryOp (SMESH.FunctorType): SMESH.FT_LogicalNOT or SMESH.FT_Undefined
2529 Tolerance (float): the tolerance used by SMESH.FT_BelongToGeom, SMESH.FT_BelongToSurface,
2530 SMESH.FT_LyingOnGeom, SMESH.FT_CoplanarFaces criteria
2533 :class:`SMESH.SMESH_GroupOnFilter`
2536 aCriterion = self.smeshpyD.GetCriterion(elementType, CritType, Compare, Threshold, UnaryOp, FT_Undefined,Tolerance)
2537 group = self.MakeGroupByCriterion(groupName, aCriterion)
2540 def MakeGroupByCriterion(self, groupName, Criterion):
2542 Create a mesh group by the given criterion
2545 groupName: the name of the mesh group
2546 Criterion: the instance of :class:`SMESH.Filter.Criterion` class
2549 :class:`SMESH.SMESH_GroupOnFilter`
2552 :meth:`smeshBuilder.GetCriterion`
2555 return self.MakeGroupByCriteria( groupName, [Criterion] )
2557 def MakeGroupByCriteria(self, groupName, theCriteria, binOp=SMESH.FT_LogicalAND):
2559 Create a mesh group by the given criteria (list of :class:`SMESH.Filter.Criterion`)
2562 groupName: the name of the mesh group
2563 theCriteria: the list of :class:`SMESH.Filter.Criterion`
2564 binOp: binary operator (SMESH.FT_LogicalAND or SMESH.FT_LogicalOR ) used when binary operator of criteria is undefined
2567 :class:`SMESH.SMESH_GroupOnFilter`
2570 :meth:`smeshBuilder.GetCriterion`
2573 aFilter = self.smeshpyD.GetFilterFromCriteria( theCriteria, binOp )
2574 group = self.MakeGroupByFilter(groupName, aFilter)
2577 def MakeGroupByFilter(self, groupName, theFilter):
2579 Create a mesh group by the given filter
2582 groupName (string): the name of the mesh group
2583 theFilter (SMESH.Filter): the filter
2586 :class:`SMESH.SMESH_GroupOnFilter`
2589 :meth:`smeshBuilder.GetFilter`
2592 #group = self.CreateEmptyGroup(theFilter.GetElementType(), groupName)
2593 #theFilter.SetMesh( self.mesh )
2594 #group.AddFrom( theFilter )
2595 group = self.GroupOnFilter( theFilter.GetElementType(), groupName, theFilter )
2598 def RemoveGroup(self, group):
2603 group (SMESH.SMESH_GroupBase): group to remove
2606 self.mesh.RemoveGroup(group)
2608 def RemoveGroupWithContents(self, group):
2610 Remove a group with its contents
2613 group (SMESH.SMESH_GroupBase): group to remove
2616 self.mesh.RemoveGroupWithContents(group)
2618 def GetGroups(self, elemType = SMESH.ALL):
2620 Get the list of groups existing in the mesh in the order
2621 of creation (starting from the oldest one)
2624 elemType (SMESH.ElementType): type of elements the groups contain;
2625 by default groups of elements of all types are returned
2628 a sequence of :class:`SMESH.SMESH_GroupBase`
2631 groups = self.mesh.GetGroups()
2632 if elemType == SMESH.ALL:
2636 if g.GetType() == elemType:
2637 typedGroups.append( g )
2644 Get the number of groups existing in the mesh
2647 the quantity of groups as an integer value
2650 return self.mesh.NbGroups()
2652 def GetGroupNames(self):
2654 Get the list of names of groups existing in the mesh
2660 groups = self.GetGroups()
2662 for group in groups:
2663 names.append(group.GetName())
2666 def GetGroupByName(self, name, elemType = None):
2668 Find groups by name and type
2671 name (string): name of the group of interest
2672 elemType (SMESH.ElementType): type of elements the groups contain;
2673 by default one group of any type is returned;
2674 if elemType == SMESH.ALL then all groups of any type are returned
2677 a list of :class:`SMESH.SMESH_GroupBase`
2681 for group in self.GetGroups():
2682 if group.GetName() == name:
2683 if elemType is None:
2685 if ( elemType == SMESH.ALL or
2686 group.GetType() == elemType ):
2687 groups.append( group )
2690 def UnionGroups(self, group1, group2, name):
2692 Produce a union of two groups.
2693 A new group is created. All mesh elements that are
2694 present in the initial groups are added to the new one
2697 group1 (SMESH.SMESH_GroupBase): a group
2698 group2 (SMESH.SMESH_GroupBase): another group
2701 instance of :class:`SMESH.SMESH_Group`
2704 return self.mesh.UnionGroups(group1, group2, name)
2706 def UnionListOfGroups(self, groups, name):
2708 Produce a union list of groups.
2709 New group is created. All mesh elements that are present in
2710 initial groups are added to the new one
2713 groups: list of :class:`SMESH.SMESH_GroupBase`
2716 instance of :class:`SMESH.SMESH_Group`
2718 return self.mesh.UnionListOfGroups(groups, name)
2720 def IntersectGroups(self, group1, group2, name):
2722 Prodice an intersection of two groups.
2723 A new group is created. All mesh elements that are common
2724 for the two initial groups are added to the new one.
2727 group1 (SMESH.SMESH_GroupBase): a group
2728 group2 (SMESH.SMESH_GroupBase): another group
2731 instance of :class:`SMESH.SMESH_Group`
2734 return self.mesh.IntersectGroups(group1, group2, name)
2736 def IntersectListOfGroups(self, groups, name):
2738 Produce an intersection of groups.
2739 New group is created. All mesh elements that are present in all
2740 initial groups simultaneously are added to the new one
2743 groups: a list of :class:`SMESH.SMESH_GroupBase`
2746 instance of :class:`SMESH.SMESH_Group`
2748 return self.mesh.IntersectListOfGroups(groups, name)
2750 def CutGroups(self, main_group, tool_group, name):
2752 Produce a cut of two groups.
2753 A new group is created. All mesh elements that are present in
2754 the main group but are not present in the tool group are added to the new one
2757 main_group (SMESH.SMESH_GroupBase): a group to cut from
2758 tool_group (SMESH.SMESH_GroupBase): a group to cut by
2761 an instance of :class:`SMESH.SMESH_Group`
2764 return self.mesh.CutGroups(main_group, tool_group, name)
2766 def CutListOfGroups(self, main_groups, tool_groups, name):
2768 Produce a cut of groups.
2769 A new group is created. All mesh elements that are present in main groups
2770 but do not present in tool groups are added to the new one
2773 main_group: groups to cut from (list of :class:`SMESH.SMESH_GroupBase`)
2774 tool_group: groups to cut by (list of :class:`SMESH.SMESH_GroupBase`)
2777 an instance of :class:`SMESH.SMESH_Group`
2780 return self.mesh.CutListOfGroups(main_groups, tool_groups, name)
2782 def CreateDimGroup(self, groups, elemType, name,
2783 nbCommonNodes = SMESH.ALL_NODES, underlyingOnly = True):
2785 Create a standalone group of entities basing on nodes of other groups.
2788 groups: list of reference :class:`sub-meshes, groups or filters <SMESH.SMESH_IDSource>`, of any type.
2789 elemType: a type of elements to include to the new group; either of
2790 (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME).
2791 name: a name of the new group.
2792 nbCommonNodes: a criterion of inclusion of an element to the new group
2793 basing on number of element nodes common with reference *groups*.
2794 Meaning of possible values are:
2796 - SMESH.ALL_NODES - include if all nodes are common,
2797 - SMESH.MAIN - include if all corner nodes are common (meaningful for a quadratic mesh),
2798 - SMESH.AT_LEAST_ONE - include if one or more node is common,
2799 - SMEHS.MAJORITY - include if half of nodes or more are common.
2800 underlyingOnly: if *True* (default), an element is included to the
2801 new group provided that it is based on nodes of an element of *groups*;
2802 in this case the reference *groups* are supposed to be of higher dimension
2803 than *elemType*, which can be useful for example to get all faces lying on
2804 volumes of the reference *groups*.
2807 an instance of :class:`SMESH.SMESH_Group`
2810 if isinstance( groups, SMESH._objref_SMESH_IDSource ):
2812 return self.mesh.CreateDimGroup(groups, elemType, name, nbCommonNodes, underlyingOnly)
2815 def ConvertToStandalone(self, group):
2817 Convert group on geom into standalone group
2820 return self.mesh.ConvertToStandalone(group)
2822 # Get some info about mesh:
2823 # ------------------------
2825 def GetLog(self, clearAfterGet):
2827 Return the log of nodes and elements added or removed
2828 since the previous clear of the log.
2831 clearAfterGet: log is emptied after Get (safe if concurrents access)
2834 list of SMESH.log_block structures { commandType, number, coords, indexes }
2837 return self.mesh.GetLog(clearAfterGet)
2841 Clear the log of nodes and elements added or removed since the previous
2842 clear. Must be used immediately after :meth:`GetLog` if clearAfterGet is false.
2845 self.mesh.ClearLog()
2847 def SetAutoColor(self, theAutoColor):
2849 Toggle auto color mode on the object.
2850 If switched on, a default color of a new group in Create Group dialog is chosen randomly.
2853 theAutoColor (boolean): the flag which toggles auto color mode.
2856 self.mesh.SetAutoColor(theAutoColor)
2858 def GetAutoColor(self):
2860 Get flag of object auto color mode.
2866 return self.mesh.GetAutoColor()
2873 integer value, which is the internal Id of the mesh
2876 return self.mesh.GetId()
2878 def HasDuplicatedGroupNamesMED(self):
2880 Check the group names for duplications.
2881 Consider the maximum group name length stored in MED file.
2887 return self.mesh.HasDuplicatedGroupNamesMED()
2889 def GetMeshEditor(self):
2891 Obtain the mesh editor tool
2894 an instance of :class:`SMESH.SMESH_MeshEditor`
2899 def GetIDSource(self, ids, elemType = SMESH.ALL):
2901 Wrap a list of IDs of elements or nodes into :class:`SMESH.SMESH_IDSource` which
2902 can be passed as argument to a method accepting :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
2906 elemType: type of elements; this parameter is used to distinguish
2907 IDs of nodes from IDs of elements; by default ids are treated as
2908 IDs of elements; use SMESH.NODE if ids are IDs of nodes.
2911 an instance of :class:`SMESH.SMESH_IDSource`
2914 call UnRegister() for the returned object as soon as it is no more useful::
2916 idSrc = mesh.GetIDSource( [1,3,5], SMESH.NODE )
2917 mesh.DoSomething( idSrc )
2921 if isinstance( ids, int ):
2923 return self.editor.MakeIDSource(ids, elemType)
2926 # Get information about mesh contents:
2927 # ------------------------------------
2929 def GetMeshInfo(self, obj = None):
2931 Get the mesh statistic.
2932 Use :meth:`smeshBuilder.EnumToLong` to get an integer from
2933 an item of :class:`SMESH.EntityType`.
2936 dictionary { :class:`SMESH.EntityType` - "count of elements" }
2939 if not obj: obj = self.mesh
2940 return self.smeshpyD.GetMeshInfo(obj)
2944 Return the number of nodes in the mesh
2950 return self.mesh.NbNodes()
2952 def NbElements(self):
2954 Return the number of elements in the mesh
2960 return self.mesh.NbElements()
2962 def Nb0DElements(self):
2964 Return the number of 0d elements in the mesh
2970 return self.mesh.Nb0DElements()
2974 Return the number of ball discrete elements in the mesh
2980 return self.mesh.NbBalls()
2984 Return the number of edges in the mesh
2990 return self.mesh.NbEdges()
2992 def NbEdgesOfOrder(self, elementOrder):
2994 Return the number of edges with the given order in the mesh
2997 elementOrder: the order of elements
2998 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3004 return self.mesh.NbEdgesOfOrder(elementOrder)
3008 Return the number of faces in the mesh
3014 return self.mesh.NbFaces()
3016 def NbFacesOfOrder(self, elementOrder):
3018 Return the number of faces with the given order in the mesh
3021 elementOrder: the order of elements
3022 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3028 return self.mesh.NbFacesOfOrder(elementOrder)
3030 def NbTriangles(self):
3032 Return the number of triangles in the mesh
3038 return self.mesh.NbTriangles()
3040 def NbTrianglesOfOrder(self, elementOrder):
3042 Return the number of triangles with the given order in the mesh
3045 elementOrder: is the order of elements
3046 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3052 return self.mesh.NbTrianglesOfOrder(elementOrder)
3054 def NbBiQuadTriangles(self):
3056 Return the number of biquadratic triangles in the mesh
3062 return self.mesh.NbBiQuadTriangles()
3064 def NbQuadrangles(self):
3066 Return the number of quadrangles in the mesh
3072 return self.mesh.NbQuadrangles()
3074 def NbQuadranglesOfOrder(self, elementOrder):
3076 Return the number of quadrangles with the given order in the mesh
3079 elementOrder: the order of elements
3080 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3086 return self.mesh.NbQuadranglesOfOrder(elementOrder)
3088 def NbBiQuadQuadrangles(self):
3090 Return the number of biquadratic quadrangles in the mesh
3096 return self.mesh.NbBiQuadQuadrangles()
3098 def NbPolygons(self, elementOrder = SMESH.ORDER_ANY):
3100 Return the number of polygons of given order in the mesh
3103 elementOrder: the order of elements
3104 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3110 return self.mesh.NbPolygonsOfOrder(elementOrder)
3112 def NbVolumes(self):
3114 Return the number of volumes in the mesh
3120 return self.mesh.NbVolumes()
3123 def NbVolumesOfOrder(self, elementOrder):
3125 Return the number of volumes with the given order in the mesh
3128 elementOrder: the order of elements
3129 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3135 return self.mesh.NbVolumesOfOrder(elementOrder)
3139 Return the number of tetrahedrons in the mesh
3145 return self.mesh.NbTetras()
3147 def NbTetrasOfOrder(self, elementOrder):
3149 Return the number of tetrahedrons with the given order in the mesh
3152 elementOrder: the order of elements
3153 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3159 return self.mesh.NbTetrasOfOrder(elementOrder)
3163 Return the number of hexahedrons in the mesh
3169 return self.mesh.NbHexas()
3171 def NbHexasOfOrder(self, elementOrder):
3173 Return the number of hexahedrons with the given order in the mesh
3176 elementOrder: the order of elements
3177 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3183 return self.mesh.NbHexasOfOrder(elementOrder)
3185 def NbTriQuadraticHexas(self):
3187 Return the number of triquadratic hexahedrons in the mesh
3193 return self.mesh.NbTriQuadraticHexas()
3195 def NbPyramids(self):
3197 Return the number of pyramids in the mesh
3203 return self.mesh.NbPyramids()
3205 def NbPyramidsOfOrder(self, elementOrder):
3207 Return the number of pyramids with the given order in the mesh
3210 elementOrder: the order of elements
3211 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3217 return self.mesh.NbPyramidsOfOrder(elementOrder)
3221 Return the number of prisms in the mesh
3227 return self.mesh.NbPrisms()
3229 def NbPrismsOfOrder(self, elementOrder):
3231 Return the number of prisms with the given order in the mesh
3234 elementOrder: the order of elements
3235 (SMESH.ORDER_ANY, SMESH.ORDER_LINEAR or SMESH.ORDER_QUADRATIC)
3241 return self.mesh.NbPrismsOfOrder(elementOrder)
3243 def NbHexagonalPrisms(self):
3245 Return the number of hexagonal prisms in the mesh
3251 return self.mesh.NbHexagonalPrisms()
3253 def NbPolyhedrons(self):
3255 Return the number of polyhedrons in the mesh
3261 return self.mesh.NbPolyhedrons()
3263 def NbSubMesh(self):
3265 Return the number of submeshes in the mesh
3271 return self.mesh.NbSubMesh()
3273 def GetElementsId(self):
3275 Return the list of all mesh elements IDs
3278 the list of integer values
3281 :meth:`GetElementsByType`
3284 return self.mesh.GetElementsId()
3286 def GetElementsByType(self, elementType):
3288 Return the list of IDs of mesh elements with the given type
3291 elementType (SMESH.ElementType): the required type of elements
3294 list of integer values
3297 return self.mesh.GetElementsByType(elementType)
3299 def GetNodesId(self):
3301 Return the list of mesh nodes IDs
3304 the list of integer values
3307 return self.mesh.GetNodesId()
3309 # Get the information about mesh elements:
3310 # ------------------------------------
3312 def GetElementType(self, id, iselem=True):
3314 Return the type of mesh element or node
3317 the value from :class:`SMESH.ElementType` enumeration.
3318 Return SMESH.ALL if element or node with the given ID does not exist
3321 return self.mesh.GetElementType(id, iselem)
3323 def GetElementGeomType(self, id):
3325 Return the geometric type of mesh element
3328 the value from :class:`SMESH.EntityType` enumeration.
3331 return self.mesh.GetElementGeomType(id)
3333 def GetElementShape(self, id):
3335 Return the shape type of mesh element
3338 the value from :class:`SMESH.GeometryType` enumeration.
3341 return self.mesh.GetElementShape(id)
3343 def GetSubMeshElementsId(self, Shape):
3345 Return the list of sub-mesh elements IDs
3348 Shape (GEOM.GEOM_Object): a geom object (sub-shape).
3349 *Shape* must be the sub-shape of the :meth:`main shape <GetShape>`
3352 list of integer values
3355 if isinstance( Shape, geomBuilder.GEOM._objref_GEOM_Object):
3356 ShapeID = self.geompyD.GetSubShapeID( self.geom, Shape )
3359 return self.mesh.GetSubMeshElementsId(ShapeID)
3361 def GetSubMeshNodesId(self, Shape, all):
3363 Return the list of sub-mesh nodes IDs
3366 Shape: a geom object (sub-shape).
3367 *Shape* must be the sub-shape of a :meth:`GetShape`
3368 all: If True, gives all nodes of sub-mesh elements, otherwise gives only sub-mesh nodes
3371 list of integer values
3374 if isinstance( Shape, geomBuilder.GEOM._objref_GEOM_Object):
3375 ShapeID = self.geompyD.GetSubShapeID( self.geom, Shape )
3378 return self.mesh.GetSubMeshNodesId(ShapeID, all)
3380 def GetSubMeshElementType(self, Shape):
3382 Return type of elements on given shape
3385 Shape: a geom object (sub-shape).
3386 *Shape* must be a sub-shape of a ShapeToMesh()
3389 :class:`SMESH.ElementType`
3392 if isinstance( Shape, geomBuilder.GEOM._objref_GEOM_Object):
3393 ShapeID = self.geompyD.GetSubShapeID( self.geom, Shape )
3396 return self.mesh.GetSubMeshElementType(ShapeID)
3400 Get the mesh description
3406 return self.mesh.Dump()
3409 # Get the information about nodes and elements of a mesh by its IDs:
3410 # -----------------------------------------------------------
3412 def GetNodeXYZ(self, id):
3414 Get XYZ coordinates of a node.
3415 If there is no node for the given ID - return an empty list
3418 list of float values
3421 return self.mesh.GetNodeXYZ(id)
3423 def GetNodeInverseElements(self, id):
3425 Return list of IDs of inverse elements for the given node.
3426 If there is no node for the given ID - return an empty list
3429 list of integer values
3432 return self.mesh.GetNodeInverseElements(id)
3434 def GetNodePosition(self,NodeID):
3436 Return the position of a node on the shape
3439 :class:`SMESH.NodePosition`
3442 return self.mesh.GetNodePosition(NodeID)
3444 def GetElementPosition(self,ElemID):
3446 Return the position of an element on the shape
3449 :class:`SMESH.ElementPosition`
3452 return self.mesh.GetElementPosition(ElemID)
3454 def GetShapeID(self, id):
3456 Return the ID of the shape, on which the given node was generated.
3459 an integer value > 0 or -1 if there is no node for the given
3460 ID or the node is not assigned to any geometry
3463 return self.mesh.GetShapeID(id)
3465 def GetShapeIDForElem(self,id):
3467 Return the ID of the shape, on which the given element was generated.
3470 an integer value > 0 or -1 if there is no element for the given
3471 ID or the element is not assigned to any geometry
3474 return self.mesh.GetShapeIDForElem(id)
3476 def GetElemNbNodes(self, id):
3478 Return the number of nodes of the given element
3481 an integer value > 0 or -1 if there is no element for the given ID
3484 return self.mesh.GetElemNbNodes(id)
3486 def GetElemNode(self, id, index):
3488 Return the node ID the given (zero based) index for the given element.
3490 * If there is no element for the given ID - return -1.
3491 * If there is no node for the given index - return -2.
3494 id (int): element ID
3495 index (int): node index within the element
3498 an integer value (ID)
3501 :meth:`GetElemNodes`
3504 return self.mesh.GetElemNode(id, index)
3506 def GetElemNodes(self, id):
3508 Return the IDs of nodes of the given element
3511 a list of integer values
3514 return self.mesh.GetElemNodes(id)
3516 def IsMediumNode(self, elementID, nodeID):
3518 Return true if the given node is the medium node in the given quadratic element
3521 return self.mesh.IsMediumNode(elementID, nodeID)
3523 def IsMediumNodeOfAnyElem(self, nodeID, elementType = SMESH.ALL ):
3525 Return true if the given node is the medium node in one of quadratic elements
3528 nodeID: ID of the node
3529 elementType: the type of elements to check a state of the node, either of
3530 (SMESH.ALL, SMESH.NODE, SMESH.EDGE, SMESH.FACE or SMESH.VOLUME)
3533 return self.mesh.IsMediumNodeOfAnyElem(nodeID, elementType)
3535 def ElemNbEdges(self, id):
3537 Return the number of edges for the given element
3540 return self.mesh.ElemNbEdges(id)
3542 def ElemNbFaces(self, id):
3544 Return the number of faces for the given element
3547 return self.mesh.ElemNbFaces(id)
3549 def GetElemFaceNodes(self,elemId, faceIndex):
3551 Return nodes of given face (counted from zero) for given volumic element.
3554 return self.mesh.GetElemFaceNodes(elemId, faceIndex)
3556 def GetFaceNormal(self, faceId, normalized=False):
3558 Return three components of normal of given mesh face
3559 (or an empty array in KO case)
3562 return self.mesh.GetFaceNormal(faceId,normalized)
3564 def FindElementByNodes(self, nodes):
3566 Return an element based on all given nodes.
3569 return self.mesh.FindElementByNodes(nodes)
3571 def GetElementsByNodes(self, nodes, elemType=SMESH.ALL):
3573 Return elements including all given nodes.
3576 return self.mesh.GetElementsByNodes( nodes, elemType )
3578 def IsPoly(self, id):
3580 Return true if the given element is a polygon
3583 return self.mesh.IsPoly(id)
3585 def IsQuadratic(self, id):
3587 Return true if the given element is quadratic
3590 return self.mesh.IsQuadratic(id)
3592 def GetBallDiameter(self, id):
3594 Return diameter of a ball discrete element or zero in case of an invalid *id*
3597 return self.mesh.GetBallDiameter(id)
3599 def BaryCenter(self, id):
3601 Return XYZ coordinates of the barycenter of the given element.
3602 If there is no element for the given ID - return an empty list
3605 a list of three double values
3608 return self.mesh.BaryCenter(id)
3610 def GetIdsFromFilter(self, theFilter):
3612 Pass mesh elements through the given filter and return IDs of fitting elements
3615 theFilter: :class:`SMESH.Filter`
3621 :meth:`SMESH.Filter.GetIDs`
3624 theFilter.SetMesh( self.mesh )
3625 return theFilter.GetIDs()
3627 # Get mesh measurements information:
3628 # ------------------------------------
3630 def GetFreeBorders(self):
3632 Verify whether a 2D mesh element has free edges (edges connected to one face only).
3633 Return a list of special structures (borders).
3636 a list of :class:`SMESH.FreeEdges.Border`
3639 aFilterMgr = self.smeshpyD.CreateFilterManager()
3640 aPredicate = aFilterMgr.CreateFreeEdges()
3641 aPredicate.SetMesh(self.mesh)
3642 aBorders = aPredicate.GetBorders()
3643 aFilterMgr.UnRegister()
3646 def MinDistance(self, id1, id2=0, isElem1=False, isElem2=False):
3648 Get minimum distance between two nodes, elements or distance to the origin
3651 id1: first node/element id
3652 id2: second node/element id (if 0, distance from *id1* to the origin is computed)
3653 isElem1: *True* if *id1* is element id, *False* if it is node id
3654 isElem2: *True* if *id2* is element id, *False* if it is node id
3657 minimum distance value **GetMinDistance()**
3660 aMeasure = self.GetMinDistance(id1, id2, isElem1, isElem2)
3661 return aMeasure.value
3663 def GetMinDistance(self, id1, id2=0, isElem1=False, isElem2=False):
3665 Get :class:`SMESH.Measure` structure specifying minimum distance data between two objects
3668 id1: first node/element id
3669 id2: second node/element id (if 0, distance from *id1* to the origin is computed)
3670 isElem1: *True* if *id1* is element id, *False* if it is node id
3671 isElem2: *True* if *id2* is element id, *False* if it is node id
3674 :class:`SMESH.Measure` structure
3680 id1 = self.editor.MakeIDSource([id1], SMESH.FACE)
3682 id1 = self.editor.MakeIDSource([id1], SMESH.NODE)
3685 id2 = self.editor.MakeIDSource([id2], SMESH.FACE)
3687 id2 = self.editor.MakeIDSource([id2], SMESH.NODE)
3692 aMeasurements = self.smeshpyD.CreateMeasurements()
3693 aMeasure = aMeasurements.MinDistance(id1, id2)
3694 genObjUnRegister([aMeasurements,id1, id2])
3697 def BoundingBox(self, objects=None, isElem=False):
3699 Get bounding box of the specified object(s)
3702 objects: single :class:`source object <SMESH.SMESH_IDSource>` or list of source objects or list of nodes/elements IDs
3703 isElem: if *objects* is a list of IDs, *True* value in this parameters specifies that *objects* are elements,
3704 *False* specifies that *objects* are nodes
3707 tuple of six values (minX, minY, minZ, maxX, maxY, maxZ)
3710 :meth:`GetBoundingBox()`
3713 result = self.GetBoundingBox(objects, isElem)
3717 result = (result.minX, result.minY, result.minZ, result.maxX, result.maxY, result.maxZ)
3720 def GetBoundingBox(self, objects=None, isElem=False):
3722 Get :class:`SMESH.Measure` structure specifying bounding box data of the specified object(s)
3725 objects: single :class:`source object <SMESH.SMESH_IDSource>` or list of source objects or list of nodes/elements IDs
3726 isElem: if *objects* is a list of IDs, True means that *objects* are elements,
3727 False means that *objects* are nodes
3730 :class:`SMESH.Measure` structure
3733 :meth:`BoundingBox()`
3737 objects = [self.mesh]
3738 elif isinstance(objects, tuple):
3739 objects = list(objects)
3740 if not isinstance(objects, list):
3742 if len(objects) > 0 and isinstance(objects[0], int):
3745 unRegister = genObjUnRegister()
3747 if isinstance(o, Mesh):
3748 srclist.append(o.mesh)
3749 elif hasattr(o, "_narrow"):
3750 src = o._narrow(SMESH.SMESH_IDSource)
3751 if src: srclist.append(src)
3753 elif isinstance(o, list):
3755 srclist.append(self.editor.MakeIDSource(o, SMESH.FACE))
3757 srclist.append(self.editor.MakeIDSource(o, SMESH.NODE))
3758 unRegister.set( srclist[-1] )
3761 aMeasurements = self.smeshpyD.CreateMeasurements()
3762 unRegister.set( aMeasurements )
3763 aMeasure = aMeasurements.BoundingBox(srclist)
3766 # Mesh edition (SMESH_MeshEditor functionality):
3767 # ---------------------------------------------
3769 def RemoveElements(self, IDsOfElements):
3771 Remove the elements from the mesh by ids
3774 IDsOfElements: is a list of ids of elements to remove
3780 return self.editor.RemoveElements(IDsOfElements)
3782 def RemoveNodes(self, IDsOfNodes):
3784 Remove nodes from mesh by ids
3787 IDsOfNodes: is a list of ids of nodes to remove
3793 return self.editor.RemoveNodes(IDsOfNodes)
3795 def RemoveOrphanNodes(self):
3797 Remove all orphan (free) nodes from mesh
3800 number of the removed nodes
3803 return self.editor.RemoveOrphanNodes()
3805 def AddNode(self, x, y, z):
3807 Add a node to the mesh by coordinates
3813 x,y,z,Parameters,hasVars = ParseParameters(x,y,z)
3814 if hasVars: self.mesh.SetParameters(Parameters)
3815 return self.editor.AddNode( x, y, z)
3817 def Add0DElement( self, IDOfNode, DuplicateElements=True ):
3819 Create a 0D element on a node with given number.
3822 IDOfNode: the ID of node for creation of the element.
3823 DuplicateElements: to add one more 0D element to a node or not
3826 ID of the new 0D element
3829 return self.editor.Add0DElement( IDOfNode, DuplicateElements )
3831 def Add0DElementsToAllNodes(self, theObject, theGroupName="", DuplicateElements=False):
3833 Create 0D elements on all nodes of the given elements except those
3834 nodes on which a 0D element already exists.
3837 theObject: an object on whose nodes 0D elements will be created.
3838 It can be list of element IDs, :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
3839 theGroupName: optional name of a group to add 0D elements created
3840 and/or found on nodes of *theObject*.
3841 DuplicateElements: to add one more 0D element to a node or not
3844 an object (a new group or a temporary :class:`SMESH.SMESH_IDSource`) holding
3845 IDs of new and/or found 0D elements. IDs of 0D elements
3846 can be retrieved from the returned object by
3847 calling :meth:`GetIDs() <SMESH.SMESH_IDSource.GetIDs>`
3850 unRegister = genObjUnRegister()
3851 if isinstance( theObject, Mesh ):
3852 theObject = theObject.GetMesh()
3853 elif isinstance( theObject, list ):
3854 theObject = self.GetIDSource( theObject, SMESH.ALL )
3855 unRegister.set( theObject )
3856 return self.editor.Create0DElementsOnAllNodes( theObject, theGroupName, DuplicateElements )
3858 def AddBall(self, IDOfNode, diameter):
3860 Create a ball element on a node with given ID.
3863 IDOfNode: the ID of node for creation of the element.
3864 diameter: the bal diameter.
3867 ID of the new ball element
3870 return self.editor.AddBall( IDOfNode, diameter )
3872 def AddEdge(self, IDsOfNodes):
3874 Create a linear or quadratic edge (this is determined
3875 by the number of given nodes).
3878 IDsOfNodes: list of node IDs for creation of the element.
3879 The order of nodes in this list should correspond to
3880 the :ref:`connectivity convention <connectivity_page>`.
3886 return self.editor.AddEdge(IDsOfNodes)
3888 def AddFace(self, IDsOfNodes):
3890 Create a linear or quadratic face (this is determined
3891 by the number of given nodes).
3894 IDsOfNodes: list of node IDs for creation of the element.
3895 The order of nodes in this list should correspond to
3896 the :ref:`connectivity convention <connectivity_page>`.
3902 return self.editor.AddFace(IDsOfNodes)
3904 def AddPolygonalFace(self, IdsOfNodes):
3906 Add a polygonal face defined by a list of node IDs
3909 IdsOfNodes: the list of node IDs for creation of the element.
3915 return self.editor.AddPolygonalFace(IdsOfNodes)
3917 def AddQuadPolygonalFace(self, IdsOfNodes):
3919 Add a quadratic polygonal face defined by a list of node IDs
3922 IdsOfNodes: the list of node IDs for creation of the element;
3923 corner nodes follow first.
3929 return self.editor.AddQuadPolygonalFace(IdsOfNodes)
3931 def AddVolume(self, IDsOfNodes):
3933 Create both simple and quadratic volume (this is determined
3934 by the number of given nodes).
3937 IDsOfNodes: list of node IDs for creation of the element.
3938 The order of nodes in this list should correspond to
3939 the :ref:`connectivity convention <connectivity_page>`.
3942 ID of the new volumic element
3945 return self.editor.AddVolume(IDsOfNodes)
3947 def AddPolyhedralVolume (self, IdsOfNodes, Quantities):
3949 Create a volume of many faces, giving nodes for each face.
3952 IdsOfNodes: list of node IDs for volume creation, face by face.
3953 Quantities: list of integer values, Quantities[i]
3954 gives the quantity of nodes in face number i.
3957 ID of the new volumic element
3960 return self.editor.AddPolyhedralVolume(IdsOfNodes, Quantities)
3962 def AddPolyhedralVolumeByFaces (self, IdsOfFaces):
3964 Create a volume of many faces, giving the IDs of the existing faces.
3967 The created volume will refer only to the nodes
3968 of the given faces, not to the faces themselves.
3971 IdsOfFaces: the list of face IDs for volume creation.
3974 ID of the new volumic element
3977 return self.editor.AddPolyhedralVolumeByFaces(IdsOfFaces)
3980 def SetNodeOnVertex(self, NodeID, Vertex):
3982 Binds a node to a vertex
3986 Vertex: a vertex (GEOM.GEOM_Object) or vertex ID
3989 True if succeed else raises an exception
3992 if ( isinstance( Vertex, geomBuilder.GEOM._objref_GEOM_Object)):
3993 VertexID = self.geompyD.GetSubShapeID( self.geom, Vertex )
3997 self.editor.SetNodeOnVertex(NodeID, VertexID)
3998 except SALOME.SALOME_Exception as inst:
3999 raise ValueError(inst.details.text)
4003 def SetNodeOnEdge(self, NodeID, Edge, paramOnEdge):
4005 Stores the node position on an edge
4009 Edge: an edge (GEOM.GEOM_Object) or edge ID
4010 paramOnEdge: a parameter on the edge where the node is located
4013 True if succeed else raises an exception
4016 if ( isinstance( Edge, geomBuilder.GEOM._objref_GEOM_Object)):
4017 EdgeID = self.geompyD.GetSubShapeID( self.geom, Edge )
4021 self.editor.SetNodeOnEdge(NodeID, EdgeID, paramOnEdge)
4022 except SALOME.SALOME_Exception as inst:
4023 raise ValueError(inst.details.text)
4026 def SetNodeOnFace(self, NodeID, Face, u, v):
4028 Stores node position on a face
4032 Face: a face (GEOM.GEOM_Object) or face ID
4033 u: U parameter on the face where the node is located
4034 v: V parameter on the face where the node is located
4037 True if succeed else raises an exception
4040 if ( isinstance( Face, geomBuilder.GEOM._objref_GEOM_Object)):
4041 FaceID = self.geompyD.GetSubShapeID( self.geom, Face )
4045 self.editor.SetNodeOnFace(NodeID, FaceID, u, v)
4046 except SALOME.SALOME_Exception as inst:
4047 raise ValueError(inst.details.text)
4050 def SetNodeInVolume(self, NodeID, Solid):
4052 Binds a node to a solid
4056 Solid: a solid (GEOM.GEOM_Object) or solid ID
4059 True if succeed else raises an exception
4062 if ( isinstance( Solid, geomBuilder.GEOM._objref_GEOM_Object)):
4063 SolidID = self.geompyD.GetSubShapeID( self.geom, Solid )
4067 self.editor.SetNodeInVolume(NodeID, SolidID)
4068 except SALOME.SALOME_Exception as inst:
4069 raise ValueError(inst.details.text)
4072 def SetMeshElementOnShape(self, ElementID, Shape):
4074 Bind an element to a shape
4077 ElementID: an element ID
4078 Shape: a shape (GEOM.GEOM_Object) or shape ID
4081 True if succeed else raises an exception
4084 if ( isinstance( Shape, geomBuilder.GEOM._objref_GEOM_Object)):
4085 ShapeID = self.geompyD.GetSubShapeID( self.geom, Shape )
4089 self.editor.SetMeshElementOnShape(ElementID, ShapeID)
4090 except SALOME.SALOME_Exception as inst:
4091 raise ValueError(inst.details.text)
4095 def MoveNode(self, NodeID, x, y, z):
4097 Move the node with the given id
4100 NodeID: the id of the node
4101 x: a new X coordinate
4102 y: a new Y coordinate
4103 z: a new Z coordinate
4106 True if succeed else False
4109 x,y,z,Parameters,hasVars = ParseParameters(x,y,z)
4110 if hasVars: self.mesh.SetParameters(Parameters)
4111 return self.editor.MoveNode(NodeID, x, y, z)
4113 def MoveClosestNodeToPoint(self, x, y, z, NodeID):
4115 Find the node closest to a point and moves it to a point location
4118 x: the X coordinate of a point
4119 y: the Y coordinate of a point
4120 z: the Z coordinate of a point
4121 NodeID: if specified (>0), the node with this ID is moved,
4122 otherwise, the node closest to point (*x*, *y*, *z*) is moved
4125 the ID of a moved node
4128 x,y,z,Parameters,hasVars = ParseParameters(x,y,z)
4129 if hasVars: self.mesh.SetParameters(Parameters)
4130 return self.editor.MoveClosestNodeToPoint(x, y, z, NodeID)
4132 def FindNodeClosestTo(self, x, y, z):
4134 Find the node closest to a point
4137 x: the X coordinate of a point
4138 y: the Y coordinate of a point
4139 z: the Z coordinate of a point
4145 #preview = self.mesh.GetMeshEditPreviewer()
4146 #return preview.MoveClosestNodeToPoint(x, y, z, -1)
4147 return self.editor.FindNodeClosestTo(x, y, z)
4149 def FindElementsByPoint(self, x, y, z, elementType = SMESH.ALL, meshPart=None):
4151 Find the elements where a point lays IN or ON
4154 x,y,z (float): coordinates of the point
4155 elementType (SMESH.ElementType): type of elements to find; SMESH.ALL type
4156 means elements of any type excluding nodes, discrete and 0D elements.
4157 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to search within
4160 list of IDs of found elements
4163 return self.editor.FindAmongElementsByPoint( meshPart, x, y, z, elementType );
4165 return self.editor.FindElementsByPoint(x, y, z, elementType)
4167 def GetPointState(self, x, y, z):
4169 Return point state in a closed 2D mesh in terms of TopAbs_State enumeration:
4170 0-IN, 1-OUT, 2-ON, 3-UNKNOWN.
4171 UNKNOWN state means that either mesh is wrong or the analysis fails.
4174 return self.editor.GetPointState(x, y, z)
4176 def IsManifold(self):
4178 Check if a 2D mesh is manifold
4181 return self.editor.IsManifold()
4183 def IsCoherentOrientation2D(self):
4185 Check if orientation of 2D elements is coherent
4188 return self.editor.IsCoherentOrientation2D()
4190 def MeshToPassThroughAPoint(self, x, y, z):
4192 Find the node closest to a point and moves it to a point location
4195 x: the X coordinate of a point
4196 y: the Y coordinate of a point
4197 z: the Z coordinate of a point
4200 the ID of a moved node
4203 return self.editor.MoveClosestNodeToPoint(x, y, z, -1)
4205 def InverseDiag(self, NodeID1, NodeID2):
4207 Replace two neighbour triangles sharing Node1-Node2 link
4208 with the triangles built on the same 4 nodes but having other common link.
4211 NodeID1: the ID of the first node
4212 NodeID2: the ID of the second node
4215 False if proper faces were not found
4217 return self.editor.InverseDiag(NodeID1, NodeID2)
4219 def DeleteDiag(self, NodeID1, NodeID2):
4221 Replace two neighbour triangles sharing *Node1-Node2* link
4222 with a quadrangle built on the same 4 nodes.
4225 NodeID1: ID of the first node
4226 NodeID2: ID of the second node
4229 False if proper faces were not found
4232 return self.editor.DeleteDiag(NodeID1, NodeID2)
4234 def Reorient(self, IDsOfElements=None):
4236 Reorient elements by ids
4239 IDsOfElements: if undefined reorients all mesh elements
4242 True if succeed else False
4245 if IDsOfElements == None:
4246 IDsOfElements = self.GetElementsId()
4247 return self.editor.Reorient(IDsOfElements)
4249 def ReorientObject(self, theObject):
4251 Reorient all elements of the object
4254 theObject: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4257 True if succeed else False
4260 if ( isinstance( theObject, Mesh )):
4261 theObject = theObject.GetMesh()
4262 return self.editor.ReorientObject(theObject)
4264 def Reorient2D(self, the2DObject, theDirection, theFaceOrPoint ):
4266 Reorient faces contained in *the2DObject*.
4269 the2DObject: is a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>` or list of IDs of 2D elements
4270 theDirection: is a desired direction of normal of *theFace*.
4271 It can be either a GEOM vector or a list of coordinates [x,y,z].
4272 theFaceOrPoint: defines a face of *the2DObject* whose normal will be
4273 compared with theDirection. It can be either ID of face or a point
4274 by which the face will be found. The point can be given as either
4275 a GEOM vertex or a list of point coordinates.
4278 number of reoriented faces
4281 unRegister = genObjUnRegister()
4283 if isinstance( the2DObject, Mesh ):
4284 the2DObject = the2DObject.GetMesh()
4285 if isinstance( the2DObject, list ):
4286 the2DObject = self.GetIDSource( the2DObject, SMESH.FACE )
4287 unRegister.set( the2DObject )
4288 # check theDirection
4289 if isinstance( theDirection, geomBuilder.GEOM._objref_GEOM_Object):
4290 theDirection = self.smeshpyD.GetDirStruct( theDirection )
4291 if isinstance( theDirection, list ):
4292 theDirection = self.smeshpyD.MakeDirStruct( *theDirection )
4293 # prepare theFace and thePoint
4294 theFace = theFaceOrPoint
4295 thePoint = PointStruct(0,0,0)
4296 if isinstance( theFaceOrPoint, geomBuilder.GEOM._objref_GEOM_Object):
4297 thePoint = self.smeshpyD.GetPointStruct( theFaceOrPoint )
4299 if isinstance( theFaceOrPoint, list ):
4300 thePoint = PointStruct( *theFaceOrPoint )
4302 if isinstance( theFaceOrPoint, PointStruct ):
4303 thePoint = theFaceOrPoint
4305 return self.editor.Reorient2D( the2DObject, theDirection, theFace, thePoint )
4307 def Reorient2DBy3D(self, the2DObject, the3DObject, theOutsideNormal=True ):
4309 Reorient faces according to adjacent volumes.
4312 the2DObject: is a :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>` or list of
4313 either IDs of faces or face groups.
4314 the3DObject: is a :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>` or list of IDs of volumes.
4315 theOutsideNormal: to orient faces to have their normals
4316 pointing either *outside* or *inside* the adjacent volumes.
4319 number of reoriented faces.
4322 unRegister = genObjUnRegister()
4324 if not isinstance( the2DObject, list ):
4325 the2DObject = [ the2DObject ]
4326 elif the2DObject and isinstance( the2DObject[0], int ):
4327 the2DObject = self.GetIDSource( the2DObject, SMESH.FACE )
4328 unRegister.set( the2DObject )
4329 the2DObject = [ the2DObject ]
4330 for i,obj2D in enumerate( the2DObject ):
4331 if isinstance( obj2D, Mesh ):
4332 the2DObject[i] = obj2D.GetMesh()
4333 if isinstance( obj2D, list ):
4334 the2DObject[i] = self.GetIDSource( obj2D, SMESH.FACE )
4335 unRegister.set( the2DObject[i] )
4337 if isinstance( the3DObject, Mesh ):
4338 the3DObject = the3DObject.GetMesh()
4339 if isinstance( the3DObject, list ):
4340 the3DObject = self.GetIDSource( the3DObject, SMESH.VOLUME )
4341 unRegister.set( the3DObject )
4342 return self.editor.Reorient2DBy3D( the2DObject, the3DObject, theOutsideNormal )
4344 def TriToQuad(self, IDsOfElements, theCriterion, MaxAngle):
4346 Fuse the neighbouring triangles into quadrangles.
4349 IDsOfElements: The triangles to be fused.
4350 theCriterion: a numerical functor, in terms of enum :class:`SMESH.FunctorType`, used to
4351 applied to possible quadrangles to choose a neighbour to fuse with.
4352 Note that not all items of :class:`SMESH.FunctorType` corresponds
4353 to numerical functors.
4354 MaxAngle: is the maximum angle between element normals at which the fusion
4355 is still performed; theMaxAngle is measured in radians.
4356 Also it could be a name of variable which defines angle in degrees.
4359 True in case of success, False otherwise.
4362 MaxAngle,Parameters,hasVars = ParseAngles(MaxAngle)
4363 self.mesh.SetParameters(Parameters)
4364 if not IDsOfElements:
4365 IDsOfElements = self.GetElementsId()
4366 Functor = self.smeshpyD.GetFunctor(theCriterion)
4367 return self.editor.TriToQuad(IDsOfElements, Functor, MaxAngle)
4369 def TriToQuadObject (self, theObject, theCriterion, MaxAngle):
4371 Fuse the neighbouring triangles of the object into quadrangles
4374 theObject: is :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4375 theCriterion: is a numerical functor, in terms of enum :class:`SMESH.FunctorType`,
4376 applied to possible quadrangles to choose a neighbour to fuse with.
4377 Note that not all items of :class:`SMESH.FunctorType` corresponds
4378 to numerical functors.
4379 MaxAngle: a max angle between element normals at which the fusion
4380 is still performed; theMaxAngle is measured in radians.
4383 True in case of success, False otherwise.
4386 MaxAngle,Parameters,hasVars = ParseAngles(MaxAngle)
4387 self.mesh.SetParameters(Parameters)
4388 if isinstance( theObject, Mesh ):
4389 theObject = theObject.GetMesh()
4390 Functor = self.smeshpyD.GetFunctor(theCriterion)
4391 return self.editor.TriToQuadObject(theObject, Functor, MaxAngle)
4393 def QuadToTri (self, IDsOfElements, theCriterion = None):
4395 Split quadrangles into triangles.
4398 IDsOfElements: the faces to be splitted.
4399 theCriterion: is a numerical functor, in terms of enum :class:`SMESH.FunctorType`, used to
4400 choose a diagonal for splitting. If *theCriterion* is None, which is a default
4401 value, then quadrangles will be split by the smallest diagonal.
4402 Note that not all items of :class:`SMESH.FunctorType` corresponds
4403 to numerical functors.
4406 True in case of success, False otherwise.
4408 if IDsOfElements == []:
4409 IDsOfElements = self.GetElementsId()
4410 if theCriterion is None:
4411 theCriterion = FT_MaxElementLength2D
4412 Functor = self.smeshpyD.GetFunctor(theCriterion)
4413 return self.editor.QuadToTri(IDsOfElements, Functor)
4415 def QuadToTriObject (self, theObject, theCriterion = None):
4417 Split quadrangles into triangles.
4420 theObject: the object from which the list of elements is taken,
4421 this is :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4422 theCriterion: is a numerical functor, in terms of enum :class:`SMESH.FunctorType`, used to
4423 choose a diagonal for splitting. If *theCriterion* is None, which is a default
4424 value, then quadrangles will be split by the smallest diagonal.
4425 Note that not all items of :class:`SMESH.FunctorType` corresponds
4426 to numerical functors.
4429 True in case of success, False otherwise.
4431 if ( isinstance( theObject, Mesh )):
4432 theObject = theObject.GetMesh()
4433 if theCriterion is None:
4434 theCriterion = FT_MaxElementLength2D
4435 Functor = self.smeshpyD.GetFunctor(theCriterion)
4436 return self.editor.QuadToTriObject(theObject, Functor)
4438 def QuadTo4Tri (self, theElements=[]):
4440 Split each of given quadrangles into 4 triangles. A node is added at the center of
4444 theElements: the faces to be splitted. This can be either
4445 :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>`
4446 or a list of face IDs. By default all quadrangles are split
4448 unRegister = genObjUnRegister()
4449 if isinstance( theElements, Mesh ):
4450 theElements = theElements.mesh
4451 elif not theElements:
4452 theElements = self.mesh
4453 elif isinstance( theElements, list ):
4454 theElements = self.GetIDSource( theElements, SMESH.FACE )
4455 unRegister.set( theElements )
4456 return self.editor.QuadTo4Tri( theElements )
4458 def SplitQuad (self, IDsOfElements, Diag13):
4460 Split quadrangles into triangles.
4463 IDsOfElements: the faces to be splitted
4464 Diag13: is used to choose a diagonal for splitting.
4467 True in case of success, False otherwise.
4469 if IDsOfElements == []:
4470 IDsOfElements = self.GetElementsId()
4471 return self.editor.SplitQuad(IDsOfElements, Diag13)
4473 def SplitQuadObject (self, theObject, Diag13):
4475 Split quadrangles into triangles.
4478 theObject: the object from which the list of elements is taken,
4479 this is :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4480 Diag13: is used to choose a diagonal for splitting.
4483 True in case of success, False otherwise.
4485 if ( isinstance( theObject, Mesh )):
4486 theObject = theObject.GetMesh()
4487 return self.editor.SplitQuadObject(theObject, Diag13)
4489 def BestSplit (self, IDOfQuad, theCriterion):
4491 Find a better splitting of the given quadrangle.
4494 IDOfQuad: the ID of the quadrangle to be splitted.
4495 theCriterion: is a numerical functor, in terms of enum :class:`SMESH.FunctorType`, used to
4496 choose a diagonal for splitting.
4497 Note that not all items of :class:`SMESH.FunctorType` corresponds
4498 to numerical functors.
4501 * 1 if 1-3 diagonal is better,
4502 * 2 if 2-4 diagonal is better,
4503 * 0 if error occurs.
4505 return self.editor.BestSplit(IDOfQuad, self.smeshpyD.GetFunctor(theCriterion))
4507 def SplitVolumesIntoTetra(self, elems, method=smeshBuilder.Hex_5Tet ):
4509 Split volumic elements into tetrahedrons
4512 elems: either a list of elements or a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4513 method: flags passing splitting method:
4514 smesh.Hex_5Tet, smesh.Hex_6Tet, smesh.Hex_24Tet.
4515 smesh.Hex_5Tet - to split the hexahedron into 5 tetrahedrons, etc.
4517 unRegister = genObjUnRegister()
4518 if isinstance( elems, Mesh ):
4519 elems = elems.GetMesh()
4520 if ( isinstance( elems, list )):
4521 elems = self.editor.MakeIDSource(elems, SMESH.VOLUME)
4522 unRegister.set( elems )
4523 self.editor.SplitVolumesIntoTetra(elems, method)
4526 def SplitBiQuadraticIntoLinear(self, elems=None):
4528 Split bi-quadratic elements into linear ones without creation of additional nodes:
4530 - bi-quadratic triangle will be split into 3 linear quadrangles;
4531 - bi-quadratic quadrangle will be split into 4 linear quadrangles;
4532 - tri-quadratic hexahedron will be split into 8 linear hexahedra.
4534 Quadratic elements of lower dimension adjacent to the split bi-quadratic element
4535 will be split in order to keep the mesh conformal.
4538 elems: elements to split\: :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>` or element IDs;
4539 if None (default), all bi-quadratic elements will be split
4541 unRegister = genObjUnRegister()
4542 if elems and isinstance( elems, list ) and isinstance( elems[0], int ):
4543 elems = self.editor.MakeIDSource(elems, SMESH.ALL)
4544 unRegister.set( elems )
4546 elems = [ self.GetMesh() ]
4547 if isinstance( elems, Mesh ):
4548 elems = [ elems.GetMesh() ]
4549 if not isinstance( elems, list ):
4551 self.editor.SplitBiQuadraticIntoLinear( elems )
4553 def SplitHexahedraIntoPrisms(self, elems, startHexPoint, facetNormal,
4554 method=smeshBuilder.Hex_2Prisms, allDomains=False ):
4556 Split hexahedra into prisms
4559 elems: either a list of elements or a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4560 startHexPoint: a point used to find a hexahedron for which *facetNormal*
4561 gives a normal vector defining facets to split into triangles.
4562 *startHexPoint* can be either a triple of coordinates or a vertex.
4563 facetNormal: a normal to a facet to split into triangles of a
4564 hexahedron found by *startHexPoint*.
4565 *facetNormal* can be either a triple of coordinates or an edge.
4566 method: flags passing splitting method: smesh.Hex_2Prisms, smesh.Hex_4Prisms.
4567 smesh.Hex_2Prisms - to split the hexahedron into 2 prisms, etc.
4568 allDomains: if :code:`False`, only hexahedra adjacent to one closest
4569 to *startHexPoint* are split, else *startHexPoint*
4570 is used to find the facet to split in all domains present in *elems*.
4573 unRegister = genObjUnRegister()
4574 if isinstance( elems, Mesh ):
4575 elems = elems.GetMesh()
4576 if ( isinstance( elems, list )):
4577 elems = self.editor.MakeIDSource(elems, SMESH.VOLUME)
4578 unRegister.set( elems )
4581 if isinstance( startHexPoint, geomBuilder.GEOM._objref_GEOM_Object):
4582 startHexPoint = self.smeshpyD.GetPointStruct( startHexPoint )
4583 elif isinstance( startHexPoint, list ):
4584 startHexPoint = SMESH.PointStruct( startHexPoint[0],
4587 if isinstance( facetNormal, geomBuilder.GEOM._objref_GEOM_Object):
4588 facetNormal = self.smeshpyD.GetDirStruct( facetNormal )
4589 elif isinstance( facetNormal, list ):
4590 facetNormal = self.smeshpyD.MakeDirStruct( facetNormal[0],
4593 self.mesh.SetParameters( startHexPoint.parameters + facetNormal.PS.parameters )
4595 self.editor.SplitHexahedraIntoPrisms(elems, startHexPoint, facetNormal, method, allDomains)
4597 def SplitQuadsNearTriangularFacets(self):
4599 Split quadrangle faces near triangular facets of volumes
4601 faces_array = self.GetElementsByType(SMESH.FACE)
4602 for face_id in faces_array:
4603 if self.GetElemNbNodes(face_id) == 4: # quadrangle
4604 quad_nodes = self.mesh.GetElemNodes(face_id)
4605 node1_elems = self.GetNodeInverseElements(quad_nodes[1 -1])
4606 isVolumeFound = False
4607 for node1_elem in node1_elems:
4608 if not isVolumeFound:
4609 if self.GetElementType(node1_elem, True) == SMESH.VOLUME:
4610 nb_nodes = self.GetElemNbNodes(node1_elem)
4611 if 3 < nb_nodes and nb_nodes < 7: # tetra or penta, or prism
4612 volume_elem = node1_elem
4613 volume_nodes = self.mesh.GetElemNodes(volume_elem)
4614 if volume_nodes.count(quad_nodes[2 -1]) > 0: # 1,2
4615 if volume_nodes.count(quad_nodes[4 -1]) > 0: # 1,2,4
4616 isVolumeFound = True
4617 if volume_nodes.count(quad_nodes[3 -1]) == 0: # 1,2,4 & !3
4618 self.SplitQuad([face_id], False) # diagonal 2-4
4619 elif volume_nodes.count(quad_nodes[3 -1]) > 0: # 1,2,3 & !4
4620 isVolumeFound = True
4621 self.SplitQuad([face_id], True) # diagonal 1-3
4622 elif volume_nodes.count(quad_nodes[4 -1]) > 0: # 1,4 & !2
4623 if volume_nodes.count(quad_nodes[3 -1]) > 0: # 1,4,3 & !2
4624 isVolumeFound = True
4625 self.SplitQuad([face_id], True) # diagonal 1-3
4627 def SplitHexaToTetras (self, theObject, theNode000, theNode001):
4629 Split hexahedrons into tetrahedrons.
4631 This operation uses :doc:`pattern_mapping` functionality for splitting.
4634 theObject: the object from which the list of hexahedrons is taken;
4635 this is :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
4636 theNode000,theNode001: within the range [0,7]; gives the orientation of the
4637 pattern relatively each hexahedron: the (0,0,0) key-point of the pattern
4638 will be mapped into *theNode000*-th node of each volume, the (0,0,1)
4639 key-point will be mapped into *theNode001*-th node of each volume.
4640 The (0,0,0) key-point of the used pattern corresponds to a non-split corner.
4643 True in case of success, False otherwise.
4651 # (0,0,1) 4.---------.7 * |
4658 # (0,0,0) 0.---------.3
4659 pattern_tetra = "!!! Nb of points: \n 8 \n\
4669 !!! Indices of points of 6 tetras: \n\
4677 pattern = self.smeshpyD.GetPattern()
4678 isDone = pattern.LoadFromFile(pattern_tetra)
4680 print('Pattern.LoadFromFile :', pattern.GetErrorCode())
4683 pattern.ApplyToHexahedrons(self.mesh, theObject.GetIDs(), theNode000, theNode001)
4684 isDone = pattern.MakeMesh(self.mesh, False, False)
4685 if not isDone: print('Pattern.MakeMesh :', pattern.GetErrorCode())
4687 # split quafrangle faces near triangular facets of volumes
4688 self.SplitQuadsNearTriangularFacets()
4692 def SplitHexaToPrisms (self, theObject, theNode000, theNode001):
4694 Split hexahedrons into prisms.
4696 Uses the :doc:`pattern_mapping` functionality for splitting.
4699 theObject: the object (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`) from where the list of hexahedrons is taken;
4700 theNode000,theNode001: (within the range [0,7]) gives the orientation of the
4701 pattern relatively each hexahedron: keypoint (0,0,0) of the pattern
4702 will be mapped into the *theNode000* -th node of each volume, keypoint (0,0,1)
4703 will be mapped into the *theNode001* -th node of each volume.
4704 Edge (0,0,0)-(0,0,1) of used pattern connects two not split corners.
4707 True in case of success, False otherwise.
4709 # Pattern: 5.---------.6
4714 # (0,0,1) 4.---------.7 |
4721 # (0,0,0) 0.---------.3
4722 pattern_prism = "!!! Nb of points: \n 8 \n\
4732 !!! Indices of points of 2 prisms: \n\
4736 pattern = self.smeshpyD.GetPattern()
4737 isDone = pattern.LoadFromFile(pattern_prism)
4739 print('Pattern.LoadFromFile :', pattern.GetErrorCode())
4742 pattern.ApplyToHexahedrons(self.mesh, theObject.GetIDs(), theNode000, theNode001)
4743 isDone = pattern.MakeMesh(self.mesh, False, False)
4744 if not isDone: print('Pattern.MakeMesh :', pattern.GetErrorCode())
4746 # Split quafrangle faces near triangular facets of volumes
4747 self.SplitQuadsNearTriangularFacets()
4751 def Smooth(self, IDsOfElements, IDsOfFixedNodes,
4752 MaxNbOfIterations, MaxAspectRatio, Method):
4757 IDsOfElements: the list if ids of elements to smooth
4758 IDsOfFixedNodes: the list of ids of fixed nodes.
4759 Note that nodes built on edges and boundary nodes are always fixed.
4760 MaxNbOfIterations: the maximum number of iterations
4761 MaxAspectRatio: varies in range [1.0, inf]
4762 Method: is either Laplacian (smesh.LAPLACIAN_SMOOTH)
4763 or Centroidal (smesh.CENTROIDAL_SMOOTH)
4766 True in case of success, False otherwise.
4769 if IDsOfElements == []:
4770 IDsOfElements = self.GetElementsId()
4771 MaxNbOfIterations,MaxAspectRatio,Parameters,hasVars = ParseParameters(MaxNbOfIterations,MaxAspectRatio)
4772 self.mesh.SetParameters(Parameters)
4773 return self.editor.Smooth(IDsOfElements, IDsOfFixedNodes,
4774 MaxNbOfIterations, MaxAspectRatio, Method)
4776 def SmoothObject(self, theObject, IDsOfFixedNodes,
4777 MaxNbOfIterations, MaxAspectRatio, Method):
4779 Smooth elements which belong to the given object
4782 theObject: the object to smooth
4783 IDsOfFixedNodes: the list of ids of fixed nodes.
4784 Note that nodes built on edges and boundary nodes are always fixed.
4785 MaxNbOfIterations: the maximum number of iterations
4786 MaxAspectRatio: varies in range [1.0, inf]
4787 Method: is either Laplacian (smesh.LAPLACIAN_SMOOTH)
4788 or Centroidal (smesh.CENTROIDAL_SMOOTH)
4791 True in case of success, False otherwise.
4794 if ( isinstance( theObject, Mesh )):
4795 theObject = theObject.GetMesh()
4796 return self.editor.SmoothObject(theObject, IDsOfFixedNodes,
4797 MaxNbOfIterations, MaxAspectRatio, Method)
4799 def SmoothParametric(self, IDsOfElements, IDsOfFixedNodes,
4800 MaxNbOfIterations, MaxAspectRatio, Method):
4802 Parametrically smooth the given elements
4805 IDsOfElements: the list if ids of elements to smooth
4806 IDsOfFixedNodes: the list of ids of fixed nodes.
4807 Note that nodes built on edges and boundary nodes are always fixed.
4808 MaxNbOfIterations: the maximum number of iterations
4809 MaxAspectRatio: varies in range [1.0, inf]
4810 Method: is either Laplacian (smesh.LAPLACIAN_SMOOTH)
4811 or Centroidal (smesh.CENTROIDAL_SMOOTH)
4814 True in case of success, False otherwise.
4817 if IDsOfElements == []:
4818 IDsOfElements = self.GetElementsId()
4819 MaxNbOfIterations,MaxAspectRatio,Parameters,hasVars = ParseParameters(MaxNbOfIterations,MaxAspectRatio)
4820 self.mesh.SetParameters(Parameters)
4821 return self.editor.SmoothParametric(IDsOfElements, IDsOfFixedNodes,
4822 MaxNbOfIterations, MaxAspectRatio, Method)
4824 def SmoothParametricObject(self, theObject, IDsOfFixedNodes,
4825 MaxNbOfIterations, MaxAspectRatio, Method):
4827 Parametrically smooth the elements which belong to the given object
4830 theObject: the object to smooth
4831 IDsOfFixedNodes: the list of ids of fixed nodes.
4832 Note that nodes built on edges and boundary nodes are always fixed.
4833 MaxNbOfIterations: the maximum number of iterations
4834 MaxAspectRatio: varies in range [1.0, inf]
4835 Method: is either Laplacian (smesh.LAPLACIAN_SMOOTH)
4836 or Centroidal (smesh.CENTROIDAL_SMOOTH)
4839 True in case of success, False otherwise.
4842 if ( isinstance( theObject, Mesh )):
4843 theObject = theObject.GetMesh()
4844 return self.editor.SmoothParametricObject(theObject, IDsOfFixedNodes,
4845 MaxNbOfIterations, MaxAspectRatio, Method)
4847 def ConvertToQuadratic(self, theForce3d=False, theSubMesh=None, theToBiQuad=False):
4849 Convert the mesh to quadratic or bi-quadratic, deletes old elements, replacing
4850 them with quadratic with the same id.
4853 theForce3d: method of new node creation:
4855 * False - the medium node lies at the geometrical entity from which the mesh element is built
4856 * True - the medium node lies at the middle of the line segments connecting two nodes of a mesh element
4857 theSubMesh: a :class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>` to convert
4858 theToBiQuad: If True, converts the mesh to bi-quadratic
4861 :class:`SMESH.ComputeError` which can hold a warning
4864 If *theSubMesh* is provided, the mesh can become non-conformal
4867 if isinstance( theSubMesh, Mesh ):
4868 theSubMesh = theSubMesh.mesh
4870 self.editor.ConvertToBiQuadratic(theForce3d,theSubMesh)
4873 self.editor.ConvertToQuadraticObject(theForce3d,theSubMesh)
4875 self.editor.ConvertToQuadratic(theForce3d)
4876 error = self.editor.GetLastError()
4877 if error and error.comment:
4878 print(error.comment)
4881 def ConvertFromQuadratic(self, theSubMesh=None):
4883 Convert the mesh from quadratic to ordinary,
4884 deletes old quadratic elements,
4885 replacing them with ordinary mesh elements with the same id.
4888 theSubMesh: a :class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>` to convert
4891 If *theSubMesh* is provided, the mesh can become non-conformal
4895 self.editor.ConvertFromQuadraticObject(theSubMesh)
4897 return self.editor.ConvertFromQuadratic()
4899 def Make2DMeshFrom3D(self):
4901 Create 2D mesh as skin on boundary faces of a 3D mesh
4904 True if operation has been completed successfully, False otherwise
4907 return self.editor.Make2DMeshFrom3D()
4909 def MakeBoundaryMesh(self, elements, dimension=SMESH.BND_2DFROM3D, groupName="", meshName="",
4910 toCopyElements=False, toCopyExistingBondary=False):
4912 Create missing boundary elements
4915 elements: elements whose boundary is to be checked:
4916 :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>` or list of elements.
4917 If *elements* is mesh, it must be the mesh whose MakeBoundaryMesh() is called
4918 dimension: defines type of boundary elements to create, either of
4919 { SMESH.BND_2DFROM3D, SMESH.BND_1DFROM3D, SMESH.BND_1DFROM2D }.
4920 SMESH.BND_1DFROM3D create mesh edges on all borders of free facets of 3D cells
4921 groupName: a name of group to store created boundary elements in,
4922 "" means not to create the group
4923 meshName: a name of new mesh to store created boundary elements in,
4924 "" means not to create the new mesh
4925 toCopyElements: if True, the checked elements will be copied into
4926 the new mesh else only boundary elements will be copied into the new mesh
4927 toCopyExistingBondary: if True, not only new but also pre-existing
4928 boundary elements will be copied into the new mesh
4931 tuple (:class:`Mesh`, :class:`group <SMESH.SMESH_Group>`) where boundary elements were added to
4934 unRegister = genObjUnRegister()
4935 if isinstance( elements, Mesh ):
4936 elements = elements.GetMesh()
4937 if ( isinstance( elements, list )):
4938 elemType = SMESH.ALL
4939 if elements: elemType = self.GetElementType( elements[0], iselem=True)
4940 elements = self.editor.MakeIDSource(elements, elemType)
4941 unRegister.set( elements )
4942 mesh, group = self.editor.MakeBoundaryMesh(elements,dimension,groupName,meshName,
4943 toCopyElements,toCopyExistingBondary)
4944 if mesh: mesh = self.smeshpyD.Mesh(mesh)
4947 def MakeBoundaryElements(self, dimension=SMESH.BND_2DFROM3D, groupName="", meshName="",
4948 toCopyAll=False, groups=[]):
4950 Create missing boundary elements around either the whole mesh or
4954 dimension: defines type of boundary elements to create, either of
4955 { SMESH.BND_2DFROM3D, SMESH.BND_1DFROM3D, SMESH.BND_1DFROM2D }
4956 groupName: a name of group to store all boundary elements in,
4957 "" means not to create the group
4958 meshName: a name of a new mesh, which is a copy of the initial
4959 mesh + created boundary elements; "" means not to create the new mesh
4960 toCopyAll: if True, the whole initial mesh will be copied into
4961 the new mesh else only boundary elements will be copied into the new mesh
4962 groups: list of :class:`sub-meshes, groups or filters <SMESH.SMESH_IDSource>` of elements to make boundary around
4965 tuple( long, mesh, groups )
4966 - long - number of added boundary elements
4967 - mesh - the :class:`Mesh` where elements were added to
4968 - group - the :class:`group <SMESH.SMESH_Group>` of boundary elements or None
4971 nb, mesh, group = self.editor.MakeBoundaryElements(dimension,groupName,meshName,
4973 if mesh: mesh = self.smeshpyD.Mesh(mesh)
4974 return nb, mesh, group
4976 def RenumberNodes(self):
4978 Renumber mesh nodes to remove unused node IDs
4980 self.editor.RenumberNodes()
4982 def RenumberElements(self):
4984 Renumber mesh elements to remove unused element IDs
4986 self.editor.RenumberElements()
4988 def _getIdSourceList(self, arg, idType, unRegister):
4990 Private method converting *arg* into a list of :class:`SMESH.SMESH_IDSource`
4992 if arg and isinstance( arg, list ):
4993 if isinstance( arg[0], int ):
4994 arg = self.GetIDSource( arg, idType )
4995 unRegister.set( arg )
4996 elif isinstance( arg[0], Mesh ):
4997 arg[0] = arg[0].GetMesh()
4998 elif isinstance( arg, Mesh ):
5000 if arg and isinstance( arg, SMESH._objref_SMESH_IDSource ):
5004 def RotationSweepObjects(self, nodes, edges, faces, Axis, AngleInRadians, NbOfSteps, Tolerance,
5005 MakeGroups=False, TotalAngle=False):
5007 Generate new elements by rotation of the given elements and nodes around the axis
5010 nodes: nodes to revolve: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5011 edges: edges to revolve: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5012 faces: faces to revolve: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5013 Axis: the axis of rotation: :class:`SMESH.AxisStruct`, line (geom object) or [x,y,z,dx,dy,dz]
5014 AngleInRadians: the angle of Rotation (in radians) or a name of variable
5015 which defines angle in degrees
5016 NbOfSteps: the number of steps
5017 Tolerance: tolerance
5018 MakeGroups: forces the generation of new groups from existing ones
5019 TotalAngle: gives meaning of AngleInRadians: if True then it is an angular size
5020 of all steps, else - size of each step
5023 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5026 unRegister = genObjUnRegister()
5027 nodes = self._getIdSourceList( nodes, SMESH.NODE, unRegister )
5028 edges = self._getIdSourceList( edges, SMESH.EDGE, unRegister )
5029 faces = self._getIdSourceList( faces, SMESH.FACE, unRegister )
5031 if isinstance( Axis, geomBuilder.GEOM._objref_GEOM_Object):
5032 Axis = self.smeshpyD.GetAxisStruct( Axis )
5033 if isinstance( Axis, list ):
5034 Axis = SMESH.AxisStruct( *Axis )
5036 AngleInRadians,AngleParameters,hasVars = ParseAngles(AngleInRadians)
5037 NbOfSteps,Tolerance,Parameters,hasVars = ParseParameters(NbOfSteps,Tolerance)
5038 Parameters = Axis.parameters + var_separator + AngleParameters + var_separator + Parameters
5039 self.mesh.SetParameters(Parameters)
5040 if TotalAngle and NbOfSteps:
5041 AngleInRadians /= NbOfSteps
5042 return self.editor.RotationSweepObjects( nodes, edges, faces,
5043 Axis, AngleInRadians,
5044 NbOfSteps, Tolerance, MakeGroups)
5046 def RotationSweep(self, IDsOfElements, Axis, AngleInRadians, NbOfSteps, Tolerance,
5047 MakeGroups=False, TotalAngle=False):
5049 Generate new elements by rotation of the elements around the axis
5052 IDsOfElements: the list of ids of elements to sweep
5053 Axis: the axis of rotation, :class:`SMESH.AxisStruct` or line(geom object)
5054 AngleInRadians: the angle of Rotation (in radians) or a name of variable which defines angle in degrees
5055 NbOfSteps: the number of steps
5056 Tolerance: tolerance
5057 MakeGroups: forces the generation of new groups from existing ones
5058 TotalAngle: gives meaning of AngleInRadians: if True then it is an angular size
5059 of all steps, else - size of each step
5062 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5065 return self.RotationSweepObjects([], IDsOfElements, IDsOfElements, Axis,
5066 AngleInRadians, NbOfSteps, Tolerance,
5067 MakeGroups, TotalAngle)
5069 def RotationSweepObject(self, theObject, Axis, AngleInRadians, NbOfSteps, Tolerance,
5070 MakeGroups=False, TotalAngle=False):
5072 Generate new elements by rotation of the elements of object around the axis
5073 theObject object which elements should be sweeped.
5074 It can be a mesh, a sub mesh or a group.
5077 Axis: the axis of rotation, :class:`SMESH.AxisStruct` or line(geom object)
5078 AngleInRadians: the angle of Rotation
5079 NbOfSteps: number of steps
5080 Tolerance: tolerance
5081 MakeGroups: forces the generation of new groups from existing ones
5082 TotalAngle: gives meaning of AngleInRadians: if True then it is an angular size
5083 of all steps, else - size of each step
5086 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5089 return self.RotationSweepObjects( [], theObject, theObject, Axis,
5090 AngleInRadians, NbOfSteps, Tolerance,
5091 MakeGroups, TotalAngle )
5093 def RotationSweepObject1D(self, theObject, Axis, AngleInRadians, NbOfSteps, Tolerance,
5094 MakeGroups=False, TotalAngle=False):
5096 Generate new elements by rotation of the elements of object around the axis
5097 theObject object which elements should be sweeped.
5098 It can be a mesh, a sub mesh or a group.
5101 Axis: the axis of rotation, :class:`SMESH.AxisStruct` or line(geom object)
5102 AngleInRadians: the angle of Rotation
5103 NbOfSteps: number of steps
5104 Tolerance: tolerance
5105 MakeGroups: forces the generation of new groups from existing ones
5106 TotalAngle: gives meaning of AngleInRadians: if True then it is an angular size
5107 of all steps, else - size of each step
5110 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True,
5111 empty list otherwise
5114 return self.RotationSweepObjects([],theObject,[], Axis,
5115 AngleInRadians, NbOfSteps, Tolerance,
5116 MakeGroups, TotalAngle)
5118 def RotationSweepObject2D(self, theObject, Axis, AngleInRadians, NbOfSteps, Tolerance,
5119 MakeGroups=False, TotalAngle=False):
5121 Generate new elements by rotation of the elements of object around the axis
5122 theObject object which elements should be sweeped.
5123 It can be a mesh, a sub mesh or a group.
5126 Axis: the axis of rotation, :class:`SMESH.AxisStruct` or line(geom object)
5127 AngleInRadians: the angle of Rotation
5128 NbOfSteps: number of steps
5129 Tolerance: tolerance
5130 MakeGroups: forces the generation of new groups from existing ones
5131 TotalAngle: gives meaning of AngleInRadians: if True then it is an angular size
5132 of all steps, else - size of each step
5135 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5138 return self.RotationSweepObjects([],[],theObject, Axis, AngleInRadians,
5139 NbOfSteps, Tolerance, MakeGroups, TotalAngle)
5141 def ExtrusionSweepObjects(self, nodes, edges, faces, StepVector, NbOfSteps, MakeGroups=False,
5142 scaleFactors=[], linearVariation=False, basePoint=[] ):
5144 Generate new elements by extrusion of the given elements and nodes
5147 nodes: nodes to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5148 edges: edges to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5149 faces: faces to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5150 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5151 the direction and value of extrusion for one step (the total extrusion
5152 length will be NbOfSteps * ||StepVector||)
5153 NbOfSteps: the number of steps
5154 MakeGroups: forces the generation of new groups from existing ones
5155 scaleFactors: optional scale factors to apply during extrusion
5156 linearVariation: if *True*, scaleFactors are spread over all *scaleFactors*,
5157 else scaleFactors[i] is applied to nodes at the i-th extrusion step
5158 basePoint: optional scaling center; if not provided, a gravity center of
5159 nodes and elements being extruded is used as the scaling center.
5162 - a list of tree components of the point or
5166 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5168 Example: :ref:`tui_extrusion`
5170 unRegister = genObjUnRegister()
5171 nodes = self._getIdSourceList( nodes, SMESH.NODE, unRegister )
5172 edges = self._getIdSourceList( edges, SMESH.EDGE, unRegister )
5173 faces = self._getIdSourceList( faces, SMESH.FACE, unRegister )
5175 if isinstance( StepVector, geomBuilder.GEOM._objref_GEOM_Object):
5176 StepVector = self.smeshpyD.GetDirStruct(StepVector)
5177 if isinstance( StepVector, list ):
5178 StepVector = self.smeshpyD.MakeDirStruct(*StepVector)
5180 if isinstance( basePoint, int):
5181 xyz = self.GetNodeXYZ( basePoint )
5183 raise RuntimeError("Invalid node ID: %s" % basePoint)
5185 if isinstance( basePoint, geomBuilder.GEOM._objref_GEOM_Object ):
5186 basePoint = self.geompyD.PointCoordinates( basePoint )
5188 NbOfSteps,Parameters,hasVars = ParseParameters(NbOfSteps)
5189 Parameters = StepVector.PS.parameters + var_separator + Parameters
5190 self.mesh.SetParameters(Parameters)
5192 return self.editor.ExtrusionSweepObjects( nodes, edges, faces,
5193 StepVector, NbOfSteps,
5194 scaleFactors, linearVariation, basePoint,
5198 def ExtrusionSweep(self, IDsOfElements, StepVector, NbOfSteps, MakeGroups=False, IsNodes = False):
5200 Generate new elements by extrusion of the elements with given ids
5203 IDsOfElements: the list of ids of elements or nodes for extrusion
5204 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5205 the direction and value of extrusion for one step (the total extrusion
5206 length will be NbOfSteps * ||StepVector||)
5207 NbOfSteps: the number of steps
5208 MakeGroups: forces the generation of new groups from existing ones
5209 IsNodes: is True if elements with given ids are nodes
5212 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5214 Example: :ref:`tui_extrusion`
5217 if IsNodes: n = IDsOfElements
5218 else : e,f, = IDsOfElements,IDsOfElements
5219 return self.ExtrusionSweepObjects(n,e,f, StepVector, NbOfSteps, MakeGroups)
5221 def ExtrusionByNormal(self, Elements, StepSize, NbOfSteps,
5222 ByAverageNormal=False, UseInputElemsOnly=True, MakeGroups=False, Dim = 2):
5224 Generate new elements by extrusion along the normal to a discretized surface or wire
5227 Elements: elements to extrude - a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`.
5228 Only faces can be extruded so far. A sub-mesh should be a sub-mesh on geom faces.
5229 StepSize: length of one extrusion step (the total extrusion
5230 length will be *NbOfSteps* *StepSize*).
5231 NbOfSteps: number of extrusion steps.
5232 ByAverageNormal: if True each node is translated by *StepSize*
5233 along the average of the normal vectors to the faces sharing the node;
5234 else each node is translated along the same average normal till
5235 intersection with the plane got by translation of the face sharing
5236 the node along its own normal by *StepSize*.
5237 UseInputElemsOnly: to use only *Elements* when computing extrusion direction
5238 for every node of *Elements*.
5239 MakeGroups: forces generation of new groups from existing ones.
5240 Dim: dimension of elements to extrude: 2 - faces or 1 - edges. Extrusion of edges
5241 is not yet implemented. This parameter is used if *Elements* contains
5242 both faces and edges, i.e. *Elements* is a Mesh.
5245 the list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True,
5246 empty list otherwise.
5247 Example: :ref:`tui_extrusion`
5250 unRegister = genObjUnRegister()
5251 if isinstance( Elements, Mesh ):
5252 Elements = [ Elements.GetMesh() ]
5253 if isinstance( Elements, list ):
5255 raise RuntimeError("Elements empty!")
5256 if isinstance( Elements[0], int ):
5257 Elements = self.GetIDSource( Elements, SMESH.ALL )
5258 unRegister.set( Elements )
5259 if not isinstance( Elements, list ):
5260 Elements = [ Elements ]
5261 StepSize,NbOfSteps,Parameters,hasVars = ParseParameters(StepSize,NbOfSteps)
5262 self.mesh.SetParameters(Parameters)
5263 return self.editor.ExtrusionByNormal(Elements, StepSize, NbOfSteps,
5264 ByAverageNormal, UseInputElemsOnly, MakeGroups, Dim)
5266 def ExtrusionSweepObject(self, theObject, StepVector, NbOfSteps, MakeGroups=False, IsNodes=False):
5268 Generate new elements by extrusion of the elements or nodes which belong to the object
5271 theObject: the object whose elements or nodes should be processed.
5272 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5273 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5274 the direction and value of extrusion for one step (the total extrusion
5275 length will be NbOfSteps * ||StepVector||)
5276 NbOfSteps: the number of steps
5277 MakeGroups: forces the generation of new groups from existing ones
5278 IsNodes: is True if elements to extrude are nodes
5281 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5282 Example: :ref:`tui_extrusion`
5286 if IsNodes: n = theObject
5287 else : e,f, = theObject,theObject
5288 return self.ExtrusionSweepObjects(n,e,f, StepVector, NbOfSteps, MakeGroups)
5290 def ExtrusionSweepObject1D(self, theObject, StepVector, NbOfSteps, MakeGroups=False):
5292 Generate new elements by extrusion of edges which belong to the object
5295 theObject: object whose 1D elements should be processed.
5296 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5297 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5298 the direction and value of extrusion for one step (the total extrusion
5299 length will be NbOfSteps * ||StepVector||)
5300 NbOfSteps: the number of steps
5301 MakeGroups: to generate new groups from existing ones
5304 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5305 Example: :ref:`tui_extrusion`
5308 return self.ExtrusionSweepObjects([],theObject,[], StepVector, NbOfSteps, MakeGroups)
5310 def ExtrusionSweepObject2D(self, theObject, StepVector, NbOfSteps, MakeGroups=False):
5312 Generate new elements by extrusion of faces which belong to the object
5315 theObject: object whose 2D elements should be processed.
5316 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5317 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5318 the direction and value of extrusion for one step (the total extrusion
5319 length will be NbOfSteps * ||StepVector||)
5320 NbOfSteps: the number of steps
5321 MakeGroups: forces the generation of new groups from existing ones
5324 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5325 Example: :ref:`tui_extrusion`
5328 return self.ExtrusionSweepObjects([],[],theObject, StepVector, NbOfSteps, MakeGroups)
5330 def AdvancedExtrusion(self, IDsOfElements, StepVector, NbOfSteps,
5331 ExtrFlags, SewTolerance, MakeGroups=False):
5333 Generate new elements by extrusion of the elements with given ids
5336 IDsOfElements: is ids of elements
5337 StepVector: vector or :class:`SMESH.DirStruct` or 3 vector components, defining
5338 the direction and value of extrusion for one step (the total extrusion
5339 length will be NbOfSteps * ||StepVector||)
5340 NbOfSteps: the number of steps
5341 ExtrFlags: sets flags for extrusion
5342 SewTolerance: uses for comparing locations of nodes if flag
5343 EXTRUSION_FLAG_SEW is set
5344 MakeGroups: forces the generation of new groups from existing ones
5347 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5350 if isinstance( StepVector, geomBuilder.GEOM._objref_GEOM_Object):
5351 StepVector = self.smeshpyD.GetDirStruct(StepVector)
5352 if isinstance( StepVector, list ):
5353 StepVector = self.smeshpyD.MakeDirStruct(*StepVector)
5354 return self.editor.AdvancedExtrusion(IDsOfElements, StepVector, NbOfSteps,
5355 ExtrFlags, SewTolerance, MakeGroups)
5357 def ExtrusionAlongPathObjects(self, Nodes, Edges, Faces, PathMesh, PathShape=None,
5358 NodeStart=1, HasAngles=False, Angles=[], LinearVariation=False,
5359 HasRefPoint=False, RefPoint=[0,0,0], MakeGroups=False):
5361 Generate new elements by extrusion of the given elements and nodes along the path.
5362 The path of extrusion must be a meshed edge.
5365 Nodes: nodes to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5366 Edges: edges to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5367 Faces: faces to extrude: a list including ids, :class:`a mesh, sub-meshes, groups or filters <SMESH.SMESH_IDSource>`
5368 PathMesh: 1D mesh or 1D sub-mesh, along which proceeds the extrusion
5369 PathShape: shape (edge) defines the sub-mesh of PathMesh if PathMesh
5370 contains not only path segments, else it can be None
5371 NodeStart: the first or the last node on the path. Defines the direction of extrusion
5372 HasAngles: allows the shape to be rotated around the path
5373 to get the resulting mesh in a helical fashion
5374 Angles: list of angles
5375 LinearVariation: forces the computation of rotation angles as linear
5376 variation of the given Angles along path steps
5377 HasRefPoint: allows using the reference point
5378 RefPoint: the reference point around which the shape is rotated (the mass center of the
5379 shape by default). The User can specify any point as the Reference Point.
5380 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5381 MakeGroups: forces the generation of new groups from existing ones
5384 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5385 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>`
5386 Example: :ref:`tui_extrusion_along_path`
5389 unRegister = genObjUnRegister()
5390 Nodes = self._getIdSourceList( Nodes, SMESH.NODE, unRegister )
5391 Edges = self._getIdSourceList( Edges, SMESH.EDGE, unRegister )
5392 Faces = self._getIdSourceList( Faces, SMESH.FACE, unRegister )
5394 if isinstance( RefPoint, geomBuilder.GEOM._objref_GEOM_Object):
5395 RefPoint = self.smeshpyD.GetPointStruct(RefPoint)
5396 if isinstance( RefPoint, list ):
5397 if not RefPoint: RefPoint = [0,0,0]
5398 RefPoint = SMESH.PointStruct( *RefPoint )
5399 if isinstance( PathMesh, Mesh ):
5400 PathMesh = PathMesh.GetMesh()
5401 Angles,AnglesParameters,hasVars = ParseAngles(Angles)
5402 Parameters = AnglesParameters + var_separator + RefPoint.parameters
5403 self.mesh.SetParameters(Parameters)
5404 return self.editor.ExtrusionAlongPathObjects(Nodes, Edges, Faces,
5405 PathMesh, PathShape, NodeStart,
5406 HasAngles, Angles, LinearVariation,
5407 HasRefPoint, RefPoint, MakeGroups)
5409 def ExtrusionAlongPathX(self, Base, Path, NodeStart,
5410 HasAngles=False, Angles=[], LinearVariation=False,
5411 HasRefPoint=False, RefPoint=[0,0,0], MakeGroups=False,
5412 ElemType=SMESH.FACE):
5414 Generate new elements by extrusion of the given elements.
5415 The path of extrusion must be a meshed edge.
5418 Base: :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>`, or list of ids of elements for extrusion
5419 Path: 1D mesh or 1D sub-mesh, along which proceeds the extrusion
5420 NodeStart: the start node from Path. Defines the direction of extrusion
5421 HasAngles: allows the shape to be rotated around the path
5422 to get the resulting mesh in a helical fashion
5423 Angles: list of angles in radians
5424 LinearVariation: forces the computation of rotation angles as linear
5425 variation of the given Angles along path steps
5426 HasRefPoint: allows using the reference point
5427 RefPoint: the reference point around which the elements are rotated (the mass
5428 center of the elements by default).
5429 The User can specify any point as the Reference Point.
5430 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5431 MakeGroups: forces the generation of new groups from existing ones
5432 ElemType: type of elements for extrusion (if param Base is a mesh)
5435 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5436 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>`
5437 if *MakeGroups* == True, only :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>`
5439 Example: :ref:`tui_extrusion_along_path`
5443 if ElemType == SMESH.NODE: n = Base
5444 if ElemType == SMESH.EDGE: e = Base
5445 if ElemType == SMESH.FACE: f = Base
5446 gr,er = self.ExtrusionAlongPathObjects(n,e,f, Path, None, NodeStart,
5447 HasAngles, Angles, LinearVariation,
5448 HasRefPoint, RefPoint, MakeGroups)
5449 if MakeGroups: return gr,er
5452 def ExtrusionAlongPath(self, IDsOfElements, PathMesh, PathShape, NodeStart,
5453 HasAngles=False, Angles=[], HasRefPoint=False, RefPoint=[],
5454 MakeGroups=False, LinearVariation=False):
5456 Generate new elements by extrusion of the given elements.
5457 The path of extrusion must be a meshed edge.
5460 IDsOfElements: ids of elements
5461 PathMesh: mesh containing a 1D sub-mesh on the edge, along which proceeds the extrusion
5462 PathShape: shape (edge) defines the sub-mesh for the path
5463 NodeStart: the first or the last node on the edge. Defines the direction of extrusion
5464 HasAngles: allows the shape to be rotated around the path
5465 to get the resulting mesh in a helical fashion
5466 Angles: list of angles in radians
5467 HasRefPoint: allows using the reference point
5468 RefPoint: the reference point around which the shape is rotated (the mass center of the shape by default).
5469 The User can specify any point as the Reference Point.
5470 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5471 MakeGroups: forces the generation of new groups from existing ones
5472 LinearVariation: forces the computation of rotation angles as linear
5473 variation of the given Angles along path steps
5476 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5477 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>`
5478 if *MakeGroups* == True, only :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` otherwise
5479 Example: :ref:`tui_extrusion_along_path`
5482 n,e,f = [],IDsOfElements,IDsOfElements
5483 gr,er = self.ExtrusionAlongPathObjects(n,e,f, PathMesh, PathShape,
5484 NodeStart, HasAngles, Angles,
5486 HasRefPoint, RefPoint, MakeGroups)
5487 if MakeGroups: return gr,er
5490 def ExtrusionAlongPathObject(self, theObject, PathMesh, PathShape, NodeStart,
5491 HasAngles=False, Angles=[], HasRefPoint=False, RefPoint=[],
5492 MakeGroups=False, LinearVariation=False):
5494 Generate new elements by extrusion of the elements which belong to the object.
5495 The path of extrusion must be a meshed edge.
5498 theObject: the object whose elements should be processed.
5499 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5500 PathMesh: mesh containing a 1D sub-mesh on the edge, along which the extrusion proceeds
5501 PathShape: shape (edge) defines the sub-mesh for the path
5502 NodeStart: the first or the last node on the edge. Defines the direction of extrusion
5503 HasAngles: allows the shape to be rotated around the path
5504 to get the resulting mesh in a helical fashion
5505 Angles: list of angles
5506 HasRefPoint: allows using the reference point
5507 RefPoint: the reference point around which the shape is rotated (the mass center of the shape by default).
5508 The User can specify any point as the Reference Point.
5509 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5510 MakeGroups: forces the generation of new groups from existing ones
5511 LinearVariation: forces the computation of rotation angles as linear
5512 variation of the given Angles along path steps
5515 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5516 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` if *MakeGroups* == True,
5517 only :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` otherwise
5518 Example: :ref:`tui_extrusion_along_path`
5521 n,e,f = [],theObject,theObject
5522 gr,er = self.ExtrusionAlongPathObjects(n,e,f, PathMesh, PathShape, NodeStart,
5523 HasAngles, Angles, LinearVariation,
5524 HasRefPoint, RefPoint, MakeGroups)
5525 if MakeGroups: return gr,er
5528 def ExtrusionAlongPathObject1D(self, theObject, PathMesh, PathShape, NodeStart,
5529 HasAngles=False, Angles=[], HasRefPoint=False, RefPoint=[],
5530 MakeGroups=False, LinearVariation=False):
5532 Generate new elements by extrusion of mesh segments which belong to the object.
5533 The path of extrusion must be a meshed edge.
5536 theObject: the object whose 1D elements should be processed.
5537 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5538 PathMesh: mesh containing a 1D sub-mesh on the edge, along which the extrusion proceeds
5539 PathShape: shape (edge) defines the sub-mesh for the path
5540 NodeStart: the first or the last node on the edge. Defines the direction of extrusion
5541 HasAngles: allows the shape to be rotated around the path
5542 to get the resulting mesh in a helical fashion
5543 Angles: list of angles
5544 HasRefPoint: allows using the reference point
5545 RefPoint: the reference point around which the shape is rotated (the mass center of the shape by default).
5546 The User can specify any point as the Reference Point.
5547 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5548 MakeGroups: forces the generation of new groups from existing ones
5549 LinearVariation: forces the computation of rotation angles as linear
5550 variation of the given Angles along path steps
5553 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5554 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` if *MakeGroups* == True,
5555 only :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` otherwise
5556 Example: :ref:`tui_extrusion_along_path`
5559 n,e,f = [],theObject,[]
5560 gr,er = self.ExtrusionAlongPathObjects(n,e,f, PathMesh, PathShape, NodeStart,
5561 HasAngles, Angles, LinearVariation,
5562 HasRefPoint, RefPoint, MakeGroups)
5563 if MakeGroups: return gr,er
5566 def ExtrusionAlongPathObject2D(self, theObject, PathMesh, PathShape, NodeStart,
5567 HasAngles=False, Angles=[], HasRefPoint=False, RefPoint=[],
5568 MakeGroups=False, LinearVariation=False):
5570 Generate new elements by extrusion of faces which belong to the object.
5571 The path of extrusion must be a meshed edge.
5574 theObject: the object whose 2D elements should be processed.
5575 It can be a :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
5576 PathMesh: mesh containing a 1D sub-mesh on the edge, along which the extrusion proceeds
5577 PathShape: shape (edge) defines the sub-mesh for the path
5578 NodeStart: the first or the last node on the edge. Defines the direction of extrusion
5579 HasAngles: allows the shape to be rotated around the path
5580 to get the resulting mesh in a helical fashion
5581 Angles: list of angles
5582 HasRefPoint: allows using the reference point
5583 RefPoint: the reference point around which the shape is rotated (the mass center of the shape by default).
5584 The User can specify any point as the Reference Point.
5585 *RefPoint* can be either GEOM Vertex, [x,y,z] or :class:`SMESH.PointStruct`
5586 MakeGroups: forces the generation of new groups from existing ones
5587 LinearVariation: forces the computation of rotation angles as linear
5588 variation of the given Angles along path steps
5591 list of created :class:`groups <SMESH.SMESH_GroupBase>` and
5592 :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` if *MakeGroups* == True,
5593 only :class:`error code <SMESH.SMESH_MeshEditor.Extrusion_Error>` otherwise
5594 Example: :ref:`tui_extrusion_along_path`
5597 n,e,f = [],[],theObject
5598 gr,er = self.ExtrusionAlongPathObjects(n,e,f, PathMesh, PathShape, NodeStart,
5599 HasAngles, Angles, LinearVariation,
5600 HasRefPoint, RefPoint, MakeGroups)
5601 if MakeGroups: return gr,er
5604 def Mirror(self, IDsOfElements, Mirror, theMirrorType=None, Copy=0, MakeGroups=False):
5606 Create a symmetrical copy of mesh elements
5609 IDsOfElements: list of elements ids
5610 Mirror: is :class:`SMESH.AxisStruct` or geom object (point, line, plane)
5611 theMirrorType: smeshBuilder.POINT, smeshBuilder.AXIS or smeshBuilder.PLANE.
5612 If the *Mirror* is a geom object this parameter is unnecessary
5613 Copy: allows to copy element (Copy is 1) or to replace with its mirroring (Copy is 0)
5614 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5617 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5620 if IDsOfElements == []:
5621 IDsOfElements = self.GetElementsId()
5622 if ( isinstance( Mirror, geomBuilder.GEOM._objref_GEOM_Object)):
5623 Mirror = self.smeshpyD.GetAxisStruct(Mirror)
5624 theMirrorType = Mirror._mirrorType
5626 self.mesh.SetParameters(Mirror.parameters)
5627 if Copy and MakeGroups:
5628 return self.editor.MirrorMakeGroups(IDsOfElements, Mirror, theMirrorType)
5629 self.editor.Mirror(IDsOfElements, Mirror, theMirrorType, Copy)
5632 def MirrorMakeMesh(self, IDsOfElements, Mirror, theMirrorType=0, MakeGroups=0, NewMeshName=""):
5634 Create a new mesh by a symmetrical copy of mesh elements
5637 IDsOfElements: the list of elements ids
5638 Mirror: is :class:`SMESH.AxisStruct` or geom object (point, line, plane)
5639 theMirrorType: smeshBuilder.POINT, smeshBuilder.AXIS or smeshBuilder.PLANE.
5640 If the *Mirror* is a geom object this parameter is unnecessary
5641 MakeGroups: to generate new groups from existing ones
5642 NewMeshName: a name of the new mesh to create
5645 instance of class :class:`Mesh`
5648 if IDsOfElements == []:
5649 IDsOfElements = self.GetElementsId()
5650 if ( isinstance( Mirror, geomBuilder.GEOM._objref_GEOM_Object)):
5651 Mirror = self.smeshpyD.GetAxisStruct(Mirror)
5652 theMirrorType = Mirror._mirrorType
5654 self.mesh.SetParameters(Mirror.parameters)
5655 mesh = self.editor.MirrorMakeMesh(IDsOfElements, Mirror, theMirrorType,
5656 MakeGroups, NewMeshName)
5657 return Mesh(self.smeshpyD,self.geompyD,mesh)
5659 def MirrorObject (self, theObject, Mirror, theMirrorType=None, Copy=0, MakeGroups=False):
5661 Create a symmetrical copy of the object
5664 theObject: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
5665 Mirror: :class:`SMESH.AxisStruct` or geom object (point, line, plane)
5666 theMirrorType: smeshBuilder.POINT, smeshBuilder.AXIS or smeshBuilder.PLANE.
5667 If the *Mirror* is a geom object this parameter is unnecessary
5668 Copy: allows copying the element (Copy==True) or replacing it with its mirror (Copy==False)
5669 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5672 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5675 if ( isinstance( theObject, Mesh )):
5676 theObject = theObject.GetMesh()
5677 if ( isinstance( Mirror, geomBuilder.GEOM._objref_GEOM_Object)):
5678 Mirror = self.smeshpyD.GetAxisStruct(Mirror)
5679 theMirrorType = Mirror._mirrorType
5681 self.mesh.SetParameters(Mirror.parameters)
5682 if Copy and MakeGroups:
5683 return self.editor.MirrorObjectMakeGroups(theObject, Mirror, theMirrorType)
5684 self.editor.MirrorObject(theObject, Mirror, theMirrorType, Copy)
5687 def MirrorObjectMakeMesh (self, theObject, Mirror, theMirrorType=0,MakeGroups=0,NewMeshName=""):
5689 Create a new mesh by a symmetrical copy of the object
5692 theObject: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
5693 Mirror: :class:`SMESH.AxisStruct` or geom object (point, line, plane)
5694 theMirrorType: smeshBuilder.POINT, smeshBuilder.AXIS or smeshBuilder.PLANE.
5695 If the *Mirror* is a geom object this parameter is unnecessary
5696 MakeGroups: forces the generation of new groups from existing ones
5697 NewMeshName: the name of the new mesh to create
5700 instance of class :class:`Mesh`
5703 if ( isinstance( theObject, Mesh )):
5704 theObject = theObject.GetMesh()
5705 if ( isinstance( Mirror, geomBuilder.GEOM._objref_GEOM_Object)):
5706 Mirror = self.smeshpyD.GetAxisStruct(Mirror)
5707 theMirrorType = Mirror._mirrorType
5709 self.mesh.SetParameters(Mirror.parameters)
5710 mesh = self.editor.MirrorObjectMakeMesh(theObject, Mirror, theMirrorType,
5711 MakeGroups, NewMeshName)
5712 return Mesh( self.smeshpyD,self.geompyD,mesh )
5714 def Translate(self, IDsOfElements, Vector, Copy, MakeGroups=False):
5716 Translate the elements
5719 IDsOfElements: list of elements ids
5720 Vector: the direction of translation (:class:`SMESH.DirStruct` or vector or 3 vector components)
5721 Copy: allows copying the translated elements
5722 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5725 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5728 if IDsOfElements == []:
5729 IDsOfElements = self.GetElementsId()
5730 if ( isinstance( Vector, geomBuilder.GEOM._objref_GEOM_Object)):
5731 Vector = self.smeshpyD.GetDirStruct(Vector)
5732 if isinstance( Vector, list ):
5733 Vector = self.smeshpyD.MakeDirStruct(*Vector)
5734 self.mesh.SetParameters(Vector.PS.parameters)
5735 if Copy and MakeGroups:
5736 return self.editor.TranslateMakeGroups(IDsOfElements, Vector)
5737 self.editor.Translate(IDsOfElements, Vector, Copy)
5740 def TranslateMakeMesh(self, IDsOfElements, Vector, MakeGroups=False, NewMeshName=""):
5742 Create a new mesh of translated elements
5745 IDsOfElements: list of elements ids
5746 Vector: the direction of translation (:class:`SMESH.DirStruct` or vector or 3 vector components)
5747 MakeGroups: forces the generation of new groups from existing ones
5748 NewMeshName: the name of the newly created mesh
5751 instance of class :class:`Mesh`
5754 if IDsOfElements == []:
5755 IDsOfElements = self.GetElementsId()
5756 if ( isinstance( Vector, geomBuilder.GEOM._objref_GEOM_Object)):
5757 Vector = self.smeshpyD.GetDirStruct(Vector)
5758 if isinstance( Vector, list ):
5759 Vector = self.smeshpyD.MakeDirStruct(*Vector)
5760 self.mesh.SetParameters(Vector.PS.parameters)
5761 mesh = self.editor.TranslateMakeMesh(IDsOfElements, Vector, MakeGroups, NewMeshName)
5762 return Mesh ( self.smeshpyD, self.geompyD, mesh )
5764 def TranslateObject(self, theObject, Vector, Copy, MakeGroups=False):
5766 Translate the object
5769 theObject: the object to translate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5770 Vector: direction of translation (:class:`SMESH.DirStruct` or geom vector or 3 vector components)
5771 Copy: allows copying the translated elements
5772 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5775 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5778 if ( isinstance( theObject, Mesh )):
5779 theObject = theObject.GetMesh()
5780 if ( isinstance( Vector, geomBuilder.GEOM._objref_GEOM_Object)):
5781 Vector = self.smeshpyD.GetDirStruct(Vector)
5782 if isinstance( Vector, list ):
5783 Vector = self.smeshpyD.MakeDirStruct(*Vector)
5784 self.mesh.SetParameters(Vector.PS.parameters)
5785 if Copy and MakeGroups:
5786 return self.editor.TranslateObjectMakeGroups(theObject, Vector)
5787 self.editor.TranslateObject(theObject, Vector, Copy)
5790 def TranslateObjectMakeMesh(self, theObject, Vector, MakeGroups=False, NewMeshName=""):
5792 Create a new mesh from the translated object
5795 theObject: the object to translate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5796 Vector: the direction of translation (:class:`SMESH.DirStruct` or geom vector or 3 vector components)
5797 MakeGroups: forces the generation of new groups from existing ones
5798 NewMeshName: the name of the newly created mesh
5801 instance of class :class:`Mesh`
5804 if isinstance( theObject, Mesh ):
5805 theObject = theObject.GetMesh()
5806 if isinstance( Vector, geomBuilder.GEOM._objref_GEOM_Object ):
5807 Vector = self.smeshpyD.GetDirStruct(Vector)
5808 if isinstance( Vector, list ):
5809 Vector = self.smeshpyD.MakeDirStruct(*Vector)
5810 self.mesh.SetParameters(Vector.PS.parameters)
5811 mesh = self.editor.TranslateObjectMakeMesh(theObject, Vector, MakeGroups, NewMeshName)
5812 return Mesh( self.smeshpyD, self.geompyD, mesh )
5816 def Scale(self, theObject, thePoint, theScaleFact, Copy, MakeGroups=False):
5821 theObject: the object to translate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5822 thePoint: base point for scale (:class:`SMESH.PointStruct` or list of 3 coordinates)
5823 theScaleFact: list of 1-3 scale factors for axises
5824 Copy: allows copying the translated elements
5825 MakeGroups: forces the generation of new groups from existing
5829 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True,
5830 empty list otherwise
5832 unRegister = genObjUnRegister()
5833 if ( isinstance( theObject, Mesh )):
5834 theObject = theObject.GetMesh()
5835 if ( isinstance( theObject, list )):
5836 theObject = self.GetIDSource(theObject, SMESH.ALL)
5837 unRegister.set( theObject )
5838 if ( isinstance( thePoint, list )):
5839 thePoint = PointStruct( thePoint[0], thePoint[1], thePoint[2] )
5840 if ( isinstance( theScaleFact, float )):
5841 theScaleFact = [theScaleFact]
5842 if ( isinstance( theScaleFact, int )):
5843 theScaleFact = [ float(theScaleFact)]
5845 self.mesh.SetParameters(thePoint.parameters)
5847 if Copy and MakeGroups:
5848 return self.editor.ScaleMakeGroups(theObject, thePoint, theScaleFact)
5849 self.editor.Scale(theObject, thePoint, theScaleFact, Copy)
5852 def ScaleMakeMesh(self, theObject, thePoint, theScaleFact, MakeGroups=False, NewMeshName=""):
5854 Create a new mesh from the translated object
5857 theObject: the object to translate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5858 thePoint: base point for scale (:class:`SMESH.PointStruct` or list of 3 coordinates)
5859 theScaleFact: list of 1-3 scale factors for axises
5860 MakeGroups: forces the generation of new groups from existing ones
5861 NewMeshName: the name of the newly created mesh
5864 instance of class :class:`Mesh`
5866 unRegister = genObjUnRegister()
5867 if (isinstance(theObject, Mesh)):
5868 theObject = theObject.GetMesh()
5869 if ( isinstance( theObject, list )):
5870 theObject = self.GetIDSource(theObject,SMESH.ALL)
5871 unRegister.set( theObject )
5872 if ( isinstance( thePoint, list )):
5873 thePoint = PointStruct( thePoint[0], thePoint[1], thePoint[2] )
5874 if ( isinstance( theScaleFact, float )):
5875 theScaleFact = [theScaleFact]
5876 if ( isinstance( theScaleFact, int )):
5877 theScaleFact = [ float(theScaleFact)]
5879 self.mesh.SetParameters(thePoint.parameters)
5880 mesh = self.editor.ScaleMakeMesh(theObject, thePoint, theScaleFact,
5881 MakeGroups, NewMeshName)
5882 return Mesh( self.smeshpyD, self.geompyD, mesh )
5886 def Rotate (self, IDsOfElements, Axis, AngleInRadians, Copy, MakeGroups=False):
5891 IDsOfElements: list of elements ids
5892 Axis: the axis of rotation (:class:`SMESH.AxisStruct` or geom line)
5893 AngleInRadians: the angle of rotation (in radians) or a name of variable which defines angle in degrees
5894 Copy: allows copying the rotated elements
5895 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5898 list of created :class:`groups <SMESH.SMESH_GroupBase>` if *MakeGroups* == True, empty list otherwise
5902 if IDsOfElements == []:
5903 IDsOfElements = self.GetElementsId()
5904 if ( isinstance( Axis, geomBuilder.GEOM._objref_GEOM_Object)):
5905 Axis = self.smeshpyD.GetAxisStruct(Axis)
5906 AngleInRadians,Parameters,hasVars = ParseAngles(AngleInRadians)
5907 Parameters = Axis.parameters + var_separator + Parameters
5908 self.mesh.SetParameters(Parameters)
5909 if Copy and MakeGroups:
5910 return self.editor.RotateMakeGroups(IDsOfElements, Axis, AngleInRadians)
5911 self.editor.Rotate(IDsOfElements, Axis, AngleInRadians, Copy)
5914 def RotateMakeMesh (self, IDsOfElements, Axis, AngleInRadians, MakeGroups=0, NewMeshName=""):
5916 Create a new mesh of rotated elements
5919 IDsOfElements: list of element ids
5920 Axis: the axis of rotation (:class:`SMESH.AxisStruct` or geom line)
5921 AngleInRadians: the angle of rotation (in radians) or a name of variable which defines angle in degrees
5922 MakeGroups: forces the generation of new groups from existing ones
5923 NewMeshName: the name of the newly created mesh
5926 instance of class :class:`Mesh`
5929 if IDsOfElements == []:
5930 IDsOfElements = self.GetElementsId()
5931 if ( isinstance( Axis, geomBuilder.GEOM._objref_GEOM_Object)):
5932 Axis = self.smeshpyD.GetAxisStruct(Axis)
5933 AngleInRadians,Parameters,hasVars = ParseAngles(AngleInRadians)
5934 Parameters = Axis.parameters + var_separator + Parameters
5935 self.mesh.SetParameters(Parameters)
5936 mesh = self.editor.RotateMakeMesh(IDsOfElements, Axis, AngleInRadians,
5937 MakeGroups, NewMeshName)
5938 return Mesh( self.smeshpyD, self.geompyD, mesh )
5940 def RotateObject (self, theObject, Axis, AngleInRadians, Copy, MakeGroups=False):
5945 theObject: the object to rotate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5946 Axis: the axis of rotation (:class:`SMESH.AxisStruct` or geom line)
5947 AngleInRadians: the angle of rotation (in radians) or a name of variable which defines angle in degrees
5948 Copy: allows copying the rotated elements
5949 MakeGroups: forces the generation of new groups from existing ones (if Copy)
5952 list of created :class:`groups <SMESH.SMESH_GroupBase>` if MakeGroups==True, empty list otherwise
5955 if (isinstance(theObject, Mesh)):
5956 theObject = theObject.GetMesh()
5957 if (isinstance(Axis, geomBuilder.GEOM._objref_GEOM_Object)):
5958 Axis = self.smeshpyD.GetAxisStruct(Axis)
5959 AngleInRadians,Parameters,hasVars = ParseAngles(AngleInRadians)
5960 Parameters = Axis.parameters + ":" + Parameters
5961 self.mesh.SetParameters(Parameters)
5962 if Copy and MakeGroups:
5963 return self.editor.RotateObjectMakeGroups(theObject, Axis, AngleInRadians)
5964 self.editor.RotateObject(theObject, Axis, AngleInRadians, Copy)
5967 def RotateObjectMakeMesh(self, theObject, Axis, AngleInRadians, MakeGroups=0,NewMeshName=""):
5969 Create a new mesh from the rotated object
5972 theObject: the object to rotate (:class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`)
5973 Axis: the axis of rotation (:class:`SMESH.AxisStruct` or geom line)
5974 AngleInRadians: the angle of rotation (in radians) or a name of variable which defines angle in degrees
5975 MakeGroups: forces the generation of new groups from existing ones
5976 NewMeshName: the name of the newly created mesh
5979 instance of class :class:`Mesh`
5982 if (isinstance( theObject, Mesh )):
5983 theObject = theObject.GetMesh()
5984 if (isinstance(Axis, geomBuilder.GEOM._objref_GEOM_Object)):
5985 Axis = self.smeshpyD.GetAxisStruct(Axis)
5986 AngleInRadians,Parameters,hasVars = ParseAngles(AngleInRadians)
5987 Parameters = Axis.parameters + ":" + Parameters
5988 mesh = self.editor.RotateObjectMakeMesh(theObject, Axis, AngleInRadians,
5989 MakeGroups, NewMeshName)
5990 self.mesh.SetParameters(Parameters)
5991 return Mesh( self.smeshpyD, self.geompyD, mesh )
5993 def Offset(self, theObject, Value, MakeGroups=False, CopyElements=False, NewMeshName=''):
5995 Create an offset mesh from the given 2D object
5998 theObject (SMESH.SMESH_IDSource): the source object (mesh, sub-mesh, group or filter)
5999 theValue (float): signed offset size
6000 MakeGroups (boolean): forces the generation of new groups from existing ones
6001 CopyElements (boolean): if *NewMeshName* is empty, True means to keep original elements,
6002 False means to remove original elements.
6003 NewMeshName (string): the name of a mesh to create. If empty, offset elements are added to this mesh
6006 A tuple (:class:`Mesh`, list of :class:`groups <SMESH.SMESH_Group>`)
6009 if isinstance( theObject, Mesh ):
6010 theObject = theObject.GetMesh()
6011 theValue,Parameters,hasVars = ParseParameters(Value)
6012 mesh_groups = self.editor.Offset(theObject, Value, MakeGroups, CopyElements, NewMeshName)
6013 self.mesh.SetParameters(Parameters)
6014 # if mesh_groups[0]:
6015 # return Mesh( self.smeshpyD, self.geompyD, mesh_groups[0] ), mesh_groups[1]
6018 def FindCoincidentNodes (self, Tolerance, SeparateCornerAndMediumNodes=False):
6020 Find groups of adjacent nodes within Tolerance.
6023 Tolerance (float): the value of tolerance
6024 SeparateCornerAndMediumNodes (boolean): if *True*, in quadratic mesh puts
6025 corner and medium nodes in separate groups thus preventing
6026 their further merge.
6029 the list of groups of nodes IDs (e.g. [[1,12,13],[4,25]])
6032 return self.editor.FindCoincidentNodes( Tolerance, SeparateCornerAndMediumNodes )
6034 def FindCoincidentNodesOnPart (self, SubMeshOrGroup, Tolerance,
6035 exceptNodes=[], SeparateCornerAndMediumNodes=False):
6037 Find groups of ajacent nodes within Tolerance.
6040 Tolerance: the value of tolerance
6041 SubMeshOrGroup: :class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`
6042 exceptNodes: list of either SubMeshes, Groups or node IDs to exclude from search
6043 SeparateCornerAndMediumNodes: if *True*, in quadratic mesh puts
6044 corner and medium nodes in separate groups thus preventing
6045 their further merge.
6048 the list of groups of nodes IDs (e.g. [[1,12,13],[4,25]])
6051 unRegister = genObjUnRegister()
6052 if (isinstance( SubMeshOrGroup, Mesh )):
6053 SubMeshOrGroup = SubMeshOrGroup.GetMesh()
6054 if not isinstance( exceptNodes, list ):
6055 exceptNodes = [ exceptNodes ]
6056 if exceptNodes and isinstance( exceptNodes[0], int ):
6057 exceptNodes = [ self.GetIDSource( exceptNodes, SMESH.NODE )]
6058 unRegister.set( exceptNodes )
6059 return self.editor.FindCoincidentNodesOnPartBut(SubMeshOrGroup, Tolerance,
6060 exceptNodes, SeparateCornerAndMediumNodes)
6062 def MergeNodes (self, GroupsOfNodes, NodesToKeep=[], AvoidMakingHoles=False):
6067 GroupsOfNodes: a list of groups of nodes IDs for merging.
6068 E.g. [[1,12,13],[25,4]] means that nodes 12, 13 and 4 will be removed and replaced
6069 in all elements and groups by nodes 1 and 25 correspondingly
6070 NodesToKeep: nodes to keep in the mesh: a list of groups, sub-meshes or node IDs.
6071 If *NodesToKeep* does not include a node to keep for some group to merge,
6072 then the first node in the group is kept.
6073 AvoidMakingHoles: prevent merging nodes which cause removal of elements becoming
6076 # NodesToKeep are converted to SMESH.SMESH_IDSource in meshEditor.MergeNodes()
6077 self.editor.MergeNodes( GroupsOfNodes, NodesToKeep, AvoidMakingHoles )
6079 def FindEqualElements (self, MeshOrSubMeshOrGroup=None):
6081 Find the elements built on the same nodes.
6084 MeshOrSubMeshOrGroup: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
6087 the list of groups of equal elements IDs (e.g. [[1,12,13],[4,25]])
6090 if not MeshOrSubMeshOrGroup:
6091 MeshOrSubMeshOrGroup=self.mesh
6092 elif isinstance( MeshOrSubMeshOrGroup, Mesh ):
6093 MeshOrSubMeshOrGroup = MeshOrSubMeshOrGroup.GetMesh()
6094 return self.editor.FindEqualElements( MeshOrSubMeshOrGroup )
6096 def MergeElements(self, GroupsOfElementsID):
6098 Merge elements in each given group.
6101 GroupsOfElementsID: a list of groups (lists) of elements IDs for merging
6102 (e.g. [[1,12,13],[25,4]] means that elements 12, 13 and 4 will be removed and
6103 replaced in all groups by elements 1 and 25)
6106 self.editor.MergeElements(GroupsOfElementsID)
6108 def MergeEqualElements(self):
6110 Leave one element and remove all other elements built on the same nodes.
6113 self.editor.MergeEqualElements()
6115 def FindFreeBorders(self, ClosedOnly=True):
6117 Returns all or only closed free borders
6120 list of SMESH.FreeBorder's
6123 return self.editor.FindFreeBorders( ClosedOnly )
6125 def FillHole(self, holeNodes):
6127 Fill with 2D elements a hole defined by a SMESH.FreeBorder.
6130 FreeBorder: either a SMESH.FreeBorder or a list on node IDs. These nodes
6131 must describe all sequential nodes of the hole border. The first and the last
6132 nodes must be the same. Use :meth:`FindFreeBorders` to get nodes of holes.
6136 if holeNodes and isinstance( holeNodes, list ) and isinstance( holeNodes[0], int ):
6137 holeNodes = SMESH.FreeBorder(nodeIDs=holeNodes)
6138 if not isinstance( holeNodes, SMESH.FreeBorder ):
6139 raise TypeError("holeNodes must be either SMESH.FreeBorder or list of integer and not %s" % holeNodes)
6140 self.editor.FillHole( holeNodes )
6142 def FindCoincidentFreeBorders (self, tolerance=0.):
6144 Return groups of FreeBorder's coincident within the given tolerance.
6147 tolerance: the tolerance. If the tolerance <= 0.0 then one tenth of an average
6148 size of elements adjacent to free borders being compared is used.
6151 SMESH.CoincidentFreeBorders structure
6154 return self.editor.FindCoincidentFreeBorders( tolerance )
6156 def SewCoincidentFreeBorders (self, freeBorders, createPolygons=False, createPolyhedra=False):
6158 Sew FreeBorder's of each group
6161 freeBorders: either a SMESH.CoincidentFreeBorders structure or a list of lists
6162 where each enclosed list contains node IDs of a group of coincident free
6163 borders such that each consequent triple of IDs within a group describes
6164 a free border in a usual way: n1, n2, nLast - i.e. 1st node, 2nd node and
6165 last node of a border.
6166 For example [[1, 2, 10, 20, 21, 40], [11, 12, 15, 55, 54, 41]] describes two
6167 groups of coincident free borders, each group including two borders.
6168 createPolygons: if :code:`True` faces adjacent to free borders are converted to
6169 polygons if a node of opposite border falls on a face edge, else such
6170 faces are split into several ones.
6171 createPolyhedra: if :code:`True` volumes adjacent to free borders are converted to
6172 polyhedra if a node of opposite border falls on a volume edge, else such
6173 volumes, if any, remain intact and the mesh becomes non-conformal.
6176 a number of successfully sewed groups
6179 if freeBorders and isinstance( freeBorders, list ):
6180 # construct SMESH.CoincidentFreeBorders
6181 if isinstance( freeBorders[0], int ):
6182 freeBorders = [freeBorders]
6184 coincidentGroups = []
6185 for nodeList in freeBorders:
6186 if not nodeList or len( nodeList ) % 3:
6187 raise ValueError("Wrong number of nodes in this group: %s" % nodeList)
6190 group.append ( SMESH.FreeBorderPart( len(borders), 0, 1, 2 ))
6191 borders.append( SMESH.FreeBorder( nodeList[:3] ))
6192 nodeList = nodeList[3:]
6194 coincidentGroups.append( group )
6196 freeBorders = SMESH.CoincidentFreeBorders( borders, coincidentGroups )
6198 return self.editor.SewCoincidentFreeBorders( freeBorders, createPolygons, createPolyhedra )
6200 def SewFreeBorders (self, FirstNodeID1, SecondNodeID1, LastNodeID1,
6201 FirstNodeID2, SecondNodeID2, LastNodeID2,
6202 CreatePolygons, CreatePolyedrs):
6207 :class:`error code <SMESH.SMESH_MeshEditor.Sew_Error>`
6210 return self.editor.SewFreeBorders(FirstNodeID1, SecondNodeID1, LastNodeID1,
6211 FirstNodeID2, SecondNodeID2, LastNodeID2,
6212 CreatePolygons, CreatePolyedrs)
6214 def SewConformFreeBorders (self, FirstNodeID1, SecondNodeID1, LastNodeID1,
6215 FirstNodeID2, SecondNodeID2):
6217 Sew conform free borders
6220 :class:`error code <SMESH.SMESH_MeshEditor.Sew_Error>`
6223 return self.editor.SewConformFreeBorders(FirstNodeID1, SecondNodeID1, LastNodeID1,
6224 FirstNodeID2, SecondNodeID2)
6226 def SewBorderToSide (self, FirstNodeIDOnFreeBorder, SecondNodeIDOnFreeBorder, LastNodeIDOnFreeBorder,
6227 FirstNodeIDOnSide, LastNodeIDOnSide, CreatePolygons, CreatePolyedrs):
6232 :class:`error code <SMESH.SMESH_MeshEditor.Sew_Error>`
6235 return self.editor.SewBorderToSide(FirstNodeIDOnFreeBorder, SecondNodeIDOnFreeBorder, LastNodeIDOnFreeBorder,
6236 FirstNodeIDOnSide, LastNodeIDOnSide, CreatePolygons, CreatePolyedrs)
6238 def SewSideElements (self, IDsOfSide1Elements, IDsOfSide2Elements,
6239 NodeID1OfSide1ToMerge, NodeID1OfSide2ToMerge,
6240 NodeID2OfSide1ToMerge, NodeID2OfSide2ToMerge):
6242 Sew two sides of a mesh. The nodes belonging to Side1 are
6243 merged with the nodes of elements of Side2.
6244 The number of elements in theSide1 and in theSide2 must be
6245 equal and they should have similar nodal connectivity.
6246 The nodes to merge should belong to side borders and
6247 the first node should be linked to the second.
6250 :class:`error code <SMESH.SMESH_MeshEditor.Sew_Error>`
6253 return self.editor.SewSideElements(IDsOfSide1Elements, IDsOfSide2Elements,
6254 NodeID1OfSide1ToMerge, NodeID1OfSide2ToMerge,
6255 NodeID2OfSide1ToMerge, NodeID2OfSide2ToMerge)
6257 def ChangeElemNodes(self, ide, newIDs):
6259 Set new nodes for the given element.
6266 False if the number of nodes does not correspond to the type of element
6269 return self.editor.ChangeElemNodes(ide, newIDs)
6271 def GetLastCreatedNodes(self):
6273 If during the last operation of :class:`SMESH.SMESH_MeshEditor` some nodes were
6274 created, this method return the list of their IDs.
6275 If new nodes were not created - return empty list
6278 the list of integer values (can be empty)
6281 return self.editor.GetLastCreatedNodes()
6283 def GetLastCreatedElems(self):
6285 If during the last operation of :class:`SMESH.SMESH_MeshEditor` some elements were
6286 created this method return the list of their IDs.
6287 If new elements were not created - return empty list
6290 the list of integer values (can be empty)
6293 return self.editor.GetLastCreatedElems()
6295 def ClearLastCreated(self):
6297 Forget what nodes and elements were created by the last mesh edition operation
6300 self.editor.ClearLastCreated()
6302 def DoubleElements(self, theElements, theGroupName=""):
6304 Create duplicates of given elements, i.e. create new elements based on the
6305 same nodes as the given ones.
6308 theElements: container of elements to duplicate. It can be a
6309 :class:`mesh, sub-mesh, group, filter <SMESH.SMESH_IDSource>`
6310 or a list of element IDs. If *theElements* is
6311 a :class:`Mesh`, elements of highest dimension are duplicated
6312 theGroupName: a name of group to contain the generated elements.
6313 If a group with such a name already exists, the new elements
6314 are added to the existng group, else a new group is created.
6315 If *theGroupName* is empty, new elements are not added
6319 a :class:`group <SMESH.SMESH_Group>` where the new elements are added.
6320 None if *theGroupName* == "".
6323 unRegister = genObjUnRegister()
6324 if isinstance( theElements, Mesh ):
6325 theElements = theElements.mesh
6326 elif isinstance( theElements, list ):
6327 theElements = self.GetIDSource( theElements, SMESH.ALL )
6328 unRegister.set( theElements )
6329 return self.editor.DoubleElements(theElements, theGroupName)
6331 def DoubleNodes(self, theNodes, theModifiedElems):
6333 Create a hole in a mesh by doubling the nodes of some particular elements
6336 theNodes: IDs of nodes to be doubled
6337 theModifiedElems: IDs of elements to be updated by the new (doubled)
6338 nodes. If list of element identifiers is empty then nodes are doubled but
6339 they not assigned to elements
6342 True if operation has been completed successfully, False otherwise
6345 return self.editor.DoubleNodes(theNodes, theModifiedElems)
6347 def DoubleNode(self, theNodeId, theModifiedElems):
6349 Create a hole in a mesh by doubling the nodes of some particular elements.
6350 This method provided for convenience works as :meth:`DoubleNodes`.
6353 theNodeId: IDs of node to double
6354 theModifiedElems: IDs of elements to update
6357 True if operation has been completed successfully, False otherwise
6360 return self.editor.DoubleNode(theNodeId, theModifiedElems)
6362 def DoubleNodeGroup(self, theNodes, theModifiedElems, theMakeGroup=False):
6364 Create a hole in a mesh by doubling the nodes of some particular elements.
6365 This method provided for convenience works as :meth:`DoubleNodes`.
6368 theNodes: group of nodes to double.
6369 theModifiedElems: group of elements to update.
6370 theMakeGroup: forces the generation of a group containing new nodes.
6373 True or a created group if operation has been completed successfully,
6374 False or None otherwise
6378 return self.editor.DoubleNodeGroupNew(theNodes, theModifiedElems)
6379 return self.editor.DoubleNodeGroup(theNodes, theModifiedElems)
6381 def DoubleNodeGroups(self, theNodes, theModifiedElems, theMakeGroup=False):
6383 Create a hole in a mesh by doubling the nodes of some particular elements.
6384 This method provided for convenience works as :meth:`DoubleNodes`.
6387 theNodes: list of groups of nodes to double.
6388 theModifiedElems: list of groups of elements to update.
6389 theMakeGroup: forces the generation of a group containing new nodes.
6392 True if operation has been completed successfully, False otherwise
6396 return self.editor.DoubleNodeGroupsNew(theNodes, theModifiedElems)
6397 return self.editor.DoubleNodeGroups(theNodes, theModifiedElems)
6399 def DoubleNodeElem(self, theElems, theNodesNot, theAffectedElems):
6401 Create a hole in a mesh by doubling the nodes of some particular elements
6404 theElems: the list of elements (edges or faces) to replicate.
6405 The nodes for duplication could be found from these elements
6406 theNodesNot: list of nodes NOT to replicate
6407 theAffectedElems: the list of elements (cells and edges) to which the
6408 replicated nodes should be associated to
6411 True if operation has been completed successfully, False otherwise
6414 return self.editor.DoubleNodeElem(theElems, theNodesNot, theAffectedElems)
6416 def DoubleNodeElemInRegion(self, theElems, theNodesNot, theShape):
6418 Create a hole in a mesh by doubling the nodes of some particular elements
6421 theElems: the list of elements (edges or faces) to replicate.
6422 The nodes for duplication could be found from these elements
6423 theNodesNot: list of nodes NOT to replicate
6424 theShape: shape to detect affected elements (element which geometric center
6425 located on or inside shape).
6426 The replicated nodes should be associated to affected elements.
6429 True if operation has been completed successfully, False otherwise
6432 return self.editor.DoubleNodeElemInRegion(theElems, theNodesNot, theShape)
6434 def DoubleNodeElemGroup(self, theElems, theNodesNot, theAffectedElems,
6435 theMakeGroup=False, theMakeNodeGroup=False):
6437 Create a hole in a mesh by doubling the nodes of some particular elements.
6438 This method provided for convenience works as :meth:`DoubleNodes`.
6441 theElems: group of of elements (edges or faces) to replicate.
6442 theNodesNot: group of nodes NOT to replicate.
6443 theAffectedElems: group of elements to which the replicated nodes
6444 should be associated to.
6445 theMakeGroup: forces the generation of a group containing new elements.
6446 theMakeNodeGroup: forces the generation of a group containing new nodes.
6449 True or created groups (one or two) if operation has been completed successfully,
6450 False or None otherwise
6453 if theMakeGroup or theMakeNodeGroup:
6454 twoGroups = self.editor.DoubleNodeElemGroup2New(theElems, theNodesNot,
6456 theMakeGroup, theMakeNodeGroup)
6457 if theMakeGroup and theMakeNodeGroup:
6460 return twoGroups[ int(theMakeNodeGroup) ]
6461 return self.editor.DoubleNodeElemGroup(theElems, theNodesNot, theAffectedElems)
6463 def DoubleNodeElemGroupInRegion(self, theElems, theNodesNot, theShape):
6465 Create a hole in a mesh by doubling the nodes of some particular elements.
6466 This method provided for convenience works as :meth:`DoubleNodes`.
6469 theElems: group of of elements (edges or faces) to replicate
6470 theNodesNot: group of nodes not to replicate
6471 theShape: shape to detect affected elements (element which geometric center
6472 located on or inside shape).
6473 The replicated nodes should be associated to affected elements
6476 return self.editor.DoubleNodeElemGroupInRegion(theElems, theNodesNot, theShape)
6478 def DoubleNodeElemGroups(self, theElems, theNodesNot, theAffectedElems,
6479 theMakeGroup=False, theMakeNodeGroup=False):
6481 Create a hole in a mesh by doubling the nodes of some particular elements.
6482 This method provided for convenience works as :meth:`DoubleNodes`.
6485 theElems: list of groups of elements (edges or faces) to replicate
6486 theNodesNot: list of groups of nodes NOT to replicate
6487 theAffectedElems: group of elements to which the replicated nodes
6488 should be associated to
6489 theMakeGroup: forces generation of a group containing new elements.
6490 theMakeNodeGroup: forces generation of a group containing new nodes
6493 True or created groups (one or two) if operation has been completed successfully,
6494 False or None otherwise
6497 if theMakeGroup or theMakeNodeGroup:
6498 twoGroups = self.editor.DoubleNodeElemGroups2New(theElems, theNodesNot,
6500 theMakeGroup, theMakeNodeGroup)
6501 if theMakeGroup and theMakeNodeGroup:
6504 return twoGroups[ int(theMakeNodeGroup) ]
6505 return self.editor.DoubleNodeElemGroups(theElems, theNodesNot, theAffectedElems)
6507 def DoubleNodeElemGroupsInRegion(self, theElems, theNodesNot, theShape):
6509 Create a hole in a mesh by doubling the nodes of some particular elements.
6510 This method provided for convenience works as :meth:`DoubleNodes`.
6513 theElems: list of groups of elements (edges or faces) to replicate
6514 theNodesNot: list of groups of nodes NOT to replicate
6515 theShape: shape to detect affected elements (element which geometric center
6516 located on or inside shape).
6517 The replicated nodes should be associated to affected elements
6520 True if operation has been completed successfully, False otherwise
6523 return self.editor.DoubleNodeElemGroupsInRegion(theElems, theNodesNot, theShape)
6525 def AffectedElemGroupsInRegion(self, theElems, theNodesNot, theShape):
6527 Identify the elements that will be affected by node duplication (actual duplication is not performed).
6528 This method is the first step of :meth:`DoubleNodeElemGroupsInRegion`.
6531 theElems: list of groups of nodes or elements (edges or faces) to replicate
6532 theNodesNot: list of groups of nodes NOT to replicate
6533 theShape: shape to detect affected elements (element which geometric center
6534 located on or inside shape).
6535 The replicated nodes should be associated to affected elements
6538 groups of affected elements in order: volumes, faces, edges
6541 return self.editor.AffectedElemGroupsInRegion(theElems, theNodesNot, theShape)
6543 def DoubleNodesOnGroupBoundaries(self, theDomains, createJointElems, onAllBoundaries=False ):
6546 Double nodes on shared faces between groups of volumes and create flat elements on demand.
6547 The list of groups must describe a partition of the mesh volumes.
6548 The nodes of the internal faces at the boundaries of the groups are doubled.
6549 In option, the internal faces are replaced by flat elements.
6550 Triangles are transformed to prisms, and quadrangles to hexahedrons.
6553 theDomains: list of groups of volumes
6554 createJointElems: if True, create the elements
6555 onAllBoundaries: if True, the nodes and elements are also created on
6556 the boundary between *theDomains* and the rest mesh
6559 True if operation has been completed successfully, False otherwise
6562 return self.editor.DoubleNodesOnGroupBoundaries( theDomains, createJointElems, onAllBoundaries )
6564 def CreateFlatElementsOnFacesGroups(self, theGroupsOfFaces ):
6566 Double nodes on some external faces and create flat elements.
6567 Flat elements are mainly used by some types of mechanic calculations.
6569 Each group of the list must be constituted of faces.
6570 Triangles are transformed in prisms, and quadrangles in hexahedrons.
6573 theGroupsOfFaces: list of groups of faces
6576 True if operation has been completed successfully, False otherwise
6579 return self.editor.CreateFlatElementsOnFacesGroups( theGroupsOfFaces )
6581 def CreateHoleSkin(self, radius, theShape, groupName, theNodesCoords):
6583 Identify all the elements around a geom shape, get the faces delimiting the hole
6585 return self.editor.CreateHoleSkin( radius, theShape, groupName, theNodesCoords )
6587 def MakePolyLine(self, segments, groupName='', isPreview=False ):
6589 Create a polyline consisting of 1D mesh elements each lying on a 2D element of
6590 the initial mesh. Positions of new nodes are found by cutting the mesh by the
6591 plane passing through pairs of points specified by each :class:`SMESH.PolySegment` structure.
6592 If there are several paths connecting a pair of points, the shortest path is
6593 selected by the module. Position of the cutting plane is defined by the two
6594 points and an optional vector lying on the plane specified by a PolySegment.
6595 By default the vector is defined by Mesh module as following. A middle point
6596 of the two given points is computed. The middle point is projected to the mesh.
6597 The vector goes from the middle point to the projection point. In case of planar
6598 mesh, the vector is normal to the mesh.
6600 *segments* [i].vector returns the used vector which goes from the middle point to its projection.
6603 segments: list of :class:`SMESH.PolySegment` defining positions of cutting planes.
6604 groupName: optional name of a group where created mesh segments will be added.
6607 editor = self.editor
6609 editor = self.mesh.GetMeshEditPreviewer()
6610 segmentsRes = editor.MakePolyLine( segments, groupName )
6611 for i, seg in enumerate( segmentsRes ):
6612 segments[i].vector = seg.vector
6614 return editor.GetPreviewData()
6617 def GetFunctor(self, funcType ):
6619 Return a cached numerical functor by its type.
6622 funcType: functor type: an item of :class:`SMESH.FunctorType` enumeration.
6623 Note that not all items correspond to numerical functors.
6626 :class:`SMESH.NumericalFunctor`. The functor is already initialized with a mesh
6629 fn = self.functors[ funcType._v ]
6631 fn = self.smeshpyD.GetFunctor(funcType)
6632 fn.SetMesh(self.mesh)
6633 self.functors[ funcType._v ] = fn
6636 def FunctorValue(self, funcType, elemId, isElem=True):
6638 Return value of a functor for a given element
6641 funcType: an item of :class:`SMESH.FunctorType` enum.
6642 elemId: element or node ID
6643 isElem: *elemId* is ID of element or node
6646 the functor value or zero in case of invalid arguments
6649 fn = self.GetFunctor( funcType )
6650 if fn.GetElementType() == self.GetElementType(elemId, isElem):
6651 val = fn.GetValue(elemId)
6656 def GetLength(self, elemId=None):
6658 Get length of 1D element or sum of lengths of all 1D mesh elements
6661 elemId: mesh element ID (if not defined - sum of length of all 1D elements will be calculated)
6664 element's length value if *elemId* is specified or sum of all 1D mesh elements' lengths otherwise
6669 length = self.smeshpyD.GetLength(self)
6671 length = self.FunctorValue(SMESH.FT_Length, elemId)
6674 def GetArea(self, elemId=None):
6676 Get area of 2D element or sum of areas of all 2D mesh elements
6677 elemId mesh element ID (if not defined - sum of areas of all 2D elements will be calculated)
6680 element's area value if *elemId* is specified or sum of all 2D mesh elements' areas otherwise
6685 area = self.smeshpyD.GetArea(self)
6687 area = self.FunctorValue(SMESH.FT_Area, elemId)
6690 def GetVolume(self, elemId=None):
6692 Get volume of 3D element or sum of volumes of all 3D mesh elements
6695 elemId: mesh element ID (if not defined - sum of volumes of all 3D elements will be calculated)
6698 element's volume value if *elemId* is specified or sum of all 3D mesh elements' volumes otherwise
6703 volume = self.smeshpyD.GetVolume(self)
6705 volume = self.FunctorValue(SMESH.FT_Volume3D, elemId)
6708 def GetMaxElementLength(self, elemId):
6710 Get maximum element length.
6713 elemId: mesh element ID
6716 element's maximum length value
6719 if self.GetElementType(elemId, True) == SMESH.VOLUME:
6720 ftype = SMESH.FT_MaxElementLength3D
6722 ftype = SMESH.FT_MaxElementLength2D
6723 return self.FunctorValue(ftype, elemId)
6725 def GetAspectRatio(self, elemId):
6727 Get aspect ratio of 2D or 3D element.
6730 elemId: mesh element ID
6733 element's aspect ratio value
6736 if self.GetElementType(elemId, True) == SMESH.VOLUME:
6737 ftype = SMESH.FT_AspectRatio3D
6739 ftype = SMESH.FT_AspectRatio
6740 return self.FunctorValue(ftype, elemId)
6742 def GetWarping(self, elemId):
6744 Get warping angle of 2D element.
6747 elemId: mesh element ID
6750 element's warping angle value
6753 return self.FunctorValue(SMESH.FT_Warping, elemId)
6755 def GetMinimumAngle(self, elemId):
6757 Get minimum angle of 2D element.
6760 elemId: mesh element ID
6763 element's minimum angle value
6766 return self.FunctorValue(SMESH.FT_MinimumAngle, elemId)
6768 def GetTaper(self, elemId):
6770 Get taper of 2D element.
6773 elemId: mesh element ID
6776 element's taper value
6779 return self.FunctorValue(SMESH.FT_Taper, elemId)
6781 def GetSkew(self, elemId):
6783 Get skew of 2D element.
6786 elemId: mesh element ID
6789 element's skew value
6792 return self.FunctorValue(SMESH.FT_Skew, elemId)
6794 def GetMinMax(self, funType, meshPart=None):
6796 Return minimal and maximal value of a given functor.
6799 funType (SMESH.FunctorType): a functor type.
6800 Note that not all items of :class:`SMESH.FunctorType` corresponds
6801 to numerical functors.
6802 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to treat
6808 unRegister = genObjUnRegister()
6809 if isinstance( meshPart, list ):
6810 meshPart = self.GetIDSource( meshPart, SMESH.ALL )
6811 unRegister.set( meshPart )
6812 if isinstance( meshPart, Mesh ):
6813 meshPart = meshPart.mesh
6814 fun = self.GetFunctor( funType )
6817 if hasattr( meshPart, "SetMesh" ):
6818 meshPart.SetMesh( self.mesh ) # set mesh to filter
6819 hist = fun.GetLocalHistogram( 1, False, meshPart )
6821 hist = fun.GetHistogram( 1, False )
6823 return hist[0].min, hist[0].max
6826 pass # end of Mesh class
6829 class meshProxy(SMESH._objref_SMESH_Mesh):
6831 Private class used to compensate change of CORBA API of SMESH_Mesh for backward compatibility
6832 with old dump scripts which call SMESH_Mesh directly and not via smeshBuilder.Mesh
6834 def __init__(self,*args):
6835 SMESH._objref_SMESH_Mesh.__init__(self,*args)
6836 def __deepcopy__(self, memo=None):
6837 new = self.__class__(self)
6839 def CreateDimGroup(self,*args): # 2 args added: nbCommonNodes, underlyingOnly
6840 if len( args ) == 3:
6841 args += SMESH.ALL_NODES, True
6842 return SMESH._objref_SMESH_Mesh.CreateDimGroup(self, *args)
6843 def ExportToMEDX(self, *args): # function removed
6844 print("WARNING: ExportToMEDX() is deprecated, use ExportMED() instead")
6845 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]]
6846 SMESH._objref_SMESH_Mesh.ExportMED(self, *args)
6847 def ExportToMED(self, *args): # function removed
6848 print("WARNING: ExportToMED() is deprecated, use ExportMED() instead")
6849 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]]
6850 while len(args) < 4: # !!!! nb of parameters for ExportToMED IDL's method
6852 SMESH._objref_SMESH_Mesh.ExportMED(self, *args)
6853 def ExportPartToMED(self, *args): # 'version' parameter removed
6854 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]]
6855 SMESH._objref_SMESH_Mesh.ExportPartToMED(self, *args)
6856 def ExportMED(self, *args): # signature of method changed
6857 args = [i for i in args if i not in [SMESH.MED_V2_1, SMESH.MED_V2_2]]
6858 while len(args) < 4: # !!!! nb of parameters for ExportToMED IDL's method
6860 SMESH._objref_SMESH_Mesh.ExportMED(self, *args)
6862 omniORB.registerObjref(SMESH._objref_SMESH_Mesh._NP_RepositoryId, meshProxy)
6865 class submeshProxy(SMESH._objref_SMESH_subMesh):
6868 Private class wrapping SMESH.SMESH_SubMesh in order to add Compute()
6870 def __init__(self,*args):
6871 SMESH._objref_SMESH_subMesh.__init__(self,*args)
6873 def __deepcopy__(self, memo=None):
6874 new = self.__class__(self)
6877 def Compute(self,refresh=False):
6879 Compute the sub-mesh and return the status of the computation
6882 refresh: if *True*, Object Browser is automatically updated (when running in GUI)
6887 This is a method of SMESH.SMESH_submesh that can be obtained via Mesh.GetSubMesh() or
6888 :meth:`smeshBuilder.Mesh.GetSubMesh`.
6892 self.mesh = Mesh( smeshBuilder(), None, self.GetMesh())
6894 ok = self.mesh.Compute( self.GetSubShape(),refresh=[] )
6896 if salome.sg.hasDesktop():
6897 smeshgui = salome.ImportComponentGUI("SMESH")
6899 smeshgui.SetMeshIcon( salome.ObjectToID( self ), ok, (self.GetNumberOfElements()==0) )
6900 if refresh: salome.sg.updateObjBrowser()
6905 omniORB.registerObjref(SMESH._objref_SMESH_subMesh._NP_RepositoryId, submeshProxy)
6908 class meshEditor(SMESH._objref_SMESH_MeshEditor):
6910 Private class used to compensate change of CORBA API of SMESH_MeshEditor for backward
6911 compatibility with old dump scripts which call SMESH_MeshEditor directly and not via
6914 def __init__(self,*args):
6915 SMESH._objref_SMESH_MeshEditor.__init__( self, *args)
6917 def __getattr__(self, name ): # method called if an attribute not found
6918 if not self.mesh: # look for name() method in Mesh class
6919 self.mesh = Mesh( None, None, SMESH._objref_SMESH_MeshEditor.GetMesh(self))
6920 if hasattr( self.mesh, name ):
6921 return getattr( self.mesh, name )
6922 if name == "ExtrusionAlongPathObjX":
6923 return getattr( self.mesh, "ExtrusionAlongPathX" ) # other method name
6924 print("meshEditor: attribute '%s' NOT FOUND" % name)
6926 def __deepcopy__(self, memo=None):
6927 new = self.__class__(self)
6929 def FindCoincidentNodes(self,*args): # a 2nd arg added (SeparateCornerAndMediumNodes)
6930 if len( args ) == 1: args += False,
6931 return SMESH._objref_SMESH_MeshEditor.FindCoincidentNodes( self, *args )
6932 def FindCoincidentNodesOnPart(self,*args): # a 3d arg added (SeparateCornerAndMediumNodes)
6933 if len( args ) == 2: args += False,
6934 return SMESH._objref_SMESH_MeshEditor.FindCoincidentNodesOnPart( self, *args )
6935 def MergeNodes(self,*args): # 2 args added (NodesToKeep,AvoidMakingHoles)
6936 if len( args ) == 1:
6937 return SMESH._objref_SMESH_MeshEditor.MergeNodes( self, args[0], [], False )
6938 NodesToKeep = args[1]
6939 AvoidMakingHoles = args[2] if len( args ) == 3 else False
6940 unRegister = genObjUnRegister()
6942 if isinstance( NodesToKeep, list ) and isinstance( NodesToKeep[0], int ):
6943 NodesToKeep = self.MakeIDSource( NodesToKeep, SMESH.NODE )
6944 if not isinstance( NodesToKeep, list ):
6945 NodesToKeep = [ NodesToKeep ]
6946 return SMESH._objref_SMESH_MeshEditor.MergeNodes( self, args[0], NodesToKeep, AvoidMakingHoles )
6948 omniORB.registerObjref(SMESH._objref_SMESH_MeshEditor._NP_RepositoryId, meshEditor)
6950 class Pattern(SMESH._objref_SMESH_Pattern):
6952 Private class wrapping SMESH.SMESH_Pattern CORBA class in order to treat Notebook
6953 variables in some methods
6956 def LoadFromFile(self, patternTextOrFile ):
6957 text = patternTextOrFile
6958 if os.path.exists( text ):
6959 text = open( patternTextOrFile ).read()
6961 return SMESH._objref_SMESH_Pattern.LoadFromFile( self, text )
6963 def ApplyToMeshFaces(self, theMesh, theFacesIDs, theNodeIndexOnKeyPoint1, theReverse):
6964 decrFun = lambda i: i-1
6965 theNodeIndexOnKeyPoint1,Parameters,hasVars = ParseParameters(theNodeIndexOnKeyPoint1, decrFun)
6966 theMesh.SetParameters(Parameters)
6967 return SMESH._objref_SMESH_Pattern.ApplyToMeshFaces( self, theMesh, theFacesIDs, theNodeIndexOnKeyPoint1, theReverse )
6969 def ApplyToHexahedrons(self, theMesh, theVolumesIDs, theNode000Index, theNode001Index):
6970 decrFun = lambda i: i-1
6971 theNode000Index,theNode001Index,Parameters,hasVars = ParseParameters(theNode000Index,theNode001Index, decrFun)
6972 theMesh.SetParameters(Parameters)
6973 return SMESH._objref_SMESH_Pattern.ApplyToHexahedrons( self, theMesh, theVolumesIDs, theNode000Index, theNode001Index )
6975 def MakeMesh(self, mesh, CreatePolygons=False, CreatePolyhedra=False):
6976 if isinstance( mesh, Mesh ):
6977 mesh = mesh.GetMesh()
6978 return SMESH._objref_SMESH_Pattern.MakeMesh( self, mesh, CreatePolygons, CreatePolyhedra )
6980 omniORB.registerObjref(SMESH._objref_SMESH_Pattern._NP_RepositoryId, Pattern)
6982 Registering the new proxy for Pattern
6987 Private class used to bind methods creating algorithms to the class Mesh
6990 def __init__(self, method):
6992 self.defaultAlgoType = ""
6993 self.algoTypeToClass = {}
6994 self.method = method
6996 def add(self, algoClass):
6998 Store a python class of algorithm
7000 if inspect.isclass(algoClass) and \
7001 hasattr( algoClass, "algoType"):
7002 self.algoTypeToClass[ algoClass.algoType ] = algoClass
7003 if not self.defaultAlgoType and \
7004 hasattr( algoClass, "isDefault") and algoClass.isDefault:
7005 self.defaultAlgoType = algoClass.algoType
7006 #print("Add",algoClass.algoType, "dflt",self.defaultAlgoType)
7008 def copy(self, mesh):
7010 Create a copy of self and assign mesh to the copy
7013 other = algoCreator( self.method )
7014 other.defaultAlgoType = self.defaultAlgoType
7015 other.algoTypeToClass = self.algoTypeToClass
7019 def __call__(self,algo="",geom=0,*args):
7021 Create an instance of algorithm
7025 if isinstance( algo, str ):
7027 elif ( isinstance( algo, geomBuilder.GEOM._objref_GEOM_Object ) and \
7028 not isinstance( geom, geomBuilder.GEOM._objref_GEOM_Object )):
7033 if isinstance( geom, geomBuilder.GEOM._objref_GEOM_Object ):
7035 elif not algoType and isinstance( geom, str ):
7040 if isinstance( arg, geomBuilder.GEOM._objref_GEOM_Object ) and not shape:
7042 elif isinstance( arg, str ) and not algoType:
7045 import traceback, sys
7046 msg = "Warning. Unexpected argument in mesh.%s() ---> %s" % ( self.method, arg )
7047 sys.stderr.write( msg + '\n' )
7048 tb = traceback.extract_stack(None,2)
7049 traceback.print_list( [tb[0]] )
7051 algoType = self.defaultAlgoType
7052 if not algoType and self.algoTypeToClass:
7053 algoType = sorted( self.algoTypeToClass.keys() )[0]
7054 if algoType in self.algoTypeToClass:
7055 #print("Create algo",algoType)
7057 return self.algoTypeToClass[ algoType ]( self.mesh, shape )
7058 raise RuntimeError( "No class found for algo type %s" % algoType)
7061 class hypMethodWrapper:
7063 Private class used to substitute and store variable parameters of hypotheses.
7066 def __init__(self, hyp, method):
7068 self.method = method
7069 #print("REBIND:", method.__name__)
7072 def __call__(self,*args):
7074 call a method of hypothesis with calling SetVarParameter() before
7078 return self.method( self.hyp, *args ) # hypothesis method with no args
7080 #print("MethWrapper.__call__", self.method.__name__, args)
7082 parsed = ParseParameters(*args) # replace variables with their values
7083 self.hyp.SetVarParameter( parsed[-2], self.method.__name__ )
7084 result = self.method( self.hyp, *parsed[:-2] ) # call hypothesis method
7085 except omniORB.CORBA.BAD_PARAM: # raised by hypothesis method call
7086 # maybe there is a replaced string arg which is not variable
7087 result = self.method( self.hyp, *args )
7088 except ValueError as detail: # raised by ParseParameters()
7090 result = self.method( self.hyp, *args )
7091 except omniORB.CORBA.BAD_PARAM:
7092 raise ValueError(detail) # wrong variable name
7097 class genObjUnRegister:
7099 A helper class that calls UnRegister() of SALOME.GenericObj'es stored in it
7102 def __init__(self, genObj=None):
7103 self.genObjList = []
7107 def set(self, genObj):
7108 "Store one or a list of of SALOME.GenericObj'es"
7109 if isinstance( genObj, list ):
7110 self.genObjList.extend( genObj )
7112 self.genObjList.append( genObj )
7116 for genObj in self.genObjList:
7117 if genObj and hasattr( genObj, "UnRegister" ):
7120 for pluginName in os.environ[ "SMESH_MeshersList" ].split( ":" ):
7122 Bind methods creating mesher plug-ins to the Mesh class
7125 # print("pluginName: ", pluginName)
7126 pluginBuilderName = pluginName + "Builder"
7128 exec( "from salome.%s.%s import *" % (pluginName, pluginBuilderName))
7129 except Exception as e:
7130 from salome_utils import verbose
7131 if verbose(): print("Exception while loading %s: %s" % ( pluginBuilderName, e ))
7133 exec( "from salome.%s import %s" % (pluginName, pluginBuilderName))
7134 plugin = eval( pluginBuilderName )
7135 # print(" plugin:" , str(plugin))
7137 # add methods creating algorithms to Mesh
7138 for k in dir( plugin ):
7139 if k[0] == '_': continue
7140 algo = getattr( plugin, k )
7141 #print(" algo:", str(algo))
7142 if inspect.isclass(algo) and hasattr(algo, "meshMethod"):
7143 #print(" meshMethod:" , str(algo.meshMethod))
7144 if not hasattr( Mesh, algo.meshMethod ):
7145 setattr( Mesh, algo.meshMethod, algoCreator( algo.meshMethod ))
7147 _mmethod = getattr( Mesh, algo.meshMethod )
7148 if hasattr( _mmethod, "add" ):