X-Git-Url: http://git.salome-platform.org/gitweb/?p=modules%2Fsmesh.git;a=blobdiff_plain;f=src%2FSMESH_SWIG%2FStdMeshersBuilder.py;h=c2f0ed0aa068105683e627cdc64b9ae325fd6e37;hp=d50665f4e4421f27c34aec61af3c9f8fc114fd27;hb=HEAD;hpb=385d4cede5f752d0eec26c306f3b5e14511e2a3d diff --git a/src/SMESH_SWIG/StdMeshersBuilder.py b/src/SMESH_SWIG/StdMeshersBuilder.py index d50665f4e..280ae889f 100644 --- a/src/SMESH_SWIG/StdMeshersBuilder.py +++ b/src/SMESH_SWIG/StdMeshersBuilder.py @@ -1,4 +1,4 @@ -# Copyright (C) 2007-2019 CEA/DEN, EDF R&D, OPEN CASCADE +# Copyright (C) 2007-2024 CEA, EDF, OPEN CASCADE # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public @@ -25,6 +25,7 @@ LIBRARY = "libStdMeshersEngine.so" from salome.smesh.smesh_algorithm import Mesh_Algorithm import StdMeshers +from salome.geom import geomBuilder #---------------------------- # Mesh algo type identifiers @@ -42,13 +43,8 @@ Algorithm type: Python 1D algorithm, see :class:`~StdMeshersBuilder.StdMeshersBu COMPOSITE = "CompositeSegment_1D" """ - Algorithm type: Composite segment 1D algorithm, see :class:`~StdMeshersBuilder.StdMeshersBuilder_CompositeSegment` """ -MEFISTO = "MEFISTO_2D" -""" -Algorithm type: Triangle MEFISTO 2D algorithm, see :class:`~StdMeshersBuilder.StdMeshersBuilder_Triangle_MEFISTO` -""" Hexa = "Hexa_3D" """ @@ -75,6 +71,11 @@ POLYGON = "PolygonPerFace_2D" Algorithm type: Polygon Per Face 2D algorithm, see :class:`~StdMeshersBuilder.StdMeshersBuilder_PolygonPerFace` """ +POLYHEDRON = "PolyhedronPerSolid_3D" +""" +Algorithm type: Polyhedron Per Solid 3D algorithm, see :class:`~StdMeshersBuilder.StdMeshersBuilder_PolyhedronPerSolid` +""" + # import items of enums for e in StdMeshers.QuadType._items: exec('%s = StdMeshers.%s'%(e,e)) for e in StdMeshers.VLExtrusionMethod._items: exec('%s = StdMeshers.%s'%(e,e)) @@ -174,10 +175,11 @@ class StdMeshersBuilder_Segment(Mesh_Algorithm): hyp.SetLength(length) if not UseExisting: # set preestimated length + import SMESH gen = self.mesh.smeshpyD initHyp = gen.GetHypothesisParameterValues("MaxLength", "libStdMeshersEngine.so", self.mesh.GetMesh(), self.mesh.GetShape(), - False) # <- byMesh + SMESH.HypInitParams( 1, 1.0, False )) preHyp = initHyp._narrow(StdMeshers.StdMeshers_MaxLength) if preHyp: hyp.SetPreestimatedLength( preHyp.GetPreestimatedLength() ) @@ -617,72 +619,6 @@ class StdMeshersBuilder_Segment_Python(Mesh_Algorithm): pass # end of StdMeshersBuilder_Segment_Python class -class StdMeshersBuilder_Triangle_MEFISTO(Mesh_Algorithm): - """ - Triangle MEFISTO 2D algorithm. - It is created by calling smeshBuilder.Mesh.Triangle(smeshBuilder.MEFISTO,geom=0) - """ - - - meshMethod = "Triangle" - """ - name of the dynamic method in smeshBuilder.Mesh class - """ - algoType = MEFISTO - """ - type of algorithm used with helper function in smeshBuilder.Mesh class - """ - isDefault = True - """ - flag pointing whether this algorithm should be used by default in dynamic method - of smeshBuilder.Mesh class - """ - docHelper = "Create triangle 2D algorithm for faces" - """ - doc string of the method - """ - - def __init__(self, mesh, geom=0): - """ - Private constructor. - - Parameters: - mesh: parent mesh object algorithm is assigned to - geom: geometry (shape/sub-shape) algorithm is assigned to; - if it is :code:`0` (default), the algorithm is assigned to the main shape - """ - Mesh_Algorithm.__init__(self) - self.Create(mesh, geom, self.algoType) - pass - - def MaxElementArea(self, area, UseExisting=0): - """ - Defines "MaxElementArea" hypothesis basing on the definition of the maximum area of each triangle - - Parameters: - area: for the maximum area of each triangle - UseExisting: if ==true - searches for an existing hypothesis created with the - same parameters, else (default) - Create a new one - """ - - from salome.smesh.smeshBuilder import IsEqual - comparator = lambda hyp, args: IsEqual(hyp.GetMaxElementArea(), args[0]) - hyp = self.Hypothesis("MaxElementArea", [area], UseExisting=UseExisting, - CompareMethod=comparator) - hyp.SetMaxElementArea(area) - return hyp - - def LengthFromEdges(self): - """ - Defines "LengthFromEdges" hypothesis to build triangles - based on the length of the edges taken from the wire - """ - - hyp = self.Hypothesis("LengthFromEdges", UseExisting=1, CompareMethod=self.CompareEqualHyp) - return hyp - - pass # end of StdMeshersBuilder_Triangle_MEFISTO class - class StdMeshersBuilder_Quadrangle(Mesh_Algorithm): """ Defines a quadrangle 2D algorithm. @@ -726,7 +662,7 @@ class StdMeshersBuilder_Quadrangle(Mesh_Algorithm): pass def QuadrangleParameters(self, quadType=StdMeshers.QUAD_STANDARD, triangleVertex=0, - enfVertices=[],enfPoints=[],UseExisting=0): + enfVertices=[],enfPoints=[],corners=[],UseExisting=0): """ Defines "QuadrangleParameters" hypothesis quadType defines the algorithm of transition between differently descretized @@ -762,6 +698,13 @@ class StdMeshersBuilder_Quadrangle(Mesh_Algorithm): or triples of values ([[x1,y1,z1], [x2,y2,z2], ...]). In the case if the defined QuadrangleParameters() refer to a sole face, all given points must lie on this face, else the mesher fails. + corners: list of vertices that should be used as quadrangle corners. + The parameter can be useful for faces with more than four vertices, + since in some cases Quadrangle Mapping algorithm chooses corner vertices + differently than it is desired. + A hypothesis can be global and define corners for all CAD faces that + require it, but be sure that each specified vertex is a corner in all + faces the hypothesis will be applied to. UseExisting: if *True* - searches for the existing hypothesis created with the same parameters, else (default) - Create a new one """ @@ -774,6 +717,7 @@ class StdMeshersBuilder_Quadrangle(Mesh_Algorithm): if isinstance( enfVertices, int ) and not enfPoints and not UseExisting: # a call of old syntax, before inserting enfVertices and enfPoints before UseExisting UseExisting, enfVertices = enfVertices, [] + pStructs, xyz = [], [] for p in enfPoints: if isinstance( p, SMESH.PointStruct ): @@ -791,14 +735,21 @@ class StdMeshersBuilder_Quadrangle(Mesh_Algorithm): self.params = self.Hypothesis("QuadrangleParams", [quadType,vertexID,entries,xyz], UseExisting = UseExisting, CompareMethod=compFun) pass - if self.params.GetQuadType() != quadType: + + if corners and isinstance( corners[0], GEOM._objref_GEOM_Object ): + corners = [ self.mesh.geompyD.GetSubShapeID( self.mesh.geom, v ) for v in corners ] + + #If quadType is None - will used default parameter ( StdMeshers.QUAD_STANDARD ) + if quadType and self.params.GetQuadType() != quadType: self.params.SetQuadType(quadType) - if vertexID > 0: + #If triangleVertex is None - will used default parameter ( -1 ): + if triangleVertex and vertexID > 0: self.params.SetTriaVertex( vertexID ) from salome.smesh.smeshBuilder import AssureGeomPublished for v in enfVertices: AssureGeomPublished( self.mesh, v ) self.params.SetEnforcedNodes( enfVertices, pStructs ) + self.params.SetCorners( corners ) return self.params def QuadranglePreference(self, reversed=False, UseExisting=0): @@ -897,8 +848,17 @@ class StdMeshersBuilder_Hexahedron(Mesh_Algorithm): """ Mesh_Algorithm.__init__(self) self.Create(mesh, geom, Hexa) + self.renumHypothesis = 0 pass + def Renumber(self, blockCSList=[] ): + if isinstance( blockCSList, StdMeshers.BlockCS ): + blockCSList = [blockCSList] + if not self.renumHypothesis: + self.renumHypothesis = self.Hypothesis("BlockRenumber", blockCSList, UseExisting=0) + self.renumHypothesis.SetBlocksOrientation( blockCSList ) + return self.renumHypothesis + pass # end of StdMeshersBuilder_Hexahedron class class StdMeshersBuilder_Projection1D(Mesh_Algorithm): @@ -1657,6 +1617,44 @@ class StdMeshersBuilder_PolygonPerFace(Mesh_Algorithm): pass +class StdMeshersBuilder_PolyhedronPerSolid(Mesh_Algorithm): + """ Defines a Polyhedron Per Solid 3D algorithm. + It is created by calling smeshBuilder.Mesh.Polyhedron(geom=0) + """ + + meshMethod = "Polyhedron" + """ + name of the dynamic method in smeshBuilder.Mesh class + """ + algoType = POLYHEDRON + """ + type of algorithm used with helper function in smeshBuilder.Mesh class + """ + isDefault = True + """ + flag pointing whether this algorithm should be used by default in dynamic method + of smeshBuilder.Mesh class + """ + docHelper = "Create polyhedron 3D algorithm for solids" + """ + doc string of the method + """ + + def __init__(self, mesh, geom=0): + """ + Private constructor. + + Parameters: + mesh: parent mesh object algorithm is assigned to + geom: geometry (shape/sub-shape) algorithm is assigned to; + if it is :code:`0` (default), the algorithm is assigned to the main shape + """ + Mesh_Algorithm.__init__(self) + self.Create(mesh, geom, self.algoType) + pass + + pass + class StdMeshersBuilder_UseExistingElements_1D(Mesh_Algorithm): """ Defines a Use Existing Elements 1D algorithm. @@ -1834,6 +1832,12 @@ class StdMeshersBuilder_Cartesian_3D(Mesh_Algorithm): points dividing the whole shape into ranges where the functions apply; points coordinates should vary within (0.0, 1.0) range. Parameter *t* of the spacing function f(t) varies from 0.0 to 1.0 within a shape range. + Note: + The actual grid spacing can slightly differ from the defined one. This is done for the + best fitting of polyhedrons and for a better mesh quality on the interval boundaries. + For example, if a constant **Spacing** is defined along an axis, the actual grid will + fill the shape's dimension L along this axis with round number of equal cells: + Spacing_actual = L / round( L / Spacing_defined ). Examples: "10.5" - defines a grid with a constant spacing @@ -2012,3 +2016,106 @@ class StdMeshersBuilder_UseExisting_2D(Mesh_Algorithm): pass pass # end of StdMeshersBuilder_UseExisting_2D class + +class StdMeshersBuilder_ViscousLayer(Mesh_Algorithm): + """ Defines the prismatic layer builder. + + It is created by calling smeshBuilder.Mesh.ViscousLayerBuilder(geom=TheGeometry) + """ + + meshMethod = "ViscousLayerBuilder" + """ + name of the dynamic method in smeshBuilder.Mesh class + """ + algoType = "ViscousLayerBuilder" + """ + type of algorithm used with helper function in smeshBuilder.Mesh class + """ + docHelper = "Viscous layer builder for 2D and 3D geometries" + """ + doc string of the method + """ + + # On create method it will call create method from mesh python class + # + def __init__(self, mesh, geom = 0 ): + """ + Private constructor. + + Parameters: + mesh: parent mesh object algorithm is assigned to + geom: geometry (shape/sub-shape) algorithm is assigned to; + if it is :code:`0` (default), the algorithm is assigned to the main shape + """ + self.thickness = None + self.numberOfLayers = None + self.stretchFactor = None + self.elementsId = [] + self.isElementToIgnore = True + self.extrMethod = StdMeshers.SURF_OFFSET_SMOOTH + self.groupName = "" + self.shrinkGeometry = None + self.algo = self.Create(mesh, geom, self.algoType) + pass + + def setBuilderParameters( self, thickness, numberOfLayers, stretchFactor, elementsId=[], + isElementToIgnore=True, extrMethod=StdMeshers.SURF_OFFSET_SMOOTH, groupName="" ): + self.thickness = thickness + self.numberOfLayers = numberOfLayers + self.stretchFactor = stretchFactor + self.elementsId = elementsId # can be faces or edges + self.isElementToIgnore = isElementToIgnore + self.extrMethod = extrMethod + self.groupName = groupName + + self.algo.SetTotalThickness( thickness ) + self.algo.SetNumberLayers( numberOfLayers ) + self.algo.SetStretchFactor( stretchFactor ) + + #Faces are set based on int ids so if a collection of face geom objects is recived cast it to int + if elementsId and isinstance( elementsId, geomBuilder.GEOM._objref_GEOM_Object ): + elementsId = [ elementsId ] + if elementsId and isinstance( elementsId[0], geomBuilder.GEOM._objref_GEOM_Object ): + elementsIDs = [] + for shape in elementsId: + try: + ff = self.mesh.geompyD.SubShapeAll( shape, self.mesh.geompyD.ShapeType["FACE"] ) + if ( len( ff ) == 0 ): + #try to get edges + ff = self.mesh.geompyD.SubShapeAll( shape, self.mesh.geompyD.ShapeType["EDGE"] ) + + for f in ff: + elementsIDs.append( self.mesh.geompyD.GetSubShapeID(self.mesh.geom, f)) + except: + # try to get the SHAPERSTUDY engine directly, because GetGen does not work because of + # simplification of access in geomBuilder: omniORB.registerObjref + from SHAPERSTUDY_utils import getEngine + gen = getEngine() + if gen: + aShapeOp = gen.GetIShapesOperations() + ff = aShapeOp.ExtractSubShapes( shape, self.mesh.geompyD.ShapeType["FACE"], False) + if (len(ff)==0): + #try to get edges + ff = aShapeOp.ExtractSubShapes( shape, self.mesh.geompyD.ShapeType["EDGE"], False) + for f in ff: + elementsIDs.append( aShapeOp.GetSubShapeIndex( self.mesh.geom, f )) + elementsId = elementsIDs + + self.algo.SetFaces( elementsId, isElementToIgnore ) + self.algo.SetGroupName( groupName ) + self.algo.SetMethod( extrMethod ) + + def GetShrinkGeometry( self ): + if isinstance(self.geom, geomBuilder.GEOM._objref_GEOM_Object): + self.shrinkGeometry = self.algo.GetShrinkGeometry( self.mesh.GetMesh(), self.geom ) + + return self.shrinkGeometry + + def AddLayers( self, shrinkMesh ): + success = self.algo.AddLayers( shrinkMesh.GetMesh(), self.mesh.GetMesh(), self.geom ) + if ( success ): + return self.mesh #Return the original mesh of the builder + else: + return shrinkMesh + + pass # end of StdMeshersBuilder_ViscousLayer class \ No newline at end of file