33 #include <boost/type_traits.hpp>
35 #include <boost/filesystem.hpp>
36 #include <boost/assign/list_of.hpp>
37 #include <boost/range/algorithm/for_each.hpp>
38 #include <boost/icl/type_traits/is_map.hpp>
40 #include <feel/feelcore/feel.hpp>
42 #include <feel/feelcore/parameter.hpp>
48 #include <feel/feelmesh/meshmover.hpp>
52 extern const char* FEELPP_GMSH_FORMAT_VERSION;
56 #include <feel/feelfilters/exportergmsh.hpp>
104 enum DomainType { GMSH_REFERENCE_DOMAIN = 0, GMSH_REAL_DOMAIN };
115 Gmsh(
int nDim = 1,
int nOrder = GMSH_ORDER_ONE, WorldComm
const&
worldComm=Environment::worldComm() );
134 static boost::shared_ptr<Gmsh> New( po::variables_map
const& vm );
135 static boost::shared_ptr<Gmsh> New( std::string
const& shape, uint16_type d = 2, uint16_type o = 1, std::string
const& ct =
"simplex" );
207 return M_I[0].second;
215 return M_I[1].second;
223 return M_I[2].second;
229 double const&
h()
const
241 if ( !d.empty() ) M_desc = d;
253 return boost::lexical_cast<
double>( M_geoParamMap.at( _name ) );
260 return M_geoParamMap;
314 int structuredMesh()
const
318 int refinementLevels()
const
373 M_geoParamMap[
"ElementOrder"]=boost::lexical_cast<std::string>(o);
381 if ( version !=
"1" && version !=
"2" && version != FEELPP_GMSH_FORMAT_VERSION )
382 throw std::invalid_argument(
"invalid gmsh file format version" );
403 void setSubStructuring(
bool substruct )
405 M_substructuring = substruct;
407 bool subStructuring()
const
409 return M_substructuring;
418 virtual void setX( std::pair<double,double>
const& x )
422 M_geoParamMap[
"xmin"]=boost::lexical_cast<std::string>(x.first);
423 M_geoParamMap[
"xmax"]=boost::lexical_cast<std::string>(x.second);
425 virtual void setY( std::pair<double,double>
const& y )
432 M_geoParamMap[
"ymin"]=boost::lexical_cast<std::string>(y.first);
433 M_geoParamMap[
"ymax"]=boost::lexical_cast<std::string>(y.second);
436 virtual void setZ( std::pair<double,double>
const& z )
443 M_geoParamMap[
"zmin"]=boost::lexical_cast<std::string>(z.first);
444 M_geoParamMap[
"zmax"]=boost::lexical_cast<std::string>(z.second);
452 M_I[0] = std::make_pair( -1, 1 );
455 M_I[1] = std::make_pair( -1, 1 );
458 M_I[2] = std::make_pair( -1, 1 );
483 M_geoParamMap.at( _name ) = boost::lexical_cast<std::string>( _value );
494 for(
const auto& iter : geomap)
495 M_geoParamMap.at(iter.first) = iter.second;
498 M_geoParamMap = geomap;
529 void setStructuredMesh(
int s )
533 void setRefinementLevels(
int levels )
565 std::string
generate( std::string
const& name )
const;
575 boost::tuple<std::string,bool>
577 std::string
const& geo,
578 bool const forceRebuild =
false,
579 bool const parametric =
false,
580 bool const modifGeo =
true )
const;
587 std::string
refine( std::string
const& name,
int level = 1,
bool const parametric =
false )
const;
600 void rebuildPartitionMsh( std::string
const& nameMshInput,std::string
const& nameMshOutput )
const;
613 static std::map<std::string, std::string>
gpstr2map( std::string
const& geopars );
624 return std::string();
635 bool generateGeo( std::string
const& name, std::string
const& geo,
bool const modifGeo=
true )
const;
639 void generate( std::string
const& __name, uint16_type dim,
bool parametric =
false )
const;
641 std::string
prefix( std::string
const& __name, uint16_type dim )
const;
653 std::string M_version;
656 GMSH_FORMAT M_format;
662 mutable std::string M_desc;
665 std::map< std::string, std::string > M_geoParamMap;
668 std::vector<std::pair<double,double> >
M_I;
691 bool M_substructuring;
697 typedef boost::shared_ptr<gmsh_type> gmsh_ptrtype;
702 template<
typename Args,
typename Tag=tag::mesh>
705 typedef typename boost::remove_pointer<
706 typename boost::remove_const<
707 typename boost::remove_reference<
708 typename parameter::binding<Args, Tag>::type
712 typedef typename mpl::if_<is_shared_ptr<_type>,
713 mpl::identity<typename _type::element_type>,
714 mpl::identity<_type> >::type::type type;
715 typedef boost::shared_ptr<type> ptrtype;
718 template<
typename Args,
typename Tag=tag::geoentity>
719 struct meshFromGeoEntity
721 typedef typename boost::remove_pointer<
722 typename boost::remove_const<
723 typename boost::remove_reference<
724 typename parameter::binding<Args, Tag>::type
729 typedef typename _type::GeoShape GeoShape;
730 typedef typename mpl::if_< mpl::bool_<GeoShape::is_simplex>,
731 mpl::identity< Mesh< Simplex< GeoShape::nDim,GeoShape::nOrder,GeoShape::nRealDim> > >,
732 mpl::identity< Mesh< Hypercube< GeoShape::nDim,GeoShape::nOrder,GeoShape::nRealDim> > >
737 template <
typename ElementSpaceType>
739 straightenMeshUpdateEdgesOnBoundaryIsolated( ElementSpaceType & straightener, mpl::int_<0> )
741 template <
typename ElementSpaceType>
743 straightenMeshUpdateEdgesOnBoundaryIsolated( ElementSpaceType & straightener, mpl::int_<1> )
745 template <
typename ElementSpaceType>
747 straightenMeshUpdateEdgesOnBoundaryIsolated( ElementSpaceType & straightener, mpl::int_<2> )
749 template <
typename ElementSpaceType>
751 straightenMeshUpdateEdgesOnBoundaryIsolated( ElementSpaceType & straightener, mpl::int_<3> )
753 typedef typename ElementSpaceType::functionspace_type space_type;
754 typedef typename space_type::mesh_type mesh_type;
755 typedef typename space_type::dof_type::fe_type fe_type;
757 auto const ncdof = space_type::dof_type::nComponents;
758 auto const dofshift = fe_type::nDofPerVertex*mesh_type::element_type::numVertices;
760 auto mesh = straightener.mesh();
761 auto const myrank = mesh->
worldComm().localRank();
763 std::set<size_type> edgeIdFoundToUpdate;
765 auto itedge = mesh->beginEdgeOnBoundary();
766 auto const enedge = mesh->endEdgeOnBoundary();
767 for ( ; itedge!=enedge ; ++itedge )
769 if (itedge->processId()!=myrank || itedge->numberOfElementsGhost()==0 )
continue;
771 auto const theedgeid = itedge->id();
773 std::set<size_type> ghostFaceIdFoundOnBoundary;
775 auto iteltghost = itedge->elementsGhost().begin();
776 auto const eneltghost = itedge->elementsGhost().end();
777 for ( ; iteltghost!=eneltghost ; ++iteltghost )
779 auto const& eltGhost = mesh->element(iteltghost->template get<1>(),iteltghost->template get<0>());
780 for ( uint16_type f = 0 ; f < mesh_type::element_type::numTopologicalFaces ; ++f )
782 auto const& theface = eltGhost.face(f);
783 if ( theface.isOnBoundary() )
786 for ( uint16_type e = 0; e < mesh_type::face_type::numEdges && !findEdge ; ++e )
788 if ( theface.edge(e).id() == theedgeid) { findEdge=
true; ghostFaceIdFoundOnBoundary.insert(theface.id());}
794 if (ghostFaceIdFoundOnBoundary.size()==2) edgeIdFoundToUpdate.insert(theedgeid);
799 if (edgeIdFoundToUpdate.size() > 0)
801 auto iteltactif = mesh->beginElementOnBoundary();
802 auto const eneltactif = mesh->endElementOnBoundary();
803 for ( ; iteltactif!=eneltactif ; ++iteltactif )
807 for ( uint16_type e = 0; e < mesh_type::element_type::numEdges ; ++e )
809 if ( edgeIdFoundToUpdate.find(iteltactif->edge(e).id()) != edgeIdFoundToUpdate.end())
812 auto const idEltFind = iteltactif->id();
813 for ( uint16_type locdof = 0 ; locdof<fe_type::nDofPerEdge ; ++locdof )
815 auto const local_id = dofshift + e*fe_type::nDofPerEdge + locdof;
817 for ( uint16_type comp = 0; comp < ncdof; ++comp )
819 auto const globdof = straightener.functionSpace()->dof()->localToGlobal( idEltFind, local_id, comp ).template get<0>();
821 straightener(globdof) = 0;
842 BOOST_PARAMETER_FUNCTION(
843 (
typename Feel::detail::mesh<Args>::ptrtype ),
852 ( refine, *( boost::is_integral<mpl::_> ), 0 )
853 ( save, *( boost::is_integral<mpl::_> ), 0 )
854 ( worldcomm, ( WorldComm ), Environment::worldComm() )
857 typedef typename Feel::detail::mesh<Args>::type _mesh_type;
858 typedef typename Feel::detail::mesh<Args>::ptrtype _mesh_ptrtype;
860 VLOG(1) <<
"straighten mesh of order " << _mesh_type::nOrder <<
" start";
862 _mesh_ptrtype _mesh( mesh );
865 typedef FunctionSpace<_mesh_type,bases<Lagrange<_mesh_type::nOrder,Vectorial> > > space_t;
866 #if defined(FEELPP_ENABLE_MPI_MODE)
867 auto Xh = space_t::New( _mesh=_mesh, _worldscomm=std::vector<WorldComm>(1,worldcomm) );
869 auto Xh = space_t::New( _mesh=_mesh );
872 auto xHo =
vf::project( _space=Xh, _range=
elements( mesh ), _expr=vf::P(), _geomap=GeomapStrategyType::GEOMAP_HO );
873 auto xLo =
vf::project( _space=Xh, _range=
elements( mesh ), _expr=vf::P(), _geomap=GeomapStrategyType::GEOMAP_O1 );
874 auto xHoBdy =
vf::project( _space=Xh, _range=
boundaryfaces( mesh ), _expr=vf::P(), _geomap=GeomapStrategyType::GEOMAP_HO );
875 auto xLoBdy =
vf::project( _space=Xh, _range=
boundaryfaces( mesh ), _expr=vf::P(), _geomap=GeomapStrategyType::GEOMAP_O1 );
877 auto straightener = Xh->element();
878 straightener=( xLo-xHo )-( xLoBdy-xHoBdy );
880 if (worldcomm.localSize()>1)
881 Feel::detail::straightenMeshUpdateEdgesOnBoundaryIsolated( straightener,mpl::int_<_mesh_type::nDim>() );
883 double norm_mean_value =
integrate( _range=
boundaryfaces( _mesh ), _expr=idv( straightener ) ).evaluate(
true,worldcomm).norm();
885 if ( norm_mean_value > 1e-12 )
886 std::cout <<
"the straightening process may have failed\n"
887 <<
"norm of component-wise mean value of displacement on the boundary should be 0"
888 <<
"norm_mean_value: " << norm_mean_value <<
"\n"
889 <<
"you should consider not using straightenMesh()\n"
892 boost::shared_ptr<Exporter<_mesh_type,_mesh_type::nOrder> > exporter;
897 exporter->step( 0 )->setMesh( _mesh );
898 exporter->step( 0 )->add(
"xHo", xHo );
899 exporter->step( 0 )->add(
"xLo", xLo );
900 exporter->step( 0 )->add(
"xHoBdy", xHoBdy );
901 exporter->step( 0 )->add(
"xLoBdy", xLoBdy );
902 exporter->step( 0 )->add(
"straightener", straightener );
906 MeshMover<_mesh_type> meshmove;
907 meshmove.apply( _mesh, straightener );
909 VLOG(1) <<
"straighten mesh of order " << _mesh_type::nOrder <<
" finish";
924 BOOST_PARAMETER_FUNCTION(
925 (
typename Feel::detail::mesh<Args>::ptrtype ),
936 ( straighten, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.straighten").
template as<bool>() )
937 ( refine, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.refine").
template as<int>() )
938 ( update, *( boost::is_integral<mpl::_> ), 0 )
939 ( physical_are_elementary_regions, *, option(_name=
"gmsh.physical_are_elementary_regions").
template as<bool>() )
940 ( worldcomm, *, Environment::worldComm() )
941 ( rebuild_partitions, (
bool), option(_name=
"gmsh.partition").
template as<bool>() )
942 ( rebuild_partitions_filename, *, filename )
943 ( partitions, *( boost::is_integral<mpl::_> ), worldcomm.globalSize() )
944 ( partitioner, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.partitioner").template as<int>() )
945 ( partition_file, *( boost::is_integral<mpl::_> ), 0 )
949 typedef typename Feel::detail::mesh<Args>::type _mesh_type;
950 typedef typename Feel::detail::mesh<Args>::ptrtype _mesh_ptrtype;
952 _mesh_ptrtype _mesh( mesh );
953 _mesh->setWorldComm( worldcomm );
955 std::string filename_with_path = Environment::findFile( filename );
956 if ( filename_with_path.empty() )
958 std::vector<std::string> plist = Environment::geoPathList();
959 std::ostringstream ostr;
960 std::for_each( plist.begin(), plist.end(), [&ostr]( std::string s ) { ostr <<
" - " << s <<
"\n"; } );
961 CHECK( !filename_with_path.empty() ) <<
"File " << filename <<
" cannot be found in the following paths list:\n " << ostr.str();
964 Gmsh gmsh( _mesh_type::nDim,_mesh_type::nOrder, worldcomm );
965 gmsh.setRefinementLevels( refine );
966 gmsh.setNumberOfPartitions( partitions );
967 gmsh.setPartitioner( (GMSH_PARTITIONER)partitioner );
968 gmsh.setMshFileByPartition( partition_file );
974 filename_with_path = gmsh.refine( filename_with_path, refine );
976 else if ( rebuild_partitions )
978 gmsh.rebuildPartitionMsh(filename_with_path,rebuild_partitions_filename);
979 filename_with_path=rebuild_partitions_filename;
982 ImporterGmsh<_mesh_type>
import( filename_with_path, FEELPP_GMSH_FORMAT_VERSION, worldcomm );
985 if ( physical_are_elementary_regions )
987 import.setElementRegionAsPhysicalRegion( physical_are_elementary_regions );
990 _mesh->accept(
import );
994 _mesh->components().reset();
995 _mesh->components().set( update );
996 _mesh->updateForUse();
1001 _mesh->components().reset();
1004 if ( straighten && _mesh_type::nOrder > 1 )
1005 return straightenMesh( _mesh=_mesh,
1006 _worldcomm=worldcomm.subWorldComm() );
1018 BOOST_PARAMETER_FUNCTION(
1026 ( parametricnodes, *( boost::is_integral<mpl::_> ), 0 ) )
1029 typedef typename Feel::detail::mesh<Args>::type _mesh_type;
1030 typedef typename Feel::detail::mesh<Args>::ptrtype _mesh_ptrtype;
1032 #if BOOST_FILESYSTEM_VERSION == 3
1033 ExporterGmsh<_mesh_type,1> exporter( fs::path( filename ).stem().
string(), 1, mesh->worldComm() );
1034 #elif BOOST_FILESYSTEM_VERSION == 2
1035 ExporterGmsh<_mesh_type,1> exporter( fs::path( filename ).stem(), 1, mesh->worldComm() );
1037 exporter.saveMesh( filename, mesh, parametricnodes );
1041 BOOST_PARAMETER_FUNCTION(
1043 saveGeoEntityAsGMSHMesh,
1050 typedef typename Feel::detail::meshFromGeoEntity<Args>::type _mesh_type;
1052 #if BOOST_FILESYSTEM_VERSION == 3
1053 ExporterGmsh<_mesh_type,1> exporter( fs::path( filename ).stem().
string(), 1, Environment::worldComm().subWorldCommSeq() );
1054 #elif BOOST_FILESYSTEM_VERSION == 2
1055 ExporterGmsh<_mesh_type,1> exporter( fs::path( filename ).stem(), 1, Environment::worldComm().subWorldCommSeq() );
1057 exporter.gmshSaveOneElementAsMesh( filename, geoentity );
1075 BOOST_PARAMETER_FUNCTION(
1076 (
typename Feel::detail::mesh<Args>::ptrtype ),
1087 ( format, *, option(_name=
"gmsh.format").
template as<int>() )
1088 ( h, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.hsize").
template as<double>() )
1089 ( geo_parameters, *( boost::icl::is_map<mpl::_> ),
Gmsh::gpstr2map(
"") )
1090 ( parametricnodes, *( boost::is_integral<mpl::_> ), 0 )
1091 ( straighten, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.straighten").
template as<bool>() )
1092 ( refine, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.refine").
template as<int>() )
1093 ( structured, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.structured").
template as<int>() )
1094 ( update, *( boost::is_integral<mpl::_> ), MESH_RENUMBER|MESH_UPDATE_EDGES|MESH_UPDATE_FACES|MESH_CHECK )
1095 ( force_rebuild, *( boost::is_integral<mpl::_> ), 0 )
1096 ( physical_are_elementary_regions, *,
false )
1097 ( rebuild_partitions, (
bool), option(_name=
"gmsh.partition").
template as<bool>() )
1098 ( rebuild_partitions_filename, *( boost::is_convertible<mpl::_,std::string> ) , desc->prefix()+
".msh" )
1099 ( worldcomm, *, Environment::worldComm() )
1100 ( partitions, *( boost::is_integral<mpl::_> ), worldcomm.globalSize() )
1101 ( partition_file, *( boost::is_integral<mpl::_> ), 0 )
1102 ( partitioner, *( boost::is_integral<mpl::_> ), GMSH_PARTITIONER_CHACO )
1106 typedef typename Feel::detail::mesh<Args>::type _mesh_type;
1107 typedef typename Feel::detail::mesh<Args>::ptrtype _mesh_ptrtype;
1109 _mesh_ptrtype _mesh( mesh );
1110 _mesh->setWorldComm( worldcomm );
1112 if ( worldcomm.isActive() )
1114 desc->setDimension( mesh->nDim );
1115 desc->setOrder( mesh->nOrder );
1116 desc->setWorldComm( worldcomm );
1117 desc->setNumberOfPartitions( partitions );
1118 desc->setPartitioner( (GMSH_PARTITIONER) partitioner );
1119 desc->setMshFileByPartition( partition_file );
1120 desc->setRefinementLevels( refine );
1121 desc->setFileFormat( (GMSH_FORMAT)format );
1122 desc->setStructuredMesh( structured );
1125 bool generated_or_modified;
1126 boost::tie( fname, generated_or_modified ) = desc->generate( desc->prefix(), desc->description(), force_rebuild, parametricnodes );
1130 if ( refine && !generated_or_modified )
1132 VLOG(1) <<
"Refine mesh ( level: " << refine <<
")\n";
1133 fname = desc->refine( fname, refine, parametricnodes );
1136 if ( rebuild_partitions )
1138 desc->rebuildPartitionMsh(fname,rebuild_partitions_filename);
1139 fname=rebuild_partitions_filename;
1142 ImporterGmsh<_mesh_type>
import( fname, FEELPP_GMSH_FORMAT_VERSION, worldcomm );
1145 if ( physical_are_elementary_regions )
1147 import.setElementRegionAsPhysicalRegion( physical_are_elementary_regions );
1150 _mesh->accept(
import );
1154 _mesh->components().reset();
1155 _mesh->components().set( update );
1156 _mesh->updateForUse();
1161 _mesh->components().reset();
1164 if ( straighten && _mesh_type::nOrder > 1 )
1165 return straightenMesh( _mesh=_mesh,
1166 _worldcomm=worldcomm.subWorldComm() );
1195 BOOST_PARAMETER_FUNCTION(
1200 ( name, *( boost::is_convertible<mpl::_,std::string> ) )
1203 ( shape, *( boost::is_convertible<mpl::_,std::string> ), option(_name=
"gmsh.domain.shape").
template as<std::string>() )
1204 ( shear, *( boost::is_arithmetic<mpl::_> ) , option(_name=
"gmsh.domain.shear").
template as<double>() )
1205 ( recombine, *( boost::is_integral<mpl::_> ) , option(_name=
"gmsh.domain.recombine").
template as<bool>() )
1206 ( dim, *( boost::is_integral<mpl::_> ), 3 )
1207 ( order, *( boost::is_integral<mpl::_> ), 1 )
1208 ( geo_parameters, *( boost::icl::is_map<mpl::_> ),
Gmsh::gpstr2map(
"") )
1209 ( h, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.hsize").
template as<double>() )
1210 ( convex, *( boost::is_convertible<mpl::_,std::string> ), option(_name=
"gmsh.domain.convex").
template as<std::string>() )
1211 ( addmidpoint, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.domain.addmidpoint").
template as<bool>() )
1212 ( usenames, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.domain.usenames").
template as<bool>() )
1213 ( xmin, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.xmin").
template as<double>() )
1214 ( xmax, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.xmax").
template as<double>())
1215 ( ymin, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.ymin").
template as<double>() )
1216 ( ymax, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.ymax").
template as<double>() )
1217 ( zmin, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.zmin").
template as<double>() )
1218 ( zmax, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.domain.zmax").
template as<double>() )
1219 ( substructuring, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.domain.substructuring").
template as<bool>() ) ) )
1221 gmsh_ptrtype gmsh_ptr = Gmsh::New( shape, 3, 1, convex );
1223 gmsh_ptr->setPrefix( name );
1224 gmsh_ptr->setGeoParameters( gmsh_ptr->retrieveGeoParameters( gmsh_ptr->description() ), 0 );
1225 gmsh_ptr->setGeoParameters( geo_parameters );
1226 gmsh_ptr->setCharacteristicLength( h );
1227 gmsh_ptr->setAddMidPoint( addmidpoint );
1228 gmsh_ptr->usePhysicalNames( usenames );
1229 gmsh_ptr->setShear( shear );
1230 gmsh_ptr->setRecombine( recombine );
1231 gmsh_ptr->setX( std::make_pair( xmin, xmax ) );
1232 gmsh_ptr->setY( std::make_pair( ymin, ymax ) );
1233 gmsh_ptr->setZ( std::make_pair( zmin, zmax ) );
1234 gmsh_ptr->setSubStructuring( substructuring );
1246 BOOST_PARAMETER_FUNCTION(
1251 ( filename, *( boost::is_convertible<mpl::_,std::string> ) ) )
1253 ( h, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.hsize").
template as<double>() )
1254 ( geo_parameters, *( boost::icl::is_map<mpl::_> ),
Gmsh::gpstr2map( option(_name=
"gmsh.geo-variables-list").
template as<std::string>() ) )
1255 ( dim, *( boost::is_integral<mpl::_> ), 3 )
1256 ( order, *( boost::is_integral<mpl::_> ), 1 )
1257 ( files_path, *( boost::is_convertible<mpl::_,std::string> ), Environment::localGeoRepository() )
1258 ( depends, *( boost::is_convertible<mpl::_,std::string> ), option(_name=
"gmsh.depends").
template as<std::string>() )
1259 ( worldcomm, (WorldComm), Environment::worldComm() ) )
1263 gmsh_ptrtype gmsh_ptr(
new Gmsh( 3, 1, worldcomm ) );
1265 gmsh_ptr->setCharacteristicLength( h );
1266 #if BOOST_FILESYSTEM_VERSION == 3
1267 gmsh_ptr->setPrefix( fs::path( filename ).stem().
string() );
1268 #elif BOOST_FILESYSTEM_VERSION == 2
1269 gmsh_ptr->setPrefix( fs::path( filename ).stem() );
1272 std::string filename_with_path = Environment::findFile( filename );
1273 if ( filename_with_path.empty() )
1275 std::vector<std::string> plist = Environment::geoPathList();
1276 std::ostringstream ostr;
1277 std::for_each( plist.begin(), plist.end(), [&ostr]( std::string s ) { ostr <<
" - " << s <<
"\n"; } );
1278 CHECK( !filename_with_path.empty() ) <<
"File " << filename <<
" cannot be found in the following paths list:\n " << ostr.str();
1281 gmsh_ptr->setDescription( gmsh_ptr->getDescriptionFromFile( filename_with_path ) );
1282 gmsh_ptr->setGeoParameters( gmsh_ptr->retrieveGeoParameters( gmsh_ptr->description() ), 0 );
1283 gmsh_ptr->setGeoParameters( geo_parameters );
1285 if( worldcomm.globalRank() == worldcomm.masterRank() )
1287 fs::path cp = fs::current_path();
1288 std::vector<std::string> depends_on_files;
1289 if ( !depends.empty() )
1290 algorithm::split( depends_on_files, depends, algorithm::is_any_of(
":,; " ), algorithm::token_compress_on );
1292 boost::for_each( depends_on_files,
1293 [&cp, &files_path]( std::string
const& _filename )
1295 fs::path file_path( files_path );
1296 file_path /= _filename;
1300 boost::system::error_code ec;
1302 if ( !( fs::exists( file_path ) && fs::is_regular_file( file_path ) ) )
1303 std::cout <<
"File : " << file_path <<
" doesn't exist or is not a regular file" << std::endl;
1305 else if ( !fs::exists( cp / _filename ) )
1306 fs::copy_file( file_path, fs::path( _filename ), fs::copy_option::none );
1310 catch (
const fs::filesystem_error& e )
1312 std::cerr <<
"Error: " << e.what() << std::endl;
1316 worldcomm.barrier();
1332 BOOST_PARAMETER_FUNCTION(
1337 ( filename, *( boost::is_convertible<mpl::_,std::string> ) ) )
1339 ( dim, *( boost::is_integral<mpl::_> ), 3 )
1340 ( order, *( boost::is_integral<mpl::_> ), 1 ) )
1343 gmsh_ptrtype gmsh_ptr(
new Gmsh( 3, 1 ) );
1344 #if BOOST_FILESYSTEM_VERSION == 3
1345 gmsh_ptr->setPrefix( fs::path( filename ).stem().
string() );
1346 #elif BOOST_FILESYSTEM_VERSION == 2
1347 gmsh_ptr->setPrefix( fs::path( filename ).stem() );
1351 if ( fs::exists( filename ) )
1352 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\n" ) % filename ).str() );
1354 else if ( fs::exists( fs::path( Environment::localGeoRepository() ) / filename ) )
1355 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\n" ) % ( fs::path( Environment::localGeoRepository() ) / filename ).
string() ).str() );
1357 else if ( Environment::systemGeoRepository().
template get<1>() &&
1358 fs::exists( fs::path( Environment::systemGeoRepository().get<0>() ) / filename ) )
1359 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\n" ) % ( fs::path( Environment::systemGeoRepository().get<0>() ) / filename ).
string() ).str() );
1363 std::ostringstream ostr;
1364 ostr <<
"File " << filename <<
" was not found neither in current directory or in " << Environment::localGeoRepository() <<
" or in " << Environment::systemGeoRepository();
1365 throw std::invalid_argument( ostr.str() );
1376 BOOST_PARAMETER_FUNCTION(
1381 ( filename, *( boost::is_convertible<mpl::_,std::string> ) ) )
1383 ( prefix, *( boost::is_convertible<mpl::_,std::string> ), fs::path( filename ).stem() ) )
1386 gmsh_ptrtype gmsh_ptr(
new Gmsh( 2, 1 ) );
1387 gmsh_ptr->setPrefix( prefix );
1388 std::string meshname = ( boost::format(
"%1%-0.msh" ) % prefix ).str();
1391 if ( fs::exists( filename ) )
1392 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\nSave View [0] \"%2%\";\n" ) % filename % meshname ).str() );
1394 else if ( fs::exists( fs::path( Environment::localGeoRepository() ) / filename ) )
1395 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\nSave View [0] \"%2%\";\n" ) % ( fs::path( Environment::localGeoRepository() ) / filename ).string() % meshname ).str() );
1397 else if ( Environment::systemGeoRepository().template get<1>() &&
1398 fs::exists( fs::path( Environment::systemGeoRepository().get<0>() ) / filename ) )
1399 gmsh_ptr->setDescription( ( boost::format(
"Merge \"%1%\";\nSave View [0] \"%2%\";\n" ) % ( fs::path( Environment::systemGeoRepository().get<0>() ) / filename ).
string() % meshname ).str() );
1403 std::ostringstream ostr;
1404 ostr <<
"File " << filename <<
" was not found neither in current directory or in " << Environment::localGeoRepository() <<
" or in " << Environment::systemGeoRepository();
1405 throw std::invalid_argument( ostr.str() );
1408 gmsh_ptr->generate( gmsh_ptr->prefix(), gmsh_ptr->description() );
1417 boost::shared_ptr<Mesh<Simplex<1> > >
unitSegment(
double h = option(_name=
"gmsh.hsize").as<double>() );
1422 boost::shared_ptr<Mesh<Simplex<2> > >
unitSquare(
double h = option(_name=
"gmsh.hsize").as<double>() );
1427 template<
int Ngeo=1>
1429 boost::shared_ptr<Mesh<Simplex<2,Ngeo> > >
1430 unitCircle(
double h = option(_name=
"gmsh.hsize").
template as<double>() )
1433 _desc=domain( _name=
"square",
1444 template<
int Ngeo=1>
1446 boost::shared_ptr<Mesh<Simplex<3,Ngeo> > >
1447 unitSphere(
double h = option(_name=
"gmsh.hsize").
template as<double>() )
1450 _desc=domain( _name=
"sphere",
1463 boost::shared_ptr<Mesh<Simplex<3> > >
unitCube(
double h = option(_name=
"gmsh.hsize").as<double>() );
1465 template<
int Dim,
typename Convex=Simplex<Dim>>
1467 boost::shared_ptr<Mesh<Convex> >
1468 unitHypercube(
double h = option(_name=
"gmsh.hsize").
template as<double>() )
1470 return createGMSHMesh(_mesh=
new Mesh<Convex>,
1471 _desc=domain( _name=
"hypercube",
1473 _convex=Convex::type(),
1490 BOOST_PARAMETER_FUNCTION(
1491 (
typename Feel::detail::mesh<Args>::ptrtype ),
1502 ( filename, *( boost::is_convertible<mpl::_,std::string> ), option(_name=
"gmsh.filename").
template as<std::string>() )
1503 ( h, *( boost::is_arithmetic<mpl::_> ), option(_name=
"gmsh.hsize").
template as<double>() )
1504 ( straighten, (
bool), option(_name=
"gmsh.straighten").
template as<bool>() )
1505 ( refine, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.refine").
template as<int>() )
1506 ( update, *( boost::is_integral<mpl::_> ), MESH_CHECK|MESH_UPDATE_FACES|MESH_UPDATE_EDGES )
1507 ( physical_are_elementary_regions, (
bool), option(_name=
"gmsh.physical_are_elementary_regions").
template as<bool>() )
1508 ( worldcomm, (WorldComm), Environment::worldComm() )
1509 ( force_rebuild, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.rebuild").
template as<bool>() )
1510 ( rebuild_partitions, (
bool), option(_name=
"gmsh.partition").
template as<bool>() )
1511 ( rebuild_partitions_filename, *( boost::is_convertible<mpl::_,std::string> ) , filename )
1512 ( partitions, *( boost::is_integral<mpl::_> ), worldcomm.globalSize() )
1513 ( partitioner, *( boost::is_integral<mpl::_> ), option(_name=
"gmsh.partitioner").template as<int>() )
1514 ( partition_file, *( boost::is_integral<mpl::_> ), 0 )
1515 ( depends, *( boost::is_convertible<mpl::_,std::string> ), option(_name=
"gmsh.depends").template as<std::string>() )
1519 #if defined(__clang__)
1520 #pragma clang diagnostic push
1521 #pragma clang diagnostic ignored "-Wunsequenced"
1523 typedef typename Feel::detail::mesh<Args>::type _mesh_type;
1524 typedef typename Feel::detail::mesh<Args>::ptrtype _mesh_ptrtype;
1529 fs::path mesh_name=fs::path(Environment::findFile(filename));
1530 LOG_IF( WARNING, mesh_name.extension() !=
".geo" && mesh_name.extension() !=
".msh" )
1531 <<
"Invalid filename " << filename <<
" it should have either the .geo or .msh extension\n";
1534 if ( mesh_name.extension() ==
".geo" )
1536 return createGMSHMesh( _mesh=mesh,
1537 _desc=geo( _filename=mesh_name.string(),
1538 _h=h,_depends=depends,
1539 _worldcomm=worldcomm ),
1541 _straighten=straighten,
1544 _physical_are_elementary_regions=physical_are_elementary_regions,
1545 _force_rebuild=force_rebuild,
1546 _worldcomm=worldcomm,
1547 _rebuild_partitions=rebuild_partitions,
1548 _rebuild_partitions_filename=rebuild_partitions_filename,
1549 _partitions=partitions,
1550 _partitioner=partitioner,
1551 _partition_file=partition_file
1555 if ( mesh_name.extension() ==
".msh" )
1557 return loadGMSHMesh( _mesh=mesh,
1558 _filename=mesh_name.string(),
1559 _straighten=straighten,
1562 _physical_are_elementary_regions=physical_are_elementary_regions,
1563 _worldcomm=worldcomm,
1564 _rebuild_partitions=rebuild_partitions,
1565 _rebuild_partitions_filename=rebuild_partitions_filename,
1566 _partitions=partitions,
1567 _partitioner=partitioner,
1568 _partition_file=partition_file
1573 LOG(WARNING) <<
"File " << mesh_name <<
" not found, generating instead an hypercube in " << _mesh_type::nDim <<
"D geometry and mesh...";
1574 return createGMSHMesh(_mesh=mesh,
1575 _desc=domain( _name=option(_name=
"gmsh.domain.shape").
template as<std::string>(), _h=h ),
1579 _physical_are_elementary_regions=physical_are_elementary_regions,
1580 _force_rebuild=force_rebuild,
1581 _worldcomm=worldcomm,
1582 _rebuild_partitions=rebuild_partitions,
1583 _rebuild_partitions_filename=rebuild_partitions_filename,
1584 _partitions=partitions,
1585 _partitioner=partitioner,
1586 _partition_file=partition_file );
1587 #if defined(__clang__)
1588 #pragma clang diagnostic pop