Loading...
Searching...
No Matches
tetWedgeMatcher.C
Go to the documentation of this file.
1/*---------------------------------------------------------------------------*\
2 ========= |
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4 \\ / O peration |
5 \\ / A nd | www.openfoam.com
6 \\/ M anipulation |
7-------------------------------------------------------------------------------
8 Copyright (C) 2011-2016 OpenFOAM Foundation
9-------------------------------------------------------------------------------
10License
11 This file is part of OpenFOAM.
12
13 OpenFOAM is free software: you can redistribute it and/or modify it
14 under the terms of the GNU General Public License as published by
15 the Free Software Foundation, either version 3 of the License, or
16 (at your option) any later version.
17
18 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25
26\*---------------------------------------------------------------------------*/
27
28#include "tetWedgeMatcher.H"
29#include "cellMatcher.H"
30#include "primitiveMesh.H"
31#include "cellModel.H"
32#include "ListOps.H"
33
34// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
35
37:
39 (
40 vertPerCell,
41 facePerCell,
42 maxVertPerFace,
43 "tetWedge" // == cellModel::modelNames[cellModel::TETWEDGE]
44 )
45{}
46
47
48// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
49
51(
52 const bool checkOnly,
53 const faceList& faces,
54 const labelList& owner,
55 const label celli,
56 const labelList& myFaces
57)
58{
59 if (!faceSizeMatch(faces, myFaces))
60 {
61 return false;
62 }
63
64 // Is tetWedge for sure now. No other shape has two tri, two quad
65 if (checkOnly)
66 {
67 return true;
68 }
69
70 // Calculate localFaces_ and mapping pointMap_, faceMap_
71 label numVert = calcLocalFaces(faces, myFaces);
72
73 if (numVert != vertPerCell)
74 {
75 return false;
76 }
77
78 // Set up 'edge' to face mapping.
79 calcEdgeAddressing(numVert);
80
81 // Set up point on face to index-in-face mapping
82 calcPointFaceIndex();
83
84 // Storage for maps -vertex to mesh and -face to mesh
85 vertLabels_.setSize(vertPerCell);
86 faceLabels_.setSize(facePerCell);
87
88 //
89 // Try first triangular face. Rotate in all directions.
90 // Walk path to other triangular face.
91 //
92
93 label face0I = -1;
94 forAll(faceSize_, facei)
95 {
96 if (faceSize_[facei] == 3)
97 {
98 face0I = facei;
99 break;
100 }
101 }
102
103 const face& face0 = localFaces_[face0I];
104
105 // Try all rotations of this face
106 for (label face0vert0 = 0; face0vert0 < faceSize_[face0I]; face0vert0++)
107 {
108 //
109 // Try to follow prespecified path on faces of cell,
110 // starting at face0vert0
111 //
112
113 vertLabels_[0] = pointMap_[face0[face0vert0]];
114 faceLabels_[0] = faceMap_[face0I];
115
116 // Walk face 0 from vertex 0 to 1
117 label face0vert1 =
118 nextVert
119 (
120 face0vert0,
121 faceSize_[face0I],
122 !(owner[faceMap_[face0I]] == celli)
123 );
124 vertLabels_[1] = pointMap_[face0[face0vert1]];
125
126 // Jump edge from face0 to face1 (the other triangular face)
127 label face1I =
129 (
130 numVert,
131 face0[face0vert0],
132 face0[face0vert1],
133 face0I
134 );
135
136 if (faceSize_[face1I] != 3)
137 {
138 continue;
139 }
140 faceLabels_[1] = faceMap_[face1I];
141
142
143 // Now correctly oriented tet-wedge for sure.
144
145 // Walk face 0 from vertex 1 to 2
146 label face0vert2 =
147 nextVert
148 (
149 face0vert1,
150 faceSize_[face0I],
151 !(owner[faceMap_[face0I]] == celli)
152 );
153 vertLabels_[2] = pointMap_[face0[face0vert2]];
154
155 // Jump edge from face0 to face3
156 label face3I =
158 (
159 numVert,
160 face0[face0vert1],
161 face0[face0vert2],
162 face0I
163 );
164 faceLabels_[3] = faceMap_[face3I];
165
166 // Jump edge from face0 to face2
167 label face2I =
169 (
170 numVert,
171 face0[face0vert2],
172 face0[face0vert0],
173 face0I
174 );
175 faceLabels_[2] = faceMap_[face2I];
176
177 // Get index of vertex 2 in face3
178 label face3vert2 = pointFaceIndex_[face0[face0vert2]][face3I];
179
180 // Walk face 3 from vertex 2 to 4
181 label face3vert4 =
182 nextVert
183 (
184 face3vert2,
185 faceSize_[face3I],
186 (owner[faceMap_[face3I]] == celli)
187 );
188
189 const face& face3 = localFaces_[face3I];
190
191 vertLabels_[4] = pointMap_[face3[face3vert4]];
192
193 // Walk face 3 from vertex 4 to 3
194 label face3vert3 =
195 nextVert
196 (
197 face3vert4,
198 faceSize_[face3I],
199 (owner[faceMap_[face3I]] == celli)
200 );
201 vertLabels_[3] = pointMap_[face3[face3vert3]];
202
203 return true;
205
206 // Tried all triangular faces, in all rotations but no match found
207 return false;
208}
209
211Foam::label Foam::tetWedgeMatcher::faceHashValue() const
212{
213 return 2*3 + 2*4;
214}
215
216
218(
219 const faceList& faces,
220 const labelList& myFaces
221) const
222{
223 if (myFaces.size() != 4)
224 {
225 return false;
226 }
227
228 label nTris = 0;
229 label nQuads = 0;
230
231 for (const label facei : myFaces)
232 {
233 const label size = faces[facei].size();
234
235 if (size == 3)
236 {
237 ++nTris;
238 }
239 else if (size == 4)
240 {
241 ++nQuads;
242 }
243 else
244 {
245 return false;
247 }
248
249 return (nTris == 2 && nQuads == 2);
250}
251
252
253bool Foam::tetWedgeMatcher::isA(const primitiveMesh& mesh, const label celli)
254{
255 return matchShape
256 (
257 true,
258 mesh.faces(),
259 mesh.faceOwner(),
260 celli,
261 mesh.cells()[celli]
262 );
263}
264
265
266bool Foam::tetWedgeMatcher::isA(const faceList& faces)
267{
268 // Do as if mesh with one cell only
269 return matchShape
270 (
271 true,
272 faces, // all faces in mesh
273 labelList(faces.size(), Zero), // cell 0 is owner of all faces
274 0, // cell label
275 identity(faces.size()) // faces of cell 0
276 );
277}
278
279
281(
282 const primitiveMesh& mesh,
283 const label celli,
284 cellShape& shape
285)
286{
287 if
288 (
289 matchShape
290 (
291 false,
292 mesh.faces(),
293 mesh.faceOwner(),
294 celli,
295 mesh.cells()[celli]
296 )
297 )
298 {
299 shape.reset(model(), vertLabels());
300 return true;
301 }
302
303 return false;
304}
305
306
307// ************************************************************************* //
Various functions to operate on Lists.
void size(const label n)
Older name for setAddressableSize.
Definition UList.H:118
const cellModel & model() const
labelListList pointFaceIndex_
pointFaceIndex[localVertI][localFacei] is index in localFace
labelList faceMap_
Map from local to mesh face numbering.
label calcLocalFaces(const faceList &faces, const labelList &myFaces)
Calculates localFaces. Returns number of local vertices (or -1.
Definition cellMatcher.C:67
labelList pointMap_
Map from local to mesh vertex numbering.
labelList faceLabels_
After matching: holds mesh faces in cellmodel order.
static label nextVert(const label, const label, const bool)
Step along face either in righthand or lefthand direction.
labelList vertLabels_
After matching: holds mesh vertices in cellmodel order.
const labelList & vertLabels() const
labelList faceSize_
Number of vertices per face in localFaces_.
label otherFace(const label numVert, const label v0, const label v1, const label localFacei) const
Given start,end of edge lookup both faces sharing it and return.
void calcEdgeAddressing(const label numVert)
Fill edge (start, end) to face number.
faceList localFaces_
Faces using local vertex numbering.
cellMatcher(const cellMatcher &)=delete
No copy construct.
void calcPointFaceIndex()
Fill vertex/face to index in face data structure.
An analytical geometric cellShape.
Definition cellShape.H:71
void reset(const cellModel &model, const labelUList &labels, const bool doCollapse=false)
Reset from components.
Definition cellShapeI.H:359
A face is a list of labels corresponding to mesh vertices.
Definition face.H:71
virtual const faceList & faces() const
Return raw faces.
Definition polyMesh.C:1088
Cell-face mesh analysis engine.
virtual bool faceSizeMatch(const faceList &, const labelList &) const
Check whether number of face sizes match the shape.
virtual bool matchShape(const bool checkOnly, const faceList &faces, const labelList &faceOwner, const label celli, const labelList &myFaces)
Low level shape recognition. Return true if matches.
virtual bool matches(const primitiveMesh &mesh, const label celli, cellShape &shape)
Like isA but also constructs a cellShape (if shape matches).
virtual bool isA(const primitiveMesh &mesh, const label celli)
Exact match. Uses faceSizeMatch.
virtual label faceHashValue() const
Hash value of all face sizes of this shape. Can be used for.
tetWedgeMatcher()
Default construct.
dynamicFvMesh & mesh
label otherFace(const primitiveMesh &mesh, const label celli, const label facei, const label edgeI)
Return face on cell using edgeI but not facei. Throws error.
Definition meshTools.C:548
List< label > labelList
A List of labels.
Definition List.H:62
List< face > faceList
List of faces.
Definition faceListFwd.H:41
labelList identity(const label len, label start=0)
Return an identity map of the given length with (map[i] == i), works like std::iota() but returning a...
static constexpr const zero Zero
Global zero (0).
Definition zero.H:127
#define forAll(list, i)
Loop across all elements in list.
Definition stdFoam.H:299