MeshedSurface.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  Copyright (C) 2016-2019 OpenCFD Ltd.
10 -------------------------------------------------------------------------------
11 License
12  This file is part of OpenFOAM.
13 
14  OpenFOAM is free software: you can redistribute it and/or modify it
15  under the terms of the GNU General Public License as published by
16  the Free Software Foundation, either version 3 of the License, or
17  (at your option) any later version.
18 
19  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22  for more details.
23 
24  You should have received a copy of the GNU General Public License
25  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26 
27 \*---------------------------------------------------------------------------*/
28 
29 #include "MeshedSurface.H"
30 #include "UnsortedMeshedSurface.H"
31 #include "MeshedSurfaceProxy.H"
32 #include "mergePoints.H"
33 #include "Time.H"
34 #include "ListOps.H"
35 #include "polyBoundaryMesh.H"
36 #include "polyMesh.H"
37 #include "surfMesh.H"
38 #include "primitivePatch.H"
39 #include "faceTraits.H"
41 
42 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
43 
44 template<class Face>
46 {
47  return wordHashSet(*fileExtensionConstructorTablePtr_);
48 }
49 
50 template<class Face>
52 {
53  return wordHashSet(*writefileExtensionMemberFunctionTablePtr_);
54 }
55 
56 
57 // * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
58 
59 template<class Face>
61 (
62  const word& ext,
63  bool verbose
64 )
65 {
66  return fileFormats::surfaceFormatsCore::checkSupport
67  (
68  readTypes() | FriendType::readTypes(),
69  ext,
70  verbose,
71  "reading"
72  );
73 }
74 
75 
76 template<class Face>
78 (
79  const word& ext,
80  bool verbose
81 )
82 {
83  return fileFormats::surfaceFormatsCore::checkSupport
84  (
85  writeTypes() | ProxyType::writeTypes(),
86  ext,
87  verbose,
88  "writing"
89  );
90 }
91 
92 
93 template<class Face>
95 (
96  const fileName& name,
97  bool verbose
98 )
99 {
100  word ext = name.ext();
101  if (ext == "gz")
102  {
103  ext = name.lessExt().ext();
104  }
105  return canReadType(ext, verbose);
106 }
107 
108 
109 template<class Face>
111 (
112  const fileName& name,
113  const MeshedSurface<Face>& surf,
114  const dictionary& options
115 )
116 {
117  write(name, name.ext(), surf, options);
118 }
119 
120 
121 template<class Face>
123 (
124  const fileName& name,
125  const word& ext,
126  const MeshedSurface<Face>& surf,
127  const dictionary& options
128 )
129 {
130  if (debug)
131  {
132  InfoInFunction << "Writing to " << name << endl;
133  }
134 
135  auto mfIter = writefileExtensionMemberFunctionTablePtr_->cfind(ext);
136 
137  if (!mfIter.found())
138  {
139  // No direct writer, delegate to proxy if possible
140  const wordHashSet& delegate = ProxyType::writeTypes();
141 
142  if (delegate.found(ext))
143  {
144  MeshedSurfaceProxy<Face>(surf).write(name, ext, options);
145  }
146  else
147  {
149  << "Unknown file extension " << ext << nl << nl
150  << "Valid types:" << nl
151  << flatOutput((delegate | writeTypes()).sortedToc()) << nl
152  << exit(FatalError);
153  }
154  }
155  else
156  {
157  mfIter()(name, surf, options);
158  }
159 }
160 
161 
162 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
163 
164 template<class Face>
166 :
167  ParentType(List<Face>(), pointField()),
168  zones_()
169 {}
170 
171 
172 template<class Face>
174 (
175  const MeshedSurface<Face>& surf
176 )
177 :
178  ParentType(surf.surfFaces(), surf.points()),
179  zones_(surf.surfZones())
180 {}
181 
182 
183 template<class Face>
185 (
186  const UnsortedMeshedSurface<Face>& surf
187 )
188 :
189  ParentType(List<Face>(), surf.points())
190 {
192  this->storedZones() = surf.sortedZones(faceMap);
193 
194  const List<Face>& origFaces = surf;
195  List<Face> newFaces(origFaces.size());
196 
197  forAll(newFaces, facei)
198  {
199  newFaces[faceMap[facei]] = origFaces[facei];
200  }
201 
202  this->storedFaces().transfer(newFaces);
203 }
204 
205 
206 template<class Face>
208 (
209  MeshedSurface<Face>&& surf
210 )
211 :
213 {
214  transfer(surf);
215 }
216 
217 
218 template<class Face>
220 (
222 )
223 :
225 {
226  transfer(surf);
227 }
228 
229 
230 template<class Face>
232 (
233  const pointField& pointLst,
234  const UList<Face>& faceLst,
235  const UList<surfZone>& zoneLst
236 )
237 :
238  ParentType(faceLst, pointLst), // Copy construct
239  zones_(zoneLst)
240 {}
241 
242 
243 template<class Face>
245 (
246  pointField&& pointLst,
247  List<Face>&& faceLst,
248  const UList<surfZone>& zoneLst
249 )
250 :
251  ParentType(faceLst, pointLst, true), // Move construct
252  zones_(zoneLst)
253 {}
254 
255 
256 template<class Face>
258 (
259  const pointField& pointLst,
260  const UList<Face>& faceLst,
261  const labelUList& zoneSizes,
262  const UList<word>& zoneNames
263 )
264 :
265  ParentType(faceLst, pointLst), // Copy construct
266  zones_()
267 {
268  if (zoneSizes.size())
269  {
270  if (zoneNames.size())
271  {
272  addZones(zoneSizes, zoneNames);
273  }
274  else
275  {
276  addZones(zoneSizes);
277  }
278  }
279 }
280 
281 
282 template<class Face>
284 (
285  pointField&& pointLst,
286  List<Face>&& faceLst,
287  const labelUList& zoneSizes,
288  const UList<word>& zoneNames
289 )
290 :
291  ParentType(faceLst, pointLst, true), // Move construct
292  zones_()
293 {
294  if (zoneSizes.size())
295  {
296  if (zoneNames.size())
297  {
298  addZones(zoneSizes, zoneNames);
299  }
300  else
301  {
302  addZones(zoneSizes);
303  }
304  }
305 }
306 
307 
308 template<class Face>
310 :
311  MeshedSurface<Face>()
312 {
313  // Need same face type as surfMesh
315  (
316  mesh.points(),
317  mesh.faces(),
318  mesh.surfZones()
319  );
320 
321  this->transcribe(surf);
322 }
323 
324 
325 template<class Face>
327 (
328  const polyBoundaryMesh& bMesh,
329  const bool useGlobalPoints
330 )
331 :
333 {
334  const polyMesh& mesh = bMesh.mesh();
335  const polyPatchList& bPatches = bMesh;
336 
337  // Get a single patch for all boundaries
338  primitivePatch allBoundary
339  (
341  (
342  mesh.faces(),
343  mesh.nBoundaryFaces(),
344  mesh.nInternalFaces()
345  ),
346  mesh.points()
347  );
348 
349  // use global/local points:
350  const pointField& bPoints =
351  (
352  useGlobalPoints ? mesh.points() : allBoundary.localPoints()
353  );
354 
355  // global/local face addressing:
356  const List<Face>& bFaces =
357  (
358  useGlobalPoints ? allBoundary : allBoundary.localFaces()
359  );
360 
361 
362  // create zone list
363  surfZoneList newZones(bPatches.size());
364 
365  label startFacei = 0;
366  label nZone = 0;
367  for (const polyPatch& p : bPatches)
368  {
369  if (p.size())
370  {
371  newZones[nZone] = surfZone
372  (
373  p.name(),
374  p.size(),
375  startFacei,
376  nZone
377  );
378 
379  ++nZone;
380  startFacei += p.size();
381  }
382  }
383 
384  newZones.setSize(nZone);
385 
386  // Face type as per polyBoundaryMesh
387  MeshedSurface<face> surf(bPoints, bFaces, newZones);
388 
389  this->transcribe(surf);
390 }
391 
392 
393 template<class Face>
395 :
396  MeshedSurface<Face>()
397 {
398  read(name, ext);
399 }
400 
401 
402 template<class Face>
404 :
405  MeshedSurface<Face>()
406 {
407  read(name);
408 }
409 
410 
411 template<class Face>
413 :
414  MeshedSurface<Face>()
415 {
416  read(is);
417 }
418 
419 
420 template<class Face>
422 (
423  const Time& runTime,
424  const word& surfName
425 )
426 :
428 {
429  surfMesh mesh
430  (
431  IOobject
432  (
433  "dummyName",
434  runTime.timeName(),
435  runTime,
436  IOobject::MUST_READ_IF_MODIFIED,
437  IOobject::NO_WRITE,
438  false
439  ),
440  surfName
441  );
442 
443  // The geometry components, returned via autoPtr
445  (
446  std::move(*(mesh.releaseGeom()))
447  );
448 
449  this->transcribe(surf);
450 }
451 
452 
453 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
454 
455 template<class Face>
457 {
458  clear();
459 }
460 
461 
462 // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
463 
464 template<class Face>
466 (
467  const labelUList& faceMap
468 )
469 {
470  if (faceMap.empty())
471  {
472  return;
473  }
474 
475  surfZoneList& zones = storedZones();
476 
477  if (zones.size() == 1)
478  {
479  zones[0].size() = faceMap.size(); // Single zone case is trivial
480  return;
481  }
482 
483  // Recalculate the zone start/size
484  label newFacei = 0;
485  label origEndI = 0;
486 
487  for (surfZone& zone : zones)
488  {
489  // Adjust zone start
490  zone.start() = newFacei;
491  origEndI += zone.size();
492 
493  for (label facei = newFacei; facei < faceMap.size(); ++facei)
494  {
495  if (faceMap[facei] < origEndI)
496  {
497  ++newFacei;
498  }
499  else
500  {
501  break;
502  }
503  }
504 
505  // Adjust zone size
506  zone.size() = newFacei - zone.start();
507  }
508 }
509 
510 
511 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
512 
513 template<class Face>
515 {
516  ParentType::clearOut(); // Topology changes
517 
518  storedPoints().clear();
519  storedFaces().clear();
520  storedZones().clear();
521 }
522 
523 
524 template<class Face>
526 {
527  ParentType::clearGeom(); // Changes areas, normals etc.
528 
529  // Adapt for new point position
530  ParentType::movePoints(newPoints);
531 
532  // Copy new points
533  storedPoints() = newPoints;
534 }
535 
536 
537 template<class Face>
538 void Foam::MeshedSurface<Face>::scalePoints(const scalar scaleFactor)
539 {
540  // Avoid bad scaling
541  if (scaleFactor > 0 && scaleFactor != 1.0)
542  {
543  ParentType::clearGeom(); // Changes areas, normals etc.
544 
545  pointField newPoints(scaleFactor*this->points());
546 
547  // Adapt for new point position
548  ParentType::movePoints(newPoints);
549 
550  storedPoints() = newPoints;
551  }
552 }
553 
554 
555 // Remove badly degenerate faces, double faces.
556 template<class Face>
557 void Foam::MeshedSurface<Face>::cleanup(const bool verbose)
558 {
559  // Merge points (already done for STL, TRI)
560  stitchFaces(SMALL, verbose);
561 
562  checkFaces(verbose);
563  this->checkTopology(verbose);
564 }
565 
566 
567 template<class Face>
569 (
570  const scalar tol,
571  const bool verbose
572 )
573 {
574  pointField& pointLst = this->storedPoints();
575 
576  // Merge points
577  labelList pointMap(pointLst.size());
578  pointField newPoints(pointLst.size());
579 
580  bool hasMerged = mergePoints(pointLst, tol, verbose, pointMap, newPoints);
581 
582  if (!hasMerged)
583  {
584  return false;
585  }
586 
587  if (verbose)
588  {
589  InfoInFunction<< "Renumbering all faces" << endl;
590  }
591 
592  // Set the coordinates to the merged ones
593  pointLst.transfer(newPoints);
594 
595  List<Face>& faceLst = this->storedFaces();
596 
597  List<label> faceMap(faceLst.size());
598 
599  // Reset the point labels to the unique points array
600  label newFacei = 0;
601  forAll(faceLst, facei)
602  {
603  Face& f = faceLst[facei];
604  forAll(f, fp)
605  {
606  f[fp] = pointMap[f[fp]];
607  }
608 
609  // for extra safety: collapse face as well
610  if (f.collapse() >= 3)
611  {
612  if (newFacei != facei)
613  {
614  faceLst[newFacei] = f;
615  }
616  faceMap[newFacei] = facei;
617  ++newFacei;
618  }
619  else if (verbose)
620  {
621  Pout<< "MeshedSurface::stitchFaces : "
622  << "Removing collapsed face " << facei << endl
623  << " vertices :" << f << endl;
624  }
625  }
626  pointMap.clear();
627 
628  if (newFacei != faceLst.size())
629  {
630  if (verbose)
631  {
632  Pout<< "MeshedSurface::stitchFaces : "
633  << "Removed " << faceLst.size() - newFacei
634  << " faces" << endl;
635  }
636  faceLst.setSize(newFacei);
637  faceMap.setSize(newFacei);
638  remapFaces(faceMap);
639  }
640  faceMap.clear();
641 
642  // Topology can change when points are merged, etc
643  ParentType::clearOut();
644 
645  return true;
646 }
647 
648 
649 // Remove badly degenerate faces and double faces.
650 template<class Face>
652 (
653  const bool verbose
654 )
655 {
656  bool changed = false;
657  List<Face>& faceLst = this->storedFaces();
658 
659  List<label> faceMap(faceLst.size());
660 
661  label newFacei = 0;
662  // Detect badly labelled faces and mark degenerate faces
663  const label maxPointi = this->points().size() - 1;
664  forAll(faceLst, facei)
665  {
666  Face& f = faceLst[facei];
667 
668  // avoid degenerate faces
669  if (f.collapse() >= 3)
670  {
671  forAll(f, fp)
672  {
673  if (f[fp] < 0 || f[fp] > maxPointi)
674  {
676  << "face " << f
677  << " uses point indices outside point range 0.."
678  << maxPointi
679  << exit(FatalError);
680  }
681  }
682 
683  faceMap[facei] = facei;
684  ++newFacei;
685  }
686  else
687  {
688  // mark as bad face
689  faceMap[facei] = -1;
690 
691  changed = true;
692  if (verbose)
693  {
695  << "face[" << facei << "] = " << f
696  << " does not have three unique vertices" << endl;
697  }
698  }
699  }
700 
701  // Detect doubled faces
702  // do not touch the faces
703  const labelListList& fFaces = this->faceFaces();
704  newFacei = 0;
705  forAll(faceLst, facei)
706  {
707  // skip already collapsed faces:
708  if (faceMap[facei] < 0)
709  {
710  continue;
711  }
712 
713  const Face& f = faceLst[facei];
714 
715  // duplicate face check
716  bool okay = true;
717  const labelList& neighbours = fFaces[facei];
718 
719  // Check if faceNeighbours use same points as this face.
720  // Note: discards normal information - sides of baffle are merged.
721  forAll(neighbours, neighI)
722  {
723  const label neiFacei = neighbours[neighI];
724 
725  if (neiFacei <= facei || faceMap[neiFacei] < 0)
726  {
727  // lower numbered faces already checked
728  // skip neighbours that are themselves collapsed
729  continue;
730  }
731 
732  const Face& nei = faceLst[neiFacei];
733 
734  if (f == nei)
735  {
736  okay = false;
737 
738  if (verbose)
739  {
741  << "faces share the same vertices:" << nl
742  << " face[" << facei << "] : " << f << nl
743  << " face[" << neiFacei << "] : " << nei << endl;
744  // printFace(Warning, " ", f, points());
745  // printFace(Warning, " ", nei, points());
746  }
747 
748  break;
749  }
750  }
751 
752  if (okay)
753  {
754  faceMap[facei] = facei;
755  ++newFacei;
756  }
757  else
758  {
759  faceMap[facei] = -1;
760  }
761  }
762 
763  // Phase 1: pack
764  // Done to keep numbering constant in phase 1
765 
766  if (changed || newFacei < faceLst.size())
767  {
768  changed = true;
769 
770  if (verbose)
771  {
773  << "Removed " << faceLst.size() - newFacei
774  << " illegal faces." << endl;
775  }
776 
777  // compress the face list
778  newFacei = 0;
779  forAll(faceLst, facei)
780  {
781  if (faceMap[facei] >= 0)
782  {
783  if (newFacei != facei)
784  {
785  faceLst[newFacei] = faceLst[facei];
786  }
787  faceMap[newFacei] = facei;
788  ++newFacei;
789  }
790  }
791 
792  faceLst.setSize(newFacei);
793  remapFaces(faceMap);
794  }
795  faceMap.clear();
796 
797  // Topology can change because of renumbering
798  ParentType::clearOut();
799  return changed;
800 }
801 
802 
803 template<class Face>
805 {
807  {
808  return ParentType::size();
809  }
810 
811  return nTriangles
812  (
813  const_cast<List<label>&>(List<label>::null())
814  );
815 }
816 
817 
818 template<class Face>
820 (
822 ) const
823 {
824  label nTri = 0;
825  const List<Face>& faceLst = surfFaces();
826 
827  // Count triangles needed
828  forAll(faceLst, facei)
829  {
830  nTri += faceLst[facei].nTriangles();
831  }
832 
833  // Nothing to do
834  if (nTri <= faceLst.size())
835  {
836  if (notNull(faceMap))
837  {
838  faceMap.clear();
839  }
840  }
841  else if (notNull(faceMap))
842  {
843  // face map requested
844  faceMap.setSize(nTri);
845 
846  nTri = 0;
847  forAll(faceLst, facei)
848  {
849  label n = faceLst[facei].nTriangles();
850  while (n-- > 0)
851  {
852  faceMap[nTri++] = facei;
853  }
854  }
855 
856  faceMap.setSize(nTri);
857  }
858 
859  return nTri;
860 }
861 
862 
863 template<class Face>
865 {
867  {
868  // Inplace triangulation of triFace/labelledTri surface = no-op
869  return 0;
870  }
871  else
872  {
873  return triangulate
874  (
875  const_cast<List<label>&>(List<label>::null())
876  );
877  }
878 }
879 
880 
881 template<class Face>
883 (
884  List<label>& faceMapOut
885 )
886 {
888  {
889  // Inplace triangulation of triFace/labelledTri surface = no-op
890  if (notNull(faceMapOut))
891  {
892  faceMapOut.clear();
893  }
894 
895  return 0;
896  }
897 
898  label nTri = 0;
899  label maxTri = 0; // the maximum number of triangles for any single face
900  List<Face>& faceLst = this->storedFaces();
901 
902  // determine how many triangles will be needed
903  forAll(faceLst, facei)
904  {
905  const label n = faceLst[facei].nTriangles();
906  if (maxTri < n)
907  {
908  maxTri = n;
909  }
910  nTri += n;
911  }
912 
913  // nothing to do
914  if (nTri <= faceLst.size())
915  {
916  if (notNull(faceMapOut))
917  {
918  faceMapOut.clear();
919  }
920  return 0;
921  }
922 
923  List<Face> newFaces(nTri);
925 
926  // reuse storage from optional faceMap
927  if (notNull(faceMapOut))
928  {
929  faceMap.transfer(faceMapOut);
930  }
931  faceMap.setSize(nTri);
932 
933  if (this->points().empty())
934  {
935  // triangulate without points
936  // simple face triangulation around f[0]
937  nTri = 0;
938  forAll(faceLst, facei)
939  {
940  const Face& f = faceLst[facei];
941 
942  for (label fp = 1; fp < f.size() - 1; ++fp)
943  {
944  const label fp1 = f.fcIndex(fp);
945 
946  newFaces[nTri] = Face{f[0], f[fp], f[fp1]};
947  faceMap[nTri] = facei;
948  ++nTri;
949  }
950  }
951  }
952  else
953  {
954  // triangulate with points
955  List<face> tmpTri(maxTri);
956 
957  nTri = 0;
958  forAll(faceLst, facei)
959  {
960  // 'face' not '<Face>'
961  const face& f = faceLst[facei];
962 
963  label nTmp = 0;
964  f.triangles(this->points(), nTmp, tmpTri);
965  for (label triI = 0; triI < nTmp; triI++)
966  {
967  newFaces[nTri] = Face
968  (
969  static_cast<labelUList&>(tmpTri[triI])
970  );
971  faceMap[nTri] = facei;
972  ++nTri;
973  }
974  }
975  }
976 
977  // The number of *additional* faces
978  nTri -= faceLst.size();
979 
980  faceLst.transfer(newFaces);
981  remapFaces(faceMap);
982 
983  // optionally return the faceMap
984  if (notNull(faceMapOut))
985  {
986  faceMapOut.transfer(faceMap);
987  }
988  faceMap.clear();
989 
990  // Topology can change because of renumbering
991  ParentType::clearOut();
992 
993  return nTri;
994 }
995 
996 
997 template<class Face>
998 template<class BoolListType>
1001  const BoolListType& include,
1002  labelList& pointMap,
1004 ) const
1005 {
1006  const pointField& locPoints = this->localPoints();
1007  const List<Face>& locFaces = this->localFaces();
1008 
1009 
1010  // Fill pointMap, faceMap
1011  PatchTools::subsetMap(*this, include, pointMap, faceMap);
1012 
1013  // Create compact coordinate list and forward mapping array
1014  pointField newPoints(pointMap.size());
1015  labelList oldToNew(locPoints.size());
1016  forAll(pointMap, pointi)
1017  {
1018  newPoints[pointi] = locPoints[pointMap[pointi]];
1019  oldToNew[pointMap[pointi]] = pointi;
1020  }
1021 
1022  // create/copy a new zones list, each zone with zero size
1023  surfZoneList newZones(this->surfZones());
1024  forAll(newZones, zoneI)
1025  {
1026  newZones[zoneI].size() = 0;
1027  }
1028 
1029  // Renumber face node labels
1030  List<Face> newFaces(faceMap.size());
1031  forAll(faceMap, facei)
1032  {
1033  const label origFacei = faceMap[facei];
1034  newFaces[facei] = Face(locFaces[origFacei]);
1035 
1036  // Renumber labels for face
1037  Face& f = newFaces[facei];
1038  forAll(f, fp)
1039  {
1040  f[fp] = oldToNew[f[fp]];
1041  }
1042  }
1043  oldToNew.clear();
1044 
1045  // recalculate the zones start/size
1046  label newFacei = 0;
1047  label origEndI = 0;
1048 
1049  // adjust zone sizes
1050  forAll(newZones, zoneI)
1051  {
1052  surfZone& zone = newZones[zoneI];
1053 
1054  // adjust zone start
1055  zone.start() = newFacei;
1056  origEndI += zone.size();
1057 
1058  for (label facei = newFacei; facei < faceMap.size(); ++facei)
1059  {
1060  if (faceMap[facei] < origEndI)
1061  {
1062  ++newFacei;
1063  }
1064  else
1065  {
1066  break;
1067  }
1068  }
1069 
1070  // adjust zone size
1071  zone.size() = newFacei - zone.start();
1072  }
1073 
1074  // Construct a sub-surface
1075  return MeshedSurface<Face>
1076  (
1077  std::move(newPoints),
1078  std::move(newFaces),
1079  std::move(newZones)
1080  );
1081 }
1082 
1083 
1084 template<class Face>
1087  const bitSet& include
1088 ) const
1089 {
1090  labelList pointMap, faceMap;
1091  return subsetMesh(include, pointMap, faceMap);
1092 }
1093 
1094 
1095 template<class Face>
1098  const labelHashSet& include
1099 ) const
1100 {
1101  labelList pointMap, faceMap;
1102  return subsetMesh(include, pointMap, faceMap);
1103 }
1104 
1105 
1106 template<class Face>
1109  MeshedSurface<Face>& surf
1110 )
1111 {
1112  if (this == &surf)
1113  {
1114  return; // Self-swap is a no-op
1115  }
1116 
1117  ParentType::clearOut(); // Topology changes
1118  surf.clearOut(); // Topology changes
1119 
1120  this->storedPoints().swap(surf.storedPoints());
1121  this->storedFaces().swap(surf.storedFaces());
1122  this->storedZones().swap(surf.storedZones());
1123 }
1124 
1125 
1126 template<class Face>
1129  pointField& pointLst,
1130  List<Face>& faceLst
1131 )
1132 {
1133  ParentType::clearOut(); // Topology changes
1134 
1135  this->storedPoints().transfer(pointLst);
1136  this->storedFaces().transfer(faceLst);
1137  this->storedZones().clear();
1138 }
1139 
1140 
1141 template<class Face>
1144  MeshedSurface<Face>& surf
1145 )
1146 {
1147  if (this == &surf)
1148  {
1149  return; // Self-assigment is a no-op
1150  }
1151 
1152  ParentType::clearOut(); // Topology changes
1153 
1154  this->storedPoints().transfer(surf.storedPoints());
1155  this->storedFaces().transfer(surf.storedFaces());
1156  this->storedZones().transfer(surf.storedZones());
1157 
1158  surf.clear();
1159 }
1160 
1161 
1162 template<class Face>
1166 )
1167 {
1168  clear();
1169 
1171  surfZoneList zoneLst = surf.sortedZones(faceMap);
1172 
1173  List<Face>& faceLst = surf.storedFaces();
1174 
1175  if (zoneLst.size() > 1)
1176  {
1177  // Unknown if we really need to sort the faces
1178  List<Face> sortedFaces(faceMap.size());
1179 
1180  forAll(faceMap, facei)
1181  {
1182  sortedFaces[faceMap[facei]].transfer(faceLst[facei]);
1183  }
1184 
1185  faceLst.swap(sortedFaces); // Replace with sorted faces
1186  }
1187 
1188  MeshedSurface<Face> newSurf
1189  (
1190  std::move(surf.storedPoints()),
1191  std::move(faceLst),
1192  std::move(zoneLst)
1193  );
1194 
1195  surf.clear();
1196 
1197  this->swap(newSurf);
1198 }
1199 
1200 
1201 template<class Face>
1204 {
1205  return autoPtr<MeshedSurface<Face>>::New(std::move(*this));
1206 }
1207 
1208 
1209 template<class Face>
1211 {
1212  ParentType::clearOut(); // Topology changes
1213 
1214  this->storedFaces().swap(faces);
1215 }
1216 
1217 
1218 template<class Face>
1220 {
1221  ParentType::clearOut(); // Topology changes
1222 
1223  this->storedPoints().swap(points);
1224 }
1225 
1226 
1227 template<class Face>
1229 {
1230  this->storedZones().swap(zones);
1231 }
1232 
1233 
1234 template<class Face>
1236 {
1237  const word ext(name.ext());
1238  if (ext == "gz")
1239  {
1240  fileName unzipName = name.lessExt();
1241  return read(unzipName, unzipName.ext());
1242  }
1243 
1244  return read(name, ext);
1245 }
1246 
1247 
1248 // Read from file in given format
1249 template<class Face>
1252  const fileName& name,
1253  const word& ext
1254 )
1255 {
1256  clear();
1257 
1258  // read via selector mechanism
1259  transfer(New(name, ext)());
1260  return true;
1261 }
1262 
1263 
1264 template<class Face>
1267  const Time& t,
1268  const word& surfName
1269 ) const
1270 {
1271  MeshedSurfaceProxy<Face>(*this).write(t, surfName);
1272 }
1273 
1274 
1275 // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
1276 
1277 template<class Face>
1279 {
1280  clear();
1281 
1282  this->storedPoints() = surf.points();
1283  this->storedFaces() = surf.surfFaces();
1284  this->storedZones() = surf.surfZones();
1285 }
1286 
1287 
1288 template<class Face>
1290 {
1291  transfer(surf);
1292 }
1293 
1294 
1295 template<class Face>
1297 {
1299  (
1300  this->points(),
1301  this->surfFaces(),
1302  this->surfZones()
1303  );
1304 }
1305 
1306 
1307 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
1308 
1309 #include "MeshedSurfaceZones.C"
1310 #include "MeshedSurfaceIO.C"
1311 #include "MeshedSurfaceNew.C"
1312 
1313 // ************************************************************************* //
Foam::expressions::patchExpr::debug
int debug
Static debugging option.
Foam::word::lessExt
word lessExt() const
Return word without extension (part before last .)
Definition: word.C:113
runTime
engineTime & runTime
Definition: createEngineTime.H:13
Foam::IOobject
Defines the attributes of an object for which implicit objectRegistry management is supported,...
Definition: IOobject.H:104
InfoInFunction
#define InfoInFunction
Report an information message using Foam::Info.
Definition: messageStream.H:316
p
volScalarField & p
Definition: createFieldRefs.H:8
MeshedSurfaceProxy.H
Foam::MeshedSurface::surfZones
const surfZoneList & surfZones() const
Const access to the surface zones.
Definition: MeshedSurface.H:370
Foam::MeshedSurface::~MeshedSurface
virtual ~MeshedSurface()
Destructor.
Definition: MeshedSurface.C:456
Foam::Time
Class to control time during OpenFOAM simulations that is also the top-level objectRegistry.
Definition: Time.H:73
Foam::faceMap
Pair< int > faceMap(const label facePi, const face &faceP, const label faceNi, const face &faceN)
Definition: blockMeshMergeFast.C:94
Foam::word
A class for handling words, derived from Foam::string.
Definition: word.H:62
Foam::MeshedSurface::swapZones
void swapZones(surfZoneList &zones)
Swap the stored zones.
Definition: MeshedSurface.C:1228
Foam::MeshedSurface::storedFaces
List< Face > & storedFaces()
Non-const access to the faces.
Definition: MeshedSurface.H:157
Foam::fileName
A class for handling file names.
Definition: fileName.H:69
Foam::bitSet
A bitSet stores bits (elements with only two states) in packed internal format and supports a variety...
Definition: bitSet.H:64
Foam::polyBoundaryMesh
A polyBoundaryMesh is a polyPatch list with additional search methods and registered IO.
Definition: polyBoundaryMesh.H:62
Foam::MeshedSurface::triangulate
virtual label triangulate()
Triangulate in-place, returning the number of triangles added.
Definition: MeshedSurface.C:864
Foam::MeshedSurface::swap
void swap(MeshedSurface< Face > &surf)
Swap contents.
Definition: MeshedSurface.C:1108
Foam::MeshedSurface::storedPoints
pointField & storedPoints()
Non-const access to global points.
Definition: MeshedSurface.H:151
Foam::MeshedSurface::stitchFaces
virtual bool stitchFaces(const scalar tol=SMALL, const bool verbose=false)
Definition: MeshedSurface.C:569
Foam::SubList
A List obtained as a section of another List.
Definition: SubList.H:53
Foam::MeshedSurface::subsetMesh
MeshedSurface subsetMesh(const BoolListType &include, labelList &pointMap, labelList &faceMap) const
Return new surface.
Foam::MeshedSurface::operator=
void operator=(const MeshedSurface< Face > &surf)
Copy assignment.
Definition: MeshedSurface.C:1278
Foam::zone
Base class for mesh zones.
Definition: zone.H:63
Foam::MeshedSurface::surfFaces
const List< Face > & surfFaces() const
Return const access to the faces.
Definition: MeshedSurface.H:362
Foam::MeshedSurface::scalePoints
virtual void scalePoints(const scalar scaleFactor)
Scale points. A non-positive factor is ignored.
Definition: MeshedSurface.C:538
Foam::surfMesh
A surface mesh consisting of general polygon faces.
Definition: surfMesh.H:64
Foam::endl
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:337
Foam::word::ext
word ext() const
Return file name extension (part after last .)
Definition: word.C:126
Foam::MeshedSurface::clear
virtual void clear()
Clear all storage.
Definition: MeshedSurface.C:514
Foam::checkTopology
label checkTopology(const polyMesh &mesh, const bool allTopology, const bool allGeometry, autoPtr< surfaceWriter > &surfWriter, const autoPtr< writer< scalar >> &setWriter)
Foam::Pout
prefixOSstream Pout
An Ostream wrapper for parallel output to std::cout.
polyMesh.H
Foam::HashSet< word >
Foam::MeshedSurfaceProxy
A proxy for writing MeshedSurface, UnsortedMeshedSurface and surfMesh to various file formats.
Definition: MeshedSurface.H:78
Foam::polyMesh
Mesh consisting of general polyhedral cells.
Definition: polyMesh.H:77
Foam::MeshedSurface::checkFaces
virtual bool checkFaces(const bool verbose=false)
Definition: MeshedSurface.C:652
Foam::MeshedSurface::canWriteType
static bool canWriteType(const word &ext, bool verbose=false)
Can we write this file format?
Definition: MeshedSurface.C:78
forAll
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:290
Foam::MeshedSurface::canRead
static bool canRead(const fileName &name, bool verbose=false)
Can we read this file format?
Definition: MeshedSurface.C:95
UnsortedMeshedSurface.H
Foam::MeshedSurface::remapFaces
virtual void remapFaces(const labelUList &faceMap)
Set new zones from faceMap.
Definition: MeshedSurface.C:466
n
label n
Definition: TABSMDCalcMethod2.H:31
Foam::MeshedSurface::storedZones
surfZoneList & storedZones()
Non-const access to the zones.
Definition: MeshedSurface.H:163
Foam::faceTraits
Traits class for faces.
Definition: faceTraits.H:50
Foam::MeshedSurfaceProxy::write
static void write(const fileName &name, const MeshedSurfaceProxy &surf, const dictionary &options)
Write to file, select based on its extension.
Definition: MeshedSurfaceProxy.C:62
Foam::MeshedSurface::transfer
void transfer(pointField &pointLst, List< Face > &faceLst)
Transfer the components.
Definition: MeshedSurface.C:1128
Foam::label
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:62
Foam::Field< vector >
Foam::Istream
An Istream is an abstract base class for all input systems (streams, files, token lists etc)....
Definition: Istream.H:61
Foam::UnsortedMeshedSurface
A surface geometry mesh, in which the surface zone information is conveyed by the 'zoneId' associated...
Definition: MeshedSurface.H:79
Foam::polyPatch
A patch is a list of labels that address the faces in the global face list.
Definition: polyPatch.H:66
Foam::name
word name(const complex &c)
Return string representation of complex.
Definition: complex.C:76
Foam::bMesh
PrimitivePatch< face, List, const pointField > bMesh
Holder of faceList and points. (v.s. e.g. primitivePatch which references points)
Definition: bMesh.H:47
Foam::List::transfer
void transfer(List< T > &list)
Definition: List.C:436
Foam::MeshedSurface::nTriangles
virtual label nTriangles() const
Count number of triangles.
Definition: MeshedSurface.C:804
Foam::PtrList
A list of pointers to objects of type <T>, with allocation/deallocation management of the pointers....
Definition: List.H:65
MeshedSurfaceIO.C
Foam::blockMeshTools::read
void read(Istream &, label &, const dictionary &)
In-place read with dictionary lookup.
Definition: blockMeshTools.C:33
Foam::MeshedSurface::swapPoints
void swapPoints(pointField &points)
Swap the stored points.
Definition: MeshedSurface.C:1219
Foam::notNull
bool notNull(const T *ptr)
True if ptr is not a pointer (of type T) to the nullObject.
Definition: nullObject.H:195
Foam::FatalError
error FatalError
Foam::dictionary
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:121
mesh
dynamicFvMesh & mesh
Definition: createDynamicFvMesh.H:6
addToRunTimeSelectionTable.H
Macros for easy insertion into run-time selection tables.
MeshedSurfaceZones.C
surfMesh.H
Foam::fileName::ext
word ext() const
Return file name extension (part after last .)
Definition: fileNameI.H:228
Foam::MeshedSurface::readTypes
static wordHashSet readTypes()
Known readable file-types.
Definition: MeshedSurface.C:45
Foam::MeshedSurface::canReadType
static bool canReadType(const word &ext, bool verbose=false)
Can we read this file format?
Definition: MeshedSurface.C:61
Foam::mergePoints
label mergePoints(const PointList &points, const scalar mergeTol, const bool verbose, labelList &pointMap, typename PointList::const_reference origin=PointList::value_type::zero)
Sorts and merges points. All points closer than/equal mergeTol get merged.
Foam::exit
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:130
Foam::New
tmp< DimensionedField< TypeR, GeoMesh > > New(const tmp< DimensionedField< TypeR, GeoMesh >> &tdf1, const word &name, const dimensionSet &dimensions)
Global function forwards to reuseTmpDimensionedField::New.
Definition: DimensionedFieldReuseFunctions.H:105
Time.H
Foam::autoPtr
Pointer management similar to std::unique_ptr, with some additional methods and type checking.
Definition: HashPtrTable.H:53
Foam::MeshedSurface::movePoints
virtual void movePoints(const pointField &newPoints)
Move points.
Definition: MeshedSurface.C:525
FatalErrorInFunction
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:355
clear
patchWriters clear()
Foam::nl
constexpr char nl
Definition: Ostream.H:372
Foam::flatOutput
FlatOutput< Container > flatOutput(const Container &obj, label len=0)
Global flatOutput function.
Definition: FlatOutput.H:85
f
labelList f(nPoints)
Foam::UnsortedMeshedSurface::clear
virtual void clear()
Clear all storage.
Definition: UnsortedMeshedSurface.C:452
Foam::List
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition: HashTable.H:102
Foam::surfZone
A surface zone on a MeshedSurface.
Definition: surfZone.H:65
Foam::UList< Face >
points
const pointField & points
Definition: gmvOutputHeader.H:1
Foam::List::clear
void clear()
Clear the list, i.e. set size to zero.
Definition: ListI.H:115
polyBoundaryMesh.H
Foam::MeshedSurface::MeshedSurface
MeshedSurface()
Construct null, an empty surface.
Definition: MeshedSurface.C:165
Foam::vtk::write
void write(vtk::formatter &fmt, const Type &val, const label n=1)
Component-wise write of a value (N times)
Definition: foamVtkOutputTemplates.C:35
mergePoints.H
Merge points. See below.
Foam::wordHashSet
HashSet< word > wordHashSet
A HashSet with word keys.
Definition: HashSet.H:412
Foam::MeshedSurface::writeTypes
static wordHashSet writeTypes()
Known writable file-types.
Definition: MeshedSurface.C:51
Foam::UList::size
void size(const label n) noexcept
Override size to be inconsistent with allocated storage.
Definition: UListI.H:360
Foam::face
A face is a list of labels corresponding to mesh vertices.
Definition: face.H:74
MeshedSurfaceNew.C
ListOps.H
Various functions to operate on Lists.
Foam::HashTable::found
bool found(const Key &key) const
Return true if hashed entry is found in table.
Definition: HashTableI.H:100
Foam::MeshedSurface::swapFaces
void swapFaces(List< Face > &faces)
Swap the stored faces.
Definition: MeshedSurface.C:1210
Foam::List::setSize
void setSize(const label newSize)
Alias for resize(const label)
Definition: ListI.H:146
Foam::MeshedSurface
A surface geometry mesh with zone information, not to be confused with the similarly named surfaceMes...
Definition: triSurfaceTools.H:80
faceTraits.H
primitivePatch.H
WarningInFunction
#define WarningInFunction
Report a warning using Foam::Warning.
Definition: messageStream.H:294
Foam::UnsortedMeshedSurface::sortedZones
surfZoneList sortedZones(labelList &faceMap) const
Sort faces according to zoneIds.
Definition: UnsortedMeshedSurface.C:462
Foam::MeshedSurface::releaseGeom
autoPtr< MeshedSurface< Face > > releaseGeom()
Release (clear) geometry and return for reuse.
Definition: MeshedSurface.C:1203
Foam::MeshedSurface::cleanup
virtual void cleanup(const bool verbose)
Remove invalid faces.
Definition: MeshedSurface.C:557
MeshedSurface.H
Foam::PrimitivePatch
A list of faces which address into the list of points.
Definition: PrimitivePatch.H:90