From 3b72c5426cd7d1b2e86246c430a1fee54b7d870c Mon Sep 17 00:00:00 2001 From: Luca Heltai Date: Thu, 28 Jan 2021 12:34:02 +0100 Subject: [PATCH] Added GridIn::read_msh() --- include/deal.II/grid/grid_in.h | 59 ++ source/grid/grid_in.cc | 218 +++++++ tests/gmsh/gmsh_api_03.cc | 65 ++ .../gmsh_api_03.with_gmsh_with_api=on.output | 451 +++++++++++++ tests/gmsh/gmsh_api_04.cc | 86 +++ .../gmsh_api_04.with_gmsh_with_api=on.output | 616 ++++++++++++++++++ 6 files changed, 1495 insertions(+) create mode 100644 tests/gmsh/gmsh_api_03.cc create mode 100644 tests/gmsh/gmsh_api_03.with_gmsh_with_api=on.output create mode 100644 tests/gmsh/gmsh_api_04.cc create mode 100644 tests/gmsh/gmsh_api_04.with_gmsh_with_api=on.output diff --git a/include/deal.II/grid/grid_in.h b/include/deal.II/grid/grid_in.h index 03f7a9e5dc..465f786f0a 100644 --- a/include/deal.II/grid/grid_in.h +++ b/include/deal.II/grid/grid_in.h @@ -521,6 +521,65 @@ public: void read_msh(std::istream &in); +#ifdef DEAL_II_GMSH_WITH_API + /** + * Read grid data using Gmsh API. Any file supported by Gmsh can be passed as + * argument. The format is deduced from the filename extension. + * + * This function interprets non-named physical ids (gmsh format < 4.0) as + * material or boundary ids (similarly to what happens with the other + * read_msh() function). If you want to specify non default manifold or + * boundary ids, you must group all entities that require a non default + * boundary or manifold id into named physical groups, where the name is + * interpreted using the function Patterns::Tools::to_value() applied to a + * `std::map`. The keys can be either `MaterialID` (if the + * physical group refers to object of dimension `dim`), `BoundaryID` (if the + * group refers to objects of dimension < `dim`), or `ManifoldID`. + * + * From the Gmsh documentation, the formats of the physical tags follows the + * following conventions: + * @code + * $PhysicalNames // same as MSH version 2 + * numPhysicalNames(ASCII int) + * dimension(ASCII int) physicalTag(ASCII int) "name"(127 characters max) + * ... + * $EndPhysicalNames + * @endcode + * + * For example, the following snippet of mesh file + * @code + * MeshFormat + * 4.1 0 8 + * $EndMeshFormat + * $PhysicalNames + * 4 + * 1 1 "ManifoldID:0" + * 1 2 "BoundaryID: -1, ManifoldID: 1" + * 2 3 "ManifoldID: 1" + * 2 4 "MaterialID: 2, ManifoldID: 1" + * $EndPhysicalNames + * $Entities + * ... + * @endcode + * + * refers to a two dimensional grid where: + * - a portion of the boundary of dimension 1 has physical tag 1, and manifold + * id 0 + * - some internal faces (lines of dimension 1) have manifold id 1 + * - some elements have manifold id 1 (and material id equal to the default + * value, i.e., zero) + * - some elements have manifold id 1 and material id equal to 2 + * + * If the physical groups are not named, then the behaviour is the same as + * the other read_msh() function, i.e., the physical tag itself is interpreted + * as a boundary or material id. + * + * @ingroup simplex + */ + void + read_msh(const std::string &filename); +#endif + /** * Read grid data from a file containing tecplot ASCII data. This also works * in the absence of any tecplot installation. diff --git a/source/grid/grid_in.cc b/source/grid/grid_in.cc index 2eec0e3195..a0b57ff5b2 100644 --- a/source/grid/grid_in.cc +++ b/source/grid/grid_in.cc @@ -16,6 +16,7 @@ #include #include +#include #include #include @@ -29,6 +30,10 @@ #include #include +#ifdef DEAL_II_GMSH_WITH_API +# include +#endif + #include #include #include @@ -2178,6 +2183,219 @@ GridIn::read_msh(std::istream &in) +#ifdef DEAL_II_GMSH_WITH_API +template +void +GridIn::read_msh(const std::string &fname) +{ + Assert(tria != nullptr, ExcNoTriangulationSelected()); + // gmsh -> deal.II types + const std::map gmsh_to_dealii_type = { + {{15, 0}, {1, 1}, {2, 2}, {3, 3}, {4, 4}, {7, 5}, {6, 6}, {5, 7}}}; + + // Vertex renumbering, by dealii type + const std::vector> gmsh_to_dealii = { + {{{0}}, + {{0, 1}}, + {{0, 1, 2}}, + {{0, 1, 3, 2}}, + {{0, 1, 2, 3}}, + {{0, 1, 3, 2, 4}}, + {{0, 1, 2, 3, 4, 5}}, + {{0, 1, 3, 2, 4, 5, 7, 6}}}}; + + std::vector> vertices; + std::vector> cells; + SubCellData subcelldata; + std::map boundary_ids_1d; + + gmsh::initialize(); + gmsh::option::setNumber("General.Verbosity", 0); + gmsh::open(fname); + + AssertThrow(gmsh::model::getDimension() == dim, + ExcMessage("You are trying to read a gmsh file with dimension " + + std::to_string(gmsh::model::getDimension()) + + " into a grid of dimension " + std::to_string(dim))); + + // Read all nodes, and store them in our vector of vertices. Before we do + // that, make sure all tags are consecutive + { + gmsh::model::mesh::removeDuplicateNodes(); + gmsh::model::mesh::renumberNodes(); + std::vector node_tags; + std::vector coord; + std::vector parametricCoord; + gmsh::model::mesh::getNodes( + node_tags, coord, parametricCoord, -1, -1, false, false); + vertices.resize(node_tags.size()); + for (unsigned int i = 0; i < node_tags.size(); ++i) + { + // Check that renumbering worked! + AssertDimension(node_tags[i], i + 1); + for (unsigned int d = 0; d < spacedim; ++d) + vertices[i][d] = coord[i * 3 + d]; +# ifdef DEBUG + // Make sure the embedded dimension is right + for (unsigned int d = spacedim; d < 3; ++d) + Assert(coord[i * 3 + d] == 0, + ExcMessage("The grid you are reading contains nodes that are " + "nonzero in the coordinate with index " + + std::to_string(d) + + ", but you are trying to save " + "it on a grid embedded in a " + + std::to_string(spacedim) + " dimensional space.")); +# endif + } + } + + // Get all the elementary entities in the model, as a vector of (dimension, + // tag) pairs: + std::vector> entities; + gmsh::model::getEntities(entities); + + for (const auto &e : entities) + { + // Dimension and tag of the entity: + const int &entity_dim = e.first; + const int &entity_tag = e.second; + + types::manifold_id manifold_id = numbers::flat_manifold_id; + types::boundary_id boundary_id = 0; + + // Get the physical tags, to deduce boundary, material, and manifold_id + std::vector physical_tags; + gmsh::model::getPhysicalGroupsForEntity(entity_dim, + entity_tag, + physical_tags); + + // Now fill manifold id and boundary or material id + if (physical_tags.size()) + for (auto physical_tag : physical_tags) + { + std::string name; + gmsh::model::getPhysicalName(entity_dim, physical_tag, name); + if (!name.empty()) + try + { + std::map id_names; + Patterns::Tools::to_value(name, id_names); + bool throw_anyway = false; + bool found_boundary_id = false; + // If the above did not throw, we keep going, and retrieve + // all the information that we know how to translate. + for (const auto &it : id_names) + { + const auto &name = it.first; + const auto &id = it.second; + if (entity_dim == dim && name == "MaterialID") + { + boundary_id = static_cast(id); + found_boundary_id = true; + } + else if (entity_dim < dim && name == "BoundaryID") + { + boundary_id = static_cast(id); + found_boundary_id = true; + } + else if (name == "ManifoldID") + manifold_id = static_cast(id); + else + // We did not recognize one of the keys. We'll fall + // back to setting the boundary id to the physical tag + // after reading all strings. + throw_anyway = true; + } + // If we didn't find a BoundaryID:XX or MaterialID:XX, and + // something was found but not recognized, then we set the + // material id or boundary id in the catch block below, using + // directly the physical tag + if (throw_anyway && !found_boundary_id) + throw; + } + catch (...) + { + // When the above didn't work, we revert to the old + // behaviour: the physical tag itself is interpreted either + // as a material_id or a boundary_id, and no manifold id is + // known + boundary_id = physical_tag; + } + } + + // Get the mesh elements for the entity (dim, tag): + std::vector element_types; + std::vector> element_ids, element_nodes; + gmsh::model::mesh::getElements( + element_types, element_ids, element_nodes, entity_dim, entity_tag); + + for (unsigned int i = 0; i < element_types.size(); ++i) + { + const auto &type = gmsh_to_dealii_type.at(element_types[i]); + const auto n_vertices = gmsh_to_dealii[type].size(); + const auto &elements = element_ids[i]; + const auto &nodes = element_nodes[i]; + for (unsigned int j = 0; j < elements.size(); ++j) + { + if (entity_dim == dim) + { + cells.emplace_back(n_vertices); + auto &cell = cells.back(); + for (unsigned int v = 0; v < n_vertices; ++v) + cell.vertices[v] = + nodes[n_vertices * j + gmsh_to_dealii[type][v]] - 1; + cell.manifold_id = manifold_id; + cell.material_id = boundary_id; + } + else if (entity_dim == 2) + { + subcelldata.boundary_quads.emplace_back(n_vertices); + auto &face = subcelldata.boundary_quads.back(); + for (unsigned int v = 0; v < n_vertices; ++v) + face.vertices[v] = + nodes[n_vertices * j + gmsh_to_dealii[type][v]] - 1; + + face.manifold_id = manifold_id; + face.boundary_id = boundary_id; + } + else if (entity_dim == 1) + { + subcelldata.boundary_lines.emplace_back(n_vertices); + auto &line = subcelldata.boundary_lines.back(); + for (unsigned int v = 0; v < n_vertices; ++v) + line.vertices[v] = + nodes[n_vertices * j + gmsh_to_dealii[type][v]] - 1; + + line.manifold_id = manifold_id; + line.boundary_id = boundary_id; + } + else if (entity_dim == 0) + { + // This should only happen in one dimension. + AssertDimension(dim, 1); + for (unsigned int j = 0; j < elements.size(); ++j) + boundary_ids_1d[nodes[j] - 1] = boundary_id; + } + } + } + } + + Assert(subcelldata.check_consistency(dim), ExcInternalError()); + + tria->create_triangulation(vertices, cells, subcelldata); + + // in 1d, we also have to attach boundary ids to vertices, which does not + // currently work through the call above + if (dim == 1) + assign_1d_boundary_ids(boundary_ids_1d, *tria); + + gmsh::clear(); + gmsh::finalize(); +} +#endif + + + template void GridIn::parse_tecplot_header( diff --git a/tests/gmsh/gmsh_api_03.cc b/tests/gmsh/gmsh_api_03.cc new file mode 100644 index 0000000000..af2483b5fd --- /dev/null +++ b/tests/gmsh/gmsh_api_03.cc @@ -0,0 +1,65 @@ +// --------------------------------------------------------------------- +// +// Copyright (C) 2021 by the deal.II authors +// +// This file is part of the deal.II library. +// +// The deal.II library is free software; you can use it, redistribute +// it, and/or modify it under the terms of the GNU Lesser General +// Public License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// The full text of the license can be found in the file LICENSE.md at +// the top level directory of deal.II. +// +// --------------------------------------------------------------------- + +// Create a hyper ball, use gmsh to output it and to read it back in. + +#include +#include +#include +#include + +#include "../tests.h" + +template +void +test(const Triangulation &tria) +{ + GridOut go; + go.write_msh(tria, "output.msh"); + + Triangulation tria2; + GridIn gi(tria2); + gi.read_msh("output.msh"); + + go.write_msh(tria2, "output2.msh"); + + deallog << "Original mesh: " << std::endl; + cat_file("output.msh"); + deallog << "Regenerated mesh: " << std::endl; + cat_file("output2.msh"); +} + + + +int +main() +{ + initlog(); + { + Triangulation<2> tria; + GridGenerator::hyper_ball(tria); + test(tria); + } + { + Triangulation<2, 3> tria; + GridGenerator::hyper_sphere(tria); + test(tria); + } + { + Triangulation<3, 3> tria; + GridGenerator::hyper_ball(tria); + test(tria); + } +} diff --git a/tests/gmsh/gmsh_api_03.with_gmsh_with_api=on.output b/tests/gmsh/gmsh_api_03.with_gmsh_with_api=on.output new file mode 100644 index 0000000000..7a7a7685f7 --- /dev/null +++ b/tests/gmsh/gmsh_api_03.with_gmsh_with_api=on.output @@ -0,0 +1,451 @@ + +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +2 +1 1 "ManifoldID:0" +2 2 "ManifoldID:1" +$EndPhysicalNames +$Entities +0 1 2 0 +1 -0.7071067811865475 -0.7071067811865475 0 0.7071067811865475 0.7071067811865475 0 1 1 0 +2 -0.7071067811865475 -0.7071067811865475 0 0.7071067811865475 0.7071067811865475 0 1 2 0 +3 -0.2928932188134525 -0.2928932188134525 0 0.2928932188134525 0.2928932188134525 0 1 3 0 +$EndEntities +$Nodes +3 8 1 8 +1 1 0 4 +1 +2 +7 +8 +-0.7071067811865475 -0.7071067811865475 0 +0.7071067811865475 -0.7071067811865475 0 +-0.7071067811865475 0.7071067811865475 0 +0.7071067811865475 0.7071067811865475 0 +2 2 0 4 +3 +4 +5 +6 +-0.2928932188134525 -0.2928932188134525 0 +0.2928932188134525 -0.2928932188134525 0 +-0.2928932188134525 0.2928932188134525 0 +0.2928932188134525 0.2928932188134525 0 +2 3 0 0 +$EndNodes +$Elements +3 9 1 9 +1 1 1 4 +2 1 2 +4 1 7 +7 2 8 +9 7 8 +2 2 3 4 +1 1 2 4 3 +3 1 3 5 7 +6 2 8 6 4 +8 7 5 6 8 +2 3 3 1 +5 3 4 6 5 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +2 +1 1 "ManifoldID:0" +2 2 "ManifoldID:1" +$EndPhysicalNames +$Entities +0 1 2 0 +1 -0.7071067811865475 -0.7071067811865475 0 0.7071067811865475 0.7071067811865475 0 1 1 0 +2 -0.7071067811865475 -0.7071067811865475 0 0.7071067811865475 0.7071067811865475 0 1 2 0 +3 -0.2928932188134525 -0.2928932188134525 0 0.2928932188134525 0.2928932188134525 0 1 3 0 +$EndEntities +$Nodes +3 8 1 8 +1 1 0 4 +1 +2 +3 +4 +-0.7071067811865475 -0.7071067811865475 0 +0.7071067811865475 -0.7071067811865475 0 +-0.7071067811865475 0.7071067811865475 0 +0.7071067811865475 0.7071067811865475 0 +2 2 0 4 +5 +6 +7 +8 +-0.2928932188134525 -0.2928932188134525 0 +0.2928932188134525 -0.2928932188134525 0 +-0.2928932188134525 0.2928932188134525 0 +0.2928932188134525 0.2928932188134525 0 +2 3 0 0 +$EndNodes +$Elements +3 9 1 9 +1 1 1 4 +2 1 2 +4 1 3 +6 2 4 +8 3 4 +2 2 3 4 +1 1 2 6 5 +3 1 5 7 3 +5 2 4 8 6 +7 3 7 8 4 +2 3 3 1 +9 5 6 8 7 +$EndElements + +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +2 +1 1 "BoundaryID:-1, ManifoldID:0" +2 2 "ManifoldID:0" +$EndPhysicalNames +$Entities +0 1 1 0 +2 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 1 0 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 2 0 +$EndEntities +$Nodes +2 8 1 8 +1 2 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +-0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +-0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 0.5773502691896258 +0.5773502691896258 0.5773502691896258 0.5773502691896258 +-0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 0.5773502691896258 +2 1 0 0 +$EndNodes +$Elements +2 30 1 30 +1 2 1 24 +2 1 2 +3 3 4 +4 1 3 +5 2 4 +7 2 5 +8 4 6 +9 2 4 +10 5 6 +12 7 8 +13 5 6 +14 7 5 +15 8 6 +17 1 3 +18 7 8 +19 1 7 +20 3 8 +22 1 7 +23 2 5 +24 1 2 +25 7 5 +27 3 4 +28 8 6 +29 3 8 +30 4 6 +2 1 3 6 +1 1 3 4 2 +6 2 4 6 5 +11 7 5 6 8 +16 1 7 8 3 +21 1 2 5 7 +26 3 8 6 4 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +2 +1 1 "BoundaryID:-1, ManifoldID:0" +2 2 "ManifoldID:0" +$EndPhysicalNames +$Entities +0 1 1 0 +2 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 1 0 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 2 0 +$EndEntities +$Nodes +2 8 1 8 +1 2 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +-0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +-0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 0.5773502691896258 +0.5773502691896258 0.5773502691896258 0.5773502691896258 +-0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 0.5773502691896258 +2 1 0 0 +$EndNodes +$Elements +2 30 1 30 +1 2 1 24 +2 1 2 +3 3 4 +4 1 3 +5 2 4 +7 2 5 +8 4 6 +9 2 4 +10 5 6 +12 7 8 +13 5 6 +14 7 5 +15 8 6 +17 1 3 +18 7 8 +19 1 7 +20 3 8 +22 1 7 +23 2 5 +24 1 2 +25 7 5 +27 3 4 +28 8 6 +29 3 8 +30 4 6 +2 1 3 6 +1 1 3 4 2 +6 2 4 6 5 +11 7 5 6 8 +16 1 7 8 3 +21 1 2 5 7 +26 3 8 6 4 +$EndElements + +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +3 +1 1 "ManifoldID:0" +2 2 "ManifoldID:0" +3 3 "ManifoldID:1" +$EndPhysicalNames +$Entities +0 1 1 2 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 1 0 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 2 0 +2 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 3 0 +3 -0.2113248654051872 -0.2113248654051872 -0.2113248654051872 0.2113248654051872 0.2113248654051872 0.2113248654051872 1 4 0 +$EndEntities +$Nodes +4 16 1 16 +1 1 0 8 +9 +10 +11 +12 +13 +14 +15 +16 +-0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 0.5773502691896258 +2 1 0 0 +3 2 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +-0.2113248654051872 -0.2113248654051872 -0.2113248654051872 +0.2113248654051872 -0.2113248654051872 -0.2113248654051872 +0.2113248654051872 -0.2113248654051872 0.2113248654051872 +-0.2113248654051872 -0.2113248654051872 0.2113248654051872 +-0.2113248654051872 0.2113248654051872 -0.2113248654051872 +0.2113248654051872 0.2113248654051872 -0.2113248654051872 +0.2113248654051872 0.2113248654051872 0.2113248654051872 +-0.2113248654051872 0.2113248654051872 0.2113248654051872 +3 3 0 0 +$EndNodes +$Elements +4 37 1 37 +1 1 1 24 +4 9 13 +5 10 14 +6 9 10 +7 13 14 +10 10 14 +11 11 15 +12 10 11 +13 14 15 +16 12 11 +17 16 15 +18 12 16 +19 11 15 +22 9 13 +23 12 16 +24 9 12 +25 13 16 +28 9 10 +29 12 11 +30 9 12 +31 10 11 +34 13 14 +35 16 15 +36 13 16 +37 14 15 +2 1 3 6 +3 9 10 14 13 +9 10 11 15 14 +15 12 16 15 11 +21 9 13 16 12 +27 9 12 11 10 +33 13 14 15 16 +3 2 5 6 +2 9 10 14 13 1 2 6 5 +8 10 14 6 2 11 15 7 3 +14 12 11 3 4 16 15 7 8 +20 9 1 5 13 12 4 8 16 +26 9 10 2 1 12 11 3 4 +32 13 5 6 14 16 8 7 15 +3 3 5 1 +1 1 2 6 5 4 3 7 8 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +3 +1 1 "ManifoldID:0" +2 2 "ManifoldID:0" +3 3 "ManifoldID:1" +$EndPhysicalNames +$Entities +0 1 1 2 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 1 0 +1 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 2 0 +2 -0.5773502691896258 -0.5773502691896258 -0.5773502691896258 0.5773502691896258 0.5773502691896258 0.5773502691896258 1 3 0 +3 -0.2113248654051872 -0.2113248654051872 -0.2113248654051872 0.2113248654051872 0.2113248654051872 0.2113248654051872 1 4 0 +$EndEntities +$Nodes +4 16 1 16 +1 1 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +-0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 -0.5773502691896258 +0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 -0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 -0.5773502691896258 +0.5773502691896258 0.5773502691896258 0.5773502691896258 +-0.5773502691896258 0.5773502691896258 0.5773502691896258 +2 1 0 0 +3 2 0 8 +9 +10 +11 +12 +13 +14 +15 +16 +-0.2113248654051872 -0.2113248654051872 -0.2113248654051872 +0.2113248654051872 -0.2113248654051872 -0.2113248654051872 +0.2113248654051872 -0.2113248654051872 0.2113248654051872 +-0.2113248654051872 -0.2113248654051872 0.2113248654051872 +-0.2113248654051872 0.2113248654051872 -0.2113248654051872 +0.2113248654051872 0.2113248654051872 -0.2113248654051872 +0.2113248654051872 0.2113248654051872 0.2113248654051872 +-0.2113248654051872 0.2113248654051872 0.2113248654051872 +3 3 0 0 +$EndNodes +$Elements +4 37 1 37 +1 1 1 24 +3 1 5 +4 2 6 +5 1 2 +6 5 6 +9 2 6 +10 3 7 +11 2 3 +12 6 7 +15 4 3 +16 8 7 +17 4 8 +18 3 7 +21 1 5 +22 4 8 +23 1 4 +24 5 8 +27 1 2 +28 4 3 +29 1 4 +30 2 3 +33 5 6 +34 8 7 +35 5 8 +36 6 7 +2 1 3 6 +2 1 2 6 5 +8 2 3 7 6 +14 4 8 7 3 +20 1 5 8 4 +26 1 4 3 2 +32 5 6 7 8 +3 2 5 6 +1 1 2 6 5 9 10 14 13 +7 2 6 14 10 3 7 15 11 +13 4 3 11 12 8 7 15 16 +19 1 9 13 5 4 12 16 8 +25 1 2 10 9 4 3 11 12 +31 5 13 14 6 8 16 15 7 +3 3 5 1 +37 9 10 14 13 12 11 15 16 +$EndElements + diff --git a/tests/gmsh/gmsh_api_04.cc b/tests/gmsh/gmsh_api_04.cc new file mode 100644 index 0000000000..76c8db52fc --- /dev/null +++ b/tests/gmsh/gmsh_api_04.cc @@ -0,0 +1,86 @@ +// --------------------------------------------------------------------- +// +// Copyright (C) 2021 by the deal.II authors +// +// This file is part of the deal.II library. +// +// The deal.II library is free software; you can use it, redistribute +// it, and/or modify it under the terms of the GNU Lesser General +// Public License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// The full text of the license can be found in the file LICENSE.md at +// the top level directory of deal.II. +// +// --------------------------------------------------------------------- + +// Create all reference cells, and output them with gmsh. + +#include +#include +#include +#include + +#include "../tests.h" + +template +void +test(const std::uint8_t kind, const std::string out = "") +{ + deallog << "Testing kind(" << (int)kind << ") in dimensions " + << "<" << dim << "," << spacedim << ">" << std::endl; + + Triangulation tria; + ReferenceCell::make_triangulation( + ReferenceCell::internal::make_reference_cell_from_int(kind), tria); + + GridOut go; + go.write_msh(tria, "output.msh"); + + Triangulation tria2; + GridIn gi(tria2); + gi.read_msh("output.msh"); + + go.write_msh(tria2, "output2.msh"); + + deallog << "Original mesh: " << std::endl; + cat_file("output.msh"); + deallog << "Regenerated mesh: " << std::endl; + cat_file("output2.msh"); + + // Uncomment to inspect each file separately + // if (out != "") + // go.write_msh(tria2, out); + (void)out; +} + +int +main() +{ + initlog(); + + // Generate and print all reference cells + // Lines + test<1, 1>(1, "line_11.msh"); + test<1, 2>(1, "line_12.msh"); + test<1, 3>(1, "line_13.msh"); + + // Triangles + test<2, 2>(2, "tri_22.msh"); + test<2, 3>(2, "tri_23.msh"); + + // Quads + test<2, 2>(3, "quad_22.msh"); + test<2, 3>(3, "quad_23.msh"); + + // Tet + test<3, 3>(4, "tet_3.msh"); + + // Pyramid + test<3, 3>(5, "pyramid_3.msh"); + + // Wedge + test<3, 3>(6, "wedge_3.msh"); + + // Hex + test<3, 3>(7, "hex_3.msh"); +} diff --git a/tests/gmsh/gmsh_api_04.with_gmsh_with_api=on.output b/tests/gmsh/gmsh_api_04.with_gmsh_with_api=on.output new file mode 100644 index 0000000000..c1c89d142d --- /dev/null +++ b/tests/gmsh/gmsh_api_04.with_gmsh_with_api=on.output @@ -0,0 +1,616 @@ + +DEAL::Testing kind(1) in dimensions <1,1> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Testing kind(1) in dimensions <1,2> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Testing kind(1) in dimensions <1,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$PhysicalNames +1 +0 1 "BoundaryID:1" +$EndPhysicalNames +$Entities +1 1 0 0 +2 0 0 0 1 1 +1 0 0 0 1 0 0 1 2 0 +$EndEntities +$Nodes +2 2 1 2 +0 2 0 0 +1 1 0 2 +1 +2 +0 0 0 +1 0 0 +$EndNodes +$Elements +1 1 1 1 +1 1 1 1 +1 1 2 +$EndElements + +DEAL::Testing kind(2) in dimensions <2,2> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 3 1 3 +2 1 0 3 +1 +2 +3 +0 0 0 +1 0 0 +0 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 2 1 +1 1 2 3 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 3 1 3 +2 1 0 3 +1 +2 +3 +0 0 0 +1 0 0 +0 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 2 1 +1 1 2 3 +$EndElements + +DEAL::Testing kind(2) in dimensions <2,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 3 1 3 +2 1 0 3 +1 +2 +3 +0 0 0 +1 0 0 +0 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 2 1 +1 1 2 3 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 3 1 3 +2 1 0 3 +1 +2 +3 +0 0 0 +1 0 0 +0 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 2 1 +1 1 2 3 +$EndElements + +DEAL::Testing kind(3) in dimensions <2,2> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +2 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 3 1 +1 1 2 4 3 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +2 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 3 1 +1 1 2 4 3 +$EndElements + +DEAL::Testing kind(3) in dimensions <2,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +2 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 3 1 +1 1 2 4 3 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 1 0 +1 0 0 0 1 1 0 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +2 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +$EndNodes +$Elements +1 1 1 1 +2 1 3 1 +1 1 2 4 3 +$EndElements + +DEAL::Testing kind(4) in dimensions <3,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +3 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 4 1 +1 1 2 3 4 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 4 1 4 +3 1 0 4 +1 +2 +3 +4 +0 0 0 +1 0 0 +0 1 0 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 4 1 +1 1 2 3 4 +$EndElements + +DEAL::Testing kind(5) in dimensions <3,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 -1 -1 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 5 1 5 +3 1 0 5 +1 +2 +3 +4 +5 +-1 -1 0 +1 -1 0 +-1 1 0 +1 1 0 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 7 1 +1 1 2 4 3 5 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 -1 -1 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 5 1 5 +3 1 0 5 +1 +2 +3 +4 +5 +-1 -1 0 +1 -1 0 +-1 1 0 +1 1 0 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 7 1 +1 1 2 4 3 5 +$EndElements + +DEAL::Testing kind(6) in dimensions <3,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 6 1 6 +3 1 0 6 +1 +2 +3 +4 +5 +6 +1 0 0 +0 1 0 +0 0 0 +1 0 1 +0 1 1 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 6 1 +1 1 2 3 4 5 6 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 6 1 6 +3 1 0 6 +1 +2 +3 +4 +5 +6 +1 0 0 +0 1 0 +0 0 0 +1 0 1 +0 1 1 +0 0 1 +$EndNodes +$Elements +1 1 1 1 +3 1 6 1 +1 1 2 3 4 5 6 +$EndElements + +DEAL::Testing kind(7) in dimensions <3,3> +DEAL::Original mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 8 1 8 +3 1 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +0 0 1 +1 0 1 +0 1 1 +1 1 1 +$EndNodes +$Elements +1 1 1 1 +3 1 5 1 +1 1 2 4 3 5 6 8 7 +$EndElements + +DEAL::Regenerated mesh: +$MeshFormat +4.1 0 8 +$EndMeshFormat +$Entities +0 0 0 1 +1 0 0 0 1 1 1 1 1 0 +$EndEntities +$Nodes +1 8 1 8 +3 1 0 8 +1 +2 +3 +4 +5 +6 +7 +8 +0 0 0 +1 0 0 +0 1 0 +1 1 0 +0 0 1 +1 0 1 +0 1 1 +1 1 1 +$EndNodes +$Elements +1 1 1 1 +3 1 5 1 +1 1 2 4 3 5 6 8 7 +$EndElements + -- 2.39.5