wallPointsI.H
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) 2018-2023 OpenCFD Ltd.
9 -------------------------------------------------------------------------------
10 License
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 "polyMesh.H"
29 #include "transform.H"
30 
31 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
32 
33 template<class TrackingData>
34 inline bool Foam::wallPoints::update
35 (
36  const point& pt,
37  const label index1,
38  const wallPoints& w2,
39  const label index2,
40 
41  const scalar tol,
42  TrackingData& td
43 )
44 {
45  const scalar dist2 = magSqr(pt - w2.origin_[index2]);
46 
47  if (!valid(td))
48  {
49  // currently not yet set so use any value
50  distSqr_[index1] = dist2;
51  origin_[index1] = w2.origin_[index2];
52  surface_[index1] = w2.surface_[index2];
53  //normal_[index1] = w2.normal_[index2];
54 
55  return true;
56  }
57 
58  const scalar diff = distSqr_[index1] - dist2;
59 
60  if (diff < 0)
61  {
62  // already nearer to pt
63  return false;
64  }
65 
66  if
67  (
68  (diff < SMALL)
69  || ((distSqr_[index1] > SMALL) && (diff/distSqr_[index1] < tol))
70  )
71  {
72  // don't propagate small changes
73  return false;
74  }
75  else
76  {
77  // update with new values
78  distSqr_[index1] = dist2;
79  origin_[index1] = w2.origin_[index2];
80  surface_[index1] = w2.surface_[index2];
81  //normal_[index1] = w2.normal_[index2];
82 
83  return true;
84  }
85 }
86 
87 
88 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
89 
91 :
92  origin_(0),
93  distSqr_(0),
94  surface_(0)
95  //normal_(0)
96 {}
97 
98 
100 (
101  const UList<point>& origin,
102  const UList<scalar>& distSqr,
104  //const UList<vector>& normal
105 )
106 :
107  origin_(origin),
108  distSqr_(distSqr),
109  surface_(surface)
110  //normal_(normal)
111 {}
112 
113 
114 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
115 
116 template<class TrackingData>
117 inline bool Foam::wallPoints::valid(TrackingData& td) const
118 {
119  return origin_.size();
120 }
121 
122 
123 // No geometric data so never any problem on cyclics
124 template<class TrackingData>
126 (
127  const polyMesh&,
128  const wallPoints&,
129  const scalar,
130  TrackingData&
131 ) const
132 {
133  return true;
134 }
135 
136 
137 // No geometric data.
138 template<class TrackingData>
140 (
141  const polyMesh&,
142  const polyPatch& patch,
143  const label patchFacei,
144  const point& faceCentre,
145  TrackingData&
146 )
147 {
148  for (auto& o : origin_)
149  {
150  o -= faceCentre;
151  }
152 }
153 
154 
155 // No geometric data.
156 template<class TrackingData>
157 inline void Foam::wallPoints::transform
158 (
159  const polyMesh&,
160  const tensor& rotTensor,
161  TrackingData&
162 )
163 {
164  for (auto& o : origin_)
165  {
166  o = Foam::transform(rotTensor, o);
167  }
168 }
169 
170 
171 // No geometric data.
172 template<class TrackingData>
174 (
175  const polyMesh&,
176  const polyPatch& patch,
177  const label patchFacei,
178  const point& faceCentre,
179  TrackingData&
180 )
181 {
182  // back to absolute form
183  for (auto& o : origin_)
184  {
185  o += faceCentre;
186  }
187 }
188 
189 
190 // Update cell with neighbouring face information
191 template<class TrackingData>
193 (
194  const polyMesh& mesh,
195  const label thisCelli,
196  const label neighbourFacei,
197  const wallPoints& neighbourInfo,
198  const scalar tol,
199  TrackingData& td
200 )
201 {
202  const point& cc = mesh.cellCentres()[thisCelli];
203 
204  bool hasChanged = false;
205 
206  forAll(neighbourInfo.surface_, i)
207  {
208  const FixedList<label, 3>& nbrSurface = neighbourInfo.surface_[i];
209 
210  const scalar d2 = magSqr(cc-neighbourInfo.origin_[i]);
211 
212  // Optionally check against surface-based block size
213  bool propagate = false;
214  if (nbrSurface[0] == labelMax)
215  {
216  // nbrSurface has special value to ignore regionToBlockSize
217  propagate = true;
218  }
219  else
220  {
221  // Check distance from nbr origin to cc against max walking distance
222  const scalar blockSize =
223  td.regionToBlockSize_[nbrSurface[0]][nbrSurface[1]];
224 
225  propagate = (d2 < Foam::sqr(3*blockSize));
226  }
227 
228  if (propagate)
229  {
230  // Real distance less than max gap distance. Note that it should
231  // be at least 2 * blockSize (since gap is two cells across).
232  // Should be
233  // a little bit more to account for castellated path walk. Bit
234  // heuristic - try 3. Should be as low as possible to kill off
235  // unnecessary waves asap.
236 
237  // Find in my surfaces
238  label index = surface_.find(nbrSurface);
239  if (index == -1)
240  {
241  // Append
242  origin_.append(neighbourInfo.origin_[i]);
243  distSqr_.append(d2);
244  surface_.append(nbrSurface);
245  //normal_.append(neighbourInfo.normal_[i]);
246  hasChanged = true;
247  }
248  else
249  {
250  hasChanged =
251  update(cc, index, neighbourInfo, i, tol, td)
252  || hasChanged;
253  }
254  }
255  else
256  {
257  // Real distance more than gap distance so ignore
258  //Pout<< "at cell:" << cc << " ignoring nbr info:"
259  // << neighbourInfo.origin_[i]
260  // << " from surface:" << nbrSurface[0]
261  // << " from region:" << nbrSurface[1]
262  // << " bloxkSize:" << blockSize
263  // << " distance:" << Foam::sqrt(d2)
264  // << endl;
265  }
266  }
267 
268  return hasChanged;
269 }
270 
271 
272 // Update face with neighbouring cell information
273 template<class TrackingData>
275 (
276  const polyMesh& mesh,
277  const label thisFacei,
278  const label neighbourCelli,
279  const wallPoints& neighbourInfo,
280  const scalar tol,
281  TrackingData& td
282 )
283 {
284  // From cell to its faces.
285  bool hasChanged = false;
286 
287  if (!td.isBlockedFace_[thisFacei])
288  {
289  const point& fc = mesh.faceCentres()[thisFacei];
290 
291  forAll(neighbourInfo.surface_, i)
292  {
293  const FixedList<label, 3>& nbrSurface = neighbourInfo.surface_[i];
294 
295  const scalar d2 = magSqr(fc-neighbourInfo.origin_[i]);
296 
297  // Optionally check against surface-based block size
298  bool propagate = false;
299  if (nbrSurface[0] == labelMax)
300  {
301  // nbrSurface has special value to ignore regionToBlockSize
302  propagate = true;
303  }
304  else
305  {
306  // Check distance from nbr origin to cc against max walking
307  // distance
308  const scalar blockSize =
309  td.regionToBlockSize_[nbrSurface[0]][nbrSurface[1]];
310 
311  propagate = (d2 < Foam::sqr(3*blockSize));
312  }
313 
314  if (propagate)
315  {
316  // Real distance less than max gap distance
317 
318  // Find in my surfaces
319  label index = surface_.find(nbrSurface);
320  if (index == -1)
321  {
322  // Append
323  origin_.append(neighbourInfo.origin_[i]);
324  distSqr_.append(d2);
325  surface_.append(nbrSurface);
326  //normal_.append(neighbourInfo.normal_[i]);
327  hasChanged = true;
328  }
329  else
330  {
331  hasChanged =
332  update(fc, index, neighbourInfo, i, tol, td)
333  || hasChanged;
334  }
335  }
336  else
337  {
338  // Real distance more than gap distance so ignore
339  //Pout<< "at face:" << fc << " ignoring nbr info:"
340  // << neighbourInfo.origin_[i]
341  // << " from surface:" << nbrSurface[0]
342  // << " from region:" << nbrSurface[1]
343  // << " bloxkSize:" << blockSize
344  // << " distance:" << Foam::sqrt(d2)
345  // << endl;
346  }
347  }
348  }
349 
350  return hasChanged;
351 }
352 
353 
354 // Update face with coupled face information
355 template<class TrackingData>
357 (
358  const polyMesh& mesh,
359  const label thisFacei,
360  const wallPoints& neighbourInfo,
361  const scalar tol,
362  TrackingData& td
363 )
364 {
365  // From face to face (e.g. coupled faces)
366  bool hasChanged = false;
367 
368  if (!td.isBlockedFace_[thisFacei])
369  {
370  const point& fc = mesh.faceCentres()[thisFacei];
371 
372  forAll(neighbourInfo.surface_, i)
373  {
374  const FixedList<label, 3>& nbrSurface = neighbourInfo.surface_[i];
375 
376  const scalar d2 = magSqr(fc-neighbourInfo.origin_[i]);
377 
378  // Optionally check against surface-based block size
379  bool propagate = false;
380  if (nbrSurface[0] == labelMax)
381  {
382  // nbrSurface has special value to ignore regionToBlockSize
383  propagate = true;
384  }
385  else
386  {
387  // Check distance from nbr origin to cc against max walking
388  // distance
389  const scalar blockSize =
390  td.regionToBlockSize_[nbrSurface[0]][nbrSurface[1]];
391 
392  propagate = (d2 < Foam::sqr(3*blockSize));
393  }
394 
395  if (propagate)
396  {
397  // Real distance less than max gap distance
398 
399  // Find in my surfaces
400  const label index = surface_.find(nbrSurface);
401  if (index == -1)
402  {
403  // Append
404  origin_.append(neighbourInfo.origin_[i]);
405  distSqr_.append(d2);
406  surface_.append(nbrSurface);
407  //normal_.append(neighbourInfo.normal_[i]);
408  hasChanged = true;
409  }
410  else
411  {
412  hasChanged =
413  update(fc, index, neighbourInfo, i, tol, td)
414  || hasChanged;
415  }
416  }
417  else
418  {
419  // Real distance more than gap distance so ignore
420  //Pout<< "at face:" << fc << " ignoring nbr info:"
421  // << neighbourInfo.origin_[i]
422  // << " from surface:" << nbrSurface[0]
423  // << " from region:" << nbrSurface[1]
424  // << " bloxkSize:" << blockSize
425  // << " distance:" << Foam::sqrt(d2)
426  // << endl;
427  }
428  }
429  }
431  return hasChanged;
432 }
433 
434 
435 template<class TrackingData>
436 inline bool Foam::wallPoints::equal
437 (
438  const wallPoints& rhs,
439  TrackingData& td
440 ) const
441 {
442  return operator==(rhs);
443 }
444 
445 
446 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
447 
448 inline bool Foam::wallPoints::operator==
449 (
450  const wallPoints& rhs
451 ) const
452 {
453  return
454  surface_ == rhs.surface_
455  && distSqr_ == rhs.distSqr_
456  && origin_ == rhs.origin_;
457  //&& normal_ == rhs.normal_;
458 }
459 
460 
461 inline bool Foam::wallPoints::operator!=
462 (
463  const wallPoints& rhs
464 ) const
465 {
466  return !(*this == rhs);
467 }
468 
469 
470 // ************************************************************************* //
scalar diff(const triad &A, const triad &B)
Return a quantity of the difference between two triads.
Definition: triad.C:373
bool updateFace(const polyMesh &, const label thisFacei, const label neighbourCelli, const wallPoints &neighbourInfo, const scalar tol, TrackingData &td)
Influence of neighbouring cell.
Definition: wallPointsI.H:268
bool update(const point &pt, const label index1, const wallPoints &w2, const label index2, const scalar tol, TrackingData &td)
Originating normal.
Definition: wallPointsI.H:28
bool valid(TrackingData &td) const
Changed or contains original (invalid) value.
Definition: wallPointsI.H:110
bool updateCell(const polyMesh &, const label thisCelli, const label neighbourFacei, const wallPoints &neighbourInfo, const scalar tol, TrackingData &td)
Influence of neighbouring face.
Definition: wallPointsI.H:186
wallPoints::trackData td(isBlockedFace, regionToBlockSize)
dimensionedSymmTensor sqr(const dimensionedVector &dv)
const bitSet & isBlockedFace_
Per face whether the face should not be walked through.
Definition: wallPoints.H:73
Tensor< scalar > tensor
Definition: symmTensor.H:57
#define w2
Definition: blockCreate.C:28
const List< scalarList > & regionToBlockSize_
Per surface, per region the blockSize.
Definition: wallPoints.H:78
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:421
bool equal(const wallPoints &, TrackingData &) const
Test for equality, with TrackingData.
Definition: wallPointsI.H:430
void leaveDomain(const polyMesh &, const polyPatch &, const label patchFacei, const point &faceCentre, TrackingData &td)
Convert any absolute coordinates into relative to (patch)face.
Definition: wallPointsI.H:133
dynamicFvMesh & mesh
3D tensor transformation operations.
bool sameGeometry(const polyMesh &, const wallPoints &, const scalar, TrackingData &td) const
Check for identical geometrical data (eg, cyclics checking)
Definition: wallPointsI.H:119
DynamicList< FixedList< label, 3 > > surface_
Originating surface,region and topological region.
Definition: wallPoints.H:109
const vectorField & cellCentres() const
A 1D vector of objects of type <T>, where the size of the vector is known and can be used for subscri...
Definition: HashTable.H:105
label find(const T &val) const
Find index of the first occurrence of the value.
Definition: UList.C:173
const wordList surface
Standard surface field types (scalar, vector, tensor, etc)
A Vector of values with scalar precision, where scalar is float/double depending on the compilation f...
wallPoints()
Default construct.
Definition: wallPointsI.H:83
mesh update()
void transform(const polyMesh &, const tensor &, TrackingData &td)
Apply rotation matrix to any coordinates.
Definition: wallPointsI.H:151
For use with FaceCellWave. Determines topological distance to starting faces.
Definition: wallPoints.H:59
const vectorField & faceCentres() const
vector point
Point is a vector.
Definition: point.H:37
const std::string patch
OpenFOAM patch number as a std::string.
constexpr label labelMax
Definition: label.H:55
Mesh consisting of general polyhedral cells.
Definition: polyMesh.H:75
DynamicList< scalar > distSqr_
Distance (squared) from cellcenter to origin.
Definition: wallPoints.H:104
DynamicList< point > origin_
Starting points.
Definition: wallPoints.H:99
tmp< faMatrix< Type > > operator==(const faMatrix< Type > &, const faMatrix< Type > &)
A patch is a list of labels that address the faces in the global face list.
Definition: polyPatch.H:69
void enterDomain(const polyMesh &, const polyPatch &, const label patchFacei, const point &faceCentre, TrackingData &td)
Reverse of leaveDomain.
Definition: wallPointsI.H:167
dimensionSet transform(const dimensionSet &ds)
Return the argument; transformations do not change the dimensions.
Definition: dimensionSet.C:521
dimensioned< typename typeOfMag< Type >::type > magSqr(const dimensioned< Type > &dt)