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