88#include <libmesh/dirichlet_boundaries.h>
99#include <libmesh/dof_map.h>
1010#include <libmesh/parallel.h>
11+ #include <libmesh/mesh_refinement.h>
1112
1213#include "test_comm.h"
1314#include "libmesh_cppunit.h"
@@ -27,6 +28,9 @@ public:
2728#if LIBMESH_DIM > 1
2829 CPPUNIT_TEST ( testMesh );
2930 CPPUNIT_TEST ( testRenumber );
31+ #ifdef LIBMESH_ENABLE_AMR
32+ CPPUNIT_TEST ( testBoundaryOnChildrenElements );
33+ # endif
3034# ifdef LIBMESH_ENABLE_DIRICHLET
3135 CPPUNIT_TEST ( testShellFaceConstraints );
3236# endif
@@ -474,6 +478,116 @@ public:
474478 }
475479#endif // LIBMESH_ENABLE_DIRICHLET
476480
481+ #ifdef LIBMESH_ENABLE_AMR
482+ void testBoundaryOnChildrenElements ()
483+ {
484+ LOG_UNIT_TEST ;
485+
486+ std ::unique_ptr < Mesh > mesh ;
487+ mesh = std ::make_unique < Mesh > (* TestCommWorld );
488+
489+ MeshTools ::Generation ::build_square (* mesh ,
490+ 2 , 1 ,
491+ 0. , 2. ,
492+ 0. , 1. ,
493+ QUAD4 );
494+
495+ BoundaryInfo & bi = mesh -> get_boundary_info ();
496+
497+ // Set subdomain ids for specific elements
498+ // _____________
499+ // | 1 | 2 |
500+ // |_____|_____|
501+
502+ for (auto & elem : mesh -> active_element_ptr_range ())
503+ {
504+ const Point c = elem -> vertex_average ();
505+ if (c (0 ) < 1 )
506+ {
507+ elem -> subdomain_id () = 1 ;
508+ elem -> set_refinement_flag (Elem ::REFINE );
509+ }
510+ else
511+ elem -> subdomain_id () = 2 ;
512+ }
513+ mesh -> prepare_for_use ();
514+
515+ // Refine the elements once in subdomain 1, and
516+ // add the right side subdomain 1 as boundary 5
517+ MeshRefinement (* mesh ).refine_elements ();
518+ for (auto & elem : mesh -> active_element_ptr_range ())
519+ {
520+ const Point c = elem -> vertex_average ();
521+ if (c (0 ) < 1 && c (0 ) > 0.5 )
522+ bi .add_side (elem , 1 , 5 );
523+ }
524+ mesh -> prepare_for_use ();
525+
526+ // Check the middle boundary, we expect to have two sides in boundary 5
527+ auto boundary_side_id = bi .get_sideset_map ();
528+ unsigned int count = 0 ;
529+ for (auto & elem : mesh -> active_element_ptr_range ())
530+ {
531+ if (bi .has_boundary_id (elem , 1 , 5 ))
532+ count ++ ;
533+ }
534+ CPPUNIT_ASSERT_EQUAL ((unsigned int ) 2 , count );
535+ CPPUNIT_ASSERT (bi .is_children_on_boundary_side ());
536+
537+ // Remove the top element side on boundary 5, mark it to coarsen
538+ for (auto & elem : mesh -> active_element_ptr_range ())
539+ {
540+ const Point c = elem -> vertex_average ();
541+ if (c (0 ) > 0.5 && c (0 ) < 1 && c (1 ) > 0.5 )
542+ {
543+ elem -> set_refinement_flag (Elem ::COARSEN );
544+ bi .remove_side (elem , 1 , 5 );
545+ CPPUNIT_ASSERT (!bi .has_boundary_id (elem , 1 , 5 ));
546+ }
547+ }
548+ mesh -> prepare_for_use ();
549+
550+ // The coarsened element should have its side on boundary 5
551+ // This is boundary info transferred from this child element
552+ MeshRefinement (* mesh ).coarsen_elements ();
553+ mesh -> prepare_for_use ();
554+ for (auto & elem : mesh -> active_element_ptr_range ())
555+ {
556+ const Point c = elem -> vertex_average ();
557+ if (c (0 ) < 1 )
558+ CPPUNIT_ASSERT (bi .has_boundary_id (elem , 1 , 5 ));
559+ // we refine again later
560+ elem -> set_refinement_flag (Elem ::REFINE );
561+ }
562+ CPPUNIT_ASSERT_EQUAL ((unsigned int ) 2 , count );
563+
564+ MeshRefinement (* mesh ).refine_elements ();
565+ mesh -> prepare_for_use ();
566+
567+ // This time we remove boundary 5 from all children sides
568+ for (auto & elem : mesh -> active_element_ptr_range ())
569+ {
570+ const Point c = elem -> vertex_average ();
571+ if (c (0 ) < 1 && c (0 ) > 0.5 )
572+ {
573+ bi .remove_side (elem , 1 , 5 );
574+ elem -> set_refinement_flag (Elem ::COARSEN );
575+ }
576+ }
577+ mesh -> prepare_for_use ();
578+
579+ MeshRefinement (* mesh ).coarsen_elements ();
580+ mesh -> prepare_for_use ();
581+
582+ // The parent element should not have any side associated with boundary 5
583+ for (auto & elem : mesh -> active_element_ptr_range ())
584+ {
585+ const Point c = elem -> vertex_average ();
586+ if (c (0 ) < 1 )
587+ CPPUNIT_ASSERT (!bi .has_boundary_id (elem , 1 , 5 ));
588+ }
589+ }
590+ #endif //LIBMESH_ENABLE_AMR
477591};
478592
479593CPPUNIT_TEST_SUITE_REGISTRATION ( BoundaryInfoTest );
0 commit comments