Loading [MathJax]/extensions/tex2jax.js

dune-mmesh (1.4)

intersections.hh
Go to the documentation of this file.
1// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2// vi: set et ts=4 sw=2 sts=2:
3#ifndef DUNE_MMESH_INTERFACE_INTERSECTIONS_HH
4#define DUNE_MMESH_INTERFACE_INTERSECTIONS_HH
5
6#include <unordered_set>
7
8// Dune MMesh includes
12#include <dune/mmesh/misc/twistutility.hh>
13
14// local includes
15
20namespace Dune
21{
22
23 // External forward declarations
24 template< class Grid >
25 struct HostGridAccess;
26
35 template<class GridImp>
37 {
39
40 friend struct HostGridAccess< typename std::remove_const< GridImp >::type >;
41
42 enum {dim=GridImp::dimension};
43
44 enum {dimworld=GridImp::dimensionworld};
45
46 // The type used to store coordinates
47 typedef typename GridImp::ctype ctype;
48
49 typedef typename GridImp::template MMeshInterfaceEntity<0> MMeshInterfaceEntity;
50 typedef typename GridImp::template MMeshInterfaceEntity<1> HostLeafIntersection;
51
52 typedef typename GridImp::MMeshType::template Codim<0>::Entity MMeshEntity;
53
54 using LocalIndexMap = std::unordered_map< std::size_t, std::size_t >;
55 typedef typename GridImp::MMeshType::template Codim<dimworld>::Entity MMeshVertex;
56
57 public:
58 enum {dimension=GridImp::dimension};
59 enum {dimensionworld=GridImp::dimensionworld};
60 typedef typename GridImp::template Codim<1>::Geometry Geometry;
61 typedef typename GridImp::template Codim<1>::LocalGeometry LocalGeometry;
62 typedef typename GridImp::template Codim<0>::Entity Entity;
63 typedef FieldVector<ctype, dimensionworld> NormalVector;
64
66 {}
67
68 MMeshInterfaceGridLeafIntersection(const GridImp* grid,
69 const MMeshInterfaceEntity& hostEntity,
70 const std::size_t index,
71 const std::size_t nbIdx)
72 : grid_(grid),
73 interfaceEntity_(hostEntity),
74 index_(index),
75 nbIdx_(nbIdx),
76 cgalIndex_( MMeshInterfaceImpl::computeCGALIndices<MMeshInterfaceEntity, dim>( interfaceEntity_ ) )
77 {
78 const auto& indexSet = grid_->leafIndexSet();
79
80 std::array< std::size_t, dimension > ids;
81
82 if constexpr (dim == 1)
83 {
84 ids[0] = indexSet.vertexIndexMap().at( interfaceEntity_.first->vertex( cgalIndex_[index_] )->info().id );
85 }
86 else // dim == 2
87 {
88 ids[0] = indexSet.vertexIndexMap().at( interfaceEntity_.first->vertex( cgalIndex_[index_==2 ? 1 : 0] )->info().id );
89 ids[1] = indexSet.vertexIndexMap().at( interfaceEntity_.first->vertex( cgalIndex_[index_==0 ? 1 : 2] )->info().id );
90 }
91 std::sort(ids.begin(), ids.end());
92 try {
93 localIndexMap_ = indexSet.indexMap().at( ids );
94 } catch (std::exception &e) {
95 DUNE_THROW(InvalidStateException, e.what());
96 }
97 assert( 0 <= nbIdx_ && ( nbIdx_ < numOutside() || boundary() ) );
98 }
99
102 {
103 return interfaceEntity_ == other.interfaceEntity_
104 && index_ == other.index_
105 && nbIdx_ == other.nbIdx_;
106 }
107
110 Entity inside() const {
111 return MMeshInterfaceGridEntity<0,dimension,GridImp>(grid_, interfaceEntity_);
112 }
113
116 std::size_t numOutside() const {
117 return localIndexMap_.size() - 1;
118 }
119
122 Entity outside() const
123 {
124 assert( neighbor() );
125
126 const auto& vertexIndexMap = grid_->leafIndexSet().vertexIndexMap();
127
128 std::size_t myLastVertexIndex = vertexIndexMap.at(
129 interfaceEntity_.first->vertex(cgalIndex_[dim-index_])->info().id
130 );
131
132 // get the i-th index map entry
133 auto it = localIndexMap_.begin();
134 // exclude myself
135 while ( it->first == myLastVertexIndex )
136 ++it;
137
138 for( std::size_t count = 0; count < nbIdx_; count++ )
139 {
140 ++it;
141
142 // exclude myself
143 if ( it->first == myLastVertexIndex )
144 count--;
145 }
146
147 // obtain neighbor by searching in incident elements of intersection vertex
148 std::size_t v0idx = index_;
149 if constexpr (dim == 2)
150 if (index_ == 1)
151 v0idx = 0;
152
153 const auto& vertex0 = interfaceEntity_.first->vertex( cgalIndex_[v0idx] );
154
155 std::array< std::size_t, dimensionworld > vIdx;
156 vIdx[0] = vertexIndexMap.at( vertex0->info().id );
157 vIdx[1] = it->first;
158
159 if constexpr ( dimensionworld == 3 )
160 try {
161 std::size_t v1idx = (index_ == 1) ? 2 : 1;
162 vIdx[2] = vertexIndexMap.at( interfaceEntity_.first->vertex( cgalIndex_[v1idx] )->info().id );
163 } catch (std::exception &e) {
164 DUNE_THROW(InvalidStateException, e.what());
165 }
166 std::sort(vIdx.begin(), vIdx.end());
167
168 // search in incident facets for the right entity
169 for( const auto& facet : incidentFacets( MMeshVertex {{ &grid_->getMMesh(), vertex0 }} ) )
170 {
171 std::array< std::size_t, dimensionworld > tmpIdx;
172 bool notInterface = false;
173 for( std::size_t i = 0; i < facet.subEntities(dimensionworld); ++i )
174 {
175 std::size_t idx = facet.impl().template subEntity<dimensionworld>(i).impl().hostEntity()->info().id;
176 auto it = vertexIndexMap.find( idx );
177 if( it != vertexIndexMap.end() )
178 tmpIdx[i] = it->second;
179 else
180 notInterface = true;
181 }
182 if( notInterface )
183 continue;
184 std::sort(tmpIdx.begin(), tmpIdx.end());
185
186 if ( vIdx == tmpIdx )
187 return MMeshInterfaceGridEntity<0,dimension,GridImp>(grid_, facet.impl().hostEntity());
188 }
189 DUNE_THROW( InvalidStateException, "Neighbor could not be determined!" );
190 }
191
193 bool boundary () const {
194 return localIndexMap_.size() == 1;
195 }
196
202 NormalVector centerUnitOuterNormal () const {
203 return unitOuterNormal( FieldVector<ctype, dimension-1> ( 0 ) );
204 }
205
207 bool neighbor() const {
208 return !boundary();
209 }
210
212 size_t boundarySegmentIndex() const
213 {
214 auto iid = grid_->globalIdSet().id( grid_->entity( getHostIntersection() ) );
215 auto it = grid_->boundarySegments().find( iid );
216 if( it == grid_->boundarySegments().end() )
217 return 0;
218
219 return it->second;
220 }
221
223 std::size_t boundaryId() const
224 {
225 return 0; // TODO
226 }
227
229 bool conforming () const {
230 // we are always conforming
231 return true;
232 }
233
235 GeometryType type () const {
236 return GeometryTypes::simplex(dimension-1);
237 }
238
243 LocalGeometry geometryInInside () const
244 {
245 return LocalGeometry( indexInInside() );
246 }
247
250 LocalGeometry geometryInOutside () const
251 {
252 assert( neighbor() );
253 return LocalGeometry( indexInOutside() );
254 }
255
258 template< int d = dimension >
259 typename std::enable_if_t< d == 1, Geometry >
260 geometry () const
261 {
262 return Geometry( interfaceEntity_.first->vertex( cgalIndex_[index_] ) );
263 }
264
265 template< int d = dimension >
266 typename std::enable_if_t< d == 2, Geometry >
267 geometry () const
268 {
269 int vIdx0 = cgalIndex_[index_==2 ? 1 : 0];
270 int vIdx1 = cgalIndex_[index_==0 ? 1 : 2];
271
272 return Geometry( {{ interfaceEntity_.first, vIdx0, vIdx1 }} );
273 }
274
276 int indexInInside () const
277 {
278 return index_;
279 }
280
282 int indexInOutside () const
283 {
284 const auto& subEn = inside().template subEntity<1>( index_ );
285
286 const auto neighbor = outside();
287 for ( int i = 0; i < dimensionworld; ++i )
288 if ( neighbor.template subEntity<1>( i ) == subEn )
289 return i;
290
291 DUNE_THROW( InvalidStateException, "indexInOutside() could not be determined!" );
292 }
293
295 FieldVector<ctype, GridImp::dimensionworld> outerNormal (const FieldVector<ctype, GridImp::dimension-1>& local) const {
296 return integrationOuterNormal( local );
297 }
298
300 template< int d = dimension >
301 typename std::enable_if_t< d == 1, NormalVector >
302 integrationOuterNormal (const FieldVector<ctype, dimension-1>& local) const
303 {
304 auto face = interfaceEntity_.first;
305
306 const auto& p1 = face->vertex( cgalIndex_[ index_ ] )->point();
307 const auto& p2 = face->vertex( cgalIndex_[1-index_] )->point();
308
309 NormalVector n ( { p1.x() - p2.x(), p1.y() - p2.y() } );
310 n /= n.two_norm();
311 return n;
312 }
313
314 template< int d = dimension >
315 typename std::enable_if_t< d == 2, NormalVector >
316 integrationOuterNormal (const FieldVector<ctype, dimension-1>& local) const
317 {
318 const auto& cell = interfaceEntity_.first;
319
320 int vIdx0 = cgalIndex_[index_==2 ? 1 : 0];
321 int vIdx1 = cgalIndex_[index_==0 ? 1 : 2];
322 int vIdxLast = cgalIndex_[2-index_];
323
324 auto a = makeFieldVector( cell->vertex( vIdx0 )->point() );
325 auto b = makeFieldVector( cell->vertex( vIdx1 )->point() );
326 auto v = makeFieldVector( cell->vertex( vIdxLast )->point() );
327
328 // return vector that is orthogonal to edge a-b and triangle a-b-v
329 NormalVector ab = b - a;
330 NormalVector vb = b - v;
331
332 NormalVector elementNormal;
333 elementNormal[0] = ab[1]*vb[2] - ab[2]*vb[1];
334 elementNormal[1] = ab[2]*vb[0] - ab[0]*vb[2];
335 elementNormal[2] = ab[0]*vb[1] - ab[1]*vb[0];
336
337 NormalVector outerNormal;
338 outerNormal[0] = ab[1]*elementNormal[2] - ab[2]*elementNormal[1];
339 outerNormal[1] = ab[2]*elementNormal[0] - ab[0]*elementNormal[2];
340 outerNormal[2] = ab[0]*elementNormal[1] - ab[1]*elementNormal[0];
341
342 if( outerNormal * vb < 0.0 )
343 outerNormal *= -1.0;
344
345 return outerNormal;
346 }
347
349 FieldVector<ctype, GridImp::dimensionworld> unitOuterNormal (const FieldVector<ctype, GridImp::dimension-1>& local) const {
350 NormalVector n = integrationOuterNormal( local );
351 n /= n.two_norm();
352 return n;
353 }
354
355 const auto getHostVertex() const
356 {
357 return interfaceEntity_.first->vertex((interfaceEntity_.second+index_+1)%(dimensionworld+1));
358 }
359
360 const MMeshInterfaceEntity& getHostIntersection() const
361 {
362 return interfaceEntity_;
363 }
364
365 private:
367 const GridImp* grid_;
368 MMeshInterfaceEntity interfaceEntity_;
369 std::size_t index_;
370 std::size_t nbIdx_;
371 LocalIndexMap localIndexMap_;
372 std::array< std::size_t, dim+1 > cgalIndex_;
373 };
374
375} // namespace Dune
376
377#endif
The implementation of entities in a MMesh interface grid.
Definition: entity.hh:35
Iterator over all element neighborsMesh entities of codimension 0 ("elements") allow to visit all nei...
Definition: intersectioniterator.hh:30
An intersection with a leaf neighbor elementMesh entities of codimension 0 ("elements") allow to visi...
Definition: intersections.hh:37
std::size_t numOutside() const
Definition: intersections.hh:116
GeometryType type() const
Geometry type of an intersection.
Definition: intersections.hh:235
bool equals(const MMeshInterfaceGridLeafIntersection &other) const
returns true if the host entities are equal
Definition: intersections.hh:101
Entity inside() const
Definition: intersections.hh:110
FieldVector< ctype, GridImp::dimensionworld > unitOuterNormal(const FieldVector< ctype, GridImp::dimension-1 > &local) const
return unit outer normal
Definition: intersections.hh:349
std::enable_if_t< d==1, Geometry > geometry() const
Definition: intersections.hh:260
FieldVector< ctype, GridImp::dimensionworld > outerNormal(const FieldVector< ctype, GridImp::dimension-1 > &local) const
return outer normal
Definition: intersections.hh:295
std::enable_if_t< d==1, NormalVector > integrationOuterNormal(const FieldVector< ctype, dimension-1 > &local) const
return outer normal multiplied by the integration element
Definition: intersections.hh:302
bool boundary() const
return true if intersection is with boundary.
Definition: intersections.hh:193
std::size_t boundaryId() const
Return the boundary id.
Definition: intersections.hh:223
int indexInInside() const
local number of codim 1 entity in self where intersection is contained in
Definition: intersections.hh:276
NormalVector centerUnitOuterNormal() const
Return unit outer normal (length == 1)
Definition: intersections.hh:202
bool conforming() const
Return true if this is a conforming intersection.
Definition: intersections.hh:229
size_t boundarySegmentIndex() const
return the boundary segment index
Definition: intersections.hh:212
LocalGeometry geometryInOutside() const
Definition: intersections.hh:250
Entity outside() const
Definition: intersections.hh:122
int indexInOutside() const
local number of codim 1 entity in neighbor where intersection is contained
Definition: intersections.hh:282
bool neighbor() const
return true if across the edge an neighbor on this level exists
Definition: intersections.hh:207
LocalGeometry geometryInInside() const
Definition: intersections.hh:243
The MMeshEntity class.
The MMeshLeafIterator class.
STL namespace.
Helpers for conversion from CGAL::Point_x to DUNE::FieldVector.
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden & Uni Heidelberg  |  generated with Hugo v0.111.3 (Apr 6, 22:49, 2025)