triSurfaceIO.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) 2017-2020 OpenCFD Ltd.
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 "triSurface.H"
29#include "Fstream.H"
30#include "Time.H"
31#include "boundBox.H"
32#include "bitSet.H"
33#include "surfZoneList.H"
34#include "surfaceFormatsCore.H"
35#include "MeshedSurfaceProxy.H"
36#include "MeshedSurface.H"
37
38// * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
39
41{
42 wordHashSet known
43 (
46 );
47
48 // Additional hard-coded entry points, but do not need
49 // {"stl", "stlb"}
50 // since they are shadowed by *MeshedSurface
51
52 known.insert("ftr");
53
54 return known;
55}
56
57
59{
60 wordHashSet known
61 (
63 );
64
65 // Additional hard-coded entry points, but do not need
66 // {"gts", "stl", "stlb"}
67 // since they are shadowed by MeshedSurfaceProxy
68
69 known.insert("ftr");
70
71 return known;
72}
73
74
75bool Foam::triSurface::canReadType(const word& fileType, bool verbose)
76{
78 (
79 readTypes(),
80 fileType,
81 verbose,
82 "reading"
83 );
84}
85
86
87bool Foam::triSurface::canWriteType(const word& fileType, bool verbose)
88{
90 (
91 writeTypes(),
92 fileType,
93 verbose,
94 "writing"
95 );
96}
97
98
99bool Foam::triSurface::canRead(const fileName& name, bool verbose)
100{
101 word ext(name.ext());
102 if (ext == "gz")
103 {
104 ext = name.lessExt().ext();
105 }
106 return canReadType(ext, verbose);
107}
108
109
111(
112 const IOobject& io,
113 const fileName& f,
114 const bool isGlobal
115)
116{
118}
119
120
122(
123 const IOobject& io,
124 const bool isGlobal
125)
126{
128}
129
130
132(
133 const IOobject& io,
134 const dictionary& dict,
135 const bool isGlobal
136)
137{
139}
140
141
143(
144 const IOobject& io,
145 const bool isGlobal
146)
147{
149}
150
151
153(
154 const IOobject& io,
155 const dictionary& dict,
156 const bool isGlobal
157)
158{
160}
161
162
163// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
164
165bool Foam::triSurface::readNative(Istream& is)
166{
167 // Read triangles, points from Istream
168 is >> patches_ >> storedPoints() >> storedFaces();
169
170 return true;
171}
172
173
174void Foam::triSurface::writeNative(Ostream& os) const
175{
176 os << patches() << nl;
177
178 //Note: Write with global point numbering
179 os << points() << nl
180 << static_cast<const List<labelledTri>&>(*this) << nl;
181
183}
184
185
187(
188 const fileName& name,
189 const word& fileType,
190 const bool check
191)
192{
193 if (check && !exists(name))
194 {
196 << "No such file " << name << nl
197 << exit(FatalError);
198 }
199
200 this->clear();
201 transfer(*New(name, fileType));
202 return true;
203}
204
205
207(
208 const fileName& name,
209 const word& fileType,
210 const bool sortByRegion
211) const
212{
213 if (fileType.empty())
214 {
215 // Handle empty/missing type
216
217 const word ext(name.ext());
218
219 if (ext.empty())
220 {
222 << "Cannot determine format from filename" << nl
223 << " " << name << nl
224 << exit(FatalError);
225 }
226
227 write(name, ext, sortByRegion);
228 return;
229 }
230
231
232 // Hard-coded writers
233
234 if (fileType == "ftr")
235 {
237 writeNative(os);
238 }
239 else if (fileType == "stl")
240 {
241 writeSTLASCII(name, sortByRegion);
242 }
243 else if (fileType == "stlb")
244 {
245 writeSTLBINARY(name);
246 }
247 else if (fileType == "gts")
248 {
249 writeGTS(name, sortByRegion);
250 }
252 {
254 List<surfZone> zoneLst = this->sortedZones(faceMap);
255
257 (
258 this->points(),
259 this->surfFaces(),
260 zoneLst,
261 faceMap
262 );
263
264 proxy.write(name, fileType);
265 }
266 else
267 {
269 << "Unknown surface format " << fileType
270 << " for writing file " << name << nl
271 << "Valid types:" << nl
272 << " " << flatOutput(writeTypes().sortedToc()) << nl
273 << exit(FatalError);
274 }
275}
276
277
278// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
279
281:
282 triSurface()
283{
284 readNative(is);
285
286 setDefaultPatches();
287}
288
289
291:
292 triSurface()
293{
294 IFstream is
295 (
296 d.path()/triSurfInstance(d)/typeName/(d.caseName() + ".ftr")
297 );
298
299 readNative(is);
300
301 setDefaultPatches();
302}
303
304
306(
307 const IOobject& io,
308 const dictionary& dict,
309 const bool isGlobal
310)
311:
312 triSurface()
313{
314 fileName fName(checkFile(io, dict, isGlobal));
315
316 read(fName, dict.getOrDefault<word>("fileType", word::null));
317
318 scalePoints(dict.getOrDefault<scalar>("scale", 0));
319
320 setDefaultPatches();
321}
322
323
324// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
325
327(
328 const fileName& name,
329 const bool sortByRegion
330) const
331{
332 write(name, name.ext(), sortByRegion);
333}
334
335
337{
338 writeNative(os);
339}
340
341
342void Foam::triSurface::write(const Time& d) const
343{
345 (
346 d.path()/triSurfInstance(d)/typeName/(d.caseName() + ".ftr")
347 );
348
349 writeNative(os);
350}
351
352
354{
355 // Unfortunately nPoints constructs meshPoints() so do compact version
356 // ourselves.
357
358 bitSet pointIsUsed(points().size());
359
361 labelHashSet regionsUsed;
362
363 for (const auto& f : *this)
364 {
365 regionsUsed.insert(f.region());
366
367 for (const label pointi : f)
368 {
369 if (pointIsUsed.set(pointi))
370 {
371 bb.add(points()[pointi]);
372 }
373 }
374 }
375
376 os << "Triangles : " << size()
377 << " in " << regionsUsed.size() << " region(s)" << nl
378 << "Vertices : " << pointIsUsed.count() << nl
379 << "Bounding Box : " << bb << endl;
380}
381
382
383// * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * //
384
386{
387 s.clearOut();
388 s.readNative(is);
389 s.setDefaultPatches();
390 return is;
391}
392
393
395{
396 s.writeNative(os);
397 return os;
398}
399
400
401// ************************************************************************* //
bool insert(const Key &key)
Insert a new entry, not overwriting existing entries.
Definition: HashSet.H:191
label size() const noexcept
The number of elements in table.
Definition: HashTableI.H:52
Input from file stream, using an ISstream.
Definition: IFstream.H:57
Defines the attributes of an object for which implicit objectRegistry management is supported,...
Definition: IOobject.H:170
virtual bool check(const char *operation) const
Check IOstream status for given operation.
Definition: IOstream.C:58
An Istream is an abstract base class for all input systems (streams, files, token lists etc)....
Definition: Istream.H:64
A proxy for writing MeshedSurface, UnsortedMeshedSurface and surfMesh to various file formats.
static void write(const fileName &name, const MeshedSurfaceProxy &surf, IOstreamOption streamOpt=IOstreamOption(), const dictionary &options=dictionary::null)
Write to file, select based on its extension.
A surface geometry mesh with zone information, not to be confused with the similarly named surfaceMes...
Definition: MeshedSurface.H:99
Output to file stream, using an OSstream.
Definition: OFstream.H:57
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition: Ostream.H:62
virtual bool read()
Re-read model coefficients if they have changed.
Class to control time during OpenFOAM simulations that is also the top-level objectRegistry.
Definition: Time.H:80
const fileName & caseName() const
Return case name.
Definition: TimePathsI.H:62
fileName path() const
Return path.
Definition: Time.H:358
A surface geometry mesh, in which the surface zone information is conveyed by the 'zoneId' associated...
A bitSet stores bits (elements with only two states) in packed internal format and supports a variety...
Definition: bitSet.H:66
unsigned int count(const bool on=true) const
Count number of bits set.
Definition: bitSetI.H:500
void set(const bitSet &bitset)
Set specified bits from another bitset.
Definition: bitSetI.H:590
A bounding box defined in terms of min/max extrema points.
Definition: boundBox.H:64
static const boundBox invertedBox
A large inverted boundBox: min/max == +/- ROOTVGREAT.
Definition: boundBox.H:86
void add(const boundBox &bb)
Extend to include the second box.
Definition: boundBoxI.H:191
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:126
T getOrDefault(const word &keyword, const T &deflt, enum keyType::option matchOpt=keyType::REGEX) const
bool checkSupport() const
Check if the patch is fully supported.
static fileName checkFile(const IOobject &io, const bool isGlobal=true)
Return fileName to load IOobject from.
static fileName findFile(const IOobject &io, const bool isGlobal=true)
static fileName relativeFilePath(const IOobject &io, const fileName &f, const bool isGlobal=true)
Return fileName.
A class for handling file names.
Definition: fileName.H:76
virtual bool write()
Write the output fields.
Triangulated surface description with patch information.
Definition: triSurface.H:79
static fileName triSurfInstance(const Time &)
Name of triSurface directory to use.
Definition: triSurface.C:73
static fileName checkFile(const IOobject &io, const bool isGlobal=true)
Return fileName to load IOobject from.
Definition: triSurfaceIO.C:122
triSurface()
Default construct.
Definition: triSurface.C:432
static bool canWriteType(const word &fileType, bool verbose=false)
Can we write this file format?
Definition: triSurfaceIO.C:87
static wordHashSet writeTypes()
Known writable file-types, including via friends or proxies.
Definition: triSurfaceIO.C:58
static fileName findFile(const IOobject &io, const bool isGlobal=true)
Definition: triSurfaceIO.C:143
static bool canReadType(const word &fileType, bool verbose=false)
Can we read this file format?
Definition: triSurfaceIO.C:75
static bool canRead(const fileName &name, bool verbose=false)
Can we read this file format?
Definition: triSurfaceIO.C:99
static fileName relativeFilePath(const IOobject &io, const fileName &f, const bool isGlobal=true)
Return fileName.
Definition: triSurfaceIO.C:111
void writeStats(Ostream &os) const
Write some statistics.
Definition: triSurfaceIO.C:353
virtual void scalePoints(const scalar scaleFactor)
Scale points. A non-positive factor is ignored.
Definition: triSurface.C:638
static wordHashSet readTypes()
Known readable file-types, including via friends or proxies.
Definition: triSurfaceIO.C:40
A class for handling words, derived from Foam::string.
Definition: word.H:68
word ext() const
Return file name extension (part after last .)
Definition: word.C:126
word lessExt() const
Return word without extension (part before last .)
Definition: word.C:113
const polyBoundaryMesh & patches
patchWriters clear()
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:453
OBJstream os(runTime.globalPath()/outputName)
const pointField & points
gmvFile<< "tracers "<< particles.size()<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().x()<< " ";}gmvFile<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().y()<< " ";}gmvFile<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().z()<< " ";}gmvFile<< nl;forAll(lagrangianScalarNames, i){ word name=lagrangianScalarNames[i];IOField< scalar > s(IOobject(name, runTime.timeName(), cloud::prefix, mesh, IOobject::MUST_READ, IOobject::NO_WRITE))
IOobject io("surfaceFilmProperties", mesh.time().constant(), mesh, IOobject::READ_IF_PRESENT, IOobject::NO_WRITE, false)
#define FUNCTION_NAME
Pair< int > faceMap(const label facePi, const face &faceP, const label faceNi, const face &faceN)
bool exists(const fileName &name, const bool checkGzip=true, const bool followLink=true)
Does the name exist (as DIRECTORY or FILE) in the file system?
Definition: MSwindows.C:633
static void check(const int retVal, const char *what)
Ostream & operator<<(Ostream &, const boundaryPatch &p)
Write boundaryPatch as dictionary entries (without surrounding braces)
Definition: boundaryPatch.C:83
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:372
Istream & operator>>(Istream &, directionInfo &)
FlatOutput::OutputAdaptor< Container, Delimiters > flatOutput(const Container &obj, Delimiters delim)
Global flatOutput() function with specified output delimiters.
Definition: FlatOutput.H:215
tmp< DimensionedField< TypeR, GeoMesh > > New(const tmp< DimensionedField< TypeR, GeoMesh > > &tdf1, const word &name, const dimensionSet &dimensions)
Global function forwards to reuseTmpDimensionedField::New.
error FatalError
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for INVALID.
Definition: exprTraits.C:59
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:130
constexpr char nl
The newline '\n' character (0x0a)
Definition: Ostream.H:53
runTime write()
labelList f(nPoints)
dictionary dict