13#ifndef DUMUX_DISCRETIZATION_PQ2_GEOMETRY_HELPER_HH
14#define DUMUX_DISCRETIZATION_PQ2_GEOMETRY_HELPER_HH
18#include <dune/common/exceptions.hh>
20#include <dune/geometry/type.hh>
21#include <dune/geometry/referenceelements.hh>
22#include <dune/geometry/multilineargeometry.hh>
23#include <dune/common/reservedvector.hh>
37 template<
int mydim,
int cdim >
40 using Type = Dune::ReservedVector< Dune::FieldVector< ct, cdim >, (1<<mydim)>;
49template <
class Gr
idView,
class ScvType,
class ScvfType>
52 using Scalar =
typename GridView::ctype;
53 using GlobalPosition =
typename Dune::FieldVector<Scalar, GridView::dimensionworld>;
54 using ScvCornerStorage =
typename ScvType::Traits::CornerStorage;
55 using ScvfCornerStorage =
typename ScvfType::Traits::CornerStorage;
56 using LocalIndexType =
typename ScvType::Traits::LocalIndexType;
58 using Element =
typename GridView::template Codim<0>::Entity;
59 using Intersection =
typename GridView::Intersection;
61 static constexpr auto dim = GridView::dimension;
62 static constexpr auto dimWorld = GridView::dimensionworld;
69 , boxHelper_(geometry)
75 return getScvCorners(geo_.type(), [&](
const auto& local){ return geo_.global(local); }, localScvIdx);
79 template<
class Transformation>
80 static ScvCornerStorage
getScvCorners(Dune::GeometryType type, Transformation&& trans,
unsigned int localScvIdx)
83 const auto& ref = Dune::referenceElement<Scalar, dim>(type);
84 const auto numBoxScv = ref.size(dim);
86 if (localScvIdx < numBoxScv)
87 return BoxHelper::getScvCorners(type, trans, localScvIdx);
89 DUNE_THROW(Dune::NotImplemented,
"PQ2 scv corners call for hybrid dofs");
95 const auto numBoxScv = boxHelper_.numScv();
97 if (localScvIdx < numBoxScv)
98 return Dune::GeometryTypes::cube(dim);
100 DUNE_THROW(Dune::NotImplemented,
"PQ2 scv geometry call for hybrid dofs");
106 return getScvfCorners(geo_.type(), [&](
const auto& local){ return geo_.global(local); }, localScvfIdx);
110 template<
class Transformation>
111 static ScvfCornerStorage
getScvfCorners(Dune::GeometryType type, Transformation&& trans,
unsigned int localScvfIdx)
114 const auto& ref = Dune::referenceElement<Scalar, dim>(type);
115 const auto numBoxScvf = ref.size(dim-1);
117 if (localScvfIdx < numBoxScvf)
118 return BoxHelper::getScvfCorners(type, trans, localScvfIdx);
120 DUNE_THROW(Dune::NotImplemented,
"PQ2 scvf corners call for hybrid dofs");
125 const auto numBoxScvf = boxHelper_.numInteriorScvf();
126 if (localScvfIdx < numBoxScvf)
127 return Dune::GeometryTypes::cube(dim-1);
129 DUNE_THROW(Dune::NotImplemented,
"PQ2 interior scvf geometry type call for hybrid dofs");
134 unsigned int indexInFacet)
const
136 return boxHelper_.getBoundaryScvfCorners(localFacetIndex, indexInFacet);
141 return Dune::GeometryTypes::cube(dim-1);
144 template<
int d = dimWorld, std::enable_if_t<(d==3),
int> = 0>
145 GlobalPosition
normal(
const ScvfCornerStorage& p,
const std::array<LocalIndexType, 2>& scvPair)
150 GlobalPosition v = geo_.corner(scvPair[1]) - geo_.corner(scvPair[0]);
159 template<
int d = dimWorld, std::enable_if_t<(d==2),
int> = 0>
160 GlobalPosition
normal(
const ScvfCornerStorage& p,
const std::array<LocalIndexType, 2>& scvPair)
163 const auto t = p[1] - p[0];
164 GlobalPosition
normal({-t[1], t[0]});
167 GlobalPosition v = geo_.corner(scvPair[1]) - geo_.corner(scvPair[0]);
183 return BoxHelper::numInteriorScvf(type);
189 return Dune::referenceElement<Scalar, dim>(type).size(localFacetIndex, 1, dim);
195 return boxHelper_.numScv();
199 Scalar
scvVolume(
unsigned int localScvIdx,
const ScvCornerStorage& p)
const
203 return Dumux::convexPolytopeVolume<dim>(
205 [&](
unsigned int i){
return p[i]; }
210 template<
class LocalKey>
213 const auto& refElement = Dune::referenceElement<Scalar, dim>(type);
215 const auto numEntitiesIntersection = refElement.size(iIdx, 1, localKey.codim());
216 for(std::size_t idx=0; idx < numEntitiesIntersection; idx++)
217 if(localKey.subEntity() == refElement.subEntity(iIdx, 1, idx, localKey.codim()))
223 template<
class DofMapper,
class LocalKey>
224 static auto dofIndex(
const DofMapper& dofMapper,
const Element& element,
const LocalKey& localKey)
227 return dofMapper.subIndex(element, localKey.subEntity(), localKey.codim());
230 template<
class Geometry,
class LocalKey>
231 static GlobalPosition
dofPosition(
const Geometry& geo,
const LocalKey& localKey)
233 if(localKey.codim() == dim)
234 return geo.corner(localKey.subEntity());
235 else if(localKey.codim() == 0)
241 template<
class LocalKey>
248 template<
class LocalKey>
249 static Element::Geometry::LocalCoordinate
localDofPosition(Dune::GeometryType type,
const LocalKey& localKey)
251 return Dune::referenceElement<Scalar, dim>(type).position(localKey.subEntity(), localKey.codim());
256 const auto numBoxFaces = boxHelper_.numInteriorScvf();
257 if (localScvfIndex < numBoxFaces)
260 static_cast<LocalIndexType
>(referenceElement(geo_).subEntity(localScvfIndex, dim-1, 0, dim)),
261 static_cast<LocalIndexType
>(referenceElement(geo_).subEntity(localScvfIndex, dim-1, 1, dim))
265 DUNE_THROW(Dune::NotImplemented,
"PQ2 scv pair call for hybrid dofs");
270 const auto numBoxScvf = referenceElement(geo_).size(localFacetIndex, 1, dim);
271 if (localIsScvfIndex < numBoxScvf)
273 const LocalIndexType insideScvIdx
274 =
static_cast<LocalIndexType
>(referenceElement(geo_).subEntity(localFacetIndex, 1, localIsScvfIndex, dim));
275 return { insideScvIdx, insideScvIdx };
278 DUNE_THROW(Dune::NotImplemented,
"PQ2 scv boundary pair call for hybrid dofs");
293 const typename Element::Geometry& geo_;
294 BoxHelper boxHelper_;
Helper class constructing the dual grid finite volume geometries for the box discretizazion method.
Create sub control volumes and sub control volume face geometries.
Definition: boxgeometryhelper.hh:257
A class to create sub control volume and sub control volume face geometries per element.
Definition: discretization/pq2/geometryhelper.hh:51
Dune::GeometryType getBoundaryScvfGeometryType(unsigned int localScvfIdx) const
Definition: discretization/pq2/geometryhelper.hh:139
std::size_t numScv() const
number of sub control volumes (number of codim-1 entities)
Definition: discretization/pq2/geometryhelper.hh:193
bool isOverlappingBoundaryScvf(unsigned int localFacetIndex) const
Definition: discretization/pq2/geometryhelper.hh:285
ScvfCornerStorage getScvfCorners(unsigned int localScvfIdx) const
Create a vector with the corners of sub control volume faces.
Definition: discretization/pq2/geometryhelper.hh:104
GlobalPosition dofPosition(const LocalKey &localKey) const
Definition: discretization/pq2/geometryhelper.hh:242
bool isOverlappingScvf(unsigned int localScvfIndex) const
Definition: discretization/pq2/geometryhelper.hh:282
static auto dofIndex(const DofMapper &dofMapper, const Element &element, const LocalKey &localKey)
Definition: discretization/pq2/geometryhelper.hh:224
static auto localDofOnIntersection(Dune::GeometryType type, unsigned int iIdx, const LocalKey &localKey)
Local dof index related to a localDof, with index ilocalDofIdx, on an intersection with index iIdx.
Definition: discretization/pq2/geometryhelper.hh:211
std::array< LocalIndexType, 2 > getScvPairForBoundaryScvf(unsigned int localFacetIndex, unsigned int localIsScvfIndex) const
Definition: discretization/pq2/geometryhelper.hh:268
ScvCornerStorage getScvCorners(unsigned int localScvIdx) const
Create a vector with the scv corners.
Definition: discretization/pq2/geometryhelper.hh:73
const Element::Geometry & elementGeometry() const
the wrapped element geometry
Definition: discretization/pq2/geometryhelper.hh:177
std::array< LocalIndexType, 2 > getScvPairForScvf(unsigned int localScvfIndex) const
Definition: discretization/pq2/geometryhelper.hh:254
static auto numInteriorScvf(Dune::GeometryType type)
number of interior sub control volume faces
Definition: discretization/pq2/geometryhelper.hh:181
ScvfCornerStorage getBoundaryScvfCorners(unsigned int localFacetIndex, unsigned int indexInFacet) const
Create the sub control volume face geometries on the boundary.
Definition: discretization/pq2/geometryhelper.hh:133
Scalar scvVolume(unsigned int localScvIdx, const ScvCornerStorage &p) const
get scv volume
Definition: discretization/pq2/geometryhelper.hh:199
static auto numBoundaryScvf(Dune::GeometryType type, unsigned int localFacetIndex)
number of boundary sub control volume faces for face localFacetIndex
Definition: discretization/pq2/geometryhelper.hh:187
static Element::Geometry::LocalCoordinate localDofPosition(Dune::GeometryType type, const LocalKey &localKey)
local dof position
Definition: discretization/pq2/geometryhelper.hh:249
Dune::GeometryType getInteriorScvfGeometryType(unsigned int localScvfIdx) const
Definition: discretization/pq2/geometryhelper.hh:123
Dune::GeometryType getScvGeometryType(unsigned int localScvIdx) const
Definition: discretization/pq2/geometryhelper.hh:92
GlobalPosition normal(const ScvfCornerStorage &p, const std::array< LocalIndexType, 2 > &scvPair)
Definition: discretization/pq2/geometryhelper.hh:145
bool isOverlappingScv(unsigned int localScvIndex) const
Definition: discretization/pq2/geometryhelper.hh:289
HybridPQ2GeometryHelper(const typename Element::Geometry &geometry)
Definition: discretization/pq2/geometryhelper.hh:67
static GlobalPosition dofPosition(const Geometry &geo, const LocalKey &localKey)
Definition: discretization/pq2/geometryhelper.hh:231
static ScvfCornerStorage getScvfCorners(Dune::GeometryType type, Transformation &&trans, unsigned int localScvfIdx)
Create a vector with the corners of sub control volume faces.
Definition: discretization/pq2/geometryhelper.hh:111
static ScvCornerStorage getScvCorners(Dune::GeometryType type, Transformation &&trans, unsigned int localScvIdx)
Create a vector with the scv corners.
Definition: discretization/pq2/geometryhelper.hh:80
Dune::FieldVector< Scalar, 3 > crossProduct(const Dune::FieldVector< Scalar, 3 > &vec1, const Dune::FieldVector< Scalar, 3 > &vec2)
Cross product of two vectors in three-dimensional Euclidean space.
Definition: math.hh:671
Define some often used mathematical functions.
Definition: discretization/pq2/geometryhelper.hh:39
Dune::ReservedVector< Dune::FieldVector< ct, cdim >,(1<< mydim)> Type
Definition: discretization/pq2/geometryhelper.hh:40
Traits for an efficient corner storage for the PQ2 method.
Definition: discretization/pq2/geometryhelper.hh:34
Compute the volume of several common geometry types.