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,117 @@ 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+ {
559+ CPPUNIT_ASSERT (bi .has_boundary_id (elem , 1 , 5 ));
560+ // we refine again later
561+ elem -> set_refinement_flag (Elem ::REFINE );
562+ }
563+ }
564+
565+ MeshRefinement (* mesh ).refine_elements ();
566+ mesh -> prepare_for_use ();
567+
568+ // This time we remove boundary 5 from all children sides
569+ for (auto & elem : mesh -> active_element_ptr_range ())
570+ {
571+ const Point c = elem -> vertex_average ();
572+ if (c (0 ) < 1 && c (0 ) > 0.5 )
573+ {
574+ bi .remove_side (elem , 1 , 5 );
575+ elem -> set_refinement_flag (Elem ::COARSEN );
576+ }
577+ }
578+ mesh -> prepare_for_use ();
579+
580+ MeshRefinement (* mesh ).coarsen_elements ();
581+ mesh -> prepare_for_use ();
582+
583+ // The parent element should not have any side associated with boundary 5
584+ for (auto & elem : mesh -> active_element_ptr_range ())
585+ {
586+ const Point c = elem -> vertex_average ();
587+ if (c (0 ) < 1 )
588+ CPPUNIT_ASSERT (!bi .has_boundary_id (elem , 1 , 5 ));
589+ }
590+ }
591+ #endif //LIBMESH_ENABLE_AMR
477592};
478593
479594CPPUNIT_TEST_SUITE_REGISTRATION ( BoundaryInfoTest );
0 commit comments