48 using namespace QuadTreeNames;
51 unsigned n_p = nnode_1d();
53 Father_bound[n_p].resize(n_p * n_p, 4);
56 for (
unsigned n = 0; n < n_p * n_p; n++)
58 for (
unsigned ison = 0; ison < 4; ison++)
67 Father_bound[n_p](0,
SW) =
SW;
69 for (
unsigned n = 1; n < n_p; n++)
71 Father_bound[n_p](n,
SW) =
S;
74 for (
unsigned n = 1; n < n_p; n++)
76 Father_bound[n_p](n_p * n,
SW) =
W;
83 Father_bound[n_p](n_p * (n_p - 1),
NW) =
NW;
85 for (
unsigned n = 1; n < n_p; n++)
87 Father_bound[n_p](n_p * (n_p - 1) + n,
NW) =
N;
90 for (
unsigned n = 0; n < (n_p - 1); n++)
92 Father_bound[n_p](n_p * n,
NW) =
W;
99 Father_bound[n_p](n_p * n_p - 1,
NE) =
NE;
101 for (
unsigned n = 0; n < (n_p - 1); n++)
103 Father_bound[n_p](n_p * (n_p - 1) + n,
NE) =
N;
106 for (
unsigned n = 0; n < (n_p - 1); n++)
108 Father_bound[n_p](n_p - 1 + n_p * n,
NE) =
E;
115 Father_bound[n_p](n_p - 1,
SE) =
SE;
117 for (
unsigned n = 0; n < (n_p - 1); n++)
119 Father_bound[n_p](n,
SE) =
S;
122 for (
unsigned n = 1; n < n_p; n++)
124 Father_bound[n_p](n_p - 1 + n_p * n,
SE) =
E;
147 using namespace QuadTreeNames;
150 unsigned nvalue = ncont_interpolated_values();
152 Vector<int> bound_cons1(nvalue), bound_cons2(nvalue);
162 get_edge_bcs(bound, bound_cons);
167 get_edge_bcs(
S, bound_cons1);
168 get_edge_bcs(
E, bound_cons2);
170 for (
unsigned k = 0; k < nvalue; k++)
172 bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
178 get_edge_bcs(
S, bound_cons1);
179 get_edge_bcs(
W, bound_cons2);
181 for (
unsigned k = 0; k < nvalue; k++)
183 bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
189 get_edge_bcs(
N, bound_cons1);
190 get_edge_bcs(
W, bound_cons2);
192 for (
unsigned k = 0; k < nvalue; k++)
194 bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
200 get_edge_bcs(
N, bound_cons1);
201 get_edge_bcs(
E, bound_cons2);
203 for (
unsigned k = 0; k < nvalue; k++)
205 bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
211 "Wrong boundary", OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
227 using namespace QuadTreeNames;
230 unsigned n_p = nnode_1d();
232 unsigned left_node, right_node;
238 left_node = n_p * (n_p - 1);
239 right_node = n_p * n_p - 1;
244 right_node = n_p - 1;
249 right_node = n_p * (n_p - 1);
254 right_node = n_p * n_p - 1;
258 std::ostringstream error_stream;
259 error_stream <<
"Wrong edge " << edge <<
" passed to get_edge_bcs(..)"
263 error_stream.str(), OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
267 unsigned maxnvalue = ncont_interpolated_values();
272 for (
unsigned k = 0; k < maxnvalue; k++)
275 node_pt(left_node)->is_pinned(k) * node_pt(right_node)->is_pinned(k);
289 std::set<unsigned>& boundary)
const
291 using namespace QuadTreeNames;
294 unsigned n_p = nnode_1d();
296 int left_node = -1, right_node = -1;
302 left_node = n_p * (n_p - 1);
303 right_node = n_p * n_p - 1;
308 right_node = n_p - 1;
313 right_node = n_p * (n_p - 1);
318 right_node = n_p * n_p - 1;
323 right_node = n_p - 1;
331 right_node = n_p * n_p - 1;
335 right_node = n_p * (n_p - 1);
339 std::ostringstream error_stream;
340 error_stream <<
"Wrong edge " << edge <<
" passed" << std::endl;
343 error_stream.str(), OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
350 std::set<unsigned>* right_boundaries_pt = 0;
352 node_pt(right_node)->get_boundaries_pt(right_boundaries_pt);
355 if (right_boundaries_pt != 0)
361 copy(right_boundaries_pt->begin(),
362 right_boundaries_pt->end(),
363 inserter(boundary, boundary.begin()));
368 std::set<unsigned>* left_boundaries_pt = 0;
369 node_pt(left_node)->get_boundaries_pt(left_boundaries_pt);
371 if (left_boundaries_pt != 0)
375 std::set_intersection(right_boundaries_pt->begin(),
376 right_boundaries_pt->end(),
377 left_boundaries_pt->begin(),
378 left_boundaries_pt->end(),
379 inserter(boundary, boundary.begin()));
391 const unsigned& boundary,
396 using namespace QuadTreeNames;
399 unsigned n_p = nnode_1d();
402 Shape psi(n_p * n_p);
408 unsigned start = 0, multiplier = 1;
417 std::ostringstream error_stream;
418 error_stream <<
"Coordinate " <<
s[0] <<
" " <<
s[1]
419 <<
" is not on South edge\n";
422 OOMPH_CURRENT_FUNCTION,
423 OOMPH_EXCEPTION_LOCATION);
433 std::ostringstream error_stream;
434 error_stream <<
"Coordinate " <<
s[0] <<
" " <<
s[1]
435 <<
" is not on North edge\n";
438 OOMPH_CURRENT_FUNCTION,
439 OOMPH_EXCEPTION_LOCATION);
443 start = n_p * (n_p - 1);
450 std::ostringstream error_stream;
451 error_stream <<
"Coordinate " <<
s[0] <<
" " <<
s[1]
452 <<
" is not on West edge\n";
455 OOMPH_CURRENT_FUNCTION,
456 OOMPH_EXCEPTION_LOCATION);
467 std::ostringstream error_stream;
468 error_stream <<
"Coordinate " <<
s[0] <<
" " <<
s[1]
469 <<
" is not on East edge\n";
472 OOMPH_CURRENT_FUNCTION,
473 OOMPH_EXCEPTION_LOCATION);
484 std::ostringstream error_stream;
485 error_stream <<
"Wrong edge " << edge <<
" passed" << std::endl;
488 error_stream.str(), OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
492 double inter_zeta = 0.0;
494 for (
unsigned n = 0; n < n_p; n++)
497 unsigned node_number =
start + multiplier * n;
499 node_pt(node_number)->get_coordinates_on_boundary(boundary, zeta);
501 inter_zeta += zeta[0] * psi(node_number);
505 zeta[0] = inter_zeta;
519 using namespace QuadTreeNames;
523 if (s_fraction[0] == 0.0)
527 if (s_fraction[0] == 1.0)
531 if (s_fraction[1] == 0.0)
535 if (s_fraction[1] == 1.0)
541 unsigned n_size = edges.size();
553 int neigh_edge, diff_level;
554 bool in_neighbouring_tree;
557 for (
unsigned j = 0; j < n_size; j++)
567 in_neighbouring_tree);
583 for (
unsigned i = 0;
i < 2;
i++)
585 s[
i] = s_lo_neigh[
i] +
586 s_fraction[translate_s[
i]] * (s_hi_neigh[
i] - s_lo_neigh[
i]);
590 Node* neighbour_node_pt =
594 if (neighbour_node_pt != 0)
598 if (in_neighbouring_tree)
602 quadtree_pt()->root_pt()->is_neighbour_periodic(edges[j]);
605 return neighbour_node_pt;
644 bool& was_already_built,
645 std::ofstream& new_nodes_file)
647 using namespace QuadTreeNames;
650 unsigned n_p = nnode_1d();
653 if (Father_bound[n_p].nrow() == 0)
655 setup_father_bounds();
671 "Something fishy here: I have no father and yet \n";
672 error_message +=
"I have no nodes. Who has created me then?!\n";
675 error_message, OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
680 was_already_built =
false;
692 unsigned ntstorage = time_stepper_pt->ntstorage();
699 throw OomphLibError(
"Can't handle generalised nodal positions (yet).",
700 OOMPH_CURRENT_FUNCTION,
701 OOMPH_EXCEPTION_LOCATION);
748 for (
unsigned i = 0;
i < 2;
i++)
752 0.5 * (s_lo[
i] + 1.0) *
756 0.5 * (s_hi[
i] + 1.0) *
763 if (father_el_pt->
node_pt(0) == 0)
766 "Trouble: father_el_pt->node_pt(0)==0\n Can't build son element!\n",
767 OOMPH_CURRENT_FUNCTION,
768 OOMPH_EXCEPTION_LOCATION);
778 for (
unsigned i0 = 0; i0 < n_p; i0++)
781 s_fraction[0] = local_one_d_fraction_of_node(i0, 0);
783 s[0] = s_lo[0] + (s_hi[0] - s_lo[0]) * s_fraction[0];
785 for (
unsigned i1 = 0; i1 < n_p; i1++)
788 s_fraction[1] = local_one_d_fraction_of_node(i1, 1);
790 s[1] = s_lo[1] + (s_hi[1] - s_lo[1]) * s_fraction[1];
793 jnod = i0 + n_p * i1;
810 bool node_done =
false;
814 Node* created_node_pt =
819 if (created_node_pt != 0)
822 node_pt(jnod) = created_node_pt;
830 for (
unsigned t = 0;
t < ntstorage;
t++)
839 unsigned n_val_at_node = created_node_pt->
nvalue();
840 unsigned n_val_from_function = prev_values.size();
842 unsigned n_var = n_val_at_node < n_val_from_function ?
846 for (
unsigned k = 0; k < n_var; k++)
848 created_node_pt->
set_value(
t, k, prev_values[k]);
864 bool is_periodic =
false;
867 node_created_by_neighbour(s_fraction, is_periodic);
870 if (created_node_pt != 0)
879 Node* neighbour_node_pt = created_node_pt;
882 int father_bound = Father_bound[n_p](jnod, son_type);
889 std::set<unsigned> boundaries;
901 if (boundaries.size() > 1)
904 "boundaries.size()!=1 seems a bit strange..\n",
905 OOMPH_CURRENT_FUNCTION,
906 OOMPH_EXCEPTION_LOCATION);
910 if (boundaries.size() == 0)
912 std::ostringstream error_stream;
913 error_stream <<
"Periodic node is not on a boundary...\n"
914 <<
"Coordinates: " << created_node_pt->
x(0)
915 <<
" " << created_node_pt->
x(1) <<
"\n";
917 OOMPH_CURRENT_FUNCTION,
918 OOMPH_EXCEPTION_LOCATION);
924 construct_boundary_node(jnod, time_stepper_pt);
928 new_node_pt.push_back(created_node_pt);
931 for (
unsigned t = 0;
t < ntstorage;
t++)
939 father_el_pt->
get_x(
t,
s, x_prev);
941 for (
unsigned i = 0;
i < 2;
i++)
943 created_node_pt->
x(
t,
i) = x_prev[
i];
949 for (std::set<unsigned>::iterator it = boundaries.begin();
950 it != boundaries.end();
964 *it, father_bound,
s, zeta);
977 node_pt(jnod) = created_node_pt;
991 bool is_periodic =
false;
994 node_created_by_son_of_neighbour(s_fraction, is_periodic);
997 if (created_node_pt != 0)
1005 Node* neighbour_node_pt = created_node_pt;
1008 int father_bound = Father_bound[n_p](jnod, son_type);
1015 std::set<unsigned> boundaries;
1027 if (boundaries.size() > 1)
1030 "boundaries.size()!=1 seems a bit strange..\n",
1031 OOMPH_CURRENT_FUNCTION,
1032 OOMPH_EXCEPTION_LOCATION);
1036 if (boundaries.size() == 0)
1038 std::ostringstream error_stream;
1039 error_stream <<
"Periodic node is not on a boundary...\n"
1040 <<
"Coordinates: " << created_node_pt->
x(0)
1041 <<
" " << created_node_pt->
x(1) <<
"\n";
1043 OOMPH_CURRENT_FUNCTION,
1044 OOMPH_EXCEPTION_LOCATION);
1050 construct_boundary_node(jnod, time_stepper_pt);
1054 new_node_pt.push_back(created_node_pt);
1057 for (
unsigned t = 0;
t < ntstorage;
t++)
1065 father_el_pt->
get_x(
t,
s, x_prev);
1067 for (
unsigned i = 0;
i < 2;
i++)
1069 created_node_pt->
x(
t,
i) = x_prev[
i];
1075 for (std::set<unsigned>::iterator it = boundaries.begin();
1076 it != boundaries.end();
1090 *it, father_bound,
s, zeta);
1103 node_pt(jnod) = created_node_pt;
1122 int father_bound = Father_bound[n_p](jnod, son_type);
1129 std::set<unsigned> boundaries;
1141 if (boundaries.size() > 1)
1144 "boundaries.size()!=1 seems a bit strange..\n",
1145 OOMPH_CURRENT_FUNCTION,
1146 OOMPH_EXCEPTION_LOCATION);
1152 if (boundaries.size() > 0)
1156 construct_boundary_node(jnod, time_stepper_pt);
1158 new_node_pt.push_back(created_node_pt);
1165 Vector<int> bound_cons(ncont_interpolated_values());
1166 father_el_pt->
get_bcs(father_bound, bound_cons);
1169 unsigned n_value = created_node_pt->
nvalue();
1170 for (
unsigned k = 0; k < n_value; k++)
1174 created_node_pt->
pin(k);
1181 dynamic_cast<SolidNode*
>(created_node_pt);
1182 if (solid_node_pt != 0)
1185 unsigned n_dim = created_node_pt->
ndim();
1190 if (father_solid_el_pt == 0)
1193 "We have a SolidNode outside a refineable SolidElement\n";
1195 "during mesh refinement -- this doesn't make sense";
1198 OOMPH_CURRENT_FUNCTION,
1199 OOMPH_EXCEPTION_LOCATION);
1206 for (
unsigned k = 0; k < n_dim; k++)
1208 if (solid_bound_cons[k])
1218 for (std::set<unsigned>::iterator it = boundaries.begin();
1219 it != boundaries.end();
1233 *it, father_bound,
s, zeta);
1244 created_node_pt = construct_node(jnod, time_stepper_pt);
1246 new_node_pt.push_back(created_node_pt);
1262 for (
unsigned t = 0;
t < ntstorage;
t++)
1270 father_el_pt->
get_x(
t,
s, x_prev);
1273 for (
unsigned i = 0;
i < 2;
i++)
1275 created_node_pt->
x(
t,
i) = x_prev[
i];
1280 for (
unsigned t = 0;
t < ntstorage;
t++)
1287 unsigned n_value = created_node_pt->
nvalue();
1288 for (
unsigned k = 0; k < n_value; k++)
1290 created_node_pt->
set_value(
t, k, prev_values[k]);
1318 node_pt(jnod),
s, father_el_pt);
1323 if ((!node_done) && (new_nodes_file.is_open()))
1325 new_nodes_file << node_pt(jnod)->x(0) <<
" "
1326 << node_pt(jnod)->x(1) << std::endl;
1341 if (father_m_el_pt != 0)
1355 "Failed to cast to MacroElementNodeUpdateElementBase*\n";
1357 "Strange -- if the father is a MacroElementNodeUpdateElement\n";
1358 error_message +=
"the son should be too....\n";
1361 error_message, OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
1375 #ifdef OOMPH_HAS_MPI
1378 tree_pt()->father_pt()->object_pt()->non_halo_proc_ID();
1393 if (aux_father_el_pt == 0)
1396 "Failed to cast to ElementWithMovingNodes*\n";
1398 "Strange -- if the son is a ElementWithMovingNodes\n";
1399 error_message +=
"the father should be too....\n";
1402 error_message, OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
1408 if (aux_father_el_pt
1409 ->are_dresidual_dnodal_coordinates_always_evaluated_by_fd())
1420 if (aux_father_el_pt
1421 ->is_fill_in_jacobian_from_geometric_data_bypassed())
1436 was_already_built =
true;
1449 outfile <<
"ZONE I=2,J=2, C=" <<
colour << std::endl;
1454 outfile << corner[0] <<
" " << corner[1] <<
" " <<
Number << std::endl;
1459 outfile << corner[0] <<
" " << corner[1] <<
" " <<
Number << std::endl;
1464 outfile << corner[0] <<
" " << corner[1] <<
" " <<
Number << std::endl;
1469 outfile << corner[0] <<
" " << corner[1] <<
" " <<
Number << std::endl;
1472 outfile <<
"TEXT CS = GRID, X = " << corner[0] <<
",Y = " << corner[1]
1473 <<
", HU = GRID, H = 0.01, AN = MIDCENTER, T =\"" <<
Number <<
"\""
1485 if (output_stream.size() != 4)
1488 OOMPH_CURRENT_FUNCTION,
1489 OOMPH_EXCEPTION_LOCATION);
1493 using namespace QuadTreeNames;
1496 quad_hang_helper(-1,
S, *(output_stream[0]));
1497 quad_hang_helper(-1,
N, *(output_stream[1]));
1498 quad_hang_helper(-1,
W, *(output_stream[2]));
1499 quad_hang_helper(-1,
E, *(output_stream[3]));
1508 using namespace QuadTreeNames;
1510 std::ofstream dummy_hangfile;
1511 quad_hang_helper(value_id,
S, dummy_hangfile);
1512 quad_hang_helper(value_id,
N, dummy_hangfile);
1513 quad_hang_helper(value_id,
W, dummy_hangfile);
1514 quad_hang_helper(value_id,
E, dummy_hangfile);
1524 std::ofstream& output_hangfile)
1526 using namespace QuadTreeNames;
1531 int neigh_edge, diff_level;
1532 bool in_neighbouring_tree;
1542 in_neighbouring_tree);
1548 if (diff_level != 0)
1552 bool is_periodic =
false;
1553 if (in_neighbouring_tree)
1570 int neigh_edge_of_neigh, diff_level_of_neigh;
1571 bool in_neighbouring_tree_of_neigh;
1578 translate_s_in_neigh,
1579 s_lo_neigh_of_neigh,
1580 s_hi_neigh_of_neigh,
1581 neigh_edge_of_neigh,
1582 diff_level_of_neigh,
1583 in_neighbouring_tree_of_neigh);
1586 neigh_pt = neigh_of_neigh_pt;
1587 neigh_edge = neigh_edge_of_neigh;
1602 for (
unsigned i = 0;
i < 2;
i++)
1604 s_lo_frac[
i] = (s_lo_neigh[
i] - s_min) / (s_max - s_min);
1605 s_hi_frac[
i] = (s_hi_neigh[
i] - s_min) / (s_max - s_min);
1610 for (
unsigned i = 0;
i < 2;
i++)
1612 s_lo_neigh[
i] = s_lo_neigh_of_neigh[
i] +
1613 s_lo_frac[translate_s_in_neigh[
i]] *
1614 (s_hi_neigh_of_neigh[
i] - s_lo_neigh_of_neigh[
i]);
1615 s_hi_neigh[
i] = s_lo_neigh_of_neigh[
i] +
1616 s_hi_frac[translate_s_in_neigh[
i]] *
1617 (s_hi_neigh_of_neigh[
i] - s_lo_neigh_of_neigh[
i]);
1622 for (
unsigned i = 0;
i < 2;
i++)
1624 temp_translate[
i] = translate_s_in_neigh[translate_s[
i]];
1626 for (
unsigned i = 0;
i < 2;
i++)
1628 translate_s[
i] = temp_translate[
i];
1633 unsigned n_p = ninterpolating_node_1d(value_id);
1635 Node* local_node_pt = 0;
1637 for (
unsigned i0 = 0; i0 < n_p; i0++)
1648 local_one_d_fraction_of_interpolating_node(i0, 0, value_id);
1649 s_fraction[1] = 1.0;
1651 interpolating_node_pt(i0 + n_p * (n_p - 1), value_id);
1656 local_one_d_fraction_of_interpolating_node(i0, 0, value_id);
1657 s_fraction[1] = 0.0;
1658 local_node_pt = interpolating_node_pt(i0, value_id);
1662 s_fraction[0] = 1.0;
1664 local_one_d_fraction_of_interpolating_node(i0, 1, value_id);
1666 interpolating_node_pt(n_p - 1 + n_p * i0, value_id);
1670 s_fraction[0] = 0.0;
1672 local_one_d_fraction_of_interpolating_node(i0, 1, value_id);
1673 local_node_pt = interpolating_node_pt(n_p * i0, value_id);
1678 OOMPH_CURRENT_FUNCTION,
1679 OOMPH_EXCEPTION_LOCATION);
1684 for (
unsigned i = 0;
i < 2;
i++)
1686 s_in_neighb[
i] = s_lo_neigh[
i] + s_fraction[translate_s[
i]] *
1687 (s_hi_neigh[
i] - s_lo_neigh[
i]);
1691 Node* neighbouring_node_pt =
1693 s_in_neighb, value_id);
1696 if (0 == neighbouring_node_pt)
1700 bool make_hanging_node =
false;
1706 make_hanging_node =
true;
1715 make_hanging_node =
true;
1720 if (make_hanging_node ==
true)
1735 unsigned n_neighbour;
1738 for (
unsigned n_edge = 0; n_edge < n_p; n_edge++)
1743 n_neighbour = n_p * (n_p - 1) + n_edge;
1747 n_neighbour = n_edge;
1751 n_neighbour = n_p * n_edge;
1755 n_neighbour = n_p * n_edge + (n_p - 1);
1760 OOMPH_CURRENT_FUNCTION,
1761 OOMPH_EXCEPTION_LOCATION);
1782 if (output_hangfile.is_open())
1784 output_hangfile << local_node_pt->
x(0) <<
" "
1785 << local_node_pt->
x(1) << std::endl;
1792 if (local_node_pt != neighbouring_node_pt)
1794 std::ostringstream warning_stream;
1795 warning_stream <<
"SANITY CHECK in quad_hang_helper \n"
1796 <<
"Current node " << local_node_pt <<
" at "
1797 <<
"(" << local_node_pt->
x(0) <<
", "
1798 << local_node_pt->
x(1) <<
")"
1799 <<
" is not hanging and has " << std::endl
1800 <<
"Neighbour's node " << neighbouring_node_pt
1802 <<
"(" << neighbouring_node_pt->
x(0) <<
", "
1803 << neighbouring_node_pt->
x(1) <<
")" << std::endl
1804 <<
"even though the two should be "
1805 <<
"identical" << std::endl;
1807 "RefineableQElement<2>::quad_hang_helper()",
1808 OOMPH_EXCEPTION_LOCATION);
1822 local_node_pt->
x(0) = x_in_neighb[0];
1823 local_node_pt->
x(1) = x_in_neighb[1];
1839 using namespace QuadTreeNames;
1842 unsigned n_p = nnode_1d();
1846 unsigned n_time = 1;
1851 double max_error_val = 0.0;
1860 for (
unsigned edge_counter = 0; edge_counter < 4; edge_counter++)
1864 int neigh_edge, diff_level;
1865 bool in_neighbouring_tree;
1875 in_neighbouring_tree);
1882 bool is_periodic =
false;
1883 if (in_neighbouring_tree)
1891 for (
unsigned i0 = 0; i0 < n_p; i0++)
1894 Node* local_node_pt = 0;
1896 switch (edge_counter)
1900 s_fraction[0] = local_one_d_fraction_of_node(i0, 0);
1901 s_fraction[1] = 0.0;
1903 local_node_pt = node_pt(i0);
1908 s_fraction[0] = local_one_d_fraction_of_node(i0, 0);
1909 s_fraction[1] = 1.0;
1911 local_node_pt = node_pt(i0 + n_p * (n_p - 1));
1916 s_fraction[0] = 0.0;
1917 s_fraction[1] = local_one_d_fraction_of_node(i0, 1);
1919 local_node_pt = node_pt(n_p * i0);
1924 s_fraction[0] = 1.0;
1925 s_fraction[1] = local_one_d_fraction_of_node(i0, 1);
1927 local_node_pt = node_pt(n_p - 1 + n_p * i0);
1934 for (
unsigned i = 0;
i < 2;
i++)
1937 s[
i] = -1.0 + 2.0 * s_fraction[
i];
1939 s_in_neighb[
i] = s_lo_neigh[
i] + s_fraction[translate_s[
i]] *
1940 (s_hi_neigh[
i] - s_lo_neigh[
i]);
1944 for (
unsigned t = 0;
t < n_time;
t++)
1951 if (is_periodic ==
false)
1953 for (
int i = 0;
i < 2;
i++)
1956 double err = std::fabs(local_node_pt->
x(
t,
i) - x_in_neighb[
i]);
1962 << local_node_pt->
x(
t,
i) <<
" " << x_in_neighb[
i]
1966 << local_node_pt->
x(1) << std::endl;
1971 if (err > max_error_x[
i])
1973 max_error_x[
i] = err;
1983 t, s_in_neighb, values_in_neighb);
1987 get_interpolated_values(
t,
s, values);
1995 for (
unsigned ival = 0; ival < num_val; ival++)
1997 double err = std::fabs(values[ival] - values_in_neighb[ival]);
2001 oomph_info << local_node_pt->
x(0) <<
" " << local_node_pt->
x(1)
2003 <<
"erru (S)" << err <<
" " << ival <<
" "
2004 << get_node_number(local_node_pt) <<
" "
2005 << values[ival] <<
" " << values_in_neighb[ival]
2009 if (err > max_error_val)
2011 max_error_val = err;
2019 max_error = max_error_x[0];
2020 if (max_error_x[1] > max_error) max_error = max_error_x[1];
2021 if (max_error_val > max_error) max_error = max_error_val;
2023 if (max_error > 1
e-9)
2025 oomph_info <<
"\n#------------------------------------ \n#Max error ";
2026 oomph_info << max_error_x[0] <<
" " << max_error_x[1] <<
" "
2027 << max_error_val << std::endl;
2028 oomph_info <<
"#------------------------------------ \n " << std::endl;
2067 using namespace QuadTreeNames;
2070 unsigned n_dim = this->nodal_dimension();
2073 Vector<int> bound_cons1(n_dim), bound_cons2(n_dim);
2083 get_edge_solid_bcs(bound, solid_bound_cons);
2088 get_edge_solid_bcs(
S, bound_cons1);
2089 get_edge_solid_bcs(
E, bound_cons2);
2091 for (
unsigned k = 0; k < n_dim; k++)
2093 solid_bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
2099 get_edge_solid_bcs(
S, bound_cons1);
2100 get_edge_solid_bcs(
W, bound_cons2);
2102 for (
unsigned k = 0; k < n_dim; k++)
2104 solid_bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
2110 get_edge_solid_bcs(
N, bound_cons1);
2111 get_edge_solid_bcs(
W, bound_cons2);
2113 for (
unsigned k = 0; k < n_dim; k++)
2115 solid_bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
2121 get_edge_solid_bcs(
N, bound_cons1);
2122 get_edge_solid_bcs(
E, bound_cons2);
2124 for (
unsigned k = 0; k < n_dim; k++)
2126 solid_bound_cons[k] = (bound_cons1[k] || bound_cons2[k]);
2132 "Wrong boundary", OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
2147 const int& edge,
Vector<int>& solid_bound_cons)
const
2149 using namespace QuadTreeNames;
2152 unsigned n_p = nnode_1d();
2155 unsigned left_node, right_node;
2161 left_node = n_p * (n_p - 1);
2162 right_node = n_p * n_p - 1;
2167 right_node = n_p - 1;
2172 right_node = n_p * (n_p - 1);
2176 left_node = n_p - 1;
2177 right_node = n_p * n_p - 1;
2181 std::ostringstream error_stream;
2182 error_stream <<
"Wrong edge " << edge
2183 <<
" passed to get_solid_edge_bcs(..)" << std::endl;
2186 error_stream.str(), OOMPH_CURRENT_FUNCTION, OOMPH_EXCEPTION_LOCATION);
2194 if (left_node_pt == 0)
2197 "Left node cannot be cast to SolidNode --> something is wrong",
2198 OOMPH_CURRENT_FUNCTION,
2199 OOMPH_EXCEPTION_LOCATION);
2201 if (right_node_pt == 0)
2204 "Right node cannot be cast to SolidNode --> something is wrong",
2205 OOMPH_CURRENT_FUNCTION,
2206 OOMPH_EXCEPTION_LOCATION);
2212 unsigned n_dim = this->nodal_dimension();
2217 for (
unsigned k = 0; k < n_dim; k++)
////////////////////////////////////////////////////////////////////
void setup_algebraic_node_update(Node *&node_pt, const Vector< double > &s_father, FiniteElement *father_el_pt) const
Set up node update info for (newly created) algebraic node: I.e. work out its node update information...
void pin(const unsigned &i)
Pin the i-th stored variable.
TimeStepper *& time_stepper_pt()
Return the pointer to the timestepper.
void set_value(const unsigned &i, const double &value_)
Set the i-th stored data value to specified value. The only reason that we require an explicit set fu...
unsigned nvalue() const
Return number of values stored in data object (incl pinned ones).
/////////////////////////////////////////////////////////////////////// /////////////////////////////...
void enable_bypass_fill_in_jacobian_from_geometric_data()
Bypass the call to fill_in_jacobian_from_geometric_data.
int & method_for_shape_derivs()
Access to method (enumerated flag) for determination of shape derivs.
void enable_always_evaluate_dresidual_dnodal_coordinates_by_fd()
Insist that shape derivatives are always evaluated by fd (using FiniteElement::get_dresidual_dnodal_c...
Node *& node_pt(const unsigned &n)
Return a pointer to the local node n.
virtual Node * get_node_at_local_coordinate(const Vector< double > &s) const
If there is a node at this local coordinate, return the pointer to the node.
virtual double s_min() const
Min value of local coordinate.
virtual double interpolated_x(const Vector< double > &s, const unsigned &i) const
Return FE interpolated coordinate x[i] at local coordinate s.
MacroElement * Macro_elem_pt
Pointer to the element's macro element (NULL by default)
virtual double s_max() const
Max. value of local coordinate.
void get_x(const Vector< double > &s, Vector< double > &x) const
Global coordinates as function of local coordinates. Either via FE representation or via macro-elemen...
Class that contains data for hanging nodes.
void set_master_node_pt(const unsigned &i, Node *const &master_node_pt, const double &weight)
Set the pointer to the i-th master node and its weight.
////////////////////////////////////////////////////////////////////
Vector< GeomObject * > & geom_object_pt()
Vector of (pointers to) geometric objects involved in node update function.
virtual void set_node_update_info(const Vector< GeomObject * > &geom_object_pt)=0
Set node update information: Pass the vector of (pointers to) the geometric objects that affect the n...
void add_boundary_node(const unsigned &b, Node *const &node_pt)
Add a (pointer to) a node to the b-th boundary.
void add_node_pt(Node *const &node_pt)
Add a (pointer to a) node to the mesh.
bool boundary_coordinate_exists(const unsigned &i) const
Indicate whether the i-th boundary has an intrinsic coordinate.
Nodes are derived from Data, but, in addition, have a definite (Eulerian) position in a space of a gi...
double & x(const unsigned &i)
Return the i-th nodal coordinate.
HangInfo *const & hanging_pt() const
Return pointer to hanging node data (this refers to the geometric hanging node status) (const version...
unsigned ndim() const
Return (Eulerian) spatial dimension of the node.
virtual void set_coordinates_on_boundary(const unsigned &b, const unsigned &k, const Vector< double > &boundary_zeta)
Set the vector of the k-th generalised boundary coordinates on mesh boundary b. Broken virtual interf...
void set_hanging_pt(HangInfo *const &hang_pt, const int &i)
Set the hanging data for the i-th value. (hang_pt=0 to make non-hanging)
virtual void make_periodic(Node *const &node_pt)
Make the node periodic by copying the values from node_pt. Note that the coordinates will always rema...
unsigned nposition_type() const
Number of coordinate types needed in the mapping between local and global coordinates.
bool is_hanging() const
Test whether the node is geometrically hanging.
An OomphLibError object which should be thrown when an run-time error is encountered....
An OomphLibWarning object which should be created as a temporary object to issue a warning....
double & s_macro_ll(const unsigned &i)
Access fct to the i-th coordinate of the element's "lower left" vertex in the associated MacroElement...
double & s_macro_ur(const unsigned &i)
Access fct to the i-th coordinate of the element's "upper right" vertex in the associated MacroElemen...
QuadTree class: Recursively defined, generalised quadtree.
QuadTree * gteq_edge_neighbour(const int &direction, Vector< unsigned > &translate_s, Vector< double > &s_lo, Vector< double > &s_hi, int &edge, int &diff_level, bool &in_neighbouring_tree) const
Return pointer to greater or equal-sized edge neighbour in specified direction; also provide info reg...
RefineableElements are FiniteElements that may be subdivided into children to provide a better local ...
virtual bool nodes_built()
Return true if all the nodes have been built, false if not.
virtual unsigned ncont_interpolated_values() const =0
Number of continuously interpolated values. Note: We assume that they are located at the beginning of...
virtual unsigned ninterpolating_node(const int &value_id)
Return the number of nodes that are used to interpolate the value_id-th unknown. Default is to assume...
virtual void interpolating_basis(const Vector< double > &s, Shape &psi, const int &value_id) const
Return the basis functions that are used to interpolate the value_id-th unknown. By default assume is...
virtual Node * interpolating_node_pt(const unsigned &n, const int &value_id)
In mixed elements, different sets of nodes are used to interpolate different unknowns....
virtual Node * get_interpolating_node_at_local_coordinate(const Vector< double > &s, const int &value_id)
Return a pointer to the node that interpolates the value-id-th unknown at local coordinate s....
virtual void get_interpolated_values(const Vector< double > &s, Vector< double > &values)
Get all continously interpolated function values in this element as a Vector. Note: Vector sets is ow...
Refineable version of QElement<2,NNODE_1D>.
void get_boundaries(const int &edge, std::set< unsigned > &boundaries) const
Determine set of (mesh) boundaries that the element edge/vertex lives on.
void get_bcs(int bound, Vector< int > &bound_cons) const
Determine Vector of boundary conditions along edge (or on vertex) bound (S/W/N/E/SW/SE/NW/NE): For va...
void interpolated_zeta_on_edge(const unsigned &boundary, const int &edge, const Vector< double > &s, Vector< double > &zeta)
Return the value of the intrinsic boundary coordinate interpolated along the edge (S/W/N/E)
A class that is used to template the refineable Q elements by dimension. It's really nothing more tha...
Refineable version of Solid quad elements.
void get_solid_bcs(int bound, Vector< int > &solid_bound_cons) const
Determine vector of solid (positional) boundary conditions along edge (or on vertex) bound (S/W/N/E/S...
A class that is used to template the solid refineable Q elements by dimension. It's really nothing mo...
A Class for shape functions. In simple cases, the shape functions have only one index that can be tho...
A Class for nodes that deform elastically (i.e. position is an unknown in the problem)....
void pin_position(const unsigned &i)
Pin the nodal position.
bool position_is_pinned(const unsigned &i)
Test whether the i-th coordinate is pinned, 0: false; 1: true.
////////////////////////////////////////////////////////////////////// //////////////////////////////...
bool is_neighbour_periodic(const int &direction)
Return whether the neighbour in the particular direction is periodic.
RefineableElement * object_pt() const
Return the pointer to the object (RefineableElement) represented by the tree.
int son_type() const
Return son type.
static const int OMEGA
Default value for an unassigned neighbour.
TreeRoot *& root_pt()
Return pointer to root of the tree.
void start(const unsigned &i)
(Re-)start i-th timer
std::string string(const unsigned &i)
Return the i-th string or "" if the relevant string hasn't been defined.
unsigned Number
The unsigned.
void shape(const double &s, double *Psi)
Definition for 1D Lagrange shape functions. The value of all the shape functions at the local coordin...
Vector< std::string > colour
Tecplot colours.
//////////////////////////////////////////////////////////////////// ////////////////////////////////...
OomphInfo oomph_info
Single (global) instantiation of the OomphInfo object – this is used throughout the library as a "rep...