23 using namespace MoFEM;
25 #include <MethodForForceScaling.hpp>
29 #include <petsctime.h>
31 #include <FEMethod_LowLevelStudent.hpp>
32 #include <FEMethod_UpLevelStudent.hpp>
34 #include <PostProcVertexMethod.hpp>
35 #include <PostProcDisplacementAndStrainOnRefindedMesh.hpp>
39 #include <MethodForForceScaling.hpp>
40 #include <PotentialFlowFEMethod.hpp>
46 static char help[] =
"...\n\n";
48 int main(
int argc,
char *argv[]) {
57 MPI_Comm_rank(PETSC_COMM_WORLD,&rank);
59 PetscBool flg = PETSC_TRUE;
62 if(flg != PETSC_TRUE) {
63 SETERRQ(PETSC_COMM_SELF,1,
"*** ERROR -my_file (MESH FILE NEEDED)");
67 if(flg != PETSC_TRUE) {
71 PetscInt mesh_refinement_level;
73 if(flg != PETSC_TRUE) {
74 mesh_refinement_level = 0;
80 ParallelComm* pcomm = ParallelComm::get_pcomm(&moab,
MYPCOMM_INDEX);
81 if(pcomm == NULL) pcomm =
new ParallelComm(&moab,PETSC_COMM_WORLD);
92 Range SurTrisNeg, SurTrisPos;
93 ierr = m_field.get_cubit_msId_entities_by_dimension(101,
SIDESET,2,SurTrisNeg,
true); CHKERRQ(
ierr);
94 ierr = PetscPrintf(PETSC_COMM_WORLD,
"number of SideSet 101 = %d\n",SurTrisNeg.size()); CHKERRQ(
ierr);
95 ierr = m_field.get_cubit_msId_entities_by_dimension(102,
SIDESET,2,SurTrisPos,
true); CHKERRQ(
ierr);
96 ierr = PetscPrintf(PETSC_COMM_WORLD,
"number of SideSet 102 = %d\n",SurTrisPos.size()); CHKERRQ(
ierr);
98 Range SurNodesNeg,SurNodesPos;
100 cout<<
" All nodes on negative surfaces " << SurNodesNeg.size()<<endl;
102 cout<<
" All nodes on positive surfaces " << SurNodesPos.size()<<endl;
105 double roundfact=1e3;
double coords_nodes[3];
107 for(Range::iterator nit = SurNodesNeg.begin(); nit!=SurNodesNeg.end(); nit++) {
110 if(coords_nodes[0]>=0) coords_nodes[0]=
double(
int(coords_nodes[0]*roundfact+0.5))/roundfact;
else coords_nodes[0]=
double(
int(coords_nodes[0]*roundfact-0.5))/roundfact;
111 if(coords_nodes[1]>=0) coords_nodes[1]=
double(
int(coords_nodes[1]*roundfact+0.5))/roundfact;
else coords_nodes[1]=
double(
int(coords_nodes[1]*roundfact-0.5))/roundfact;
112 if(coords_nodes[2]>=0) coords_nodes[2]=
double(
int(coords_nodes[2]*roundfact+0.5))/roundfact;
else coords_nodes[2]=
double(
int(coords_nodes[2]*roundfact-0.5))/roundfact;
118 for(Range::iterator nit = SurNodesPos.begin(); nit!=SurNodesPos.end(); nit++) {
121 if(coords_nodes[0]>=0) coords_nodes[0]=
double(
int(coords_nodes[0]*roundfact+0.5))/roundfact;
else coords_nodes[0]=
double(
int(coords_nodes[0]*roundfact-0.5))/roundfact;
122 if(coords_nodes[1]>=0) coords_nodes[1]=
double(
int(coords_nodes[1]*roundfact+0.5))/roundfact;
else coords_nodes[1]=
double(
int(coords_nodes[1]*roundfact-0.5))/roundfact;
123 if(coords_nodes[2]>=0) coords_nodes[2]=
double(
int(coords_nodes[2]*roundfact+0.5))/roundfact;
else coords_nodes[2]=
double(
int(coords_nodes[2]*roundfact-0.5))/roundfact;
137 std::size_t found=it->getName().find(
"PotentialFlow");
138 if (found==std::string::npos)
continue;
141 cout<<
"No. of Fibres for Potential Flow : "<<noOfFibres<<endl;
143 vector<int> fibreList(noOfFibres,0);
148 std::size_t interfaceFound=it->getName().find(
"PotentialFlow_");
149 if (interfaceFound==std::string::npos)
continue;
151 std::string str2 = it->getName().substr (14,50);
153 fibreList[aaa] = atoi(str2.c_str());
159 for (
int cc = 0; cc < noOfFibres; cc++) {
161 ostringstream sss, rrr;
164 sss <<
"POTENTIAL_ELEM" << fibreList[cc];
165 cout<<sss.str().c_str()<<endl;
173 rrr <<
"POTENTIAL_PROBLEM" << fibreList[cc];
181 int def_meshset_info[2] = {0,0};
182 rval = moab.tag_get_handle(
183 "MESHSET_INFO",2,MB_TYPE_INTEGER,th_meshset_info,MB_TAG_CREAT|MB_TAG_SPARSE,&def_meshset_info
191 vector<BitRefLevel> bit_levels;
197 int meshset_data_root[2]={ll,0};
203 ierr = m_field.get_entities_by_type_and_ref_level(bit_levels.back(),
BitRefLevel().set(),MBTET,out_tet_meshset); CHKERRQ(
ierr);
209 ierr = m_field.get_entities_by_ref_level(bit_levels.back(),
BitRefLevel().set(),out_meshset); CHKERRQ(
ierr);
211 Range LatestRefinedTets;
212 rval = moab.get_entities_by_type(out_meshset, MBTET,LatestRefinedTets,
true);
CHKERRQ_MOAB(
rval);
219 for (
int cc = 0; cc < noOfFibres; cc++) {
227 ostringstream sss,rrr;
229 sss <<
"POTENTIAL_ELEM" << fibreList[cc];
230 rrr <<
"PotentialFlow_" << fibreList[cc];
232 if(it->getName() == rrr.str().c_str() ) {
235 Range block_rope_bit_level = intersect(LatestRefinedTets,TetsInBlock);
258 struct myMetaNeummanForces{
260 static PetscErrorCode addNeumannFluxBCElements(
262 const string problem_name,
265 const string mesh_nodals_positions =
"MESH_NODE_POSITIONS") {
271 ostringstream sss,rrr,ppp;
272 ppp <<
"PressureIO_" << fibre_id <<
"_1";
273 sss <<
"PressureIO_" << fibre_id <<
"_2";
274 rrr <<
"FLUX_FE" <<fibre_id;
283 if (ppp.str().c_str()==it->getName() || sss.str().c_str()==it->getName()){
295 PetscFunctionReturn(0);
298 static PetscErrorCode setNeumannFluxFiniteElementOperators(
300 boost::ptr_map<string,NeummanForcesSurface> &neumann_forces,
301 Vec &
F,
const string field_name,
const int fibre_id,
const string mesh_nodals_positions =
"MESH_NODE_POSITIONS") {
307 ostringstream sss,rrr,ppp;
308 ppp <<
"PressureIO_" << fibre_id<<
"_1";
309 sss <<
"PressureIO_" << fibre_id<<
"_2";
310 rrr <<
"FLUX_FE" <<fibre_id;
311 fe_name = rrr.str().c_str();
317 if (ppp.str().c_str()==it->getName() || sss.str().c_str()==it->getName()){
318 bool ho_geometry = m_field.
check_field(mesh_nodals_positions);
319 ierr = neumann_forces.at(fe_name).addFlux(
field_name,
F,it->getMeshsetId(),ho_geometry); CHKERRQ(
ierr);
326 PetscFunctionReturn(0);
331 for (
int cc = 0; cc < noOfFibres; cc++) {
333 sss <<
"POTENTIAL_PROBLEM" << fibreList[cc];
336 ierr = myMetaNeummanForces::addNeumannFluxBCElements(m_field,sss.str().c_str(),
"POTENTIAL_FIELD",fibreList[cc]); CHKERRQ(
ierr);
348 ierr = m_field.build_problems(); CHKERRQ(
ierr);
352 for (
int cc = 0; cc < noOfFibres; cc++) {
354 sss <<
"POTENTIAL_PROBLEM" << fibreList[cc];
355 ierr = m_field.partition_problem( sss.str().c_str() ); CHKERRQ(
ierr);
356 ierr = m_field.partition_finite_elements( sss.str().c_str() ); CHKERRQ(
ierr);
357 ierr = m_field.partition_ghost_dofs( sss.str().c_str() ); CHKERRQ(
ierr);
361 ierr = m_field.print_cubit_displacement_set(); CHKERRQ(
ierr);
362 ierr = m_field.print_cubit_pressure_set(); CHKERRQ(
ierr);
365 vector<Vec>
F(noOfFibres);
366 vector<Vec>
D(noOfFibres);
367 vector<Mat>
A(noOfFibres);
369 for (
int cc = 0; cc < noOfFibres; cc++) {
370 ostringstream sss,rrr,ttt;
371 sss <<
"POTENTIAL_PROBLEM" << fibreList[cc];
372 rrr <<
"POTENTIAL_ELEM" << fibreList[cc];
373 ttt <<
"ZeroPressure_" << fibreList[cc];
374 ierr = m_field.VecCreateGhost( sss.str().c_str() ,
ROW,&
F[cc]); CHKERRQ(
ierr);
375 ierr = m_field.VecCreateGhost( sss.str().c_str() ,
COL,&
D[cc]); CHKERRQ(
ierr);
376 ierr = m_field.MatCreateMPIAIJWithArrays( sss.str().c_str() ,&
A[cc]); CHKERRQ(
ierr);
379 ierr = m_field.
loop_dofs(
"MESH_NODE_POSITIONS",ent_method_material); CHKERRQ(
ierr);
386 if (ttt.str().c_str()==it->getName()){
394 fix_nodes.insert(adj.begin(),adj.end());
396 fix_nodes.insert(adj.begin(),adj.end());
405 boost::ptr_map<string,NeummanForcesSurface> neumann_forces;
406 ierr = myMetaNeummanForces::setNeumannFluxFiniteElementOperators(m_field,neumann_forces,
F[cc],
"POTENTIAL_FIELD",fibreList[cc]); CHKERRQ(
ierr);
407 boost::ptr_map<string,NeummanForcesSurface>::iterator mit = neumann_forces.begin();
408 for(;mit!=neumann_forces.end();mit++) {
412 LaplacianElem elem(m_field,
A[cc],
F[cc]);
414 ierr = MatZeroEntries(
A[cc]); CHKERRQ(
ierr);
420 ierr = MatAssemblyBegin(
A[cc],MAT_FINAL_ASSEMBLY); CHKERRQ(
ierr);
421 ierr = MatAssemblyEnd(
A[cc],MAT_FINAL_ASSEMBLY); CHKERRQ(
ierr);
423 ierr = VecAssemblyBegin(
F[cc]); CHKERRQ(
ierr);
424 ierr = VecAssemblyEnd(
F[cc]); CHKERRQ(
ierr);
428 ierr = MatSetOption(
A[cc],MAT_SPD,PETSC_TRUE); CHKERRQ(
ierr);
431 ierr = KSPCreate(PETSC_COMM_WORLD,&solver); CHKERRQ(
ierr);
432 ierr = KSPSetOperators(solver,
A[cc],
A[cc]); CHKERRQ(
ierr);
433 ierr = KSPSetFromOptions(solver); CHKERRQ(
ierr);
434 ierr = KSPSetUp(solver); CHKERRQ(
ierr);
436 ierr = KSPSolve(solver,
F[cc],
D[cc]); CHKERRQ(
ierr);
437 ierr = VecGhostUpdateBegin(
D[cc],INSERT_VALUES,SCATTER_FORWARD); CHKERRQ(
ierr);
438 ierr = VecGhostUpdateEnd(
D[cc],INSERT_VALUES,SCATTER_FORWARD); CHKERRQ(
ierr);
439 ierr = m_field.set_global_ghost_vector( sss.str().c_str() ,
ROW,
D[cc],INSERT_VALUES,SCATTER_REVERSE); CHKERRQ(
ierr);
441 ierr = KSPDestroy(&solver); CHKERRQ(
ierr);
442 ierr = VecDestroy(&
F[cc]); CHKERRQ(
ierr);
443 ierr = VecDestroy(&
D[cc]); CHKERRQ(
ierr);
444 ierr = MatDestroy(&
A[cc]); CHKERRQ(
ierr);
449 rval = moab.tag_get_handle(
"PHI",1,MB_TYPE_DOUBLE,th_phi,MB_TAG_CREAT|MB_TAG_SPARSE,&def_val);
CHKERRQ_MOAB(
rval);
452 double val = dof->get()->getFieldData();
457 ierr = m_field.
loop_dofs(
"POTENTIAL_FIELD",ent_method_phi_on_10nodeTet); CHKERRQ(
ierr);
458 ent_method_phi_on_10nodeTet.
setNodes =
false;
459 ierr = m_field.
loop_dofs(
"POTENTIAL_FIELD",ent_method_phi_on_10nodeTet); CHKERRQ(
ierr);
461 if(pcomm->rank()==0) {
467 ierr = m_field.get_entities_by_type_and_ref_level(bit_levels[0],
BitRefLevel().set(),MBTET,out_meshset1); CHKERRQ(
ierr);
470 if(pcomm->rank()==0) {
474 for (
int cc = 0; cc < noOfFibres; cc++) {
477 ostringstream sss,rrr,ttt;
478 sss <<
"POTENTIAL_PROBLEM" << fibreList[cc];
479 rrr <<
"POTENTIAL_ELEM" << fibreList[cc];
480 ttt <<
"out_potential_flow" << fibreList[cc] <<
".vtk";