19 #include "libmesh/face_quad.h" 20 #include "libmesh/edge_edge2.h" 21 #include "libmesh/face_quad4.h" 22 #include "libmesh/enum_elem_quality.h" 65 libmesh_assert_less (s, this->
n_sides());
75 libmesh_assert_less (s, this->
n_sides());
84 unsigned int side_node)
const 86 libmesh_assert_less (side, this->
n_sides());
95 unsigned int edge_node)
const 114 libmesh_assert_less (i, this->
n_sides());
116 std::unique_ptr<Elem> edge = std::make_unique<Edge2>();
118 for (
auto n : edge->node_index_range())
127 const unsigned int i)
129 this->simple_side_ptr<Quad,Quad4>(side, i,
EDGE2);
135 const unsigned int s)
const 138 libmesh_assert_less (s, this->
n_sides());
142 unsigned int n = (c < 2) ? c : 5-c;
143 return (n == s || n == (s+1)%4);
150 libmesh_assert_less (side_in, 4);
152 return (side_in + 2) % 4;
158 const unsigned int side_in)
const 160 libmesh_assert_less (node_in, 8);
161 libmesh_assert_less (node_in, this->
n_nodes());
162 libmesh_assert_less (side_in, this->
n_sides());
165 static const unsigned char side02_nodes_map[] =
166 {3, 2, 1, 0, 6, 255, 4, 255};
167 static const unsigned char side13_nodes_map[] =
168 {1, 0, 3, 2, 255, 7, 255, 5};
174 return side02_nodes_map[node_in];
177 return side13_nodes_map[node_in];
179 libmesh_error_msg(
"Unsupported side_in = " << side_in);
199 std::vector<unsigned int>
202 libmesh_assert_less(n, this->
n_nodes());
267 if (v0_norm == 0. || v1_norm == 0.)
273 Real v0s = v0_norm*sin_theta;
274 Real v1s = v1_norm*sin_theta;
285 auto [min0, max0] = std::minmax(v0_norm, v1s);
286 auto [min1, max1] = std::minmax(v0s, v1_norm);
289 return std::max(max0/min0, max1/min1);
304 if ((d02 > 0.) && (d13 >0.))
305 if (d02 < d13)
return d02 / d13;
306 else return d13 / d02;
317 Real min_edge = *std::min_element(lengths, lengths+4);
324 return std::sqrt(2) * min_edge / d_max;
333 typedef std::array<Real, 4> Array4;
334 typedef std::array<Real, 6> Array6;
344 std::array<Array6, 4> A;
345 for (
unsigned int k=0; k<4; ++k)
348 kp1 = k+1 > 3 ? k+1-4 : k+1,
349 kp3 = k+3 > 3 ? k+3-4 : k+3;
353 A[k] = {{x[kp1] - x[k], x[kp3] - x[k],
354 y[kp1] - y[k], y[kp3] - y[k],
355 z[kp1] - z[k], z[kp3] - z[k]}};
360 std::array<Array4, 4> T;
361 for (
unsigned int k=0; k<4; ++k)
364 top_left = A[k][0]*A[k][0] + A[k][2]*A[k][2] + A[k][4]*A[k][4],
365 off_diag = A[k][0]*A[k][1] + A[k][2]*A[k][3] + A[k][4]*A[k][5],
366 bot_rigt = A[k][1]*A[k][1] + A[k][3]*A[k][3] + A[k][5]*A[k][5];
368 T[k] = {{top_left, off_diag,
369 off_diag, bot_rigt}};
376 for (
unsigned int k=0; k<4; ++k)
377 alpha[k] = std::sqrt(T[k][0]*T[k][3] - T[k][1]*T[k][2]);
383 if (*std::min_element(alpha.begin(), alpha.end()) == 0.)
391 for (
unsigned int k=0; k<4; ++k)
392 den += (T[k][0] + T[k][3]) / alpha[k];
393 return (den == 0.) ? 0 : (8. / den);
397 for (
unsigned int k=0; k<4; ++k)
398 den += std::sqrt(T[k][0] * T[k][3]) / alpha[k];
399 return (den == 0.) ? 0 : (4. / den);
447 Real dot_01 = corner_0_vec * corner_1_vec;
448 Real dot_02 = corner_0_vec * corner_2_vec;
449 Real dot_03 = corner_0_vec * corner_3_vec;
451 if ((dot_01 <= 0.) || (dot_02 <= 0.) || (dot_03 <= 0.))
475 return std::min(n0*n2, n1*n3);
490 std::pair<Real, Real> bounds;
522 bounds.second = 135.;
555 libMesh::out <<
"Warning: Invalid quality measure chosen." << std::endl;
566 const Real eps)
const 568 const Real & xi = p(0);
569 const Real & eta = p(1);
572 return ((xi >= -1.-eps) &&
608 #ifdef LIBMESH_ENABLE_AMR 615 { 0, 2, 12, 10, 1, 7, 11, 5, 6},
618 { 2, 4, 14, 12, 3, 9, 13, 7, 8},
621 { 10, 12, 22, 20, 11, 17, 21, 15, 16},
624 { 12, 14, 24, 22, 13, 19, 23, 17, 18}
virtual std::pair< Real, Real > qual_bounds(const ElemQuality q) const override
virtual bool is_flipped() const override final
virtual unsigned int n_vertices() const override final
auto norm() const -> decltype(std::norm(T()))
virtual bool is_face(const unsigned int i) const =0
static const unsigned int side_nodes_map[num_sides][nodes_per_side]
This maps the node of the side to element node numbers.
static const int _child_node_lookup[4][9]
Lookup table from child id, child node id to "possible node location" (a simple dictionary-index in a...
static constexpr Real TOLERANCE
T cross_norm(const TypeVector< T > &b, const TypeVector< T > &c)
Calls cross_norm_sq() and takes the square root of the result.
virtual std::unique_ptr< Elem > side_ptr(const unsigned int i) override final
virtual bool is_node_on_side(const unsigned int n, const unsigned int s) const =0
virtual dof_id_type key() const override
static const Real _master_points[9][3]
Master element node locations.
The libMesh namespace provides an interface to certain functionality in the library.
virtual unsigned int n_children() const override final
Real length(const unsigned int n1, const unsigned int n2) const
static const unsigned short int _second_order_vertex_child_index[9]
Vector that names the child vertex index for each second order node.
virtual std::vector< unsigned int > edges_adjacent_to_node(const unsigned int n) const override
static const unsigned short int _second_order_vertex_child_number[9]
Vector that names a child sharing each second order node.
ElemQuality
Defines an enum for element quality metrics.
virtual unsigned int local_side_node(unsigned int side, unsigned int side_node) const override
TypeVector< typename CompareTypes< T, T2 >::supertype > cross(const TypeVector< T2 > &v) const
static const unsigned short int _second_order_adjacent_vertices[4][2]
Matrix that tells which vertices define the location of mid-side (or second-order) nodes...
virtual Real quality(const ElemQuality q) const override
static const int nodes_per_side
virtual dof_id_type low_order_key(const unsigned int s) const override
virtual unsigned int n_sides() const override final
static const int num_sides
Geometric constants for Quad4.
static const unsigned int adjacent_sides_map[4][2]
This maps the node to the (in this case) 2 side ids adjacent to the node.
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const Node * node_ptr(const unsigned int i) const
virtual bool is_vertex(const unsigned int i) const =0
virtual Real quality(const ElemQuality q) const
virtual unsigned int opposite_side(const unsigned int s) const override final
virtual unsigned int opposite_node(const unsigned int n, const unsigned int s) const override final
virtual unsigned int n_nodes() const override
static dof_id_type compute_key(dof_id_type n0)
virtual bool on_reference_element(const Point &p, const Real eps=TOLERANCE) const override final
A Point defines a location in LIBMESH_DIM dimensional Real space.
dof_id_type node_id(const unsigned int i) const
const Point & point(const unsigned int i) const
virtual unsigned int local_edge_node(unsigned int edge, unsigned int edge_node) const override
Calls local_side_node(edge, edge_node).
virtual bool is_edge(const unsigned int i) const =0
static const int num_children
virtual bool is_child_on_side(const unsigned int c, const unsigned int s) const override final