@@ -88,7 +88,8 @@ const boundary_id_type BoundaryInfo::invalid_id = -123;
8888// BoundaryInfo functions
8989BoundaryInfo ::BoundaryInfo (MeshBase & m ) :
9090 ParallelObject (m .comm ()),
91- _mesh (& m )
91+ _mesh (& m ),
92+ _children_on_boundary (false)
9293{
9394}
9495
@@ -949,8 +950,11 @@ void BoundaryInfo::add_side(const Elem * elem,
949950{
950951 libmesh_assert (elem );
951952
952- // Only add BCs for level-0 elements.
953- libmesh_assert_equal_to (elem -> level (), 0 );
953+ // Users try to mark boundary on child elements
954+ // If this happens, we will allow users to remove
955+ // side from child elements as well
956+ if (elem -> level ())
957+ _children_on_boundary = true;
954958
955959 libmesh_error_msg_if (id == invalid_id , "ERROR: You may not set a boundary ID of "
956960 << invalid_id
@@ -978,8 +982,11 @@ void BoundaryInfo::add_side(const Elem * elem,
978982
979983 libmesh_assert (elem );
980984
981- // Only add BCs for level-0 elements.
982- libmesh_assert_equal_to (elem -> level (), 0 );
985+ // Users try to mark boundary on child elements
986+ // If this happens, we will allow users to remove
987+ // side from child elements as well
988+ if (elem -> level ())
989+ _children_on_boundary = true;
983990
984991 // Don't add the same ID twice
985992 auto bounds = _boundary_side_id .equal_range (elem );
@@ -1356,8 +1363,8 @@ void BoundaryInfo::remove_edge (const Elem * elem,
13561363{
13571364 libmesh_assert (elem );
13581365
1359- // Only level 0 elements are stored in BoundaryInfo .
1360- libmesh_assert_equal_to (elem -> level (), 0 );
1366+ // Only level 0 elements unless the flag "_children_on_boundary" is on .
1367+ libmesh_assert (elem -> level ()== 0 || _children_on_boundary );
13611368
13621369 // Erase (elem, edge, *) entries from map.
13631370 erase_if (_boundary_edge_id , elem ,
@@ -1373,8 +1380,8 @@ void BoundaryInfo::remove_edge (const Elem * elem,
13731380{
13741381 libmesh_assert (elem );
13751382
1376- // Only level 0 elements are stored in BoundaryInfo .
1377- libmesh_assert_equal_to (elem -> level (), 0 );
1383+ // Only level 0 elements unless the flag "_children_on_boundary" is on .
1384+ libmesh_assert (elem -> level () == 0 || _children_on_boundary );
13781385
13791386 // Erase (elem, edge, id) entries from map.
13801387 erase_if (_boundary_edge_id , elem ,
@@ -1388,8 +1395,8 @@ void BoundaryInfo::remove_shellface (const Elem * elem,
13881395{
13891396 libmesh_assert (elem );
13901397
1391- // Only level 0 elements are stored in BoundaryInfo .
1392- libmesh_assert_equal_to (elem -> level (), 0 );
1398+ // Only level 0 elements unless the flag "_children_on_boundary" is on .
1399+ libmesh_assert (elem -> level () == 0 || _children_on_boundary );
13931400
13941401 // Shells only have 2 faces
13951402 libmesh_assert_less (shellface , 2 );
@@ -1408,8 +1415,8 @@ void BoundaryInfo::remove_shellface (const Elem * elem,
14081415{
14091416 libmesh_assert (elem );
14101417
1411- // Only level 0 elements are stored in BoundaryInfo .
1412- libmesh_assert_equal_to (elem -> level (), 0 );
1418+ // Only level 0 elements unless the flag "_children_on_boundary" is on .
1419+ libmesh_assert (elem -> level () == 0 || _children_on_boundary );
14131420
14141421 // Shells only have 2 faces
14151422 libmesh_assert_less (shellface , 2 );
@@ -1425,8 +1432,8 @@ void BoundaryInfo::remove_side (const Elem * elem,
14251432{
14261433 libmesh_assert (elem );
14271434
1428- // Only level 0 elements are stored in BoundaryInfo .
1429- libmesh_assert_equal_to (elem -> level (), 0 );
1435+ // Only level 0 elements unless the flag "_children_on_boundary" is on .
1436+ libmesh_assert (elem -> level () == 0 || _children_on_boundary );
14301437
14311438 // Erase (elem, side, *) entries from map.
14321439 erase_if (_boundary_side_id , elem ,
@@ -1442,6 +1449,9 @@ void BoundaryInfo::remove_side (const Elem * elem,
14421449{
14431450 libmesh_assert (elem );
14441451
1452+ // Only level 0 elements unless the flag "_children_on_boundary" is on.
1453+ libmesh_assert (elem -> level () == 0 || _children_on_boundary );
1454+
14451455 // Erase (elem, side, id) entries from map.
14461456 erase_if (_boundary_side_id , elem ,
14471457 [side , id ](decltype (_boundary_side_id )::mapped_type & pr )
@@ -1488,12 +1498,21 @@ void BoundaryInfo::remove_id (boundary_id_type id)
14881498unsigned int BoundaryInfo ::side_with_boundary_id (const Elem * const elem ,
14891499 const boundary_id_type boundary_id_in ) const
14901500{
1491- const Elem * searched_elem = elem ;
1501+ std ::vector < const Elem * > searched_elem_vec ;
1502+ // If elem has boundary information, we return that when
1503+ // the flag "_children_on_boundary" is on
1504+ if (_children_on_boundary )
1505+ searched_elem_vec .push_back (elem );
1506+ // Otherwise, we return boundary information of its
1507+ // parent if any
14921508 if (elem -> level () != 0 )
1493- searched_elem = elem -> top_parent ();
1509+ searched_elem_vec . push_back ( elem -> top_parent () );
14941510
1495- // elem may have zero or multiple occurrences
1496- for (const auto & pr : as_range (_boundary_side_id .equal_range (searched_elem )))
1511+ for (auto it = searched_elem_vec .begin (); it != searched_elem_vec .end (); ++ it )
1512+ {
1513+ const Elem * searched_elem = * it ;
1514+ // elem may have zero or multiple occurrences
1515+ for (const auto & pr : as_range (_boundary_side_id .equal_range (searched_elem )))
14971516 {
14981517 // if this is true we found the requested boundary_id
14991518 // of the element and want to return the side
@@ -1524,7 +1543,8 @@ unsigned int BoundaryInfo::side_with_boundary_id(const Elem * const elem,
15241543 if (!p )
15251544 return side ;
15261545 }
1527- }
1546+ }
1547+ }
15281548
15291549 // if we get here, we found elem in the data structure but not
15301550 // the requested boundary id, so return the default value
@@ -1538,12 +1558,20 @@ BoundaryInfo::sides_with_boundary_id(const Elem * const elem,
15381558{
15391559 std ::vector < unsigned int > returnval ;
15401560
1541- const Elem * searched_elem = elem ;
1561+ std ::vector < const Elem * > searched_elem_vec ;
1562+ // If elem has boundary information, that is part of return when
1563+ // the flag "_children_on_boundary" is on
1564+ if (_children_on_boundary )
1565+ searched_elem_vec .push_back (elem );
1566+ // Return boundary information of its parent as well
15421567 if (elem -> level () != 0 )
1543- searched_elem = elem -> top_parent ();
1568+ searched_elem_vec . push_back ( elem -> top_parent () );
15441569
1545- // elem may have zero or multiple occurrences
1546- for (const auto & pr : as_range (_boundary_side_id .equal_range (searched_elem )))
1570+ for (auto it = searched_elem_vec .begin (); it != searched_elem_vec .end (); ++ it )
1571+ {
1572+ const Elem * searched_elem = * it ;
1573+ // elem may have zero or multiple occurrences
1574+ for (const auto & pr : as_range (_boundary_side_id .equal_range (searched_elem )))
15471575 {
15481576 // if this is true we found the requested boundary_id
15491577 // of the element and want to return the side
@@ -1578,7 +1606,7 @@ BoundaryInfo::sides_with_boundary_id(const Elem * const elem,
15781606 returnval .push_back (side );
15791607 }
15801608 }
1581-
1609+ }
15821610 return returnval ;
15831611}
15841612
@@ -1791,7 +1819,8 @@ BoundaryInfo::build_node_list_from_side_list()
17911819 // Need to loop over the sides of any possible children
17921820 std ::vector < const Elem * > family ;
17931821#ifdef LIBMESH_ENABLE_AMR
1794- pr .first -> active_family_tree_by_side (family , pr .second .first );
1822+ if (!pr .first -> subactive ())
1823+ pr .first -> active_family_tree_by_side (family , pr .second .first );
17951824#else
17961825 family .push_back (pr .first );
17971826#endif
@@ -2152,7 +2181,8 @@ BoundaryInfo::build_active_side_list () const
21522181 // Loop over the sides of possible children
21532182 std ::vector < const Elem * > family ;
21542183#ifdef LIBMESH_ENABLE_AMR
2155- pr .first -> active_family_tree_by_side (family , pr .second .first );
2184+ if (!pr .first -> subactive ())
2185+ pr .first -> active_family_tree_by_side (family , pr .second .first );
21562186#else
21572187 family .push_back (pr .first );
21582188#endif
0 commit comments