// ---------------------------------------------------------------------
//
// Copyright (C) 1999 - 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.
//
// ---------------------------------------------------------------------


for (deal_II_dimension : DIMENSIONS; deal_II_space_dimension : SPACE_DIMENSIONS)
  {
    namespace GridGenerator
    \{
#if deal_II_dimension <= deal_II_space_dimension
      template void
      hyper_rectangle<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const Point<deal_II_dimension> &,
        const Point<deal_II_dimension> &,
        const bool);

      template void
      hyper_cube<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const double,
        const double,
        const bool);

      template void
      subdivided_hyper_cube<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const unsigned int,
        const double,
        const double,
        const bool);


      template void
      subdivided_hyper_rectangle<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const std::vector<unsigned int> &,
        const Point<deal_II_dimension> &,
        const Point<deal_II_dimension> &,
        const bool);

      template void
      subdivided_parallelepiped<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const Point<deal_II_space_dimension> &,
        const std::array<Tensor<1, deal_II_space_dimension>, deal_II_dimension>
          &,
        const std::vector<unsigned int> &,
        const bool colorize);

      template void
      hyper_cross<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const std::vector<unsigned int> &,
        const bool);

      template void
      subdivided_hyper_L(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const std::vector<unsigned int> &,
        const Point<deal_II_dimension> &,
        const Point<deal_II_dimension> &,
        const std::vector<int> &);

      template void
      cheese<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const std::vector<unsigned int> &);

      template void
      merge_triangulations(
        const std::vector<
          const Triangulation<deal_II_dimension, deal_II_space_dimension> *> &,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const double,
        const bool);

      template void
      merge_triangulations(
        const Triangulation<deal_II_dimension, deal_II_space_dimension>
          &triangulation_1,
        const Triangulation<deal_II_dimension, deal_II_space_dimension>
          &triangulation_2,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &result,
        const double duplicated_vertex_tolerance,
        const bool   copy_manifold_ids);

      template void
      replicate_triangulation(
        const Triangulation<deal_II_dimension, deal_II_space_dimension> &input,
        const std::vector<unsigned int> &                          extents,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &result);

      template void
      create_union_triangulation(
        const Triangulation<deal_II_dimension, deal_II_space_dimension>
          &triangulation_1,
        const Triangulation<deal_II_dimension, deal_II_space_dimension>
          &triangulation_2,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &result);

      template void
      create_triangulation_with_removed_cells(
        const Triangulation<deal_II_dimension, deal_II_space_dimension>
          &input_triangulation,
        const std::set<
          Triangulation<deal_II_dimension,
                        deal_II_space_dimension>::active_cell_iterator>
          &cells_to_remove,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &result);

      template void
      general_cell(Triangulation<deal_II_dimension, deal_II_space_dimension> &,
                   const std::vector<Point<deal_II_space_dimension>> &,
                   const bool);
#endif
    \}
  }


for (deal_II_dimension : DIMENSIONS; deal_II_space_dimension : SPACE_DIMENSIONS;
     Container : TRIANGULATION_AND_DOFHANDLER_TEMPLATES)
  {
#if deal_II_dimension <= deal_II_space_dimension
    namespace GridGenerator
    \{

#  if deal_II_dimension != 1
      template
#    ifndef _MSC_VER
        std::map<
          Container<deal_II_dimension - 1,
                    deal_II_space_dimension>::cell_iterator,
          Container<deal_II_dimension, deal_II_space_dimension>::face_iterator>
#    else
        ExtractBoundaryMesh<Container,
                            deal_II_dimension,
                            deal_II_space_dimension>::return_type
#    endif
        extract_boundary_mesh(
          const Container<deal_II_dimension, deal_II_space_dimension> &mesh,
          Container<deal_II_dimension - 1, deal_II_space_dimension>
            &                                 boundary_mesh,
          const std::set<types::boundary_id> &boundary_ids);
#  endif
    \}
#endif
  }


for (deal_II_dimension : DIMENSIONS)
  {
    namespace GridGenerator
    \{

      template void
      subdivided_hyper_rectangle(Triangulation<deal_II_dimension> &,
                                 const std::vector<std::vector<double>> &,
                                 const Point<deal_II_dimension> &,
                                 const Point<deal_II_dimension> &,
                                 const bool);

      template void
      simplex<deal_II_dimension>(
        Triangulation<deal_II_dimension, deal_II_dimension> &,
        const std::vector<Point<deal_II_dimension>> &);

      template void
      parallelepiped<deal_II_dimension>(
        Triangulation<deal_II_dimension> &,
        const Point<deal_II_dimension> (&)[deal_II_dimension],
        const bool);

      template void
      subdivided_parallelepiped<deal_II_dimension>(
        Triangulation<deal_II_dimension> &,
        const unsigned int,
        const Point<deal_II_dimension> (&)[deal_II_dimension],
        const bool);

#ifndef _MSC_VER
      template void
      subdivided_parallelepiped<deal_II_dimension>(
        Triangulation<deal_II_dimension> &,
        const unsigned int (&)[deal_II_dimension],
        const Point<deal_II_dimension> (&)[deal_II_dimension],
        const bool);
#else
      template void
      subdivided_parallelepiped<deal_II_dimension>(
        Triangulation<deal_II_dimension> &,
        const unsigned int *,
        const Point<deal_II_dimension> (&)[deal_II_dimension],
        const bool);
#endif

      template void
      concentric_hyper_shells(Triangulation<deal_II_dimension> &,
                              const Point<deal_II_dimension> &,
                              const double,
                              const double,
                              const unsigned int,
                              const double,
                              const unsigned int,
                              const bool);

      template void
      eccentric_hyper_shell(Triangulation<deal_II_dimension> &,
                            const Point<deal_II_dimension> &,
                            const Point<deal_II_dimension> &,
                            const double,
                            const double,
                            const unsigned int);

#if deal_II_dimension >= 2
      template void
      hyper_ball_balanced<deal_II_dimension>(Triangulation<deal_II_dimension> &,
                                             const Point<deal_II_dimension> &,
                                             const double);
#endif
    \}
  }



for (deal_II_space_dimension : DIMENSIONS)
  {
    namespace GridGenerator
    \{

#if deal_II_space_dimension >= 2
      template void
      hyper_sphere<deal_II_space_dimension>(
        Triangulation<deal_II_space_dimension - 1, deal_II_space_dimension> &,
        const Point<deal_II_space_dimension> &,
        double);
#endif

    \}
  }

for (deal_II_dimension : DIMENSIONS; deal_II_space_dimension : SPACE_DIMENSIONS;
     deal_II_space_dimension_2 : SPACE_DIMENSIONS)
  {
    namespace GridGenerator
    \{
#if (deal_II_dimension <= deal_II_space_dimension) && \
  (deal_II_dimension <= deal_II_space_dimension_2)
      template void
      flatten_triangulation<>(
        const Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        Triangulation<deal_II_dimension, deal_II_space_dimension_2> &);
#endif
    \}
  }

for (deal_II_dimension : DIMENSIONS; deal_II_space_dimension : SPACE_DIMENSIONS)
  {
    namespace GridGenerator
    \{
#if deal_II_dimension <= deal_II_space_dimension
      template void
      reference_cell<deal_II_dimension, deal_II_space_dimension>(
        Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        const ReferenceCell &);

      template void
      convert_hypercube_to_simplex_mesh(
        const Triangulation<deal_II_dimension, deal_II_space_dimension> &,
        Triangulation<deal_II_dimension, deal_II_space_dimension> &);
#endif
    \}
  }

for (deal_II_dimension : DIMENSIONS)
  {
    template void GridGenerator::subdivided_hyper_rectangle_with_simplices(
      Triangulation<deal_II_dimension> & tria,
      const std::vector<unsigned int> &repetitions,
      const Point<deal_II_dimension> & p1,
      const Point<deal_II_dimension> & p2,
      const bool                       colorize);

    template void GridGenerator::subdivided_hyper_cube_with_simplices(
      Triangulation<deal_II_dimension> & tria,
      const unsigned int repetitions,
      const double       p1,
      const double       p2,
      const bool         colorize);
  }
