Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Move a function to ReferenceCell #14624

Merged
merged 2 commits into from
Dec 30, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
48 changes: 48 additions & 0 deletions include/deal.II/grid/reference_cell.h
Original file line number Diff line number Diff line change
Expand Up @@ -632,6 +632,25 @@ class ReferenceCell
unsigned int
vtk_lagrange_type() const;

/**
* Given a set of node indices of the form $(i)$ or $(i,j)$ or $(i,j,k)$
* (depending on whether the reference cell is in 1d, 2d, or 3d), return
* the index the VTK format uses for this node for cells that are
* subdivided as many times in each of the coordinate directions as
* described by the second argument. For a uniformly subdivided cell,
* the second argument is an array whose elements will all be equal.
*
* The last argument, @p legacy_format, indicates whether to use the
* old, VTK legacy format (when `true`) or the new, VTU format (when
* `false`).
*/
template <int dim>
unsigned int
vtk_lexicographic_to_node_index(
const std::array<unsigned, dim> &node_indices,
const std::array<unsigned, dim> &nodes_per_direction,
const bool legacy_format) const;

/**
* Return the GMSH element type code that corresponds to the reference cell.
*/
Expand Down Expand Up @@ -2555,6 +2574,35 @@ ReferenceCell::permute_according_orientation(
}



template <>
unsigned int
ReferenceCell::vtk_lexicographic_to_node_index<0>(
const std::array<unsigned, 0> &node_indices,
const std::array<unsigned, 0> &nodes_per_direction,
const bool legacy_format) const;

template <>
unsigned int
ReferenceCell::vtk_lexicographic_to_node_index<1>(
const std::array<unsigned, 1> &node_indices,
const std::array<unsigned, 1> &nodes_per_direction,
const bool legacy_format) const;

template <>
unsigned int
ReferenceCell::vtk_lexicographic_to_node_index<2>(
const std::array<unsigned, 2> &node_indices,
const std::array<unsigned, 2> &nodes_per_direction,
const bool legacy_format) const;

template <>
unsigned int
ReferenceCell::vtk_lexicographic_to_node_index<3>(
const std::array<unsigned, 3> &node_indices,
const std::array<unsigned, 3> &nodes_per_direction,
const bool legacy_format) const;

DEAL_II_NAMESPACE_CLOSE

#endif
215 changes: 15 additions & 200 deletions source/base/data_out_base.cc
Original file line number Diff line number Diff line change
Expand Up @@ -995,194 +995,6 @@ namespace



template <int dim>
int
lexicographic_to_vtk_point_index(const std::array<unsigned, dim> &,
const std::array<unsigned, dim> &,
const bool)
{
Assert(false, ExcNotImplemented());
return 0;
}



/**
* Given (i,j,k) coordinates within the Lagrange quadrilateral, return an
* offset into the local connectivity array.
*
* Modified from
* https://github.com/Kitware/VTK/blob/265ca48a/Common/DataModel/vtkLagrangeQuadrilateral.cxx#L558
*/
template <>
int
lexicographic_to_vtk_point_index<2>(
const std::array<unsigned, 2> &indices,
const std::array<unsigned, 2> &points_per_direction,
const bool)
{
const unsigned int i = indices[0];
const unsigned int j = indices[1];

const bool ibdy = (i == 0 || i == points_per_direction[0]);
const bool jbdy = (j == 0 || j == points_per_direction[1]);
// How many boundaries do we lie on at once?
const int nbdy = (ibdy ? 1 : 0) + (jbdy ? 1 : 0);

if (nbdy == 2) // Vertex DOF
{ // ijk is a corner node. Return the proper index (somewhere in [0,3]):
return (i != 0u ? (j != 0u ? 2 : 1) : (j != 0u ? 3 : 0));
}

int offset = 4;
if (nbdy == 1) // Edge DOF
{
if (!ibdy)
{ // On i axis
return (i - 1) +
(j != 0u ? points_per_direction[0] - 1 +
points_per_direction[1] - 1 :
0) +
offset;
}

if (!jbdy)
{ // On j axis
return (j - 1) +
(i != 0u ? points_per_direction[0] - 1 :
2 * (points_per_direction[0] - 1) +
points_per_direction[1] - 1) +
offset;
}
}

offset += 2 * (points_per_direction[0] - 1 + points_per_direction[1] - 1);
// nbdy == 0: Face DOF
return offset + (i - 1) + (points_per_direction[0] - 1) * ((j - 1));
}



/**
* Given (i,j,k) coordinates within the Lagrange hexahedron, return an
* offset into the local connectivity array.
*
* Modified from
* https://github.com/Kitware/VTK/blob/265ca48a/Common/DataModel/vtkLagrangeHexahedron.cxx#L734
* (legacy_format=true) and from
* https://github.com/Kitware/VTK/blob/256fe70de00e3441f126276ca4a8c5477d0bcb86/Common/DataModel/vtkHigherOrderHexahedron.cxx#L593
* (legacy_format=false). The two versions differ regarding the ordering of
* lines 10 and 11 (clockwise vs. anti-clockwise). See also:
* https://github.com/Kitware/VTK/blob/7a0b92864c96680b1f42ee84920df556fc6ebaa3/Documentation/release/dev/node-numbering-change-for-VTK_LAGRANGE_HEXAHEDRON.md
*
*/
template <>
int
lexicographic_to_vtk_point_index<3>(
const std::array<unsigned, 3> &indices,
const std::array<unsigned, 3> &points_per_direction,
const bool legacy_format)
{
const unsigned int i = indices[0];
const unsigned int j = indices[1];
const unsigned int k = indices[2];

const bool ibdy = (i == 0 || i == points_per_direction[0]);
const bool jbdy = (j == 0 || j == points_per_direction[1]);
const bool kbdy = (k == 0 || k == points_per_direction[2]);
// How many boundaries do we lie on at once?
const int nbdy = (ibdy ? 1 : 0) + (jbdy ? 1 : 0) + (kbdy ? 1 : 0);

if (nbdy == 3) // Vertex DOF
{ // ijk is a corner node. Return the proper index (somewhere in [0,7]):
return (i != 0u ? (j != 0u ? 2 : 1) : (j != 0u ? 3 : 0)) +
(k != 0u ? 4 : 0);
}

int offset = 8;
if (nbdy == 2) // Edge DOF
{
if (!ibdy)
{ // On i axis
return (i - 1) +
(j != 0u ? points_per_direction[0] - 1 +
points_per_direction[1] - 1 :
0) +
(k != 0u ? 2 * (points_per_direction[0] - 1 +
points_per_direction[1] - 1) :
0) +
offset;
}
if (!jbdy)
{ // On j axis
return (j - 1) +
(i != 0u ? points_per_direction[0] - 1 :
2 * (points_per_direction[0] - 1) +
points_per_direction[1] - 1) +
(k != 0u ? 2 * (points_per_direction[0] - 1 +
points_per_direction[1] - 1) :
0) +
offset;
}
// !kbdy, On k axis
offset +=
4 * (points_per_direction[0] - 1) + 4 * (points_per_direction[1] - 1);
if (legacy_format)
return (k - 1) +
(points_per_direction[2] - 1) *
(i != 0u ? (j != 0u ? 3 : 1) : (j != 0u ? 2 : 0)) +
offset;
else
return (k - 1) +
(points_per_direction[2] - 1) *
(i != 0u ? (j != 0u ? 2 : 1) : (j != 0u ? 3 : 0)) +
offset;
}

offset += 4 * (points_per_direction[0] - 1 + points_per_direction[1] - 1 +
points_per_direction[2] - 1);
if (nbdy == 1) // Face DOF
{
if (ibdy) // On i-normal face
{
return (j - 1) + ((points_per_direction[1] - 1) * (k - 1)) +
(i != 0u ? (points_per_direction[1] - 1) *
(points_per_direction[2] - 1) :
0) +
offset;
}
offset +=
2 * (points_per_direction[1] - 1) * (points_per_direction[2] - 1);
if (jbdy) // On j-normal face
{
return (i - 1) + ((points_per_direction[0] - 1) * (k - 1)) +
(j != 0u ? (points_per_direction[2] - 1) *
(points_per_direction[0] - 1) :
0) +
offset;
}
offset +=
2 * (points_per_direction[2] - 1) * (points_per_direction[0] - 1);
// kbdy, On k-normal face
return (i - 1) + ((points_per_direction[0] - 1) * (j - 1)) +
(k != 0u ? (points_per_direction[0] - 1) *
(points_per_direction[1] - 1) :
0) +
offset;
}

// nbdy == 0: Body DOF
offset +=
2 * ((points_per_direction[1] - 1) * (points_per_direction[2] - 1) +
(points_per_direction[2] - 1) * (points_per_direction[0] - 1) +
(points_per_direction[0] - 1) * (points_per_direction[1] - 1));
return offset + (i - 1) +
(points_per_direction[0] - 1) *
((j - 1) + (points_per_direction[1] - 1) * ((k - 1)));
}



/**
* Count the number of nodes and cells referenced by the given
* argument, and return these numbers (in order nodes, then cells)
Expand Down Expand Up @@ -3116,8 +2928,9 @@ namespace DataOutBase
{
const unsigned int local_index = i1;
const unsigned int connectivity_index =
lexicographic_to_vtk_point_index<1>(
{{i1}}, {{n_subdivisions}}, legacy_format);
patch.reference_cell
.template vtk_lexicographic_to_node_index<1>(
{{i1}}, {{n_subdivisions}}, legacy_format);
connectivity[connectivity_index] = local_index;
}

Expand All @@ -3130,10 +2943,11 @@ namespace DataOutBase
{
const unsigned int local_index = i2 * n + i1;
const unsigned int connectivity_index =
lexicographic_to_vtk_point_index<2>(
{{i1, i2}},
{{n_subdivisions, n_subdivisions}},
legacy_format);
patch.reference_cell
.template vtk_lexicographic_to_node_index<2>(
{{i1, i2}},
{{n_subdivisions, n_subdivisions}},
legacy_format);
connectivity[connectivity_index] = local_index;
}

Expand All @@ -3148,12 +2962,13 @@ namespace DataOutBase
const unsigned int local_index =
i3 * n * n + i2 * n + i1;
const unsigned int connectivity_index =
lexicographic_to_vtk_point_index<3>(
{{i1, i2, i3}},
{{n_subdivisions,
n_subdivisions,
n_subdivisions}},
legacy_format);
patch.reference_cell
.template vtk_lexicographic_to_node_index<3>(
{{i1, i2, i3}},
{{n_subdivisions,
n_subdivisions,
n_subdivisions}},
legacy_format);
connectivity[connectivity_index] = local_index;
}

Expand Down