From 4971be7e3503d22d2fcc5aa399d84c713f8e0466 Mon Sep 17 00:00:00 2001 From: eap Date: Tue, 23 Aug 2016 13:37:38 +0300 Subject: [PATCH] 23308: [EDF] Re-implement DISTENE meshing plugins to use libraries instead of executables --- CMakeLists.txt | 14 +- resources/GHS3DPRLPlugin.xml | 3 +- src/GHS3DPRLPlugin/CMakeLists.txt | 4 + .../GHS3DPRLPlugin_GHS3DPRL.cxx | 270 ++-- src/GHS3DPRLPlugin/MG_TetraHPC_API.cxx | 1181 +++++++++++++++++ src/GHS3DPRLPlugin/MG_TetraHPC_API.hxx | 86 ++ .../GHS3DPRLPluginGUI_HypothesisCreator.cxx | 1 + src/tepal2med/tetrahpc2med.cxx | 19 +- 8 files changed, 1398 insertions(+), 180 deletions(-) create mode 100644 src/GHS3DPRLPlugin/MG_TetraHPC_API.cxx create mode 100644 src/GHS3DPRLPlugin/MG_TetraHPC_API.hxx diff --git a/CMakeLists.txt b/CMakeLists.txt index 4f84c12..e921bcf 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -67,6 +67,8 @@ SET(BUILD_SHARED_LIBS TRUE) # ============ OPTION(SALOME_BUILD_TESTS "Build SALOME tests" ON) OPTION(SALOME_BUILD_DOC "Generate SALOME GHS3DPRLPLUGIN documentation" ON) +OPTION(SALOME_USE_MG_LIBS "Use MeshGems libraries" ON) +MARK_AS_ADVANCED(SALOME_USE_MG_LIBS) IF(SALOME_BUILD_TESTS) ENABLE_TESTING() @@ -164,9 +166,18 @@ IF(EXISTS ${SMESH_ROOT_DIR}) ELSE(EXISTS ${SMESH_ROOT_DIR}) MESSAGE(FATAL_ERROR "We absolutely need a Salome SMESH, please define SMESH_ROOT_DIR") ENDIF(EXISTS ${SMESH_ROOT_DIR}) + # MEDFile FIND_PACKAGE(SalomeMEDFile REQUIRED) +# Find MESHGEMS +# ============= +IF(SALOME_USE_MG_LIBS) + FIND_PACKAGE(SalomeMESHGEMS) + SALOME_LOG_OPTIONAL_PACKAGE(MESHGEMS SALOME_USE_MG_LIBS) + ADD_DEFINITIONS(-DUSE_MG_LIBS) +ENDIF(SALOME_USE_MG_LIBS) + # Detection summary: SALOME_PACKAGE_REPORT_AND_CHECK() @@ -256,11 +267,12 @@ EXPORT(TARGETS ${_${PROJECT_NAME}_exposed_targets} # Ensure the variables are always defined for the configure: SET(SMESH_ROOT_DIR "${SMESH_ROOT_DIR}") +SET(MESHGEMS_ROOT_DIR "${MESHGEMS_ROOT_DIR}") SET(CONF_INCLUDE_DIRS "${PROJECT_SOURCE_DIR}/include" "${PROJECT_BINARY_DIR}/include") # Build variables that will be expanded when configuring SalomeConfig.cmake: -# SALOME_CONFIGURE_PREPARE() #For use in the future +SALOME_CONFIGURE_PREPARE(MESHGEMS) CONFIGURE_PACKAGE_CONFIG_FILE(${PROJECT_NAME}Config.cmake.in ${PROJECT_BINARY_DIR}/${PROJECT_NAME}Config.cmake diff --git a/resources/GHS3DPRLPlugin.xml b/resources/GHS3DPRLPlugin.xml index dd76e94..e45e20a 100755 --- a/resources/GHS3DPRLPlugin.xml +++ b/resources/GHS3DPRLPlugin.xml @@ -40,9 +40,10 @@ MG-Tetra Parallel=Tetrahedron(algo=smeshBuilder.MG_Tetra_Parallel) diff --git a/src/GHS3DPRLPlugin/CMakeLists.txt b/src/GHS3DPRLPlugin/CMakeLists.txt index 4f2fe3b..a4a5e33 100644 --- a/src/GHS3DPRLPlugin/CMakeLists.txt +++ b/src/GHS3DPRLPlugin/CMakeLists.txt @@ -24,6 +24,7 @@ INCLUDE_DIRECTORIES( ${GEOM_INCLUDE_DIRS} ${CAS_INCLUDE_DIRS} ${VTK_INCLUDE_DIRS} + ${MESHGEMS_INCLUDE_DIRS} ${SMESH_INCLUDE_DIRS} ${OMNIORB_INCLUDE_DIR} ${Boost_INCLUDE_DIRS} @@ -46,6 +47,7 @@ SET(_link_LIBRARIES ${CAS_TKGeomBase} ${CAS_TKGeomAlgo} ${CAS_TKCDF} + ${MESHGEMS_TETRA_HPC_LIBRARY} ${SMESH_SMESHimpl} ${SMESH_SMESHEngine} ${SMESH_SMESHDS} @@ -69,6 +71,7 @@ SET(GHS3DPRLEngine_HEADERS GHS3DPRLPlugin_GHS3DPRL_i.hxx GHS3DPRLPlugin_Hypothesis.hxx GHS3DPRLPlugin_Hypothesis_i.hxx + MG_TetraHPC_API.hxx ) # --- sources --- @@ -85,6 +88,7 @@ SET(GHS3DPRLEngine_SOURCES GHS3DPRLPlugin_Hypothesis_i.hxx GHS3DPRLPlugin_Hypothesis_i.cxx GHS3DPRLPlugin_i.cxx + MG_TetraHPC_API.cxx ) # --- scripts --- diff --git a/src/GHS3DPRLPlugin/GHS3DPRLPlugin_GHS3DPRL.cxx b/src/GHS3DPRLPlugin/GHS3DPRLPlugin_GHS3DPRL.cxx index 9b75f7b..20d122d 100755 --- a/src/GHS3DPRLPlugin/GHS3DPRLPlugin_GHS3DPRL.cxx +++ b/src/GHS3DPRLPlugin/GHS3DPRLPlugin_GHS3DPRL.cxx @@ -24,38 +24,31 @@ // #include "GHS3DPRLPlugin_GHS3DPRL.hxx" #include "GHS3DPRLPlugin_Hypothesis.hxx" +#include "MG_TetraHPC_API.hxx" #include #include +#include #include -#include -#include - #include "utilities.h" -#ifndef WIN32 -#include -#endif - -#ifdef _DEBUG_ -#define DUMP(txt) \ -// cout << txt -#else -#define DUMP(txt) -#endif - #include #include #include +#include #include #include +#include #include #include #include #include +#define GMFVERSION GmfDouble +#define GMFDIMENSION 3 + using namespace std; static void removeFile( const TCollection_AsciiString& fileName ) @@ -75,6 +68,7 @@ GHS3DPRLPlugin_GHS3DPRL::GHS3DPRLPlugin_GHS3DPRL(int hypId, int studyId, SMESH_G MESSAGE("GHS3DPRLPlugin_GHS3DPRL::GHS3DPRLPlugin_GHS3DPRL"); _name = "MG-Tetra Parallel"; _shapeType = (1 << TopAbs_SHELL) | (1 << TopAbs_SOLID);// 1 bit /shape type + _onlyUnaryInput = false; // Compute() will be called on a compound of solids _countSubMesh=0; _nodeRefNumber=0; _compatibleHypothesis.push_back(GHS3DPRLPlugin_Hypothesis::GetHypType()); @@ -102,8 +96,8 @@ bool GHS3DPRLPlugin_GHS3DPRL::CheckHypothesis int nbHyp = hyps.size(); if (!nbHyp) { - aStatus = SMESH_Hypothesis::HYP_OK; - return true; // can work with no hypothesis + aStatus = SMESH_Hypothesis::HYP_MISSING; + return false; // can't work with no hypothesis } itl = hyps.begin(); @@ -122,124 +116,6 @@ bool GHS3DPRLPlugin_GHS3DPRL::CheckHypothesis return aStatus == SMESH_Hypothesis::HYP_OK; } -//======================================================================= -// static bool writeGHS3DPRLFiles (const TCollection_AsciiString & GHS3DPRL_In, -// SMESHDS_Mesh * theMesh, -// map & theSmdsToGHS3DPRLIdMap, -// map & theGHS3DPRLIdToNodeMap) -// { -// bool Ok; -// int ifam=0; -// TCollection_AsciiString namefile(GHS3DPRL_In); -// namefile+=".points"; -// removeFile(namefile); -// ofstream theFile; -// theFile.open(namefile.ToCString(),ios::out); -// #ifdef WIN32 -// Ok = theFile.is_open(); -// #else -// Ok=theFile.rdbuf()->is_open(); -// #endif -// if (!Ok) -// { -// INFOS("Can't write into "<NbNodes(); -// int nbFaces=theMesh->NbFaces(); //triangles or quadrangles -// const char* space=" "; -// //const int dummyint=1; //nrs,nsd,refnum=1 (for wrap) - -// // Writing SMESH points into GHS3DPRL File.points -// theFile<nodesIterator(); -// //int ifam=100;//test famille -// theFile.precision(15); theFile.setf(ios::scientific,ios::floatfield); -// //cout<<"set precision 15 on float\n"; -// while (itOnNode->more()) -// { -// node_2 = itOnNode->next(); -// theSmdsToGHS3DPRLIdMap.insert(map ::value_type(node_2->GetID(),aSmdsNodeID)); -// theGHS3DPRLIdToNodeMap.insert(map ::value_type(aSmdsNodeID,node_2)); -// theFile<X()<Y()<Z()<is_open(); -// #endif -// if (!Ok) -// { -// INFOS("Can't write into "<::const_iterator itOnSmdsNode; -// SMDS_ElemIteratorPtr itOnFaceNode; -// SMDS_FaceIteratorPtr itOnSmdsFace = theMesh->facesIterator(); -// long nbNoTriangles=0; -// int ifaces=0; -// //ifam=300; -// while (itOnSmdsFace->more()) -// { -// aFace=itOnSmdsFace->next(); -// itOnFaceNode=aFace->nodesIterator(); -// const int nbNodes=aFace->NbNodes(); -// if (nbNodes!=3) nbNoTriangles++; -// ifaces++; -// theFile<more()) -// { -// aSmdsNodeID=itOnFaceNode->next()->GetID(); -// itOnSmdsNode=theSmdsToGHS3DPRLIdMap.find(aSmdsNodeID); -// ASSERT(itOnSmdsNode!=theSmdsToGHS3DPRLIdMap.end()); -// theFile<GmfOpenMesh( theFile, GmfWrite, GMFVERSION, GMFDIMENSION); + + // nodes + int iN = 0, nbNodes = theMeshDS->NbNodes(); + theTetraInput->GmfSetKwd( meshID, GmfVertices, nbNodes ); + std::map< const SMDS_MeshNode*, int, TIDCompare > node2IdMap; + SMDS_NodeIteratorPtr nodeIt = theMeshDS->nodesIterator(); + SMESH_TNodeXYZ n; + while ( nodeIt->more() ) + { + n.Set( nodeIt->next() ); + theTetraInput->GmfSetLin( meshID, GmfVertices, n.X(), n.Y(), n.Z(), n._node->getshapeId() ); + node2IdMap.insert( node2IdMap.end(), std::make_pair( n._node, ++iN )); + } + + // triangles + SMDS_ElemIteratorPtr elemIt = theMeshDS->elementGeomIterator( SMDSGeom_TRIANGLE ); + if ( elemIt->more() ) + { + int nbTria = theMeshDS->GetMeshInfo().NbElements( SMDSGeom_TRIANGLE ); + theTetraInput->GmfSetKwd(meshID, GmfTriangles, nbTria ); + for ( int gmfID = 1; elemIt->more(); ++gmfID ) + { + const SMDS_MeshElement* tria = elemIt->next(); + theTetraInput->GmfSetLin(meshID, GmfTriangles, + node2IdMap[ tria->GetNode( 0 )], + node2IdMap[ tria->GetNode( 1 )], + node2IdMap[ tria->GetNode( 2 )], + tria->getshapeId() ); + } + } + theTetraInput->GmfCloseMesh( meshID ); +} + //============================================================================= // Here we are going to use the GHS3DPRL mesher for tetra-hpc (formerly tepal in v3 (2014)) -bool GHS3DPRLPlugin_GHS3DPRL::Compute(SMESH_Mesh& theMesh, +bool GHS3DPRLPlugin_GHS3DPRL::Compute(SMESH_Mesh& theMesh, const TopoDS_Shape& theShape) { bool Ok=false; TCollection_AsciiString pluginerror("ghs3dprl: "); SMESHDS_Mesh* meshDS = theMesh.GetMeshDS(); - //cout<<"GetMeshDS done\n"; - if (_countSubMesh==0){ - MESSAGE("GHS3DPRLPlugin_GHS3DPRL::Compute for tetra-hpc"); - _countTotal=0; - TopExp_Explorer expf(meshDS->ShapeToMesh(), TopAbs_SOLID); - for ( ; expf.More(); expf.Next() ) _countTotal++; - } - _countSubMesh++; - //cout<<"Compute _countSubMesh "<<_countSubMesh< avoid warning message - //med_idt fid=MEDouvrir((const char *)fileskinmed.ToCString(),MED_CREATION); - //med_err ret=MEDfermer(fid); - //fileskinmed=fileskinmed + "cp /home/wambeke/empty.med "+ path + "GHS3DPRL_skin.med"; - //system( fileskinmed.ToCString() ); + + MG_TetraHPC_API mgTetraHPC( _computeCanceled, _progress ); + bool useLib = ( mgTetraHPC.IsLibrary() && !_Background && _Multithread ); + if ( !useLib ) + mgTetraHPC.SetUseExecutable(); + + exportGMF( &mgTetraHPC, fileskinmesh.ToCString(), meshDS ); + + if ( useLib ) + { + TCollection_AsciiString cmd = TCollection_AsciiString("mg-tetra_hpc.exe") + + " --number_of_subdomains=" + NbPart + + " --gradation=" + Gradation + + " --min_size=" + MinSize + + " --max_size=" + MaxSize + + " --verbose=3" + + " --out=" + GHS3DPRL_Out_Mesh + + " " + _AdvOptions.c_str(); + + cout << endl + << " Run mg-tetra_hpc as library. Creating a mesh file " << GHS3DPRL_Out_Mesh << endl + << " Creating a log file : " << logFileName << endl << endl; + mgTetraHPC.SetLogFile( logFileName.ToCString() ); + + mgTetraHPC.Compute( cmd.ToCString() ); + + std::string log = mgTetraHPC.GetLog(); + if ( log.find(" Dlim " ) != std::string::npos || + log.find(" license ") != std::string::npos ) + return error("License problem"); + + // set --launchtetra=no + int yesPos = run_GHS3DPRL.Search("launchtetra") + sizeof("launchtetra"); + run_GHS3DPRL.SetValue( yesPos+0, 'n' ); + run_GHS3DPRL.SetValue( yesPos+1, 'o' ); + run_GHS3DPRL.SetValue( yesPos+2, ' ' ); + } + else + { + cout<<" Write input file for mg-tetra_hpc "< +#include +#include + +#include +#include +#include + +#ifdef USE_MG_LIBS + +extern "C"{ +#include +#include +} + +struct MG_TetraHPC_API::LibData +{ + // MG objects + context_t * _context; + tetra_hpc_session_t * _session; + mesh_t * _tria_mesh; + sizemap_t * _sizemap; + mesh_t * _tetra_mesh; + + // data to pass to MG + std::vector _xyz; + std::vector _nodeSize; // required nodes + std::vector _edgeNodes; + int _nbRequiredEdges; + std::vector _triaNodes; + int _nbRequiredTria; + + int _count; + volatile bool& _cancelled_flag; + std::string _errorStr; + double& _progress; + + LibData( volatile bool & cancelled_flag, double& progress ) + : _context(0), _session(0), _tria_mesh(0), _sizemap(0), _tetra_mesh(0), + _nbRequiredEdges(0), _nbRequiredTria(0), + _cancelled_flag( cancelled_flag ), _progress( progress ) + { + } + // methods setting callbacks implemented after callback definitions + void Init(); + bool Compute( const std::string& outFile ); + + ~LibData() + { + if ( _tetra_mesh ) + tetra_hpc_regain_mesh( _session, _tetra_mesh ); + if ( _session ) + tetra_hpc_session_delete( _session ); + if ( _tria_mesh ) + mesh_delete( _tria_mesh ); + if ( _sizemap ) + sizemap_delete( _sizemap ); + if ( _context ) + context_delete( _context ); + + _tetra_mesh = 0; + _session = 0; + _tria_mesh = 0; + _sizemap = 0; + _context = 0; + } + + void AddError( const char *txt ) + { + if ( txt ) + _errorStr += txt; + } + + const std::string& GetErrors() + { + return _errorStr; + } + + void MG_Error(const char* txt="") + { + SMESH_Comment msg("\nMeshGems error. "); + msg << txt << "\n"; + AddError( msg.c_str() ); + } + + bool SetParam( const std::string& param, const std::string& value ) + { + status_t ret = tetra_hpc_set_param( _session, param.c_str(), value.c_str() ); +#ifdef _DEBUG_ + //std::cout << param << " = " << value << std::endl; +#endif + return ( ret == STATUS_OK ); + } + + bool Cancelled() + { + return _cancelled_flag; + } + + int ReadNbSubDomains() + { + integer nb = 0; + status_t ret = mesh_get_subdomain_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_subdomain_count problem"); + return nb; + } + + int ReadNbNodes() + { + integer nb = 0; + status_t ret = mesh_get_vertex_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_vertex_count problem"); + return nb; + } + + int ReadNbEdges() + { + integer nb = 0; + status_t ret = mesh_get_edge_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_edge_count problem"); + return nb; + } + + int ReadNbTria() + { + integer nb = 0; + status_t ret = mesh_get_triangle_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_triangle_count problem"); + return nb; + } + + int ReadNbQuads() + { + integer nb = 0; + status_t ret = mesh_get_quadrangle_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_quadrangle_count problem"); + return nb; + } + + int ReadNbTetra() + { + integer nb = 0; + status_t ret = mesh_get_tetrahedron_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_tetrahedron_count problem"); + return nb; + } + + int ReadNbHexa() + { + integer nb = 0; + status_t ret = mesh_get_hexahedron_count( _tetra_mesh, & nb ); + + if ( ret != STATUS_OK ) MG_Error("mesh_get_hexahedron_count problem"); + return nb; + } + + void ResetCounter() + { + _count = 1; + } + + void ReadSubDomain( int* nbNodes, int* faceInd, int* ori, int* domain ) + { + integer tag, seed_type, seed_idx, seed_orientation; + status_t ret = mesh_get_subdomain_description( _tetra_mesh, _count, + &tag, &seed_type, &seed_idx, &seed_orientation); + + if ( ret != STATUS_OK ) MG_Error( "unable to get a sub-domain description"); + + *nbNodes = 3; + *faceInd = seed_idx; + *domain = tag; + *ori = seed_orientation; + + ++_count; + } + void ReadNodeXYZ( double* x, double* y, double *z, int* /*domain*/ ) + { + real coo[3]; + status_t ret = mesh_get_vertex_coordinates( _tetra_mesh, _count, coo ); + if ( ret != STATUS_OK ) MG_Error( "unable to get resulting vertices" ); + + *x = coo[0]; + *y = coo[1]; + *z = coo[2]; + + ++_count; + } + + void ReadEdgeNodes( int* node1, int* node2, int* domain ) + { + integer vtx[2], tag; + status_t ret = mesh_get_edge_vertices( _tetra_mesh, _count, vtx); + if (ret != STATUS_OK) MG_Error( "unable to get resulting edge" ); + + *node1 = vtx[0]; + *node2 = vtx[1]; + + ret = mesh_get_edge_tag( _tetra_mesh, _count, &tag ); + if (ret != STATUS_OK) MG_Error( "unable to get resulting edge tag" ); + + *domain = tag; + + ++_count; + } + + void ReadTriaNodes( int* node1, int* node2, int* node3, int* domain ) + { + integer vtx[3], tag; + status_t ret = mesh_get_triangle_vertices( _tetra_mesh, _count, vtx); + if (ret != STATUS_OK) MG_Error( "unable to get resulting triangle" ); + + *node1 = vtx[0]; + *node2 = vtx[1]; + *node3 = vtx[2]; + + ret = mesh_get_triangle_tag( _tetra_mesh, _count, &tag ); + if (ret != STATUS_OK) MG_Error( "unable to get resulting triangle tag" ); + + *domain = tag; + + ++_count; + } + + void ReadQuadNodes( int* node1, int* node2, int* node3, int* node4, int* domain ) + { + integer vtx[4], tag; + status_t ret = mesh_get_quadrangle_vertices( _tetra_mesh, _count, vtx); + if (ret != STATUS_OK) MG_Error( "unable to get resulting quadrangle" ); + + *node1 = vtx[0]; + *node2 = vtx[1]; + *node3 = vtx[2]; + *node4 = vtx[3]; + + ret = mesh_get_quadrangle_tag( _tetra_mesh, _count, &tag ); + if (ret != STATUS_OK) MG_Error( "unable to get resulting quadrangle tag" ); + + *domain = tag; + + ++_count; + } + + void ReadTetraNodes( int* node1, int* node2, int* node3, int* node4, int* domain ) + { + integer vtx[4], tag; + status_t ret = mesh_get_tetrahedron_vertices( _tetra_mesh, _count, vtx); + if (ret != STATUS_OK) MG_Error( "unable to get resulting tetrahedron" ); + + *node1 = vtx[0]; + *node2 = vtx[1]; + *node3 = vtx[2]; + *node4 = vtx[3]; + + ret = mesh_get_tetrahedron_tag( _tetra_mesh, _count, &tag ); + if (ret != STATUS_OK) MG_Error( "unable to get resulting tetrahedron tag" ); + + *domain = tag; + + ++_count; + } + + void ReadHexaNodes( int* node1, int* node2, int* node3, int* node4, + int* node5, int* node6, int* node7, int* node8, int* domain ) + { + integer vtx[8], tag; + status_t ret = mesh_get_hexahedron_vertices( _tetra_mesh, _count, vtx); + if (ret != STATUS_OK) MG_Error( "unable to get resulting hexahedron" ); + + *node1 = vtx[0]; + *node2 = vtx[1]; + *node3 = vtx[2]; + *node4 = vtx[3]; + *node5 = vtx[4]; + *node6 = vtx[5]; + *node7 = vtx[6]; + *node8 = vtx[7]; + + ret = mesh_get_hexahedron_tag( _tetra_mesh, _count, &tag ); + if (ret != STATUS_OK) MG_Error( "unable to get resulting hexahedron tag" ); + + *domain = tag; + + ++_count; + } + + void SetNbVertices( int nb ) + { + _xyz.reserve( _xyz.capacity() + nb ); + } + + void SetNbEdges( int nb ) + { + _edgeNodes.reserve( nb * 2 ); + } + + void SetNbTria( int nb ) + { + _triaNodes.reserve( nb * 3 ); + } + + void SetNbReqVertices( int nb ) + { + _nodeSize.reserve( nb ); + } + + void SetNbReqEdges( int nb ) + { + _nbRequiredEdges = nb; + } + + void SetNbReqTria( int nb ) + { + _nbRequiredTria = nb; + } + + void AddNode( double x, double y, double z, int domain ) + { + _xyz.push_back( x ); + _xyz.push_back( y ); + _xyz.push_back( z ); + } + + void AddSizeAtNode( double size ) + { + _nodeSize.push_back( size ); + } + + void AddEdgeNodes( int node1, int node2, int domain ) + { + _edgeNodes.push_back( node1 ); + _edgeNodes.push_back( node2 ); + } + + void AddTriaNodes( int node1, int node2, int node3, int domain ) + { + _triaNodes.push_back( node1 ); + _triaNodes.push_back( node2 ); + _triaNodes.push_back( node3 ); + } + + int NbNodes() + { + return _xyz.size() / 3; + } + + double* NodeCoord( int iNode ) + { + return & _xyz[ iNode * 3 ]; + } + + int NbEdges() + { + return _edgeNodes.size() / 2; + } + + int* GetEdgeNodes( int iEdge ) + { + return & _edgeNodes[ iEdge * 2 ]; + } + + int NbTriangles() + { + return _triaNodes.size() / 3; + } + + int * GetTriaNodes( int iTria ) + { + return & _triaNodes[ iTria * 3 ]; + } + + int IsVertexRequired( int iNode ) + { + return ! ( iNode < int( _xyz.size() - _nodeSize.size() )); + } + + double GetSizeAtVertex( int iNode ) + { + return IsVertexRequired( iNode ) ? _nodeSize[ iNode - _xyz.size() + _nodeSize.size() ] : 0.; + } +}; + +namespace // functions called by MG library to exchange with the application +{ + status_t get_vertex_count(integer * nbvtx, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + *nbvtx = data->NbNodes(); + + return STATUS_OK; + } + + status_t get_vertex_coordinates(integer ivtx, real * xyz, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + double* coord = data->NodeCoord( ivtx-1 ); + for (int j = 0; j < 3; j++) + xyz[j] = coord[j]; + + return STATUS_OK; + } + status_t get_edge_count(integer * nbedge, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + *nbedge = data->NbEdges(); + + return STATUS_OK; + } + + status_t get_edge_vertices(integer iedge, integer * vedge, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + int* nodes = data->GetEdgeNodes( iedge-1 ); + vedge[0] = nodes[0]; + vedge[1] = nodes[1]; + + return STATUS_OK; + } + + status_t get_triangle_count(integer * nbtri, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + *nbtri = data->NbTriangles(); + + return STATUS_OK; + } + + status_t get_triangle_vertices(integer itri, integer * vtri, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + int* nodes = data->GetTriaNodes( itri-1 ); + vtri[0] = nodes[0]; + vtri[1] = nodes[1]; + vtri[2] = nodes[2]; + + return STATUS_OK; + } + + // status_t get_triangle_extra_vertices(integer itri, integer * typetri, + // integer * evtri, void *user_data) + // { + // int j; + // MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + + // if (1) { + // /* We want to describe a linear "3 nodes" triangle */ + // *typetri = MESHGEMS_MESH_ELEMENT_TYPE_TRIA3; + // } else { + // /* We want to describe a quadratic "6 nodes" triangle */ + // *typetri = MESHGEMS_MESH_ELEMENT_TYPE_TRIA6; + // for (j = 0; j < 3; j++) + // evtri[j] = 0; /* the j'th quadratic vertex index of the itri'th triangle */ + // } + + // return STATUS_OK; + // } + + // status_t get_tetrahedron_count(integer * nbtetra, void *user_data) + // { + // MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + + // *nbtetra = 0; /* the number of tetra in your input mesh (0 if you describe a surface mesh) */ + + // return STATUS_OK; + // } + + // status_t get_tetrahedron_vertices(integer itetra, integer * vtetra, + // void *user_data) + // { + // int j; + // MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + + // for (j = 0; j < 4; j++) + // vtetra[j] = 0; /* the j'th vertex index of the itetra'th tetrahedron */ + + // return STATUS_OK; + // } + + status_t get_vertex_required_property(integer ivtx, integer * rvtx, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + *rvtx = data->IsVertexRequired( ivtx - 1 ); + + return STATUS_OK; + } + + // status_t get_vertex_weight(integer ivtx, real * wvtx, void *user_data) + // { + // MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + // *wvtx = data->GetSizeAtVertex( ivtx - 1 ); + + // return STATUS_OK; + // } + + status_t my_message_cb(message_t * msg, void *user_data) + { + char *desc; + message_get_description(msg, &desc); + + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + data->AddError( desc ); + +#ifdef _DEBUG_ + //std::cout << desc << std::endl; +#endif + + return STATUS_OK; + } + + status_t my_interrupt_callback(integer *interrupt_status, void *user_data) + { + MG_TetraHPC_API::LibData* data = (MG_TetraHPC_API::LibData *) user_data; + *interrupt_status = ( data->Cancelled() ? INTERRUPT_STOP : INTERRUPT_CONTINUE ); + + //std::cout << "INTERRUPT_STOP" << std::endl; + + + return STATUS_OK; + } + +} // end namespace + + +void MG_TetraHPC_API::LibData::Init() +{ + status_t ret; + + // Create the meshgems working context + _context = context_new(); + if ( !_context ) MG_Error( "unable to create a new context" ); + + // Set the message callback for the _context. + ret = context_set_message_callback( _context, my_message_cb, this ); + if ( ret != STATUS_OK ) MG_Error("in context_set_message_callback"); + + // Create the structure holding the callbacks giving access to triangle mesh + _tria_mesh = mesh_new( _context ); + if ( !_tria_mesh ) MG_Error("unable to create a new mesh"); + + // Set callbacks to provide triangle mesh data + mesh_set_get_vertex_count( _tria_mesh, get_vertex_count, this ); + mesh_set_get_vertex_coordinates( _tria_mesh, get_vertex_coordinates, this ); + mesh_set_get_vertex_required_property( _tria_mesh, get_vertex_required_property, this ); + mesh_set_get_edge_count( _tria_mesh, get_edge_count, this); + mesh_set_get_edge_vertices( _tria_mesh, get_edge_vertices, this ); + mesh_set_get_triangle_count( _tria_mesh, get_triangle_count, this ); + mesh_set_get_triangle_vertices( _tria_mesh, get_triangle_vertices, this ); + + // Create a tetra session + _session = tetra_hpc_session_new( _context ); + if ( !_session ) MG_Error( "unable to create a new tetra_hpc session"); + + ret = tetra_hpc_set_interrupt_callback( _session, my_interrupt_callback, this ); + if ( ret != STATUS_OK ) MG_Error("in tetra_set_interrupt_callback"); + +} + +bool MG_TetraHPC_API::LibData::Compute( const std::string& outFile ) +{ + // Set surface mesh + status_t ret = tetra_hpc_set_input_mesh( _session, _tria_mesh ); + if ( ret != STATUS_OK ) MG_Error( "unable to set surface mesh"); + + // // Set a sizemap + // if ( !_nodeSize.empty() ) + // { + // _sizemap = meshgems_sizemap_new( _tria_mesh, meshgems_sizemap_type_iso_mesh_vertex, + // (void*) &get_vertex_weight, this ); + // if ( !_sizemap ) MG_Error("unable to create a new sizemap"); + + // ret = tetra_hpc_set_sizemap( _session, _sizemap ); + // if ( ret != STATUS_OK ) MG_Error( "unable to set sizemap"); + // } + + ////////////////////////////////////////////////////////////////////////////////////////// + // const char* file = "/tmp/ghs3d_IN.mesh"; + // mesh_write_mesh( _tria_mesh,file); + // std::cout << std::endl << std::endl << "Write " << file << std::endl << std::endl << std::endl; + + ret = tetra_hpc_mesh( _session ); + if ( ret != STATUS_OK ) return false; + + ret = tetra_hpc_get_mesh( _session, &_tetra_mesh); + if (ret != STATUS_OK) MG_Error( "unable to get resulting mesh"); + + mesh_write_mesh( _tetra_mesh, outFile.c_str() ); + + return true; +} + + +#endif // ifdef USE_MG_LIBS + + +//================================================================================ +/*! + * \brief Constructor + */ +//================================================================================ + +MG_TetraHPC_API::MG_TetraHPC_API(volatile bool& cancelled_flag, double& progress) +{ +#ifdef USE_MG_LIBS + _useLib = true; + _libData = new LibData( cancelled_flag, progress ); + _libData->Init(); +#endif + if ( getenv("MG_TetraHPC_USE_EXE")) + _useLib = false; +} + +//================================================================================ +/*! + * \brief Destructor + */ +//================================================================================ + +MG_TetraHPC_API::~MG_TetraHPC_API() +{ +#ifdef USE_MG_LIBS + delete _libData; + _libData = 0; +#endif + std::set::iterator id = _openFiles.begin(); + for ( ; id != _openFiles.end(); ++id ) + ::GmfCloseMesh( *id ); + _openFiles.clear(); +} + +//================================================================================ +/*! + * \brief Return the way of MG usage + */ +//================================================================================ + +bool MG_TetraHPC_API::IsLibrary() +{ + return _useLib; +} + +//================================================================================ +/*! + * \brief Switch to usage of MG-Tetra executable + */ +//================================================================================ + +void MG_TetraHPC_API::SetUseExecutable() +{ + _useLib = false; +} + +//================================================================================ +/*! + * \brief Compute the tetra mesh + * \param [in] cmdLine - a command to run mg_tetra.exe + * \return bool - Ok or not + */ +//================================================================================ + +bool MG_TetraHPC_API::Compute( const std::string& cmdLine ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + + // split cmdLine + std::istringstream strm( cmdLine ); + std::istream_iterator sIt( strm ), sEnd; + std::vector< std::string > args( sIt, sEnd ); + + std::string outFile; + + // set parameters + std::string arg, param, value; + for ( size_t i = 1; i < args.size(); ++i ) + { + // look for a param name; it starts from "-" + arg = args[i]; + if ( arg.size() < 2 || arg[0] != '-') + continue; + while ( arg[0] == '-') + arg = arg.substr( 1 ); + + size_t eqPos = arg.find('='); + if ( eqPos != std::string::npos ) + { + param = arg.substr( 0, eqPos ); + value = arg.substr( eqPos+1 ); + } + else + { + param = arg; + value = ""; + } + if ( param == "out" ) + { + outFile = value; + continue; + } + while ( i+1 < args.size() && args[i+1][0] != '-' ) + { + if ( !value.empty() ) value += " "; + value += args[++i]; + } + if ( !_libData->SetParam( param, value )) + std::cout << "Warning: wrong param: '" << param <<"' = '" << value << "'" << std::endl; + } + + // compute + return _libData->Compute( outFile ); +#endif + } + + // Run library ONLY + + // int err = system( cmdLine.c_str() ); // run + + // if ( err ) + // errStr = SMESH_Comment("system(mg-tetra.exe ...) command failed with error: ") + // << strerror( errno ); + + // GetLog(); // write a log file + // _logFile = ""; // not to write it again + + return false; +} + +//================================================================================ +/*! + * \brief Prepare for reading a mesh data + */ +//================================================================================ + +int MG_TetraHPC_API::GmfOpenMesh(const char* theFile, int rdOrWr, int * ver, int * dim) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + return 1; +#endif + } + int id = ::GmfOpenMesh(theFile, rdOrWr, ver, dim ); + _openFiles.insert( id ); + return id; +} + +//================================================================================ +/*! + * \brief Return nb of entities + */ +//================================================================================ + +int MG_TetraHPC_API::GmfStatKwd( int iMesh, GmfKwdCod what ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + switch ( what ) + { + case GmfSubDomainFromGeom: return _libData->ReadNbSubDomains(); + case GmfVertices: return _libData->ReadNbNodes(); + case GmfEdges: return _libData->ReadNbEdges(); + case GmfTriangles: return _libData->ReadNbTria(); + case GmfQuadrilaterals: return _libData->ReadNbQuads(); + case GmfTetrahedra: return _libData->ReadNbTetra(); + case GmfHexahedra: return _libData->ReadNbHexa(); + default: return 0; + } + return 0; +#endif + } + return ::GmfStatKwd( iMesh, what ); +} + +//================================================================================ +/*! + * \brief Prepare for reading some data + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGotoKwd( int iMesh, GmfKwdCod what ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ResetCounter(); + return; +#endif + } + ::GmfGotoKwd( iMesh, what ); +} + +//================================================================================ +/*! + * \brief Return index of a domain identified by a triangle normal + * \param [in] iMesh - mesh file index + * \param [in] what - must be GmfSubDomainFromGeom + * \param [out] nbNodes - nb nodes in a face + * \param [out] faceInd - face index + * \param [out] ori - face orientation + * \param [out] domain - domain index + * \param [in] dummy - an artificial param used to discriminate from GmfGetLin() reading + * a triangle + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin( int iMesh, GmfKwdCod what, int* nbNodes, int* faceInd, int* ori, int* domain, int dummy ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ReadSubDomain( nbNodes, faceInd, ori, domain ); + return; +#endif + } + ::GmfGetLin( iMesh, what, nbNodes, faceInd, ori, domain ); +} + +//================================================================================ +/*! + * \brief Return coordinates of a next node + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, + double* x, double* y, double *z, int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ReadNodeXYZ( x, y, z, domain ); + return; +#endif + } + ::GmfGetLin(iMesh, what, x, y, z, domain ); +} + +//================================================================================ +/*! + * \brief Return coordinates of a next node + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, + float* x, float* y, float *z, int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + double X,Y,Z; + _libData->ReadNodeXYZ( &X, &Y, &Z, domain ); + *x = X; + *y = Y; + *z = Z; + return; +#endif + } + ::GmfGetLin(iMesh, what, x, y, z, domain ); +} + +//================================================================================ +/*! + * \brief Return node index of a next corner + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, int* node ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + node = 0; + return; +#endif + } + ::GmfGetLin(iMesh, what, node ); +} + +//================================================================================ +/*! + * \brief Return node indices of a next edge + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, int* node1, int* node2, int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ReadEdgeNodes( node1, node2, domain ); + return; +#endif + } + ::GmfGetLin( iMesh, what, node1, node2, domain ); +} + +//================================================================================ +/*! + * \brief Return node indices of a next triangle + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, + int* node1, int* node2, int* node3, int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ReadTriaNodes( node1, node2, node3, domain ); + return; +#endif + } + ::GmfGetLin(iMesh, what, node1, node2, node3, domain ); +} + +//================================================================================ +/*! + * \brief Return node indices of a next tetrahedron or quadrangle + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, + int* node1, int* node2, int* node3, int* node4, int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + if ( what == GmfQuadrilaterals ) + _libData->ReadQuadNodes( node1, node2, node3, node4, domain ); + else + _libData->ReadTetraNodes( node1, node2, node3, node4, domain ); + return; +#endif + } + ::GmfGetLin(iMesh, what, node1, node2, node3, node4, domain ); +} + +//================================================================================ +/*! + * \brief Return node indices of a next hexahedron + */ +//================================================================================ + +void MG_TetraHPC_API::GmfGetLin(int iMesh, GmfKwdCod what, + int* node1, int* node2, int* node3, int* node4, + int* node5, int* node6, int* node7, int* node8, + int* domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->ReadHexaNodes( node1, node2, node3, node4, + node5, node6, node7, node8, domain ); + return; +#endif + } + ::GmfGetLin(iMesh, what, node1, node2, node3, node4, node5, node6, node7, node8, domain ); +} + +//================================================================================ +/*! + * \brief Prepare for passing data to MeshGems + */ +//================================================================================ + +int MG_TetraHPC_API::GmfOpenMesh(const char* theFile, int rdOrWr, int ver, int dim) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + return 1; +#endif + } + int id = ::GmfOpenMesh(theFile, rdOrWr, ver, dim); + _openFiles.insert( id ); + return id; +} + +//================================================================================ +/*! + * \brief Set number of entities + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetKwd(int iMesh, GmfKwdCod what, int nb ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + switch ( what ) { + case GmfVertices: _libData->SetNbVertices( nb ); break; + case GmfEdges: _libData->SetNbEdges ( nb ); break; + case GmfRequiredEdges: _libData->SetNbReqEdges( nb ); break; + case GmfTriangles: _libData->SetNbTria ( nb ); break; + case GmfRequiredTriangles: _libData->SetNbReqTria ( nb ); break; + default:; + } + return; +#endif + } + ::GmfSetKwd(iMesh, what, nb ); +} + +//================================================================================ +/*! + * \brief Add coordinates of a node + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetLin(int iMesh, GmfKwdCod what, double x, double y, double z, int domain) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->AddNode( x, y, z, domain ); + return; +#endif + } + ::GmfSetLin(iMesh, what, x, y, z, domain); +} + +//================================================================================ +/*! + * \brief Set number of field entities + * \param [in] iMesh - solution file index + * \param [in] what - solution type + * \param [in] nbNodes - nb of entities + * \param [in] nbTypes - nb of data entries in each entity + * \param [in] type - types of the data entries + * + * Used to prepare to storing size at nodes + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetKwd(int iMesh, GmfKwdCod what, int nbNodes, int dummy, int type[] ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + if ( what == GmfSolAtVertices ) _libData->SetNbReqVertices( nbNodes ); + return; +#endif + } + ::GmfSetKwd(iMesh, what, nbNodes, dummy, type ); +} + +//================================================================================ +/*! + * \brief Add solution data + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetLin(int iMesh, GmfKwdCod what, double vals[]) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->AddSizeAtNode( vals[0] ); + return; +#endif + } + ::GmfSetLin(iMesh, what, vals); +} + +//================================================================================ +/*! + * \brief Add edge nodes + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetLin(int iMesh, GmfKwdCod what, int node1, int node2, int domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->AddEdgeNodes( node1, node2, domain ); + return; +#endif + } + ::GmfSetLin(iMesh, what, node1, node2, domain ); +} + +//================================================================================ +/*! + * \brief Add a 'required' flag + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetLin(int iMesh, GmfKwdCod what, int id ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + return; +#endif + } + ::GmfSetLin(iMesh, what, id ); +} + +//================================================================================ +/*! + * \brief Add triangle nodes + */ +//================================================================================ + +void MG_TetraHPC_API::GmfSetLin(int iMesh, GmfKwdCod what, int node1, int node2, int node3, int domain ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + _libData->AddTriaNodes( node1, node2, node3, domain ); + return; +#endif + } + ::GmfSetLin(iMesh, what, node1, node2, node3, domain ); +} + +//================================================================================ +/*! + * \brief Close a file + */ +//================================================================================ + +void MG_TetraHPC_API::GmfCloseMesh( int iMesh ) +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + return; +#endif + } + ::GmfCloseMesh( iMesh ); + _openFiles.erase( iMesh ); +} + +//================================================================================ +/*! + * \brief Return true if the log is not empty + */ +//================================================================================ + +bool MG_TetraHPC_API::HasLog() +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + return !_libData->GetErrors().empty(); +#endif + } + SMESH_File file( _logFile ); + return file.size() > 0; +} + +//================================================================================ +/*! + * \brief Return log contents + */ +//================================================================================ + +std::string MG_TetraHPC_API::GetLog() +{ + if ( _useLib ) { +#ifdef USE_MG_LIBS + const std::string& err = _libData->GetErrors(); + if ( !_logFile.empty() && !err.empty() ) + { + SMESH_File file( _logFile, /*openForReading=*/false ); + file.openForWriting(); + file.write( err.c_str(), err.size() ); + } + return err; +#endif + } + SMESH_File file( _logFile ); + return file.getPos(); +} diff --git a/src/GHS3DPRLPlugin/MG_TetraHPC_API.hxx b/src/GHS3DPRLPlugin/MG_TetraHPC_API.hxx new file mode 100644 index 0000000..4c14192 --- /dev/null +++ b/src/GHS3DPRLPlugin/MG_TetraHPC_API.hxx @@ -0,0 +1,86 @@ +// Copyright (C) 2004-2016 CEA/DEN, EDF R&D +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#ifndef __MG_TetraHPC_IO_HXX__ +#define __MG_TetraHPC_IO_HXX__ + +extern "C" +{ +#include "libmesh5.h" +} +#include +#include + +/*! + * \brief Class providing a transparent switch between MG_TetraHPC usage as + * a library and as an executable. API of libmesh5 inherited. + */ +class MG_TetraHPC_API +{ +public: + + MG_TetraHPC_API( volatile bool& cancelled_flag, double& progress ); + ~MG_TetraHPC_API(); + + bool IsLibrary(); + bool IsExecutable() { return !IsLibrary(); } + void SetUseExecutable(); + + // IN to MESHGEMS + int GmfOpenMesh(const char* theFile, int rdOrWr, int ver, int dim); + void GmfSetKwd(int iMesh, GmfKwdCod what, int nb ); + void GmfSetLin(int iMesh, GmfKwdCod what, double x, double y, double z, int domain); + void GmfSetKwd(int iMesh, GmfKwdCod what, int nbNodes, int dummy, int type[] ); // sol type + void GmfSetLin(int iMesh, GmfKwdCod what, double vals[]); // sol + void GmfSetLin(int iMesh, GmfKwdCod what, int node1, int node2, int domain ); // edge + void GmfSetLin(int iMesh, GmfKwdCod what, int id ); // required + void GmfSetLin(int iMesh, GmfKwdCod what, int node1, int node2, int node3, int domain ); // tria + + bool Compute( const std::string& cmdLine ); + + // OUT from MESHGEMS + int GmfOpenMesh(const char* theFile, int rdOrWr, int * ver, int * dim); + int GmfStatKwd( int iMesh, GmfKwdCod what ); + void GmfGotoKwd( int iMesh, GmfKwdCod what ); + void GmfGetLin( int iMesh, GmfKwdCod what, int* nbNodes, int* faceInd, int* ori, int* domain, int dummy ); + void GmfGetLin(int iMesh, GmfKwdCod what, float* x, float* y, float *z, int* domain ); + void GmfGetLin(int iMesh, GmfKwdCod what, double* x, double* y, double *z, int* domain ); + void GmfGetLin(int iMesh, GmfKwdCod what, int* node ); + void GmfGetLin(int iMesh, GmfKwdCod what, int* node1, int* node2, int* domain ); + void GmfGetLin(int iMesh, GmfKwdCod what, int* node1, int* node2, int* node3, int* domain ); + void GmfGetLin(int iMesh, GmfKwdCod what, int* node1, int* node2, int* node3, int* node4, int* domain ); + void GmfGetLin(int iMesh, GmfKwdCod what, int* node1, int* node2, int* node3, int* node4, int* node5, int* node6, int* node7, int* node8, int* domain ); + void GmfCloseMesh( int iMesh ); + + void SetLogFile( const std::string& logFileName ) { _logFile = logFileName; } + bool HasLog(); + std::string GetLog(); + + + struct LibData; + +private: + + bool _useLib; + LibData* _libData; + std::set _openFiles; + std::string _logFile; +}; + +#endif diff --git a/src/gui/GHS3DPRLPluginGUI_HypothesisCreator.cxx b/src/gui/GHS3DPRLPluginGUI_HypothesisCreator.cxx index 28d533b..c487273 100755 --- a/src/gui/GHS3DPRLPluginGUI_HypothesisCreator.cxx +++ b/src/gui/GHS3DPRLPluginGUI_HypothesisCreator.cxx @@ -269,6 +269,7 @@ bool GHS3DPRLPluginGUI_HypothesisCreator::readParamsFromWidgets( GHS3DPRLHypothe h_data.myNbPart = myNbPart->value(); h_data.myKeepFiles = myKeepFiles->isChecked(); h_data.myBackground = myBackground->isChecked(); + h_data.myMultithread= myMultithread->isChecked(); h_data.myGradation = myGradation->value(); h_data.myMinSize = myMinSize->value(); h_data.myMaxSize = myMaxSize->value(); diff --git a/src/tepal2med/tetrahpc2med.cxx b/src/tepal2med/tetrahpc2med.cxx index d3ba409..6e4d432 100755 --- a/src/tepal2med/tetrahpc2med.cxx +++ b/src/tepal2med/tetrahpc2med.cxx @@ -107,7 +107,7 @@ bool ReadFileMED(QString nomfilemed,ghs3dprl_mesh_wrap *mymailw) { med_err ret; med_idt fid=0; - med_int i,j,sdim,mdim,nmaa,edim,majeur_lu,mineur_lu,release_lu,nprofils,nstep; + med_int i,j,sdim,mdim,nmaa,/*edim,majeur_lu,mineur_lu,release_lu,nprofils,*/nstep; med_mesh_type type_maillage; char dtunit[MED_SNAME_SIZE+1]; char axisname[MED_SNAME_SIZE+1]; @@ -174,14 +174,14 @@ bool ReadFileMED(QString nomfilemed,ghs3dprl_mesh_wrap *mymailw) } //nombre d'objets MED : mailles, faces, aretes , ... - med_int nmailles[MED_N_CELL_GEO],nbtria3; - med_int nfaces[MED_N_FACE_GEO]; - med_int naretes[MED_N_EDGE_FIXED_GEO],nbseg2; + med_int /*nmailles[MED_N_CELL_GEO],*/nbtria3; + //med_int nfaces[MED_N_FACE_GEO]; + med_int /*naretes[MED_N_EDGE_FIXED_GEO],*/nbseg2; //med_int nmailles[MED_NBR_GEOMETRIE_MAILLE],nbtria3; //med_int nfaces[MED_NBR_GEOMETRIE_FACE]; //med_int naretes[MED_NBR_GEOMETRIE_ARETE],nbseg2; //polygones et polyedres familles equivalences joints - med_int nmpolygones,npolyedres,nfpolygones,nfam,nequ,njnt; + med_int /*nmpolygones,npolyedres,nfpolygones,*/nfam/*,nequ,njnt*/; //Combien de mailles, faces ou aretes pour chaque type geometrique ? /*for (i=0;i famdelete = std::vector(nfam); char *gro; char nomfam[MED_NAME_SIZE+1]; med_int numfam; - char str1[MED_COMMENT_SIZE+1]; + //char str1[MED_COMMENT_SIZE+1]; char str2[MED_LNAME_SIZE+1]; med_err ret = 0; @@ -799,6 +799,13 @@ int main(int argc, char *argv[]) std::cout<<"\nlaunch tetra_hpc command:"<< "\n "<