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
623 geompyD = geomBuilder.New()
626 self.SetGeomEngine(geompyD)
627 SMESH._objref_SMESH_Gen.UpdateStudy(self)
628 sb = salome.myStudy.NewBuilder()
629 sc = salome.myStudy.FindComponent("SMESH")
631 sb.LoadWith(sc, self)
634 def SetEnablePublish( self, theIsEnablePublish ):
636 Set enable publishing in the study. Calling SetEnablePublish( False ) allows to
637 switch **off** publishing in the Study of mesh objects.
639 #self.SetEnablePublish(theIsEnablePublish)
640 SMESH._objref_SMESH_Gen.SetEnablePublish(self,theIsEnablePublish)
642 notebook = salome_notebook.NoteBook( theIsEnablePublish )
645 def CreateMeshesFromUNV( self,theFileName ):
647 Create a Mesh object importing data from the given UNV file
650 an instance of class :class:`Mesh`
653 aSmeshMesh = SMESH._objref_SMESH_Gen.CreateMeshesFromUNV(self,theFileName)
654 aMesh = Mesh(self, self.geompyD, aSmeshMesh)
657 def CreateMeshesFromMED( self,theFileName ):
659 Create a Mesh object(s) importing data from the given MED file
662 a tuple ( list of class :class:`Mesh` instances,
663 :class:`SMESH.DriverMED_ReadStatus` )
666 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromMED(self,theFileName)
667 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
668 return aMeshes, aStatus
670 def CreateMeshesFromSAUV( self,theFileName ):
672 Create a Mesh object(s) importing data from the given SAUV file
675 a tuple ( list of class :class:`Mesh` instances, :class:`SMESH.DriverMED_ReadStatus` )
678 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromSAUV(self,theFileName)
679 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
680 return aMeshes, aStatus
682 def CreateMeshesFromSTL( self, theFileName ):
684 Create a Mesh object importing data from the given STL file
687 an instance of class :class:`Mesh`
690 aSmeshMesh = SMESH._objref_SMESH_Gen.CreateMeshesFromSTL(self,theFileName)
691 aMesh = Mesh(self, self.geompyD, aSmeshMesh)
694 def CreateMeshesFromCGNS( self, theFileName ):
696 Create Mesh objects importing data from the given CGNS file
699 a tuple ( list of class :class:`Mesh` instances, :class:`SMESH.DriverMED_ReadStatus` )
702 aSmeshMeshes, aStatus = SMESH._objref_SMESH_Gen.CreateMeshesFromCGNS(self,theFileName)
703 aMeshes = [ Mesh(self, self.geompyD, m) for m in aSmeshMeshes ]
704 return aMeshes, aStatus
706 def CreateMeshesFromGMF( self, theFileName ):
708 Create a Mesh object importing data from the given GMF file.
709 GMF files must have .mesh extension for the ASCII format and .meshb for
713 ( an instance of class :class:`Mesh`, :class:`SMESH.ComputeError` )
716 aSmeshMesh, error = SMESH._objref_SMESH_Gen.CreateMeshesFromGMF(self,
719 if error.comment: print("*** CreateMeshesFromGMF() errors:\n", error.comment)
720 return Mesh(self, self.geompyD, aSmeshMesh), error
722 def Concatenate( self, meshes, uniteIdenticalGroups,
723 mergeNodesAndElements = False, mergeTolerance = 1e-5, allGroups = False,
726 Concatenate the given meshes into one mesh. All groups of input meshes will be
727 present in the new mesh.
730 meshes: :class:`meshes, sub-meshes, groups or filters <SMESH.SMESH_IDSource>` to combine into one mesh
731 uniteIdenticalGroups: if True, groups with same names are united, else they are renamed
732 mergeNodesAndElements: if True, equal nodes and elements are merged
733 mergeTolerance: tolerance for merging nodes
734 allGroups: forces creation of groups corresponding to every input mesh
735 name: name of a new mesh
738 an instance of class :class:`Mesh`
741 if not meshes: return None
742 for i,m in enumerate(meshes):
743 if isinstance(m, Mesh):
744 meshes[i] = m.GetMesh()
745 mergeTolerance,Parameters,hasVars = ParseParameters(mergeTolerance)
746 meshes[0].SetParameters(Parameters)
748 aSmeshMesh = SMESH._objref_SMESH_Gen.ConcatenateWithGroups(
749 self,meshes,uniteIdenticalGroups,mergeNodesAndElements,mergeTolerance)
751 aSmeshMesh = SMESH._objref_SMESH_Gen.Concatenate(
752 self,meshes,uniteIdenticalGroups,mergeNodesAndElements,mergeTolerance)
753 aMesh = Mesh(self, self.geompyD, aSmeshMesh, name=name)
756 def CopyMesh( self, meshPart, meshName, toCopyGroups=False, toKeepIDs=False):
758 Create a mesh by copying a part of another mesh.
761 meshPart: a part of mesh to copy, either
762 :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`.
763 To copy nodes or elements not forming any mesh object,
764 pass result of :meth:`Mesh.GetIDSource` as *meshPart*
765 meshName: a name of the new mesh
766 toCopyGroups: to create in the new mesh groups the copied elements belongs to
767 toKeepIDs: to preserve order of the copied elements or not
770 an instance of class :class:`Mesh`
773 if (isinstance( meshPart, Mesh )):
774 meshPart = meshPart.GetMesh()
775 mesh = SMESH._objref_SMESH_Gen.CopyMesh( self,meshPart,meshName,toCopyGroups,toKeepIDs )
776 return Mesh(self, self.geompyD, mesh)
778 def GetSubShapesId( self, theMainObject, theListOfSubObjects ):
780 Return IDs of sub-shapes
783 theMainObject (GEOM.GEOM_Object): a shape
784 theListOfSubObjects: sub-shapes (list of GEOM.GEOM_Object)
786 the list of integer values
789 return SMESH._objref_SMESH_Gen.GetSubShapesId(self,theMainObject, theListOfSubObjects)
791 def GetPattern(self):
793 Create a pattern mapper.
796 an instance of :class:`SMESH.SMESH_Pattern`
798 :ref:`Example of Patterns usage <tui_pattern_mapping>`
801 return SMESH._objref_SMESH_Gen.GetPattern(self)
803 def SetBoundaryBoxSegmentation(self, nbSegments):
805 Set number of segments per diagonal of boundary box of geometry, by which
806 default segment length of appropriate 1D hypotheses is defined in GUI.
810 SMESH._objref_SMESH_Gen.SetBoundaryBoxSegmentation(self,nbSegments)
812 # Filtering. Auxiliary functions:
813 # ------------------------------
815 def GetEmptyCriterion(self):
817 Create an empty criterion
820 :class:`SMESH.Filter.Criterion`
823 Type = self.EnumToLong(FT_Undefined)
824 Compare = self.EnumToLong(FT_Undefined)
828 UnaryOp = self.EnumToLong(FT_Undefined)
829 BinaryOp = self.EnumToLong(FT_Undefined)
832 Precision = -1 ##@1e-07
833 return Filter.Criterion(Type, Compare, Threshold, ThresholdStr, ThresholdID,
834 UnaryOp, BinaryOp, Tolerance, TypeOfElement, Precision)
836 def GetCriterion(self,elementType,
838 Compare = FT_EqualTo,
840 UnaryOp=FT_Undefined,
841 BinaryOp=FT_Undefined,
844 Create a criterion by the given parameters
845 Criterion structures allow to define complex filters by combining them with logical operations (AND / OR) (see example below)
848 elementType: the :class:`type of elements <SMESH.ElementType>` (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
849 CritType: the type of criterion :class:`SMESH.FunctorType` (SMESH.FT_Taper, SMESH.FT_Area, etc.).
850 Note that the items starting from FT_LessThan are not suitable for *CritType*.
851 Compare: belongs to {SMESH.FT_LessThan, SMESH.FT_MoreThan, SMESH.FT_EqualTo}
852 Threshold: the threshold value (range of ids as string, shape, numeric)
853 UnaryOp: SMESH.FT_LogicalNOT or SMESH.FT_Undefined
854 BinaryOp: a binary logical operation SMESH.FT_LogicalAND, SMESH.FT_LogicalOR or
856 Tolerance: the tolerance used by SMESH.FT_BelongToGeom, SMESH.FT_BelongToSurface,
857 SMESH.FT_LyingOnGeom, SMESH.FT_CoplanarFaces criteria
860 :class:`SMESH.Filter.Criterion`
862 Example: :ref:`combining_filters`
865 if not CritType in SMESH.FunctorType._items:
866 raise TypeError("CritType should be of SMESH.FunctorType")
867 aCriterion = self.GetEmptyCriterion()
868 aCriterion.TypeOfElement = elementType
869 aCriterion.Type = self.EnumToLong(CritType)
870 aCriterion.Tolerance = Tolerance
872 aThreshold = Threshold
874 if Compare in [FT_LessThan, FT_MoreThan, FT_EqualTo]:
875 aCriterion.Compare = self.EnumToLong(Compare)
876 elif Compare == "=" or Compare == "==":
877 aCriterion.Compare = self.EnumToLong(FT_EqualTo)
879 aCriterion.Compare = self.EnumToLong(FT_LessThan)
881 aCriterion.Compare = self.EnumToLong(FT_MoreThan)
882 elif Compare != FT_Undefined:
883 aCriterion.Compare = self.EnumToLong(FT_EqualTo)
886 if CritType in [FT_BelongToGeom, FT_BelongToPlane, FT_BelongToGenSurface,
887 FT_BelongToCylinder, FT_LyingOnGeom]:
888 # Check that Threshold is GEOM object
889 if isinstance(aThreshold, geomBuilder.GEOM._objref_GEOM_Object):
890 aCriterion.ThresholdStr = GetName(aThreshold)
891 aCriterion.ThresholdID = aThreshold.GetStudyEntry()
892 if not aCriterion.ThresholdID:
893 name = aCriterion.ThresholdStr
895 name = "%s_%s"%(aThreshold.GetShapeType(), id(aThreshold)%10000)
896 aCriterion.ThresholdID = self.geompyD.addToStudy( aThreshold, name )
897 # or a name of GEOM object
898 elif isinstance( aThreshold, str ):
899 aCriterion.ThresholdStr = aThreshold
901 raise TypeError("The Threshold should be a shape.")
902 if isinstance(UnaryOp,float):
903 aCriterion.Tolerance = UnaryOp
904 UnaryOp = FT_Undefined
906 elif CritType == FT_BelongToMeshGroup:
907 # Check that Threshold is a group
908 if isinstance(aThreshold, SMESH._objref_SMESH_GroupBase):
909 if aThreshold.GetType() != elementType:
910 raise ValueError("Group type mismatches Element type")
911 aCriterion.ThresholdStr = aThreshold.GetName()
912 aCriterion.ThresholdID = salome.orb.object_to_string( aThreshold )
913 study = salome.myStudy
915 so = study.FindObjectIOR( aCriterion.ThresholdID )
919 aCriterion.ThresholdID = entry
921 raise TypeError("The Threshold should be a Mesh Group")
922 elif CritType == FT_RangeOfIds:
923 # Check that Threshold is string
924 if isinstance(aThreshold, str):
925 aCriterion.ThresholdStr = aThreshold
927 raise TypeError("The Threshold should be a string.")
928 elif CritType == FT_CoplanarFaces:
929 # Check the Threshold
930 if isinstance(aThreshold, int):
931 aCriterion.ThresholdID = str(aThreshold)
932 elif isinstance(aThreshold, str):
935 raise ValueError("Invalid ID of mesh face: '%s'"%aThreshold)
936 aCriterion.ThresholdID = aThreshold
938 raise TypeError("The Threshold should be an ID of mesh face and not '%s'"%aThreshold)
939 elif CritType == FT_ConnectedElements:
940 # Check the Threshold
941 if isinstance(aThreshold, geomBuilder.GEOM._objref_GEOM_Object): # shape
942 aCriterion.ThresholdID = aThreshold.GetStudyEntry()
943 if not aCriterion.ThresholdID:
944 name = aThreshold.GetName()
946 name = "%s_%s"%(aThreshold.GetShapeType(), id(aThreshold)%10000)
947 aCriterion.ThresholdID = self.geompyD.addToStudy( aThreshold, name )
948 elif isinstance(aThreshold, int): # node id
949 aCriterion.Threshold = aThreshold
950 elif isinstance(aThreshold, list): # 3 point coordinates
951 if len( aThreshold ) < 3:
952 raise ValueError("too few point coordinates, must be 3")
953 aCriterion.ThresholdStr = " ".join( [str(c) for c in aThreshold[:3]] )
954 elif isinstance(aThreshold, str):
955 if aThreshold.isdigit():
956 aCriterion.Threshold = aThreshold # node id
958 aCriterion.ThresholdStr = aThreshold # hope that it's point coordinates
960 raise TypeError("The Threshold should either a VERTEX, or a node ID, "\
961 "or a list of point coordinates and not '%s'"%aThreshold)
962 elif CritType == FT_ElemGeomType:
963 # Check the Threshold
965 aCriterion.Threshold = self.EnumToLong(aThreshold)
966 assert( aThreshold in SMESH.GeometryType._items )
968 if isinstance(aThreshold, int):
969 aCriterion.Threshold = aThreshold
971 raise TypeError("The Threshold should be an integer or SMESH.GeometryType.")
974 elif CritType == FT_EntityType:
975 # Check the Threshold
977 aCriterion.Threshold = self.EnumToLong(aThreshold)
978 assert( aThreshold in SMESH.EntityType._items )
980 if isinstance(aThreshold, int):
981 aCriterion.Threshold = aThreshold
983 raise TypeError("The Threshold should be an integer or SMESH.EntityType.")
987 elif CritType == FT_GroupColor:
988 # Check the Threshold
990 aCriterion.ThresholdStr = self.ColorToString(aThreshold)
992 raise TypeError("The threshold value should be of SALOMEDS.Color type")
994 elif CritType in [FT_FreeBorders, FT_FreeEdges, FT_FreeNodes, FT_FreeFaces,
995 FT_LinearOrQuadratic, FT_BadOrientedVolume,
996 FT_BareBorderFace, FT_BareBorderVolume,
997 FT_OverConstrainedFace, FT_OverConstrainedVolume,
998 FT_EqualNodes,FT_EqualEdges,FT_EqualFaces,FT_EqualVolumes ]:
999 # At this point the Threshold is unnecessary
1000 if aThreshold == FT_LogicalNOT:
1001 aCriterion.UnaryOp = self.EnumToLong(FT_LogicalNOT)
1002 elif aThreshold in [FT_LogicalAND, FT_LogicalOR]:
1003 aCriterion.BinaryOp = aThreshold
1007 aThreshold = float(aThreshold)
1008 aCriterion.Threshold = aThreshold
1010 raise TypeError("The Threshold should be a number.")
1013 if Threshold == FT_LogicalNOT or UnaryOp == FT_LogicalNOT:
1014 aCriterion.UnaryOp = self.EnumToLong(FT_LogicalNOT)
1016 if Threshold in [FT_LogicalAND, FT_LogicalOR]:
1017 aCriterion.BinaryOp = self.EnumToLong(Threshold)
1019 if UnaryOp in [FT_LogicalAND, FT_LogicalOR]:
1020 aCriterion.BinaryOp = self.EnumToLong(UnaryOp)
1022 if BinaryOp in [FT_LogicalAND, FT_LogicalOR]:
1023 aCriterion.BinaryOp = self.EnumToLong(BinaryOp)
1027 def GetFilter(self,elementType,
1028 CritType=FT_Undefined,
1031 UnaryOp=FT_Undefined,
1035 Create a filter with the given parameters
1038 elementType: the :class:`type of elements <SMESH.ElementType>` (SMESH.NODE, SMESH.EDGE, SMESH.FACE, SMESH.VOLUME)
1039 CritType: the :class:`type of criterion <SMESH.FunctorType>` (SMESH.FT_Taper, SMESH.FT_Area, etc.).
1040 Note that the items starting from FT_LessThan are not suitable for CritType.
1041 Compare: belongs to {SMESH.FT_LessThan, SMESH.FT_MoreThan, SMESH.FT_EqualTo}
1042 Threshold: the threshold value (range of ids as string, shape, numeric)
1043 UnaryOp: SMESH.FT_LogicalNOT or SMESH.FT_Undefined
1044 Tolerance: the tolerance used by SMESH.FT_BelongToGeom, SMESH.FT_BelongToSurface,
1045 SMESH.FT_LyingOnGeom, SMESH.FT_CoplanarFaces and SMESH.FT_EqualNodes criteria
1046 mesh: the mesh to initialize the filter with
1049 :class:`SMESH.Filter`
1052 See :doc:`Filters usage examples <tui_filters>`
1055 aCriterion = self.GetCriterion(elementType, CritType, Compare, Threshold, UnaryOp, FT_Undefined,Tolerance)
1056 aFilterMgr = self.CreateFilterManager()
1057 aFilter = aFilterMgr.CreateFilter()
1059 aCriteria.append(aCriterion)
1060 aFilter.SetCriteria(aCriteria)
1062 if isinstance( mesh, Mesh ): aFilter.SetMesh( mesh.GetMesh() )
1063 else : aFilter.SetMesh( mesh )
1064 aFilterMgr.UnRegister()
1067 def GetFilterFromCriteria(self,criteria, binOp=SMESH.FT_LogicalAND):
1069 Create a filter from criteria
1072 criteria: a list of :class:`SMESH.Filter.Criterion`
1073 binOp: binary operator used when binary operator of criteria is undefined
1076 :class:`SMESH.Filter`
1079 See :doc:`Filters usage examples <tui_filters>`
1082 for i in range( len( criteria ) - 1 ):
1083 if criteria[i].BinaryOp == self.EnumToLong( SMESH.FT_Undefined ):
1084 criteria[i].BinaryOp = self.EnumToLong( binOp )
1085 aFilterMgr = self.CreateFilterManager()
1086 aFilter = aFilterMgr.CreateFilter()
1087 aFilter.SetCriteria(criteria)
1088 aFilterMgr.UnRegister()
1091 def GetFunctor(self,theCriterion):
1093 Create a numerical functor by its type
1096 theCriterion (SMESH.FunctorType): functor type.
1097 Note that not all items correspond to numerical functors.
1100 :class:`SMESH.NumericalFunctor`
1103 if isinstance( theCriterion, SMESH._objref_NumericalFunctor ):
1105 aFilterMgr = self.CreateFilterManager()
1107 if theCriterion == FT_AspectRatio:
1108 functor = aFilterMgr.CreateAspectRatio()
1109 elif theCriterion == FT_AspectRatio3D:
1110 functor = aFilterMgr.CreateAspectRatio3D()
1111 elif theCriterion == FT_Warping:
1112 functor = aFilterMgr.CreateWarping()
1113 elif theCriterion == FT_MinimumAngle:
1114 functor = aFilterMgr.CreateMinimumAngle()
1115 elif theCriterion == FT_Taper:
1116 functor = aFilterMgr.CreateTaper()
1117 elif theCriterion == FT_Skew:
1118 functor = aFilterMgr.CreateSkew()
1119 elif theCriterion == FT_Area:
1120 functor = aFilterMgr.CreateArea()
1121 elif theCriterion == FT_Volume3D:
1122 functor = aFilterMgr.CreateVolume3D()
1123 elif theCriterion == FT_MaxElementLength2D:
1124 functor = aFilterMgr.CreateMaxElementLength2D()
1125 elif theCriterion == FT_MaxElementLength3D:
1126 functor = aFilterMgr.CreateMaxElementLength3D()
1127 elif theCriterion == FT_MultiConnection:
1128 functor = aFilterMgr.CreateMultiConnection()
1129 elif theCriterion == FT_MultiConnection2D:
1130 functor = aFilterMgr.CreateMultiConnection2D()
1131 elif theCriterion == FT_Length:
1132 functor = aFilterMgr.CreateLength()
1133 elif theCriterion == FT_Length2D:
1134 functor = aFilterMgr.CreateLength2D()
1135 elif theCriterion == FT_Deflection2D:
1136 functor = aFilterMgr.CreateDeflection2D()
1137 elif theCriterion == FT_NodeConnectivityNumber:
1138 functor = aFilterMgr.CreateNodeConnectivityNumber()
1139 elif theCriterion == FT_BallDiameter:
1140 functor = aFilterMgr.CreateBallDiameter()
1142 print("Error: given parameter is not numerical functor type.")
1143 aFilterMgr.UnRegister()
1146 def CreateHypothesis(self, theHType, theLibName="libStdMeshersEngine.so"):
1151 theHType (string): mesh hypothesis type
1152 theLibName (string): mesh plug-in library name
1155 created hypothesis instance
1157 hyp = SMESH._objref_SMESH_Gen.CreateHypothesis(self, theHType, theLibName )
1159 if isinstance( hyp, SMESH._objref_SMESH_Algo ):
1162 # wrap hypothesis methods
1163 for meth_name in dir( hyp.__class__ ):
1164 if not meth_name.startswith("Get") and \
1165 not meth_name in dir ( SMESH._objref_SMESH_Hypothesis ):
1166 method = getattr ( hyp.__class__, meth_name )
1167 if callable(method):
1168 setattr( hyp, meth_name, hypMethodWrapper( hyp, method ))
1172 def GetMeshInfo(self, obj):
1174 Get the mesh statistic.
1175 Use :meth:`smeshBuilder.EnumToLong` to get an integer from
1176 an item of :class:`SMESH.EntityType`.
1179 dictionary { :class:`SMESH.EntityType` - "count of elements" }
1182 if isinstance( obj, Mesh ):
1185 if hasattr(obj, "GetMeshInfo"):
1186 values = obj.GetMeshInfo()
1187 for i in range(SMESH.Entity_Last._v):
1188 if i < len(values): d[SMESH.EntityType._item(i)]=values[i]
1192 def MinDistance(self, src1, src2=None, id1=0, id2=0, isElem1=False, isElem2=False):
1194 Get minimum distance between two objects
1196 * If *src2* is None, and *id2* = 0, distance from *src1* / *id1* to the origin is computed.
1197 * If *src2* is None, and *id2* != 0, it is assumed that both *id1* and *id2* belong to *src1*.
1200 src1 (SMESH.SMESH_IDSource): first source object
1201 src2 (SMESH.SMESH_IDSource): second source object
1202 id1 (int): node/element id from the first source
1203 id2 (int): node/element id from the second (or first) source
1204 isElem1 (boolean): *True* if *id1* is element id, *False* if it is node id
1205 isElem2 (boolean): *True* if *id2* is element id, *False* if it is node id
1208 minimum distance value
1211 :meth:`GetMinDistance`
1214 result = self.GetMinDistance(src1, src2, id1, id2, isElem1, isElem2)
1218 result = result.value
1221 def GetMinDistance(self, src1, src2=None, id1=0, id2=0, isElem1=False, isElem2=False):
1223 Get :class:`SMESH.Measure` structure specifying minimum distance data between two objects
1225 * If *src2* is None, and *id2* = 0, distance from *src1* / *id1* to the origin is computed.
1226 * If *src2* is None, and *id2* != 0, it is assumed that both *id1* and *id2* belong to *src1*.
1229 src1 (SMESH.SMESH_IDSource): first source object
1230 src2 (SMESH.SMESH_IDSource): second source object
1231 id1 (int): node/element id from the first source
1232 id2 (int): node/element id from the second (or first) source
1233 isElem1 (boolean): *True* if **id1** is element id, *False* if it is node id
1234 isElem2 (boolean): *True* if **id2** is element id, *False* if it is node id
1237 :class:`SMESH.Measure` structure or None if input data is invalid
1242 if isinstance(src1, Mesh): src1 = src1.mesh
1243 if isinstance(src2, Mesh): src2 = src2.mesh
1244 if src2 is None and id2 != 0: src2 = src1
1245 if not hasattr(src1, "_narrow"): return None
1246 src1 = src1._narrow(SMESH.SMESH_IDSource)
1247 if not src1: return None
1248 unRegister = genObjUnRegister()
1251 e = m.GetMeshEditor()
1253 src1 = e.MakeIDSource([id1], SMESH.FACE)
1255 src1 = e.MakeIDSource([id1], SMESH.NODE)
1256 unRegister.set( src1 )
1258 if hasattr(src2, "_narrow"):
1259 src2 = src2._narrow(SMESH.SMESH_IDSource)
1260 if src2 and id2 != 0:
1262 e = m.GetMeshEditor()
1264 src2 = e.MakeIDSource([id2], SMESH.FACE)
1266 src2 = e.MakeIDSource([id2], SMESH.NODE)
1267 unRegister.set( src2 )
1270 aMeasurements = self.CreateMeasurements()
1271 unRegister.set( aMeasurements )
1272 result = aMeasurements.MinDistance(src1, src2)
1275 def BoundingBox(self, objects):
1277 Get bounding box of the specified object(s)
1280 objects (SMESH.SMESH_IDSource): single source object or list of source objects
1283 tuple of six values (minX, minY, minZ, maxX, maxY, maxZ)
1286 :meth:`GetBoundingBox`
1289 result = self.GetBoundingBox(objects)
1293 result = (result.minX, result.minY, result.minZ, result.maxX, result.maxY, result.maxZ)
1296 def GetBoundingBox(self, objects):
1298 Get :class:`SMESH.Measure` structure specifying bounding box data of the specified object(s)
1301 objects (SMESH.SMESH_IDSource): single source object or list of source objects
1304 :class:`SMESH.Measure` structure
1310 if isinstance(objects, tuple):
1311 objects = list(objects)
1312 if not isinstance(objects, list):
1316 if isinstance(o, Mesh):
1317 srclist.append(o.mesh)
1318 elif hasattr(o, "_narrow"):
1319 src = o._narrow(SMESH.SMESH_IDSource)
1320 if src: srclist.append(src)
1323 aMeasurements = self.CreateMeasurements()
1324 result = aMeasurements.BoundingBox(srclist)
1325 aMeasurements.UnRegister()
1328 def GetLength(self, obj):
1330 Get sum of lengths of all 1D elements in the mesh object.
1333 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1336 sum of lengths of all 1D elements
1339 if isinstance(obj, Mesh): obj = obj.mesh
1340 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1341 aMeasurements = self.CreateMeasurements()
1342 value = aMeasurements.Length(obj)
1343 aMeasurements.UnRegister()
1346 def GetArea(self, obj):
1348 Get sum of areas of all 2D elements in the mesh object.
1351 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1354 sum of areas of all 2D elements
1357 if isinstance(obj, Mesh): obj = obj.mesh
1358 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1359 aMeasurements = self.CreateMeasurements()
1360 value = aMeasurements.Area(obj)
1361 aMeasurements.UnRegister()
1364 def GetVolume(self, obj):
1366 Get sum of volumes of all 3D elements in the mesh object.
1369 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1372 sum of volumes of all 3D elements
1375 if isinstance(obj, Mesh): obj = obj.mesh
1376 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1377 aMeasurements = self.CreateMeasurements()
1378 value = aMeasurements.Volume(obj)
1379 aMeasurements.UnRegister()
1382 def GetGravityCenter(self, obj):
1384 Get gravity center of all nodes of the mesh object.
1387 obj: :class:`mesh, sub-mesh, group or filter <SMESH.SMESH_IDSource>`
1390 Three components of the gravity center (x,y,z)
1392 if isinstance(obj, Mesh): obj = obj.mesh
1393 if isinstance(obj, Mesh_Algorithm): obj = obj.GetSubMesh()
1394 aMeasurements = self.CreateMeasurements()
1395 pointStruct = aMeasurements.GravityCenter(obj)
1396 aMeasurements.UnRegister()
1397 return pointStruct.x, pointStruct.y, pointStruct.z
1399 pass # end of class smeshBuilder
1402 omniORB.registerObjref(SMESH._objref_SMESH_Gen._NP_RepositoryId, smeshBuilder)
1403 """Registering the new proxy for SMESH.SMESH_Gen"""
1406 def New( instance=None, instanceGeom=None):
1408 Create a new smeshBuilder instance. The smeshBuilder class provides the Python
1409 interface to create or load meshes.
1414 salome.salome_init()
1415 from salome.smesh import smeshBuilder
1416 smesh = smeshBuilder.New()
1419 instance: CORBA proxy of SMESH Engine. If None, the default Engine is used.
1420 instanceGeom: CORBA proxy of GEOM Engine. If None, the default Engine is used.
1422 :class:`smeshBuilder` instance
1427 if instance and isinstance( instance, SALOMEDS._objref_Study ):
1429 sys.stderr.write("Warning: 'study' argument is no more needed in smeshBuilder.New(). Consider updating your script!!!\n\n")
1434 smeshInst = smeshBuilder()
1435 assert isinstance(smeshInst,smeshBuilder), "Smesh engine class is %s but should be smeshBuilder.smeshBuilder. Import salome.smesh.smeshBuilder before creating the instance."%smeshInst.__class__
1436 smeshInst.init_smesh(instanceGeom)
1440 # Public class: Mesh
1441 # ==================
1444 class Mesh(metaclass = MeshMeta):
1446 This class allows defining and managing a mesh.
1447 It has a set of methods to build a mesh on the given geometry, including the definition of sub-meshes.
1448 It also has methods to define groups of mesh elements, to modify a mesh (by addition of
1449 new nodes and elements and by changing the existing entities), to get information
1450 about a mesh and to export a mesh in different formats.
1457 def __init__(self, smeshpyD, geompyD, obj=0, name=0):
1462 Create a mesh on the shape *obj* (or an empty mesh if *obj* is equal to 0) and
1463 sets the GUI name of this mesh to *name*.
1466 smeshpyD: an instance of smeshBuilder class
1467 geompyD: an instance of geomBuilder class
1468 obj: Shape to be meshed or :class:`SMESH.SMESH_Mesh` object
1469 name: Study name of the mesh
1472 self.smeshpyD = smeshpyD
1473 self.geompyD = geompyD
1478 if isinstance(obj, geomBuilder.GEOM._objref_GEOM_Object):
1481 # publish geom of mesh (issue 0021122)
1482 if not self.geom.GetStudyEntry():
1486 geo_name = name + " shape"
1488 geo_name = "%s_%s to mesh"%(self.geom.GetShapeType(), id(self.geom)%100)
1489 geompyD.addToStudy( self.geom, geo_name )
1490 self.SetMesh( self.smeshpyD.CreateMesh(self.geom) )
1492 elif isinstance(obj, SMESH._objref_SMESH_Mesh):
1495 self.SetMesh( self.smeshpyD.CreateEmptyMesh() )
1497 self.smeshpyD.SetName(self.mesh, name)
1499 self.smeshpyD.SetName(self.mesh, GetName(obj)) # + " mesh"
1502 self.geom = self.mesh.GetShapeToMesh()
1504 self.editor = self.mesh.GetMeshEditor()
1505 self.functors = [None] * SMESH.FT_Undefined._v
1507 # set self to algoCreator's
1508 for attrName in dir(self):
1509 attr = getattr( self, attrName )
1510 if isinstance( attr, algoCreator ):
1511 setattr( self, attrName, attr.copy( self ))
1518 Destructor. Clean-up resources
1521 #self.mesh.UnRegister()
1525 def SetMesh(self, theMesh):
1527 Initialize the Mesh object from an instance of :class:`SMESH.SMESH_Mesh` interface
1530 theMesh: a :class:`SMESH.SMESH_Mesh` object
1534 # do not call Register() as this prevents mesh servant deletion at closing study
1535 #if self.mesh: self.mesh.UnRegister()
1538 #self.mesh.Register()
1539 self.geom = self.mesh.GetShapeToMesh()
1544 Return the mesh, that is an encapsulated instance of :class:`SMESH.SMESH_Mesh` interface
1547 a :class:`SMESH.SMESH_Mesh` object
1554 Get the name of the mesh
1557 the name of the mesh as a string
1560 name = GetName(self.GetMesh())
1563 def SetName(self, name):
1565 Set a name to the mesh
1568 name: a new name of the mesh
1571 self.smeshpyD.SetName(self.GetMesh(), name)
1573 def GetSubMesh(self, geom, name):
1575 Get a sub-mesh object associated to a *geom* geometrical object.
1578 geom: a geometrical object (shape)
1579 name: a name for the sub-mesh in the Object Browser
1582 an object of type :class:`SMESH.SMESH_subMesh`, representing a part of mesh,
1583 which lies on the given shape
1586 A sub-mesh is implicitly created when a sub-shape is specified at
1587 creating an algorithm, for example::
1589 algo1D = mesh.Segment(geom=Edge_1)
1591 creates a sub-mesh on *Edge_1* and assign Wire Discretization algorithm to it.
1592 The created sub-mesh can be retrieved from the algorithm::
1594 submesh = algo1D.GetSubMesh()
1597 AssureGeomPublished( self, geom, name )
1598 submesh = self.mesh.GetSubMesh( geom, name )
1603 Return the shape associated to the mesh
1611 def SetShape(self, geom):
1613 Associate the given shape to the mesh (entails the recreation of the mesh)
1616 geom: the shape to be meshed (GEOM_Object)
1619 self.mesh = self.smeshpyD.CreateMesh(geom)
1623 Load mesh from the study after opening the study
1627 def IsReadyToCompute(self, theSubObject):
1629 Return true if the hypotheses are defined well
1632 theSubObject: a sub-shape of a mesh shape
1638 return self.smeshpyD.IsReadyToCompute(self.mesh, theSubObject)
1640 def GetAlgoState(self, theSubObject):
1642 Return errors of hypotheses definition.
1643 The list of errors is empty if everything is OK.
1646 theSubObject: a sub-shape of a mesh shape
1652 return self.smeshpyD.GetAlgoState(self.mesh, theSubObject)
1654 def GetGeometryByMeshElement(self, theElementID, theGeomName):
1656 Return a geometrical object on which the given element was built.
1657 The returned geometrical object, if not nil, is either found in the
1658 study or published by this method with the given name
1661 theElementID: the id of the mesh element
1662 theGeomName: the user-defined name of the geometrical object
1665 GEOM.GEOM_Object instance
1668 return self.smeshpyD.GetGeometryByMeshElement( self.mesh, theElementID, theGeomName )
1670 def MeshDimension(self):
1672 Return the mesh dimension depending on the dimension of the underlying shape
1673 or, if the mesh is not based on any shape, basing on deimension of elements
1676 mesh dimension as an integer value [0,3]
1679 if self.mesh.HasShapeToMesh():
1680 shells = self.geompyD.SubShapeAllIDs( self.geom, self.geompyD.ShapeType["SOLID"] )
1681 if len( shells ) > 0 :
1683 elif self.geompyD.NumberOfFaces( self.geom ) > 0 :
1685 elif self.geompyD.NumberOfEdges( self.geom ) > 0 :
1690 if self.NbVolumes() > 0: return 3
1691 if self.NbFaces() > 0: return 2
1692 if self.NbEdges() > 0: return 1
1695 def Evaluate(self, geom=0):
1697 Evaluate size of prospective mesh on a shape
1700 a list where i-th element is a number of elements of i-th :class:`SMESH.EntityType`.
1701 To know predicted number of e.g. edges, inquire it this way::
1703 Evaluate()[ smesh.EnumToLong( SMESH.Entity_Edge )]
1706 if geom == 0 or not isinstance(geom, geomBuilder.GEOM._objref_GEOM_Object):
1708 geom = self.mesh.GetShapeToMesh()
1711 return self.smeshpyD.Evaluate(self.mesh, geom)
1714 def Compute(self, geom=0, discardModifs=False, refresh=False):
1716 Compute the mesh and return the status of the computation
1719 geom: geomtrical shape on which mesh data should be computed
1720 discardModifs: if True and the mesh has been edited since
1721 a last total re-compute and that may prevent successful partial re-compute,
1722 then the mesh is cleaned before Compute()
1723 refresh: if *True*, Object Browser is automatically updated (when running in GUI)
1729 if geom == 0 or not isinstance(geom, geomBuilder.GEOM._objref_GEOM_Object):
1731 geom = self.mesh.GetShapeToMesh()
1736 if discardModifs and self.mesh.HasModificationsToDiscard(): # issue 0020693
1738 ok = self.smeshpyD.Compute(self.mesh, geom)
1739 except SALOME.SALOME_Exception as ex:
1740 print("Mesh computation failed, exception caught:")
1741 print(" ", ex.details.text)
1744 print("Mesh computation failed, exception caught:")
1745 traceback.print_exc()
1749 # Treat compute errors
1750 computeErrors = self.smeshpyD.GetComputeErrors( self.mesh, geom )
1752 for err in computeErrors:
1753 if self.mesh.HasShapeToMesh():
1754 shapeText = " on %s" % self.GetSubShapeName( err.subShapeID )
1756 stdErrors = ["OK", #COMPERR_OK
1757 "Invalid input mesh", #COMPERR_BAD_INPUT_MESH
1758 "std::exception", #COMPERR_STD_EXCEPTION
1759 "OCC exception", #COMPERR_OCC_EXCEPTION
1760 "..", #COMPERR_SLM_EXCEPTION
1761 "Unknown exception", #COMPERR_EXCEPTION
1762 "Memory allocation problem", #COMPERR_MEMORY_PB
1763 "Algorithm failed", #COMPERR_ALGO_FAILED
1764 "Unexpected geometry", #COMPERR_BAD_SHAPE
1765 "Warning", #COMPERR_WARNING
1766 "Computation cancelled",#COMPERR_CANCELED
1767 "No mesh on sub-shape"] #COMPERR_NO_MESH_ON_SHAPE
1769 if err.code < len(stdErrors): errText = stdErrors[err.code]
1771 errText = "code %s" % -err.code
1772 if errText: errText += ". "
1773 errText += err.comment
1774 if allReasons: allReasons += "\n"
1776 allReasons += '- "%s"%s - %s' %(err.algoName, shapeText, errText)
1778 allReasons += '- "%s" failed%s. Error: %s' %(err.algoName, shapeText, errText)
1782 errors = self.smeshpyD.GetAlgoState( self.mesh, geom )
1784 if err.isGlobalAlgo:
1792 reason = '%s %sD algorithm is missing' % (glob, dim)
1793 elif err.state == HYP_MISSING:
1794 reason = ('%s %sD algorithm "%s" misses %sD hypothesis'
1795 % (glob, dim, name, dim))
1796 elif err.state == HYP_NOTCONFORM:
1797 reason = 'Global "Not Conform mesh allowed" hypothesis is missing'
1798 elif err.state == HYP_BAD_PARAMETER:
1799 reason = ('Hypothesis of %s %sD algorithm "%s" has a bad parameter value'
1800 % ( glob, dim, name ))
1801 elif err.state == HYP_BAD_GEOMETRY:
1802 reason = ('%s %sD algorithm "%s" is assigned to mismatching'
1803 'geometry' % ( glob, dim, name ))
1804 elif err.state == HYP_HIDDEN_ALGO:
1805 reason = ('%s %sD algorithm "%s" is ignored due to presence of a %s '
1806 'algorithm of upper dimension generating %sD mesh'
1807 % ( glob, dim, name, glob, dim ))
1809 reason = ("For unknown reason. "
1810 "Developer, revise Mesh.Compute() implementation in smeshBuilder.py!")
1812 if allReasons: allReasons += "\n"
1813 allReasons += "- " + reason
1815 if not ok or allReasons != "":
1816 msg = '"' + GetName(self.mesh) + '"'
1817 if ok: msg += " has been computed with warnings"
1818 else: msg += " has not been computed"
1819 if allReasons != "": msg += ":"
1824 if salome.sg.hasDesktop():
1825 if not isinstance( refresh, list): # not a call from subMesh.Compute()
1826 if refresh: salome.sg.updateObjBrowser()
1830 def GetComputeErrors(self, shape=0 ):
1832 Return a list of error messages (:class:`SMESH.ComputeError`) of the last :meth:`Compute`
1836 shape = self.mesh.GetShapeToMesh()
1837 return self.smeshpyD.GetComputeErrors( self.mesh, shape )
1839 def GetSubShapeName(self, subShapeID ):
1841 Return a name of a sub-shape by its ID.
1842 Possible variants (for *subShapeID* == 3):
1844 - **"Face_12"** - published sub-shape
1845 - **FACE #3** - not published sub-shape
1846 - **sub-shape #3** - invalid sub-shape ID
1847 - **#3** - error in this function
1850 subShapeID: a unique ID of a sub-shape
1853 a string describing the sub-shape
1857 if not self.mesh.HasShapeToMesh():
1861 mainIOR = salome.orb.object_to_string( self.GetShape() )
1863 mainSO = s.FindObjectIOR(mainIOR)
1866 shapeText = '"%s"' % mainSO.GetName()
1867 subIt = s.NewChildIterator(mainSO)
1869 subSO = subIt.Value()
1871 obj = subSO.GetObject()
1872 if not obj: continue
1873 go = obj._narrow( geomBuilder.GEOM._objref_GEOM_Object )
1876 ids = self.geompyD.GetSubShapeID( self.GetShape(), go )
1879 if ids == subShapeID:
1880 shapeText = '"%s"' % subSO.GetName()
1883 shape = self.geompyD.GetSubShape( self.GetShape(), [subShapeID])
1885 shapeText = '%s #%s' % (shape.GetShapeType(), subShapeID)
1887 shapeText = 'sub-shape #%s' % (subShapeID)
1889 shapeText = "#%s" % (subShapeID)
1892 def GetFailedShapes(self, publish=False):
1894 Return a list of sub-shapes meshing of which failed, grouped into GEOM groups by
1895 error of an algorithm
1898 publish: if *True*, the returned groups will be published in the study
1901 a list of GEOM groups each named after a failed algorithm
1906 computeErrors = self.smeshpyD.GetComputeErrors( self.mesh, self.GetShape() )
1907 for err in computeErrors:
1908 shape = self.geompyD.GetSubShape( self.GetShape(), [err.subShapeID])
1909 if not shape: continue
1910 if err.algoName in algo2shapes:
1911 algo2shapes[ err.algoName ].append( shape )
1913 algo2shapes[ err.algoName ] = [ shape ]
1917 for algoName, shapes in list(algo2shapes.items()):
1919 groupType = self.smeshpyD.EnumToLong( shapes[0].GetShapeType() )
1920 otherTypeShapes = []
1922 group = self.geompyD.CreateGroup( self.geom, groupType )
1923 for shape in shapes:
1924 if shape.GetShapeType() == shapes[0].GetShapeType():
1925 sameTypeShapes.append( shape )
1927 otherTypeShapes.append( shape )
1928 self.geompyD.UnionList( group, sameTypeShapes )
1930 group.SetName( "%s %s" % ( algoName, shapes[0].GetShapeType() ))
1932 group.SetName( algoName )
1933 groups.append( group )
1934 shapes = otherTypeShapes
1937 for group in groups:
1938 self.geompyD.addToStudyInFather( self.geom, group, group.GetName() )
1941 def GetMeshOrder(self):
1943 Return sub-mesh objects list in meshing order
1946 list of lists of :class:`sub-meshes <SMESH.SMESH_subMesh>`
1949 return self.mesh.GetMeshOrder()
1951 def SetMeshOrder(self, submeshes):
1953 Set order in which concurrent sub-meshes should be meshed
1956 submeshes: list of lists of :class:`sub-meshes <SMESH.SMESH_subMesh>`
1959 return self.mesh.SetMeshOrder(submeshes)
1961 def Clear(self, refresh=False):
1963 Remove all nodes and elements generated on geometry. Imported elements remain.
1966 refresh: if *True*, Object browser is automatically updated (when running in GUI)
1970 if ( salome.sg.hasDesktop() ):
1971 if refresh: salome.sg.updateObjBrowser()
1973 def ClearSubMesh(self, geomId, refresh=False):
1975 Remove all nodes and elements of indicated shape
1978 geomId: the ID of a sub-shape to remove elements on
1979 refresh: if *True*, Object browser is automatically updated (when running in GUI)
1982 self.mesh.ClearSubMesh(geomId)
1983 if salome.sg.hasDesktop():
1984 if refresh: salome.sg.updateObjBrowser()
1986 def AutomaticTetrahedralization(self, fineness=0):
1988 Compute a tetrahedral mesh using AutomaticLength + MEFISTO + Tetrahedron
1991 fineness: [0.0,1.0] defines mesh fineness
1997 dim = self.MeshDimension()
1999 self.RemoveGlobalHypotheses()
2000 self.Segment().AutomaticLength(fineness)
2002 self.Triangle().LengthFromEdges()
2007 return self.Compute()
2009 def AutomaticHexahedralization(self, fineness=0):
2011 Compute an hexahedral mesh using AutomaticLength + Quadrangle + Hexahedron
2014 fineness: [0.0, 1.0] defines mesh fineness
2020 dim = self.MeshDimension()
2021 # assign the hypotheses
2022 self.RemoveGlobalHypotheses()
2023 self.Segment().AutomaticLength(fineness)
2030 return self.Compute()
2032 def AddHypothesis(self, hyp, geom=0):
2037 hyp: a hypothesis to assign
2038 geom: a subhape of mesh geometry
2041 :class:`SMESH.Hypothesis_Status`
2044 if isinstance( hyp, geomBuilder.GEOM._objref_GEOM_Object ):
2045 hyp, geom = geom, hyp
2046 if isinstance( hyp, Mesh_Algorithm ):
2047 hyp = hyp.GetAlgorithm()
2052 geom = self.mesh.GetShapeToMesh()
2055 if self.mesh.HasShapeToMesh():
2056 hyp_type = hyp.GetName()
2057 lib_name = hyp.GetLibName()
2058 # checkAll = ( not geom.IsSame( self.mesh.GetShapeToMesh() ))
2059 # if checkAll and geom:
2060 # checkAll = geom.GetType() == 37
2062 isApplicable = self.smeshpyD.IsApplicable(hyp_type, lib_name, geom, checkAll)
2064 AssureGeomPublished( self, geom, "shape for %s" % hyp.GetName())
2065 status = self.mesh.AddHypothesis(geom, hyp)
2067 status = HYP_BAD_GEOMETRY, ""
2068 hyp_name = GetName( hyp )
2071 geom_name = geom.GetName()
2072 isAlgo = hyp._narrow( SMESH_Algo )
2073 TreatHypoStatus( status, hyp_name, geom_name, isAlgo, self )
2076 def IsUsedHypothesis(self, hyp, geom):
2078 Return True if an algorithm or hypothesis is assigned to a given shape
2081 hyp: an algorithm or hypothesis to check
2082 geom: a subhape of mesh geometry
2088 if not hyp: # or not geom
2090 if isinstance( hyp, Mesh_Algorithm ):
2091 hyp = hyp.GetAlgorithm()
2093 hyps = self.GetHypothesisList(geom)
2095 if h.GetId() == hyp.GetId():
2099 def RemoveHypothesis(self, hyp, geom=0):
2101 Unassign a hypothesis
2104 hyp (SMESH.SMESH_Hypothesis): a hypothesis to unassign
2105 geom (GEOM.GEOM_Object): a sub-shape of mesh geometry
2108 :class:`SMESH.Hypothesis_Status`
2113 if isinstance( hyp, Mesh_Algorithm ):
2114 hyp = hyp.GetAlgorithm()
2120 if self.IsUsedHypothesis( hyp, shape ):
2121 return self.mesh.RemoveHypothesis( shape, hyp )
2122 hypName = GetName( hyp )
2123 geoName = GetName( shape )
2124 print("WARNING: RemoveHypothesis() failed as '%s' is not assigned to '%s' shape" % ( hypName, geoName ))
2127 def GetHypothesisList(self, geom):
2129 Get the list of hypotheses added on a geometry
2132 geom (GEOM.GEOM_Object): a sub-shape of mesh geometry
2135 the sequence of :class:`SMESH.SMESH_Hypothesis`
2138 return self.mesh.GetHypothesisList( geom )
2140 def RemoveGlobalHypotheses(self):
2142 Remove all global hypotheses
2145 current_hyps = self.mesh.GetHypothesisList( self.geom )
2146 for hyp in current_hyps:
2147 self.mesh.RemoveHypothesis( self.geom, hyp )
2150 def ExportMED(self, *args, **kwargs):
2152 Export the mesh in a file in MED format
2153 allowing to overwrite the file if it exists or add the exported data to its contents
2156 fileName: is the file name
2157 auto_groups (boolean): parameter for creating/not creating
2158 the groups Group_On_All_Nodes, Group_On_All_Faces, ... ;
2159 the typical use is auto_groups=False.
2160 overwrite (boolean): parameter for overwriting/not overwriting the file
2161 meshPart: a part of mesh (:class:`sub-mesh, group or filter <SMESH.SMESH_IDSource>`) to export instead of the mesh
2162 autoDimension: if *True* (default), a space dimension of a MED mesh can be either
2164 - 1D if all mesh nodes lie on OX coordinate axis, or
2165 - 2D if all mesh nodes lie on XOY coordinate plane, or
2166 - 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 adjacent 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 existing 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 if refresh: salome.sg.updateObjBrowser()
6902 omniORB.registerObjref(SMESH._objref_SMESH_subMesh._NP_RepositoryId, submeshProxy)
6905 class meshEditor(SMESH._objref_SMESH_MeshEditor):
6907 Private class used to compensate change of CORBA API of SMESH_MeshEditor for backward
6908 compatibility with old dump scripts which call SMESH_MeshEditor directly and not via
6911 def __init__(self,*args):
6912 SMESH._objref_SMESH_MeshEditor.__init__( self, *args)
6914 def __getattr__(self, name ): # method called if an attribute not found
6915 if not self.mesh: # look for name() method in Mesh class
6916 self.mesh = Mesh( None, None, SMESH._objref_SMESH_MeshEditor.GetMesh(self))
6917 if hasattr( self.mesh, name ):
6918 return getattr( self.mesh, name )
6919 if name == "ExtrusionAlongPathObjX":
6920 return getattr( self.mesh, "ExtrusionAlongPathX" ) # other method name
6921 print("meshEditor: attribute '%s' NOT FOUND" % name)
6923 def __deepcopy__(self, memo=None):
6924 new = self.__class__(self)
6926 def FindCoincidentNodes(self,*args): # a 2nd arg added (SeparateCornerAndMediumNodes)
6927 if len( args ) == 1: args += False,
6928 return SMESH._objref_SMESH_MeshEditor.FindCoincidentNodes( self, *args )
6929 def FindCoincidentNodesOnPart(self,*args): # a 3d arg added (SeparateCornerAndMediumNodes)
6930 if len( args ) == 2: args += False,
6931 return SMESH._objref_SMESH_MeshEditor.FindCoincidentNodesOnPart( self, *args )
6932 def MergeNodes(self,*args): # 2 args added (NodesToKeep,AvoidMakingHoles)
6933 if len( args ) == 1:
6934 return SMESH._objref_SMESH_MeshEditor.MergeNodes( self, args[0], [], False )
6935 NodesToKeep = args[1]
6936 AvoidMakingHoles = args[2] if len( args ) == 3 else False
6937 unRegister = genObjUnRegister()
6939 if isinstance( NodesToKeep, list ) and isinstance( NodesToKeep[0], int ):
6940 NodesToKeep = self.MakeIDSource( NodesToKeep, SMESH.NODE )
6941 if not isinstance( NodesToKeep, list ):
6942 NodesToKeep = [ NodesToKeep ]
6943 return SMESH._objref_SMESH_MeshEditor.MergeNodes( self, args[0], NodesToKeep, AvoidMakingHoles )
6945 omniORB.registerObjref(SMESH._objref_SMESH_MeshEditor._NP_RepositoryId, meshEditor)
6947 class Pattern(SMESH._objref_SMESH_Pattern):
6949 Private class wrapping SMESH.SMESH_Pattern CORBA class in order to treat Notebook
6950 variables in some methods
6953 def LoadFromFile(self, patternTextOrFile ):
6954 text = patternTextOrFile
6955 if os.path.exists( text ):
6956 text = open( patternTextOrFile ).read()
6958 return SMESH._objref_SMESH_Pattern.LoadFromFile( self, text )
6960 def ApplyToMeshFaces(self, theMesh, theFacesIDs, theNodeIndexOnKeyPoint1, theReverse):
6961 decrFun = lambda i: i-1
6962 theNodeIndexOnKeyPoint1,Parameters,hasVars = ParseParameters(theNodeIndexOnKeyPoint1, decrFun)
6963 theMesh.SetParameters(Parameters)
6964 return SMESH._objref_SMESH_Pattern.ApplyToMeshFaces( self, theMesh, theFacesIDs, theNodeIndexOnKeyPoint1, theReverse )
6966 def ApplyToHexahedrons(self, theMesh, theVolumesIDs, theNode000Index, theNode001Index):
6967 decrFun = lambda i: i-1
6968 theNode000Index,theNode001Index,Parameters,hasVars = ParseParameters(theNode000Index,theNode001Index, decrFun)
6969 theMesh.SetParameters(Parameters)
6970 return SMESH._objref_SMESH_Pattern.ApplyToHexahedrons( self, theMesh, theVolumesIDs, theNode000Index, theNode001Index )
6972 def MakeMesh(self, mesh, CreatePolygons=False, CreatePolyhedra=False):
6973 if isinstance( mesh, Mesh ):
6974 mesh = mesh.GetMesh()
6975 return SMESH._objref_SMESH_Pattern.MakeMesh( self, mesh, CreatePolygons, CreatePolyhedra )
6977 omniORB.registerObjref(SMESH._objref_SMESH_Pattern._NP_RepositoryId, Pattern)
6979 Registering the new proxy for Pattern
6984 Private class used to bind methods creating algorithms to the class Mesh
6987 def __init__(self, method):
6989 self.defaultAlgoType = ""
6990 self.algoTypeToClass = {}
6991 self.method = method
6993 def add(self, algoClass):
6995 Store a python class of algorithm
6997 if inspect.isclass(algoClass) and \
6998 hasattr( algoClass, "algoType"):
6999 self.algoTypeToClass[ algoClass.algoType ] = algoClass
7000 if not self.defaultAlgoType and \
7001 hasattr( algoClass, "isDefault") and algoClass.isDefault:
7002 self.defaultAlgoType = algoClass.algoType
7003 #print("Add",algoClass.algoType, "dflt",self.defaultAlgoType)
7005 def copy(self, mesh):
7007 Create a copy of self and assign mesh to the copy
7010 other = algoCreator( self.method )
7011 other.defaultAlgoType = self.defaultAlgoType
7012 other.algoTypeToClass = self.algoTypeToClass
7016 def __call__(self,algo="",geom=0,*args):
7018 Create an instance of algorithm
7022 if isinstance( algo, str ):
7024 elif ( isinstance( algo, geomBuilder.GEOM._objref_GEOM_Object ) and \
7025 not isinstance( geom, geomBuilder.GEOM._objref_GEOM_Object )):
7030 if isinstance( geom, geomBuilder.GEOM._objref_GEOM_Object ):
7032 elif not algoType and isinstance( geom, str ):
7037 if isinstance( arg, geomBuilder.GEOM._objref_GEOM_Object ) and not shape:
7039 elif isinstance( arg, str ) and not algoType:
7042 import traceback, sys
7043 msg = "Warning. Unexpected argument in mesh.%s() ---> %s" % ( self.method, arg )
7044 sys.stderr.write( msg + '\n' )
7045 tb = traceback.extract_stack(None,2)
7046 traceback.print_list( [tb[0]] )
7048 algoType = self.defaultAlgoType
7049 if not algoType and self.algoTypeToClass:
7050 algoType = sorted( self.algoTypeToClass.keys() )[0]
7051 if algoType in self.algoTypeToClass:
7052 #print("Create algo",algoType)
7053 return self.algoTypeToClass[ algoType ]( self.mesh, shape )
7054 raise RuntimeError( "No class found for algo type %s" % algoType)
7057 class hypMethodWrapper:
7059 Private class used to substitute and store variable parameters of hypotheses.
7062 def __init__(self, hyp, method):
7064 self.method = method
7065 #print("REBIND:", method.__name__)
7068 def __call__(self,*args):
7070 call a method of hypothesis with calling SetVarParameter() before
7074 return self.method( self.hyp, *args ) # hypothesis method with no args
7076 #print("MethWrapper.__call__", self.method.__name__, args)
7078 parsed = ParseParameters(*args) # replace variables with their values
7079 self.hyp.SetVarParameter( parsed[-2], self.method.__name__ )
7080 result = self.method( self.hyp, *parsed[:-2] ) # call hypothesis method
7081 except omniORB.CORBA.BAD_PARAM: # raised by hypothesis method call
7082 # maybe there is a replaced string arg which is not variable
7083 result = self.method( self.hyp, *args )
7084 except ValueError as detail: # raised by ParseParameters()
7086 result = self.method( self.hyp, *args )
7087 except omniORB.CORBA.BAD_PARAM:
7088 raise ValueError(detail) # wrong variable name
7093 class genObjUnRegister:
7095 A helper class that calls UnRegister() of SALOME.GenericObj'es stored in it
7098 def __init__(self, genObj=None):
7099 self.genObjList = []
7103 def set(self, genObj):
7104 "Store one or a list of of SALOME.GenericObj'es"
7105 if isinstance( genObj, list ):
7106 self.genObjList.extend( genObj )
7108 self.genObjList.append( genObj )
7112 for genObj in self.genObjList:
7113 if genObj and hasattr( genObj, "UnRegister" ):
7116 for pluginName in os.environ[ "SMESH_MeshersList" ].split( ":" ):
7118 Bind methods creating mesher plug-ins to the Mesh class
7121 # print("pluginName: ", pluginName)
7122 pluginBuilderName = pluginName + "Builder"
7124 exec( "from salome.%s.%s import *" % (pluginName, pluginBuilderName))
7125 except Exception as e:
7126 from salome_utils import verbose
7127 if verbose(): print("Exception while loading %s: %s" % ( pluginBuilderName, e ))
7129 exec( "from salome.%s import %s" % (pluginName, pluginBuilderName))
7130 plugin = eval( pluginBuilderName )
7131 # print(" plugin:" , str(plugin))
7133 # add methods creating algorithms to Mesh
7134 for k in dir( plugin ):
7135 if k[0] == '_': continue
7136 algo = getattr( plugin, k )
7137 #print(" algo:", str(algo))
7138 if inspect.isclass(algo) and hasattr(algo, "meshMethod"):
7139 #print(" meshMethod:" , str(algo.meshMethod))
7140 if not hasattr( Mesh, algo.meshMethod ):
7141 setattr( Mesh, algo.meshMethod, algoCreator( algo.meshMethod ))
7143 _mmethod = getattr( Mesh, algo.meshMethod )
7144 if hasattr( _mmethod, "add" ):