VTKsurfaceFormat.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 | Copyright (C) 2011-2012 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 "VTKsurfaceFormat.H"
27 #include "vtkUnstructuredReader.H"
28 #include "scalarIOField.H"
29 
30 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
31 
32 template<class Face>
34 (
35  Ostream& os,
36  const UList<Face>& faceLst
37 )
38 {
39  label nNodes = 0;
40 
41  forAll(faceLst, faceI)
42  {
43  nNodes += faceLst[faceI].size();
44  }
45 
46  os << nl
47  << "POLYGONS " << faceLst.size() << ' '
48  << faceLst.size() + nNodes << nl;
49 }
50 
51 
52 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
53 
54 template<class Face>
56 (
57  const fileName& filename
58 )
59 {
60  read(filename);
61 }
62 
63 
64 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
65 
66 template<class Face>
68 (
69  const fileName& filename
70 )
71 {
72  const bool mustTriangulate = this->isTri();
73  this->clear();
74 
75  IFstream is(filename);
76  if (!is.good())
77  {
79  (
80  "fileFormats::VTKsurfaceFormat::read(const fileName&)"
81  ) << "Cannot read file " << filename
82  << exit(FatalError);
83  }
84 
85  // assume that the groups are not intermixed
86  bool sorted = true;
87 
88 
89  // Construct dummy time so we have something to create an objectRegistry
90  // from
91  Time dummyTime
92  (
93  "dummyRoot",
94  "dummyCase",
95  "system",
96  "constant",
97  false // enableFunctionObjects
98  );
99 
100  // Make dummy object registry
101  objectRegistry obr
102  (
103  IOobject
104  (
105  "dummy",
106  dummyTime,
107  IOobject::NO_READ,
108  IOobject::NO_WRITE,
109  false
110  )
111  );
112 
113  // Read all
114  vtkUnstructuredReader reader(obr, is);
115  const faceList& faces = reader.faces();
116 
117  // Assume all faces in zone0 unless a region field is present
118  labelList zones(faces.size(), 0);
119  if (reader.cellData().foundObject<scalarIOField>("region"))
120  {
121  const scalarIOField& region =
123  (
124  "region"
125  );
126  forAll(region, i)
127  {
128  zones[i] = label(region[i]);
129  }
130  }
131  else if (reader.cellData().foundObject<scalarIOField>("STLSolidLabeling"))
132  {
133  const scalarIOField& region =
135  (
136  "STLSolidLabeling"
137  );
138  forAll(region, i)
139  {
140  zones[i] = label(region[i]);
141  }
142  }
143 
144  // Create zone names
145  const label nZones = max(zones)+1;
146  wordList zoneNames(nZones);
147  forAll(zoneNames, i)
148  {
149  zoneNames[i] = "zone" + Foam::name(i);
150  }
151 
152 
153  // See if needs triangulation
154  label nTri = 0;
155  if (mustTriangulate)
156  {
157  forAll(faces, faceI)
158  {
159  nTri += faces[faceI].size()-2;
160  }
161  }
162 
163  if (nTri > 0)
164  {
165  DynamicList<Face> dynFaces(nTri);
166  DynamicList<label> dynZones(nTri);
167  forAll(faces, faceI)
168  {
169  const face& f = faces[faceI];
170  for (label fp1 = 1; fp1 < f.size() - 1; fp1++)
171  {
172  label fp2 = f.fcIndex(fp1);
173 
174  dynFaces.append(triFace(f[0], f[fp1], f[fp2]));
175  dynZones.append(zones[faceI]);
176  }
177  }
178 
179  // Count
180  labelList zoneSizes(nZones, 0);
181  forAll(dynZones, triI)
182  {
183  zoneSizes[dynZones[triI]]++;
184  }
185 
186  this->sortFacesAndStore(dynFaces.xfer(), dynZones.xfer(), sorted);
187 
188  // add zones, culling empty ones
189  this->addZones(zoneSizes, zoneNames, true);
190  }
191  else
192  {
193  DynamicList<Face> dynFaces(faces.size());
194  forAll(faces, faceI)
195  {
196  const face& f = faces[faceI];
197  dynFaces.append(Face(f));
198  }
199 
200  // Count
201  labelList zoneSizes(nZones, 0);
202  forAll(zones, faceI)
203  {
204  zoneSizes[zones[faceI]]++;
205  }
206 
207  this->sortFacesAndStore(dynFaces.xfer(), zones.xfer(), sorted);
208 
209  // add zones, culling empty ones
210  this->addZones(zoneSizes, zoneNames, true);
211  }
212 
213  // transfer to normal lists
214  this->storedPoints().transfer(reader.points());
215 
216  return true;
217 }
218 
219 
220 template<class Face>
222 (
223  const fileName& filename,
224  const MeshedSurfaceProxy<Face>& surf
225 )
226 {
227  const pointField& pointLst = surf.points();
228  const List<Face>& faceLst = surf.faces();
229  const List<label>& faceMap = surf.faceMap();
230 
231  const List<surfZone>& zones =
232  (
233  surf.surfZones().empty()
234  ? surfaceFormatsCore::oneZone(faceLst)
235  : surf.surfZones()
236  );
237 
238  const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1);
239 
240  OFstream os(filename);
241  if (!os.good())
242  {
244  (
245  "fileFormats::VTKsurfaceFormat::write"
246  "(const fileName&, const MeshedSurfaceProxy<Face>&)"
247  )
248  << "Cannot open file for writing " << filename
249  << exit(FatalError);
250  }
251 
252 
253  writeHeader(os, pointLst);
254  writeHeaderPolygons(os, faceLst);
255 
256  label faceIndex = 0;
257  forAll(zones, zoneI)
258  {
259  const surfZone& zone = zones[zoneI];
260 
261  if (useFaceMap)
262  {
263  forAll(zone, localFaceI)
264  {
265  const Face& f = faceLst[faceMap[faceIndex++]];
266 
267  os << f.size();
268  forAll(f, fp)
269  {
270  os << ' ' << f[fp];
271  }
272  os << ' ' << nl;
273  }
274  }
275  else
276  {
277  forAll(zone, localFaceI)
278  {
279  const Face& f = faceLst[faceIndex++];
280 
281  os << f.size();
282  forAll(f, fp)
283  {
284  os << ' ' << f[fp];
285  }
286  os << ' ' << nl;
287  }
288  }
289  }
290 
291  writeTail(os, zones);
292 }
293 
294 
295 template<class Face>
297 (
298  const fileName& filename,
299  const UnsortedMeshedSurface<Face>& surf
300 )
301 {
302  OFstream os(filename);
303  if (!os.good())
304  {
306  (
307  "fileFormats::VTKsurfaceFormat::write"
308  "(const fileName&, const UnsortedMeshedSurface<Face>&)"
309  )
310  << "Cannot open file for writing " << filename
311  << exit(FatalError);
312  }
313 
314 
315  const List<Face>& faceLst = surf.faces();
316 
317  writeHeader(os, surf.points());
318  writeHeaderPolygons(os, faceLst);
319 
320  forAll(faceLst, faceI)
321  {
322  const Face& f = faceLst[faceI];
323 
324  os << f.size();
325  forAll(f, fp)
326  {
327  os << ' ' << f[fp];
328  }
329  os << ' ' << nl;
330  }
331 
332  writeTail(os, surf.zoneIds());
333 }
334 
335 
336 // ************************************************************************* //
Output to file stream.
Definition: OFstream.H:81
Pair< int > faceMap(const label facePi, const face &faceP, const label faceNi, const face &faceN)
bool useFaceMap() const
Use faceMap?
word name(const complex &)
Return a string representation of a complex.
Definition: complex.C:47
labelList f(nPoints)
bool foundObject(const word &name) const
Is the named Type found?
A proxy for writing MeshedSurface, UnsortedMeshedSurface and surfMesh to various file formats...
Definition: MeshedSurface.H:73
const List< label > & zoneIds() const
Return const access to the zone ids.
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
void size(const label)
Override size to be inconsistent with allocated storage.
Definition: ListI.H:76
DynamicList< T, SizeInc, SizeMult, SizeDiv > & append(const T &)
Append an element at the end of the list.
Definition: DynamicListI.H:310
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:124
label fcIndex(const label i) const
Return the forward circular index, i.e. the next index.
Definition: UListI.H:58
face triFace(3)
const faceList & faces() const
2D cells (=faces)
const pointField & points() const
Return const access to the points.
Input from file stream.
Definition: IFstream.H:81
const List< Face > & faces() const
Return const access to the faces.
A face is a list of labels corresponding to mesh vertices.
Definition: face.H:75
Class to control time during OpenFOAM simulations that is also the top-level objectRegistry.
Definition: Time.H:68
static const char nl
Definition: Ostream.H:260
const List< Face > & faces() const
Return const access to the faces.
IOobject defines the attributes of an object for which implicit objectRegistry management is supporte...
Definition: IOobject.H:91
Base class for zones.
Definition: zone.H:57
const List< surfZone > & surfZones() const
Const access to the surface zones.
static void write(const fileName &, const MeshedSurfaceProxy< Face > &)
Write surface mesh components by proxy.
Xfer< List< T > > xfer()
Transfer contents to the Xfer container as a plain List.
Definition: DynamicListI.H:301
dimensioned< Type > max(const dimensioned< Type > &, const dimensioned< Type > &)
#define forAll(list, i)
Definition: UList.H:421
bool good() const
Return true if next operation might succeed.
Definition: IOstream.H:333
const Type & lookupObject(const word &name) const
Lookup and return the object of the given Type.
Reader for vtk unstructured_grid legacy files. Supports single CELLS, POINTS etc. entry only...
A surface zone on a MeshedSurface.
Definition: surfZone.H:62
#define FatalErrorIn(functionName)
Report an error message using Foam::FatalError.
Definition: error.H:314
A surface geometry mesh, in which the surface zone information is conveyed by the &#39;zoneId&#39; associated...
Definition: MeshedSurface.H:74
A 1D vector of objects of type <T> that resizes itself as necessary to accept the new objects...
Definition: DynamicList.H:56
Provide a means of reading/writing VTK legacy format. The output is never sorted by zone...
error FatalError
Registry of regIOobjects.
A class for handling file names.
Definition: fileName.H:69
const List< label > & faceMap() const
Const access to the faceMap, zero-sized when unused.
bool read(const char *, int32_t &)
Definition: int32IO.C:87
void append(const T &)
Append an element at the end of the list.
Definition: ListI.H:97
const pointField & points() const
Points.
UEqn clear()
virtual bool read(const fileName &)
Read from file.
const Field< point > & points() const
Return reference to global points.
const objectRegistry & cellData() const
Cell based fields.
A primitive field of type <T> with automated input and output.
Definition: IOField.H:50