Adding option to simplify polyhedrons

This commit is contained in:
YOANN AUDOUIN 2023-12-20 08:26:11 +01:00
parent 1dab7a05bb
commit cea2aeff10
10 changed files with 108 additions and 24 deletions

View File

@ -299,10 +299,14 @@ module SMESH
* \param mesh - TetraHedron mesh to create dual from
* \param meshName - a name of the new mesh
* \param adaptToShape - if True project boundary point on shape
* \param simplify - if True merge coplanar faces of a polyhedra
* \param eps - epislon tp define coplanar faces
*/
SMESH_Mesh CreateDualMesh(in SMESH_IDSource mesh,
in string meshName,
in boolean adaptToShape)
in boolean adaptToShape,
in boolean simplify,
in double eps)
raises ( SALOME::SALOME_Exception );
/*!

View File

@ -35,6 +35,7 @@
#include <QRadioButton>
#include <QButtonGroup>
#include <QGroupBox>
#include <QDoubleValidator>
#include <QFrame>
#include <QHBoxLayout>
#include <QGridLayout>
@ -61,6 +62,16 @@ SMESHGUI_CreateDualMeshDlg::SMESHGUI_CreateDualMeshDlg()
myProjShape = new QCheckBox(QString(tr("PROJ_SHAPE")), mainFrame());
myProjShape->toggle();
mySimplify = new QCheckBox(QString(tr("SIMPLIFY")), mainFrame());
mySimplify->toggle();
mySimpEps = new QLineEdit(mainFrame());
QDoubleValidator *validator = new QDoubleValidator(1e-16, 100, 1000, mySimpEps);
mySimpEps->setValidator(validator);
mySimpEps->setText("1e-4");
myWarning = new QLabel(QString("<b>%1</b>").arg(tr("NON_TETRA_MESH_WARNING")), mainFrame());
// Fill layout
@ -71,10 +82,12 @@ SMESHGUI_CreateDualMeshDlg::SMESHGUI_CreateDualMeshDlg()
aLay->addWidget( objectWg( 0, Label ), 0, 0 );
aLay->addWidget( objectWg( 0, Btn ), 0, 1 );
aLay->addWidget( objectWg( 0, Control ), 0, 2 );
aLay->addWidget( myWarning, 3, 0, 1, 3 );
aLay->addWidget( myMeshNameLabel, 1, 0 );
aLay->addWidget( myMeshName, 1, 2 );
aLay->addWidget( myProjShape, 2, 0 );
aLay->addWidget( myProjShape, 2, 0 );
aLay->addWidget( mySimplify, 3, 0 );
aLay->addWidget( mySimpEps, 3, 1 );
aLay->addWidget( myWarning, 4, 0, 1, 3 );
}
@ -93,4 +106,13 @@ void SMESHGUI_CreateDualMeshDlg::ShowWarning(bool toShow)
bool SMESHGUI_CreateDualMeshDlg::isWarningShown()
{
return myWarning->isVisible();
}
}
void SMESHGUI_CreateDualMeshDlg::DisplayEps(bool on)
{
std::cout << "DisplayEps" << on << std::endl;
if ( on )
mySimpEps->setEnabled(true);
else
mySimpEps->setDisabled(true);
}

View File

@ -48,10 +48,13 @@ public:
virtual ~SMESHGUI_CreateDualMeshDlg();
void ShowWarning(bool);
void DisplayEps(bool);
bool isWarningShown();
QLineEdit* myMeshName;
QCheckBox* myProjShape;
QCheckBox* mySimplify;
QLineEdit* mySimpEps;
signals:
void onClicked( int );

View File

@ -103,6 +103,7 @@ void SMESHGUI_CreateDualMeshOp::startOperation()
myDlg = new SMESHGUI_CreateDualMeshDlg( );
}
connect( myDlg, SIGNAL( onClicked( int ) ), SLOT( ConnectRadioButtons( int ) ) );
connect( myDlg->mySimplify, SIGNAL( toggled( bool ) ), SLOT( DisplayEps( bool ) ) );
myHelpFileName = "create_dual_mesh.html";
@ -229,9 +230,12 @@ bool SMESHGUI_CreateDualMeshOp::onApply()
SMESH::SMESH_Mesh_var newMesh;
QByteArray newMeshName=myDlg->myMeshName->text().toUtf8();
bool adapt_to_shape=myDlg->myProjShape->isChecked();
bool simplify=myDlg->mySimplify->isChecked();
double eps=myDlg->mySimpEps->text().toDouble();
std::cout << "eps" << eps << std::endl;
try
{
newMesh = gen->CreateDualMesh(mesh, newMeshName.constData(), adapt_to_shape);
newMesh = gen->CreateDualMesh(mesh, newMeshName.constData(), adapt_to_shape, simplify, eps);
if ( !newMesh->_is_nil() )
if ( _PTR(SObject) aSObject = SMESH::ObjectToSObject( newMesh ) )

View File

@ -5745,6 +5745,10 @@ Please specify it and try again</translation>
<source>PROJ_SHAPE</source>
<translation>Project boundary elements on shape</translation>
</message>
<message>
<source>SIMPLIFY</source>
<translation>Simplify polyhedrons</translation>
</message>
</context>
<context>
<name>SMESHGUI_ConvToQuadOp</name>
@ -7926,7 +7930,7 @@ It is impossible to read point coordinates from file</translation>
<source>2D_FROM_3D_ELEMENTS</source>
<translation>2D from 3D</translation>
</message>
</context>
</context>
<context>
<name>SMESHGUI_Make2DFrom3DDlg</name>
<message>

View File

@ -5751,6 +5751,10 @@ Sélectionner des éléments et essayer encore</translation>
<source>PROJ_SHAPE</source>
<translation>Projection des élements de bord sur la géométrie</translation>
</message>
<message>
<source>SIMPLIFY</source>
<translation>Simplification des polyèdres</translation>
</message>
</context>
<context>
<name>SMESHGUI_ConvToQuadOp</name>
@ -7952,7 +7956,7 @@ Il y a trop peu de points dans le fichier </translation>
<source>2D_FROM_3D_ELEMENTS</source>
<translation>Faces des éléments volumiques</translation>
</message>
</context>
</context>
<context>
<name>SMESHGUI_Make2DFrom3DDlg</name>
<message>

View File

@ -2897,7 +2897,10 @@ SMESH_Gen_i::ConcatenateCommon(const SMESH::ListOfIDSources& theMeshesArray,
SMESH::SMESH_Mesh_ptr SMESH_Gen_i::CreateDualMesh(SMESH::SMESH_IDSource_ptr mesh,
const char* meshName,
CORBA::Boolean adapt_to_shape)
CORBA::Boolean adapt_to_shape,
CORBA::Boolean simplify,
CORBA::Double eps_poly
)
{
Unexpect aCatch(SALOME_SalomeException);
@ -2930,17 +2933,28 @@ SMESH::SMESH_Mesh_ptr SMESH_Gen_i::CreateDualMesh(SMESH::SMESH_IDSource_ptr mesh
gstate = PyGILState_Ensure();
std::string ats;
// Converting arugments in string
std::string ats = "False";
if(adapt_to_shape)
ats = "True";
else
ats = "False";
std::string sp="False";
if(simplify)
sp = "True";
std::ostringstream ss;
ss << eps_poly;
std::string cmd="import salome.smesh.smesh_tools as smt\n";
cmd +="smt.smesh_create_dual_mesh(\"" + mesh_ior + "\", r\"" +
dual_mesh_file.string() + "\", mesh_name=\"" + mesh_name + "\", adapt_to_shape=" + ats + ")";
MESSAGE(cmd);
cmd +="smt.smesh_create_dual_mesh(\"" + mesh_ior + "\"" +
", r\"" + dual_mesh_file.string() + "\"" +
", mesh_name=\"" + mesh_name + "\"" +
", adapt_to_shape=" + ats +
", simplify_poly=" + sp +
", eps_poly=" + ss.str() + ")";
MESSAGE("Dual mesh python command" + cmd);
// Calling code in Python Interperter
PyObject *py_main = PyImport_AddModule("__main__");
PyObject *py_dict = PyModule_GetDict(py_main);
PyObject *local_dict = PyDict_New();

View File

@ -259,7 +259,9 @@ public:
// Create dual mesh of a tetrahedron mesh
SMESH::SMESH_Mesh_ptr CreateDualMesh(SMESH::SMESH_IDSource_ptr meshPart,
const char* meshName,
CORBA::Boolean adapt_to_shape);
CORBA::Boolean adapt_to_shape,
CORBA::Boolean simplify,
CORBA::Double eps);
// Copy a part of mesh
SMESH::SMESH_Mesh_ptr CopyMesh(SMESH::SMESH_IDSource_ptr meshPart,

View File

@ -789,7 +789,7 @@ class smeshBuilder( SMESH._objref_SMESH_Gen, object ):
aMesh = Mesh( self, self.geompyD, aSmeshMesh, name=name )
return aMesh
def CreateDualMesh( self, mesh, meshName, adaptToShape):
def CreateDualMesh( self, mesh, meshName="", adaptToShape=True, simplify=False, eps=1e-4):
"""
Create a dual of a mesh.
@ -798,14 +798,17 @@ class smeshBuilder( SMESH._objref_SMESH_Gen, object ):
:class:`mesh, <SMESH.SMESH_IDSource>`.
meshName: a name of the new mesh
adpatToShape: if true project boundary points on shape
adaptToShape: if true project boundary points on shape
simplify: if true will merge coplanar face of polyhedrons
eps: threshold to define if two face are coplanar
Returns:
an instance of class :class:`Mesh`
"""
if isinstance( mesh, Mesh ):
mesh = mesh.GetMesh()
dualMesh = SMESH._objref_SMESH_Gen.CreateDualMesh(self, mesh, meshName, adaptToShape)
dualMesh = SMESH._objref_SMESH_Gen.CreateDualMesh(self, mesh, meshName,
adaptToShape, simplify, eps)
return Mesh(self, self.geompyD, dualMesh)

View File

@ -1,5 +1,6 @@
#!/usr/bin/env python3
from os import environ
import salome
import medcoupling as mc
@ -15,7 +16,10 @@ smesh = smeshBuilder.New()
from salome.kernel.logger import Logger
logger = Logger("salome.smesh.smesh_tools")
logger.setLevel("WARNING")
if environ.get("SALOME_VERBOSE", "0") > "1":
logger.setLevel("DEBUG")
else:
logger.setLevel("WARNING")
# prefix for groups with internal usage
# i.e. used to transfer the faces and edges sub-shapes ids to the mesh
@ -114,7 +118,7 @@ def __deleteObj(theObj):
pass
def smesh_create_dual_mesh(mesh_ior, output_file, adapt_to_shape=True,
mesh_name="MESH"):
mesh_name="MESH", simplify_poly=False, eps_poly=1e-4):
""" Create a dual of the mesh in input_file into output_file
Args:
@ -131,6 +135,7 @@ def smesh_create_dual_mesh(mesh_ior, output_file, adapt_to_shape=True,
shape = mesh.GetShapeToMesh()
if adapt_to_shape:
logger.debug("Projecting on shape")
faces = geompy.SubShapeAll(shape, geompy.ShapeType["FACE"])
faces_ids = geompy.GetSubShapesIDs(shape, faces)
@ -173,17 +178,36 @@ def smesh_create_dual_mesh(mesh_ior, output_file, adapt_to_shape=True,
tetras = mc.MEDCoupling1SGTUMesh(tetras)
# Create the polyhedra from the tetrahedra (main goal of this function)
logger.debug("Computing dual mesh")
polyh = tetras.computeDualMesh()
umesh = polyh.buildUnstructured()
if (simplify_poly):
logger.debug("Simplifying polyhedrons")
umesh.simplifyPolyhedra(eps_poly)
logger.debug("Colinearize edges")
#umesh.colinearizeEdges(eps_poly)
bad_cells = umesh.arePolyhedronsNotCorrectlyOriented()
if not bad_cells.empty():
logger.debug("Reorienting polyhedrons")
try:
umesh.orientCorrectlyPolyhedrons()
except Exception as exp:
print("Could not reorient Polyhedron")
print(exp)
## Adding skin + transfering groups on faces from tetras mesh
mesh2d = polyh.buildUnstructured().computeSkin()
logger.debug("Computing Skin")
mesh2d = umesh.computeSkin()
mesh2d.setName(mesh_name)
polyh_coords = polyh.getCoords()
polyh_coords = umesh.getCoords()
treated_edges = []
mc_groups = []
logger.debug("Transferring groups")
for grp_name in mc_mesh_file.getGroupsOnSpecifiedLev(-1):
# This group is created by the export
if grp_name == "Group_Of_All_Faces":
@ -238,8 +262,8 @@ def smesh_create_dual_mesh(mesh_ior, output_file, adapt_to_shape=True,
logger.debug("Creating file with mesh: "+mesh_name)
myfile = mc.MEDFileUMesh()
myfile.setName(mesh_name)
polyh.setName(mesh_name)
myfile.setMeshAtLevel(0, polyh)
umesh.setName(mesh_name)
myfile.setMeshAtLevel(0, umesh)
myfile.setMeshAtLevel(-1, mesh2d)
for group in mc_groups: