]> https://gitweb.dealii.org/ - dealii.git/commitdiff
Add python wrappers to generate more meshes and to flatten triangulations
authorBruno Turcksin <bruno.turcksin@gmail.com>
Sun, 10 Sep 2017 21:22:13 +0000 (17:22 -0400)
committerBruno Turcksin <bruno.turcksin@gmail.com>
Sun, 10 Sep 2017 21:22:13 +0000 (17:22 -0400)
contrib/python-bindings/include/triangulation_wrapper.h
contrib/python-bindings/source/export_triangulation.cc
contrib/python-bindings/source/triangulation_wrapper.cc

index d62f9c4823a5aada4f8b0739b6e567f8b460580e..4ddc5d63830710484eb09b07e7196f8cd4da5f70 100644 (file)
@@ -83,7 +83,7 @@ namespace python
 
     /**
      * Generate a coordinate-parallel brick from the two diagonally opposite
-     * corners points @p1 and @p2.
+     * corners points @p p1 and @p p2.
      */
     void generate_hyper_rectangle(PointWrapper &p1,
                                   PointWrapper &p2,
@@ -91,7 +91,7 @@ namespace python
 
     /**
      * Generate a coordinate-parallel brick from the two diagonally opposite
-     * corners points @p1 and @p2. In direction i, repetitions[i] cells are
+     * corners points @p p1 and @p p2. In direction i, repetitions[i] cells are
      * created.
      */
     void generate_subdivided_hyper_rectangle(boost::python::list &repetitions,
@@ -99,13 +99,156 @@ namespace python
                                              PointWrapper        &p2,
                                              const bool           colorize = false);
 
+    /**
+     * Like the previous function. However, here the first argument does not
+     * denote the number of subdivisions in each coordinate direction, but a
+     * sequence of step sizes for each coordinate direction. This function is
+     * therefore the right one to generate graded meshes where cells are
+     * concentrated in certains areas, rather than a uniformly subdidived mesh
+     * as the previous function generates.
+     */
+    void generate_subdivided_steps_hyper_rectangle(boost::python::list &step_sizes,
+                                                   PointWrapper        &p1,
+                                                   PointWrapper        &p2,
+                                                   const bool           colorize = false);
+
+    /**
+     * Like the previous function, but with the following twist: the @p
+     * material_id argument is a dim-dimensional array that, for each cell,
+     * indicates which material_id should be set. In addition, and this is the
+     * major new functionality, if the material_id of a cell is (-1), then that
+     * cell is deleted from the triangulation, i.e. the domain will have a void
+     * there.
+     */
+    void generate_subdivided_material_hyper_rectangle(boost::python::list &spacing,
+                                                      PointWrapper        &p,
+                                                      boost::python::list &material_id,
+                                                      const bool           colorize = false);
+
+    /**
+     * Rectangular domain with rectangular pattern of holes. The domain itself
+     * is rectangular, very much as if it had been generated by
+     * subdivided_hyper_rectangle(). The argument @p holes specifies how many
+     * square holes the domain should have in each coordinate direction. The
+     * total number of mesh cells in that direction is then this number plus
+     * one. The number of holes in one direction must be at least one.
+     */
+    void generate_cheese(boost::python::list &holes);
+
+    /**
+     * A general quadrilateral in 2d or a general hexahedron in 3d. It is the
+     * responsibility of the user to provide the vertices in the right order
+     * (see the documentation of the GeometryInfo class) because the vertices
+     * are stored in the same order as they are given. It is also important to
+     * make that the volume of the cell is positive. If the argument @p colorize
+     * is false, all boundary indicators are set to zero ("not colorized") for
+     * 2d and 3d. If it is true, the boundary is colorized as in
+     * hyper_rectangle(). In 1d, the indicators are always colorized.
+     */
+    void generate_general_cell(boost::python::list &vertices,
+                               const bool           colorize = false);
+
+    /**
+     * A parallelogram. The first corner point is the origin. The @tparam dim
+     * adjacent points are the ones given in the second argument and the fourth
+     * point will be the sum of these two vectors. Colorizing is done in the
+     * same way as in hyper_rectangle().
+     * @note This function is implemented in 2d only.
+     */
+    void generate_parallelogram(boost::python::list &corners,
+                                const bool           colorize = false);
+
+    /**
+     * A parallelepiped. The first corner point is the origin. The @tparam dim
+     * adjacent points are vectors describing the edges of the parallelepiped
+     * with respect to the origin. Additional points are sums of these dim
+     * vectors. Colorizing is done according to hyper_rectangle().
+     * @note This function silently reorders the vertices on the cells to
+     * lexicographic ordering (see GridReordering::reoder_grid()). In other
+     * words, if reordering of the vertices does occur, the ordering of vertices
+     * in the array of @p corners will no longer refer to the same
+     * triangulation.
+     */
+    void generate_parallelepiped(boost::python::list &corners,
+                                 const bool           colorize = false);
+
+    /**
+     * A subdivided parallelepiped. The first corner point is the origin. The
+     * @tparam dim adjacent points are vectors describing the edges of the
+     * parallelepiped with respect to the origin. Additional points are sums of
+     * these dim vectors. The variable @p n_subdivisions designates the number
+     * of subdivisions in each of the @tparam dim directions. Colorizing is odne
+     * according to hyper_rectangle().
+     */
+    void generate_fixed_subdivided_parallelepiped(const unsigned int   n_subdivisions, 
+                                                  boost::python::list &corners,
+                                                  const bool           colorize = false);
+
+    /**
+     * A subdivided parallelepided, i.e., the same as above, but where the
+     * number of subdivisions in each ot the @tparam dim directsions may vary.
+     * Colorizing is done according to hyper_rectangle().
+     */
+    void generate_varying_subdivided_parallelepiped(boost::python::list &n_subdivisions,
+                                                    boost::python::list &corners,
+                                                    const bool           colorize = false);
+
+    /**
+     * Hypercube with a layer of hypercubes around it. The first two parameters
+     * give the lower and upper bound of the inner hypercube in all coordinate
+     * directions. @p thickness marks the size of the layer cells. If the flag
+     * @p colorize is set, the outer cells get material id's according to the
+     * following scheme: extending over the inner cube (+/-) x-direction: 1/2.
+     * In y-direction 4/8, in z-direction 16/32. The cells at corners and edges
+     * (3d) get these values bitwise or'd.
+     */
+    void generate_enclosed_hyper_cube(const double left = 0.,
+                                      const double right = 1.,
+                                      const double thickness = 1.,
+                                      const bool   colorize = false);
+
     /**
      * Generate a hyperball, i.e. a circle or a ball around @p center with
-     * given @p radius.
+     * given @p radius. In order to avoid degenerate cells at the boundaries,
+     * the circle is triangulated by five cells, the ball by seven cells. The
+     * diameter of the center cell is chosen so that the aspect ratio of the
+     * boundary cells after one refinement is optimized. You should attach a
+     * SphericalManifold to the cells and faces for correct placement of
+     * vertices upon refinement and to be able to use higher order mappings.
      */
     void generate_hyper_ball(PointWrapper &center,
                              const double  radius = 1.);
 
+    /**
+     * Generate a hyper sphere, i.e., a surface of a ball in @tparam spacedim
+     * dimensions. This function only exists for dim+1=spacedim in 2 and 3 space
+     * dimensions. You should attach a SphericalManifold to the cells and faces
+     * for correct placement of vertices upon refinement and to be able to use
+     * higher order mappings.
+     */
+    void generate_hyper_sphere(PointWrapper &center,
+                               const double  radius = 1.);
+
+    /**
+     * Generate a hyper-ball intersected with the positive orthant relate to @p
+     * center, which contains three elements in 2d and four in 3d. The boundary
+     * indicators for the final triangulations are 0 for the curved boundary
+     * and 1 for the cut plane. The appropiate boundary class is
+     * HyperBallBoundary.
+     */
+    void generate_quarter_hyper_ball(PointWrapper &center,
+                                     const double  radius = 1.);
+
+    /**
+     * Generate a half hyper-ball around @p center, which contains four elements
+     * in 2d and 6 in 3d. The cut plane is perpendicular to the x-axis. The
+     * boundary indicators for the final triangulation are 0 for the curved
+     * boundary and 1 for the cut plane. The appropriate boundary class is
+     * HalfHyperBallBoundary, or HyperBallBoundary.
+     */
+    void generate_half_hyper_ball(PointWrapper &center,
+                                  const double  radius = 1.);
+
     /**
      * Shift each vertex of the Triangulation by the given @p shift_list.
      */
@@ -117,6 +260,26 @@ namespace python
      */
     void merge_triangulations(TriangulationWrapper &triangulation_1,
                               TriangulationWrapper &triangulation_2);
+    
+    /**
+     * Create a new flat triangulation @param out_tria which contains a single
+     * level with all active cells of the input triangulation. If the spacedim
+     * are different, only the smalled spacedim components of the vertices are
+     * copied over. This is useful to create a Triangulation<2,3> out of a
+     * Triangulation<2,2>, or to project a Triangulation<2,3> into a
+     * Triangulation<2,2>, by neglecting the z component of the vertices. No
+     * internal checks are performed on the vertices, which are assumed to make
+     * sense topologically in the target spacedim dimensional space. If this is
+     * not the case, you will encounter problems when using the triangulation
+     * later on. All information about cell manifold_ids and material ids are
+     * copied from one triangulation to the other, and only the boundary
+     * manifold_ids and boundary_ids are copied over from the faces of the
+     * triangulation to the faces of @p out_tria. If you need to specify
+     * manifold ids on interior faces, they have to be specified manually after
+     * the triangulation is created. This function will fail the input
+     * Triangulation contains hanging nodes.
+     */    
+    void flatten_triangulation(TriangulationWrapper &tria_out);
 
     /**
      * Refine all the cells @p n times.
index 3b6e3fb9f41a2538daecf079b35d3d43eb20db82..27e628bde499a66bc7d0b5fd529f5d863e2538e3 100644 (file)
@@ -34,8 +34,30 @@ namespace python
                                          generate_hyper_rectangle, 2, 3)
   BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_subdivided_hyper_rectangle_overloads,
                                          generate_subdivided_hyper_rectangle, 3, 4)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_subdivided_steps_hyper_rectangle_overloads,
+                                         generate_subdivided_steps_hyper_rectangle, 3, 4)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_subdivided_material_hyper_rectangle_overloads,
+                                         generate_subdivided_material_hyper_rectangle, 3, 4)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_general_cell_overloads,
+                                         generate_general_cell, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_parallelogram_overloads,
+                                         generate_parallelogram, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_parallelepiped_overloads,
+                                         generate_parallelepiped, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_fixed_subdivided_parallelepiped_overloads,
+                                         generate_fixed_subdivided_parallelepiped, 2, 3)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_varying_subdivided_parallelepiped_overloads,
+                                         generate_varying_subdivided_parallelepiped, 2, 3)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_enclosed_hyper_cube_overloads,
+                                         generate_enclosed_hyper_cube, 0, 4)
   BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_hyper_ball_overloads,
                                          generate_hyper_ball, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_hyper_sphere_overloads,
+                                         generate_hyper_sphere, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_quarter_hyper_ball_overloads,
+                                         generate_quarter_hyper_ball, 1, 2)
+  BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(generate_half_hyper_ball_overloads,
+                                         generate_half_hyper_ball, 1, 2)
 
 
 
@@ -80,70 +102,227 @@ namespace python
 
 
 
+  const char generate_subdivided_steps_hyper_rectangle_docstring [] =
+    "Like the previous function. However, here the first argument does not  \n"
+    "denote the number of subdivisions in each coordinate direction, but a  \n"
+    "sequence of step sizes for each coordinate direction. This function is \n"
+    "therefore the right one to generate graded meshes where cells are      \n"
+    "concentrated in certains areas, rather than a uniformly subdidived mesh\n"
+    "as the previous function generates.                                    \n"
+    ;
+
+
+
+  const char generate_subdivided_material_hyper_rectangle_docstring [] =
+    "Like the previous function, but with the following twist: the          \n"
+    "material_id argument is a dim-dimensional array that, for each cell,   \n"
+    "indicates which material_id should be set. In addition, and this is the\n"
+    "major new functionality, if the material_id of a cell is (-1), then    \n"
+    "that cell is deleted from the triangulation, i.e. the domain will have \n"
+    "a void there.                                                          \n"
+    ;
+
+
+
+  const char generate_cheese_docstring [] =
+    "Rectangular domain with rectangular pattern of holes. The domain itself\n"
+    "is rectangular, very much as if it had been generated by               \n"
+    "subdivided_hyper_rectangle(). The argument holes specifies how many    \n"
+    "square holes the domain should have in each coordinate direction. The  \n"
+    "total number of mesh cells in that direction is then this number plus  \n"
+    "one. The number of holes in one direction must be at least one.        \n"
+    ;
+
+
+
+  const char generate_general_cell_docstring [] =
+    "A general quadrilateral in 2d or a general hexahedron in 3d. It is the \n"
+    "responsibility of the user to provide the vertices in the right order  \n"
+    "(see the documentation of the GeometryInfo class) because the vertices \n"
+    "are stored in the same order as they are given. It is also important to\n"
+    "make that the volume of the cell is positive. If the argument          \n"
+    "colorize is false, all boundary indicators are set to zero (not        \n"
+    "colorized) for 2d and 3d. If it is true, the boundary is colorized as  \n"
+    "in hyper_rectangle(). In 1d, the indicators are always colorized.      \n"
+    ;
+
+
+
+  const char generate_parallelogram_docstring [] =
+    "A parallelogram. The first corner point is the origin. The dim         \n"
+    "adjacent points are the ones given in the second argument and the      \n"
+    "fourth point will be the sum of these two vectors. Colorizing is done  \n"
+    "in the same way as in hyper_rectangle().                               \n"
+    "Note: This function is implemented in 2d only.                         \n"
+    ;
+
+
+
+  const char generate_parallelepiped_docstring [] =
+    "A parallelepiped. The first corner point is the origin. The dim        \n"
+    "adjacent points are vectors describing the edges of the parallelepiped \n"
+    "with respect to the origin. Additional points are sums of these dim    \n"
+    "vectors. Colorizing is done according to hyper_rectangle().            \n"
+    "Note: This function silently reorders the vertices on the cells to     \n"
+    "lexicographic ordering (see GridReordering::reoder_grid()). In other   \n"
+    "words, if reordering of the vertices does occur, the ordering of       \n"
+    "vertices in the array of corners will no longer refer to the same      \n"
+    "triangulation.                                                         \n"
+    ;
+
+
+
+  const char generate_fixed_subdivided_parallelepiped_docstring [] =
+    "A subdivided parallelepiped. The first corner point is the origin. The \n"
+    "dim adjacent points are vectors describing the edges of the            \n"
+    "parallelepiped with respect to the origin. Additional points are sums  \n"
+    "of these dim vectors. The variable n_subdivisions designates the number\n"
+    "of subdivisions in each of the dim directions. Colorizing is odne      \n"
+    "according to hyper_rectangle().                                        \n"
+    ;
+
+
+
+  const char generate_varying_subdivided_parallelepiped_docstring [] =
+    "A subdivided parallelepided, i.e., the same as above, but where the    \n"
+    "number of subdivisions in each ot the dim directsions may vary.        \n"
+    "Colorizing is done according to hyper_rectangle().                     \n"
+    ;
+
+
+
+  const char generate_enclosed_hyper_cube_docstring [] =
+    "Hypercube with a layer of hypercubes around it. The first two          \n"
+    "parameters give the lower and upper bound of the inner hypercube in all\n"
+    "coordinate directions. thickness marks the size of the layer cells. If \n"
+    "the flag colorize is set, the outer cells get material id's according  \n"
+    "to the following scheme: extending over the inner cube (+/-)           \n"
+    "x-direction: 1/2. In y-direction 4/8, in z-direction 16/32. The cells i\n"
+    "at corners and edges (3d) get these values bitwise or'd.               \n"
+    ;
+
+
+
   const char generate_hyper_ball_docstring [] =
-    "Generate a hyperball, i.e., a circle or a ball around center with     \n"
-    "a given radius                                                        \n"
+    "Generate a hyperball, i.e. a circle or a ball around center with       \n"
+    "given radius. In order to avoid degenerate cells at the boundaries,    \n"
+    "the circle is triangulated by five cells, the ball by seven cells. The \n"
+    "diameter of the center cell is chosen so that the aspect ratio of the  \n"
+    "boundary cells after one refinement is optimized. You should attach a  \n"
+    "SphericalManifold to the cells and faces for correct placement of      \n"
+    "vertices upon refinement and to be able to use higher order mappings.  \n"
+    ;
+
+
+
+  const char generate_hyper_sphere_docstring [] =
+    "Generate a hyper sphere, i.e., a surface of a ball in spacedim         \n"
+    "dimensions. This function only exists for dim+1=spacedim in 2 and 3    \n"
+    "space dimensions. You should attach a SphericalManifold to the cells   \n"
+    "and faces for correct placement of vertices upon refinement and to be  \n"
+    "able to use higher order mappings.                                     \n"
+    ;
+
+
+
+  const char generate_quarter_hyper_ball_docstring [] =
+    "Generate a hyper-ball intersected with the positive orthant relate to  \n"
+    "center, which contains three elements in 2d and four in 3d. The        \n"
+    "boundary indicators for the final triangulations are 0 for the curved  \n" 
+    "boundary and 1 for the cut plane. The appropiate boundary class is     \n"
+    "HyperBallBoundary.                                                     \n"
+    ;
+
+
+
+  const char generate_half_hyper_ball_docstring [] =
+    "Generate a half hyper-ball around center, which contains four          \n"
+    "elements in 2d and 6 in 3d. The cut plane is perpendicular to the      \n"
+    "x-axis. The boundary indicators for the final triangulation are 0 for  \n"
+    "the curved boundary and 1 for the cut plane. The appropriate boundary  \n"
+    "class is HalfHyperBallBoundary, or HyperBallBoundary.                  \n"
     ;
 
 
 
   const char shift_docstring [] =
-    "Shift every vertex of the Triangulation by the gien shift vector      \n"
+    "Shift every vertex of the Triangulation by the gien shift vector       \n"
     ;
 
 
 
   const char merge_docstring [] =
-    "Given two triangulations, create the triangulation that contains      \n"
-    "the cells of both triangulations                                      \n"
+    "Given two triangulations, create the triangulation that contains       \n"
+    "the cells of both triangulations                                       \n"
+    ;
+
+
+
+  const char flatten_triangulation_docstring [] =
+    "Create a new flat triangulation out_tria which contains a single       \n"
+    "level with all active cells of the input triangulation. If the spacedim\n"
+    "are different, only the smalled spacedim components of the vertices are\n"
+    "copied over. This is useful to create a Triangulation<2,3> out of a    \n"
+    "Triangulation<2,2>, or to project a Triangulation<2,3> into a          \n"
+    "Triangulation<2,2>, by neglecting the z component of the vertices. No  \n"
+    "internal checks are performed on the vertices, which are assumed to    \n"
+    "make sense topologically in the target spacedim dimensional space. If  \n"
+    "this is not the case, you will encounter problems when using the       \n"
+    "triangulation later on. All information about cell manifold_ids and    \n"
+    "material ids are copied from one triangulation to the other, and only  \n"
+    "the boundary manifold_ids and boundary_ids are copied over from the    \n"
+    "faces of the triangulation to the faces of out_tria. If you need to    \n"
+    "specify manifold ids on interior faces, they have to be specified      \n"
+    "manually after the triangulation is created. This function will fail   \n"
+    "the input Triangulation contains hanging nodes.                        \n"
     ;
 
 
 
   const char refine_global_docstring [] =
-    "Refine all the cells times time                                       \n"
+    "Refine all the cells times time                                        \n"
     ;
 
 
 
   const char execute_coarsening_and_refinement_docstring [] =
-    "Execute both refinement and coarsening of the Triangulation           \n"
+    "Execute both refinement and coarsening of the Triangulation            \n"
     ;
 
 
   const char active_cells_docstring [] =
-    "Return the list of active cell accessors of the Triangulation         \n"
+    "Return the list of active cell accessors of the Triangulation          \n"
     ;
 
 
 
   const char write_docstring [] =
-    "Write the mesh to the output file according to the given data format. \n"
-    "The possible formats are:                                             \n"
-    "  - none                                                              \n"
-    "  - dx                                                                \n"
-    "  - gnuplot                                                           \n"
-    "  - eps                                                               \n"
-    "  - ucd                                                               \n"
-    "  - xfig                                                              \n"
-    "  - msh                                                               \n"
-    "  - svg                                                               \n"
-    "  - mathgl                                                            \n"
-    "  - vtk                                                               \n"
-    "  - vtu                                                               \n"
+    "Write the mesh to the output file according to the given data format.  \n"
+    "The possible formats are:                                              \n"
+    "  - none                                                               \n"
+    "  - dx                                                                 \n"
+    "  - gnuplot                                                            \n"
+    "  - eps                                                                \n"
+    "  - ucd                                                                \n"
+    "  - xfig                                                               \n"
+    "  - msh                                                                \n"
+    "  - svg                                                                \n"
+    "  - mathgl                                                             \n"
+    "  - vtk                                                                \n"
+    "  - vtu                                                                \n"
     ;
 
 
 
   const char save_docstring [] =
-    "Write the Triangulation to a file                                     \n"
+    "Write the Triangulation to a file                                      \n"
     ;
 
 
 
 
   const char load_docstring [] =
-    "Load the Triangulation from a file                                    \n"
+    "Load the Triangulation from a file                                     \n"
     ;
 
 
@@ -182,11 +361,75 @@ namespace python
            boost::python::args("self", "repetitions",
                                "p1", "p2", "colorize"),
            generate_subdivided_hyper_rectangle_docstring))
+    .def("generate_subdivided_steps_hyper_rectangle",
+         &TriangulationWrapper::generate_subdivided_steps_hyper_rectangle,
+         generate_subdivided_steps_hyper_rectangle_overloads(
+           boost::python::args("self", "step_sizes", 
+                               "p1", "p2", "colorize"),
+           generate_subdivided_steps_hyper_rectangle_docstring))
+    .def("generate_subdivided_material_hyper_rectangle",
+         &TriangulationWrapper::generate_subdivided_material_hyper_rectangle,
+         generate_subdivided_material_hyper_rectangle_overloads(
+           boost::python::args("self", "spacing", "p",
+                               "material_id", "colorize"),
+           generate_subdivided_material_hyper_rectangle_docstring))
+    .def("generate_cheese",
+         &TriangulationWrapper::generate_cheese,
+         generate_cheese_docstring,
+         boost::python::args("self", "holes"))
+    .def("generate_general_cell",
+         &TriangulationWrapper::generate_general_cell,
+         generate_general_cell_overloads(
+           boost::python::args("self", "vertices", "colorize"),
+           generate_general_cell_docstring))
+    .def("generate_parallelogram",
+         &TriangulationWrapper::generate_parallelogram,
+         generate_parallelogram_overloads(
+           boost::python::args("self", "corners", "colorize"),
+           generate_parallelogram_docstring))
+    .def("generate_parallelepiped",
+         &TriangulationWrapper::generate_parallelepiped,
+         generate_parallelepiped_overloads(
+           boost::python::args("self", "corners", "colorize"),
+           generate_parallelepiped_docstring))
+    .def("generate_fixed_subdivided_parallelepiped",
+         &TriangulationWrapper::generate_fixed_subdivided_parallelepiped,
+         generate_fixed_subdivided_parallelepiped_overloads(
+           boost::python::args("self", "n_subdivisions",
+                               "corners", "colorize"),
+           generate_fixed_subdivided_parallelepiped_docstring))
+    .def("generate_varying_subdivided_parallelepiped",
+         &TriangulationWrapper::generate_varying_subdivided_parallelepiped,
+         generate_varying_subdivided_parallelepiped_overloads(
+           boost::python::args("self", "n_subdivisions", 
+                               "corners", "colorize"),
+           generate_varying_subdivided_parallelepiped_docstring))
+    .def("generate_enclosed_hyper_cube",
+         &TriangulationWrapper::generate_enclosed_hyper_cube,
+         generate_enclosed_hyper_cube_overloads(
+           boost::python::args("self", "left", "right",
+                               "thickness", "colorize"),
+           generate_enclosed_hyper_cube_docstring))
     .def("generate_hyper_ball",
          &TriangulationWrapper::generate_hyper_ball,
          generate_hyper_ball_overloads(
            boost::python::args("self", "center", "radius"),
            generate_hyper_ball_docstring))
+    .def("generate_hyper_sphere",
+         &TriangulationWrapper::generate_hyper_sphere,
+         generate_hyper_sphere_overloads(
+           boost::python::args("self", "center", "radius"),
+           generate_hyper_sphere_docstring))
+    .def("generate_quarter_hyper_ball",
+         &TriangulationWrapper::generate_quarter_hyper_ball,
+         generate_quarter_hyper_ball_overloads(
+           boost::python::args("self", "center", "radius"),
+           generate_quarter_hyper_ball_docstring))
+    .def("generate_half_hyper_ball",
+         &TriangulationWrapper::generate_half_hyper_ball,
+         generate_half_hyper_ball_overloads(
+           boost::python::args("self", "center", "radius"),
+           generate_half_hyper_ball_docstring))
     .def("shift",
          &TriangulationWrapper::shift,
          shift_docstring,
@@ -195,6 +438,10 @@ namespace python
          &TriangulationWrapper::merge_triangulations,
          merge_docstring,
          boost::python::args("self", "triangulation_1", "triangulation_2"))
+    .def("flatten_triangulation",
+         &TriangulationWrapper::flatten_triangulation,
+         flatten_triangulation_docstring,
+         boost::python::args("self", "tria_out"))
     .def("refine_global",
          &TriangulationWrapper::refine_global,
          refine_global_docstring,
index 39a27c61060d0e0334471f34889d1d137e4e67ca..753587c74185e3575d59d9a1c0a601fc0c96ef69 100644 (file)
@@ -18,6 +18,7 @@
 #ifdef DEAL_II_WITH_CXX11
 
 #include <cell_accessor_wrapper.h>
+#include <deal.II/base/types.h>
 #include <deal.II/grid/tria.h>
 #include <deal.II/grid/grid_generator.h>
 #include <deal.II/grid/grid_out.h>
@@ -123,6 +124,174 @@ namespace python
 
 
 
+    template <int dim>
+    void generate_subdivided_steps_hyper_rectangle(const std::vector<std::vector<double>> &step_sizes,
+                                                   PointWrapper                           &p1,
+                                                   PointWrapper                           &p2,
+                                                   const bool                              colorize,
+                                                   void                                   *triangulation)
+    {
+      AssertThrow(p1.get_dim() == dim,
+                  ExcMessage("Dimension of p1 is not the same as the dimension of the Triangulation."));
+      AssertThrow(p2.get_dim() == dim,
+                  ExcMessage("Dimension of p2 is not the same as the dimension of the Triangulation."));
+      // Cast the PointWrapper object to Point<dim>
+      Point<dim> point_1 = *(static_cast<Point<dim>*>(p1.get_point()));
+      Point<dim> point_2 = *(static_cast<Point<dim>*>(p2.get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::subdivided_hyper_rectangle(*tria, step_sizes, point_1,
+                                                point_2, colorize);
+    }
+
+
+
+    template <int dim>
+    void generate_subdivided_material_hyper_rectangle(const std::vector<std::vector<double>> &spacing,
+                                        PointWrapper                          &p,
+                                        const Table<dim,types::material_id>   &material_ids,
+                                        const bool                             colorize,
+                                        void                                  *triangulation)
+    {
+      AssertThrow(p.get_dim() == dim,
+                  ExcMessage("Dimension of p is not the same as the dimension of the Triangulation."));
+      // Cast the PointWrapper object to Point<dim>
+      Point<dim> point = *(static_cast<Point<dim>*>(p.get_point()));
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::subdivided_hyper_rectangle(*tria, spacing, point,
+                                                material_ids, colorize);
+    }
+
+
+
+    template <int dim, int spacedim>
+    void generate_cheese(const std::vector<unsigned int> &holes, 
+                         void                            *triangulation)
+    {
+      Triangulation<dim,spacedim> *tria =
+        static_cast<Triangulation<dim,spacedim>*>(triangulation);
+      tria->clear();
+      GridGenerator::cheese(*tria, holes);
+    }
+
+
+
+    template <int dim>
+    void generate_general_cell(std::vector<PointWrapper> &wrapped_points,
+                       const bool                 colorize,
+                       void                      *triangulation)
+    {
+      // Cast the PointWrapper objects to Point<dim>
+      const unsigned int size = wrapped_points.size();
+      std::vector<Point<dim>> points(size);
+      for (unsigned int i=0; i<size; ++i)
+        points[i] = *(static_cast<Point<dim>*>((wrapped_points[i]).get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::general_cell(*tria, points, colorize);
+    }
+
+
+
+    template <int dim>
+    void generate_parallelogram(std::vector<PointWrapper> &wrapped_points,
+                                const bool                 colorize,
+                                void                      *triangulation)
+    {
+      // Cast the PointWrapper objects to Point<dim>
+      Point<dim> points[dim];
+      for (unsigned int i=0; i<dim; ++i)
+        points[i] = *(static_cast<Point<dim>*>((wrapped_points[i]).get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::parallelogram(*tria, points, colorize);
+    }
+
+
+
+    template <int dim>
+    void generate_parallelepiped(std::vector<PointWrapper> &wrapped_points,
+                                const bool                 colorize,
+                                void                      *triangulation)
+    {
+      // Cast the PointWrapper objects to Point<dim>
+      Point<dim> points[dim];
+      for (unsigned int i=0; i<dim; ++i)
+        points[i] = *(static_cast<Point<dim>*>((wrapped_points[i]).get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::parallelepiped(*tria, points, colorize);
+    }
+
+
+
+    template <int dim>
+    void generate_fixed_subdivided_parallelepiped(unsigned int               n_subdivisions,
+                                                  std::vector<PointWrapper> &wrapped_points, 
+                                                  const bool                 colorize,
+                                                  void                      *triangulation)
+    {
+      // Cast the PointWrapper objects to Point<dim>
+      Point<dim> points[dim];
+      for (unsigned int i=0; i<dim; ++i)
+        points[i] = *(static_cast<Point<dim>*>((wrapped_points[i]).get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::subdivided_parallelepiped(*tria, n_subdivisions, points, colorize);
+    }
+
+
+
+    template <int dim>
+    void generate_varying_subdivided_parallelepiped(std::vector<unsigned int> &n_subdivisions,
+                                                  std::vector<PointWrapper> &wrapped_points, 
+                                                  const bool                 colorize,
+                                                  void                      *triangulation)
+    {
+      // Cast the PointWrapper objects to Point<dim>
+      Point<dim> points[dim];
+      unsigned int subdivisions[dim];
+      for (unsigned int i=0; i<dim; ++i)
+      {
+        points[i] = *(static_cast<Point<dim>*>((wrapped_points[i]).get_point()));
+        subdivisions[i] = n_subdivisions[i];
+      }
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::subdivided_parallelepiped(*tria, subdivisions, points, colorize);
+    }
+
+
+    
+    template <int dim>
+    void generate_enclosed_hyper_cube(const double  left, 
+                                      const double  right, 
+                                      const double  thickness, 
+                                      const double  colorize,
+                                      void         *triangulation)
+    {
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::enclosed_hyper_cube(*tria, left, right, thickness, colorize);
+    }
+     
+
+
     template <int dim>
     void generate_hyper_ball(PointWrapper &center,
                              const double  radius,
@@ -140,6 +309,57 @@ namespace python
 
 
 
+    template <int dim, int spacedim>
+    void generate_hyper_sphere(PointWrapper &center, 
+                               const double  radius, 
+                               void         *triangulation)
+    {
+      // Cast the PointWrapper object to Point<dim>
+      Point<spacedim> center_point = *(static_cast<Point<spacedim>*>(
+                                    center.get_point()));
+
+      Triangulation<dim,spacedim> *tria =
+        static_cast<Triangulation<dim,spacedim>*>(triangulation);
+      tria->clear();
+      GridGenerator::hyper_sphere(*tria, center_point, radius);
+    }
+
+
+    
+    template <int dim>
+    void generate_quarter_hyper_ball(PointWrapper &center, 
+                                     const double  radius, 
+                                     void         *triangulation)
+    {
+      // Cast the PointWrapper object to Point<dim>
+      Point<dim> center_point = *(static_cast<Point<dim>*>(
+                                    center.get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::quarter_hyper_ball(*tria, center_point, radius);
+    }
+
+
+    
+    template <int dim>
+    void generate_half_hyper_ball(PointWrapper &center, 
+                                     const double  radius, 
+                                     void         *triangulation)
+    {
+      // Cast the PointWrapper object to Point<dim>
+      Point<dim> center_point = *(static_cast<Point<dim>*>(
+                                    center.get_point()));
+
+      Triangulation<dim> *tria =
+        static_cast<Triangulation<dim>*>(triangulation);
+      tria->clear();
+      GridGenerator::half_hyper_ball(*tria, center_point, radius);
+    }
+
+
+
     template <int dim, int spacedim>
     void shift(boost::python::list &shift_list,
                void                *triangulation)
@@ -176,6 +396,18 @@ namespace python
 
 
 
+    template <int dim, int spacedim_1, int spacedim_2>
+    void flatten_triangulation(void *triangulation, TriangulationWrapper &tria_out)
+    {
+      Triangulation<dim,spacedim_1> *tria =
+        static_cast<Triangulation<dim,spacedim_1>*>(triangulation);
+      Triangulation<dim,spacedim_2> *tria_2 =
+        static_cast<Triangulation<dim,spacedim_2>*>(tria_out.get_triangulation());
+      GridGenerator::flatten_triangulation(*tria, *tria_2);
+    }
+
+
+
     template <int dim, int spacedim>
     boost::python::list active_cells(TriangulationWrapper &triangulation_wrapper)
     {
@@ -393,6 +625,225 @@ namespace python
 
 
 
+  void TriangulationWrapper::generate_subdivided_steps_hyper_rectangle(boost::python::list &step_sizes_list, 
+                                                 PointWrapper        &p1,
+                                                 PointWrapper        &p2,
+                                                 const bool           colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    AssertThrow(boost::python::len(step_sizes_list) == dim,
+                ExcMessage("The list of step_sizes must have the same length as the number of dimension."));
+
+    // Extract the step sizes from the python list
+    std::vector<std::vector<double>> step_sizes(dim);
+    for (int i=0; i<dim; ++i)
+    {
+      step_sizes[i].resize(boost::python::len(step_sizes_list[i]));
+      for (unsigned int j=0; j<step_sizes[i].size(); ++j)
+        step_sizes[i][j] = boost::python::extract<double>(step_sizes_list[i][j]);
+    }
+
+    if (dim == 2)
+      internal::generate_subdivided_steps_hyper_rectangle<2>(step_sizes,
+          p1, p2, colorize, triangulation);
+    else
+      internal::generate_subdivided_steps_hyper_rectangle<3>(step_sizes,
+          p1, p2, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_subdivided_material_hyper_rectangle(boost::python::list &spacing_list,
+                                           PointWrapper        &p,
+                                           boost::python::list &material_id_list,
+                                           const bool           colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    AssertThrow(boost::python::len(spacing_list) == dim,
+                ExcMessage("The list of spacing must have the same length as the number of dimension."));
+
+    // Extract the spacing and the material ID from the python list
+    std::vector<std::vector<double>> spacing(dim);
+    for (int i=0; i<dim; ++i)
+    {
+      spacing[i].resize(boost::python::len(spacing_list[i]));
+      for (unsigned int j=0; j<spacing[i].size(); ++j)
+        spacing[i][j] = boost::python::extract<double>(spacing_list[i][j]);
+    }
+    if (dim == 2)
+    {
+      const unsigned int index_0 = boost::python::len(material_id_list);
+      const unsigned int index_1 = boost::python::len(material_id_list[0]);
+      Table<2, types::material_id> material_ids(index_0, index_1);
+      for (unsigned int i=0; i<index_0; ++i)
+        for (unsigned int j=0; j<index_1; ++j)
+          // We cannot use extract<types::material_id> because boost will throw
+          // an exception if we try to extract -1
+          material_ids[i][j] = boost::python::extract<int>(material_id_list[i][j]);
+
+        internal::generate_subdivided_material_hyper_rectangle<2>(spacing, p, 
+            material_ids, colorize, triangulation);
+    }
+    else 
+    {
+      const unsigned int index_0 = boost::python::len(material_id_list);
+      const unsigned int index_1 = boost::python::len(material_id_list[0]);
+      const unsigned int index_2 = boost::python::len(material_id_list[0][0]);
+      Table<3, types::material_id> material_ids(index_0, index_1, index_2);
+      for (unsigned int i=0; i<index_0; ++i)
+        for (unsigned int j=0; j<index_1; ++j)
+        for (unsigned int k=0; k<index_2; ++k)
+          material_ids[i][j][k] = boost::python::extract<int>(material_id_list[i][j][k]);
+      internal::generate_subdivided_material_hyper_rectangle<3>(spacing, p, 
+          material_ids, colorize, triangulation);
+    }
+  }
+
+
+
+  void TriangulationWrapper::generate_cheese(boost::python::list &holes_list)
+  {
+    const unsigned int size = boost::python::len(holes_list);
+    std::vector<unsigned int> holes(size);
+    for (unsigned int i=0; i<size; ++i)
+      holes[i] = boost::python::extract<unsigned int>(holes_list[i]);
+
+    if ((dim == 2) && (spacedim == 2))
+      internal::generate_cheese<2,2>(holes, triangulation);
+    else if ((dim == 2) && (spacedim == 3))
+      internal::generate_cheese<2,3>(holes, triangulation);
+    else
+      internal::generate_cheese<3,3>(holes, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_general_cell(boost::python::list &vertices, 
+                                                   const bool colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implementd for dim equal to spacedim."));
+    // Extract the PointWrapper object from the python list
+    const int size = boost::python::len(vertices);
+    AssertThrow(size > 0, ExcMessage("The vertices list is empty."));
+    std::vector<PointWrapper> wrapped_points(size);
+    for (int i=0; i<size; ++i)
+        wrapped_points[i] = boost::python::extract<PointWrapper>(vertices[i]);
+    if (dim == 2)
+      internal::generate_general_cell<2>(wrapped_points, colorize, triangulation);
+    else
+      internal::generate_general_cell<3>(wrapped_points, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_parallelogram(boost::python::list &corners,
+                                                     const bool colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    // Extract the PointWrapper object from the python list
+    AssertThrow(boost::python::len(corners) == dim,
+                ExcMessage("The list of corners must have the same length as the number of dimension."));
+    std::vector<PointWrapper> wrapped_points(dim);
+    for (int i=0; i<dim; ++i)
+        wrapped_points[i] = boost::python::extract<PointWrapper>(corners[i]);
+    if (dim == 2)
+      internal::generate_parallelogram<2>(wrapped_points, colorize, triangulation);
+    else
+      internal::generate_parallelogram<3>(wrapped_points, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_parallelepiped(boost::python::list &corners,
+                                                     const bool colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    // Extract the PointWrapper object from the python list
+    AssertThrow(boost::python::len(corners) == dim,
+                ExcMessage("The list of corners must have the same length as the number of dimension."));
+    std::vector<PointWrapper> wrapped_points(dim);
+    for (int i=0; i<dim; ++i)
+        wrapped_points[i] = boost::python::extract<PointWrapper>(corners[i]);
+    if (dim == 2)
+      internal::generate_parallelepiped<2>(wrapped_points, colorize, triangulation);
+    else
+      internal::generate_parallelepiped<3>(wrapped_points, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_fixed_subdivided_parallelepiped(
+    const unsigned int   n_subdivisions, 
+    boost::python::list &corners,
+    const bool           colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    // Extract the PointWrapper object from the python list
+    AssertThrow(boost::python::len(corners) == dim,
+                ExcMessage("The list of corners must have the same length as the number of dimension."));
+    std::vector<PointWrapper> wrapped_points(dim);
+    for (int i=0; i<dim; ++i)
+        wrapped_points[i] = boost::python::extract<PointWrapper>(corners[i]);
+    if ((dim == 2) && (spacedim == 2))
+      internal::generate_fixed_subdivided_parallelepiped<2>(n_subdivisions, 
+                                          wrapped_points, colorize, triangulation);
+    else
+      internal::generate_fixed_subdivided_parallelepiped<3>(n_subdivisions, 
+                                          wrapped_points, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_varying_subdivided_parallelepiped(
+    boost::python::list &n_subdivisions,
+    boost::python::list &corners,
+    const bool           colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    // Extract the subdivisions from the python list
+    AssertThrow(boost::python::len(n_subdivisions) == dim,
+                ExcMessage("The list of subdivisions must have the same length as the number of dimension."));
+    std::vector<unsigned int> subdivisions(dim);
+    for (int i=0; i<dim; ++i)
+        subdivisions[i] = boost::python::extract<unsigned int>(n_subdivisions[i]);
+    // Extract the PointWrapper object from the python list
+    AssertThrow(boost::python::len(corners) == dim,
+                ExcMessage("The list of corners must have the same length as the number of dimension."));
+    std::vector<PointWrapper> wrapped_points(dim);
+    for (int i=0; i<dim; ++i)
+        wrapped_points[i] = boost::python::extract<PointWrapper>(corners[i]);
+    if (dim == 2)
+      internal::generate_varying_subdivided_parallelepiped<2>(subdivisions, 
+                                          wrapped_points, colorize, triangulation);
+    else
+      internal::generate_varying_subdivided_parallelepiped<3>(subdivisions, 
+                                          wrapped_points, colorize, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_enclosed_hyper_cube(const double left,
+                                                          const double right,
+                                                          const double thickness,
+                                                          const bool colorize)
+  {
+    AssertThrow(spacedim == dim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    if (dim == 2)
+      internal::generate_enclosed_hyper_cube<2>(left, right, thickness, colorize, triangulation);
+    else
+      internal::generate_enclosed_hyper_cube<3>(left, right, thickness, colorize, triangulation);
+  }
+
+
+    
   void TriangulationWrapper::generate_hyper_ball(PointWrapper &center,
                                                  const double  radius)
   {
@@ -405,6 +856,40 @@ namespace python
   }
 
 
+  void TriangulationWrapper::generate_hyper_sphere(PointWrapper &center,
+                                                   const double  radius)
+  {
+    AssertThrow(spacedim == dim+1,
+                ExcMessage("This function is only implemented for spacedim equal to dim+1."));
+    internal::generate_hyper_sphere<2,3>(center, radius, triangulation);
+  }
+
+
+
+  void TriangulationWrapper::generate_quarter_hyper_ball(PointWrapper &center,
+                                                         const double  radius)
+  {
+    AssertThrow(dim == spacedim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    if (dim == 2)
+      internal::generate_quarter_hyper_ball<2>(center, radius, triangulation);
+    else
+      internal::generate_quarter_hyper_ball<3>(center, radius, triangulation);
+  }
+
+
+  void TriangulationWrapper::generate_half_hyper_ball(PointWrapper &center,
+                                                 const double  radius)
+  {
+    AssertThrow(dim == spacedim,
+                ExcMessage("This function is only implemented for dim equal to spacedim."));
+    if (dim == 2)
+      internal::generate_half_hyper_ball<2>(center, radius, triangulation);
+    else
+      internal::generate_half_hyper_ball<3>(center, radius, triangulation);
+  }
+
+
 
   void TriangulationWrapper::shift(boost::python::list &shift_list)
   {
@@ -442,6 +927,24 @@ namespace python
 
 
 
+  void TriangulationWrapper::flatten_triangulation(TriangulationWrapper &tria_out)
+  {
+    AssertThrow(dim == tria_out.get_dim(),
+                ExcMessage("The Triangulation and tria_out should have the same dimension."));
+    AssertThrow(spacedim >= tria_out.get_spacedim(),
+                ExcMessage("The Triangulation should have a spacedim greater or equal "
+                           "to the spacedim of tria_out."));
+    int spacedim_out = tria_out.get_spacedim();
+    if ((dim == 2) && (spacedim == 2) && (spacedim_out == 2))
+      internal::flatten_triangulation<2,2,2>(triangulation, tria_out);
+    else if ((dim == 2) && (spacedim == 3) && (spacedim_out == 2))
+      internal::flatten_triangulation<2,3,2>(triangulation, tria_out);
+    else
+      internal::flatten_triangulation<3,3,3>(triangulation, tria_out);
+  }
+
+
+
   void TriangulationWrapper::refine_global(const unsigned int n)
   {
     if ((dim == 2) && (spacedim == 2))

In the beginning the Universe was created. This has made a lot of people very angry and has been widely regarded as a bad move.

Douglas Adams


Typeset in Trocchi and Trocchi Bold Sans Serif.