vtkCoordSetWriter.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) 2022 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 "vtkCoordSetWriter.H"
29 #include "coordSet.H"
30 #include "fileName.H"
31 #include "foamVtkCoordSetWriter.H"
32 #include "coordSetWriterMethods.H"
34 
35 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
36 
37 namespace Foam
38 {
39 namespace coordSetWriters
40 {
41  defineTypeName(vtkWriter);
42  addToRunTimeSelectionTable(coordSetWriter, vtkWriter, word);
44 }
45 }
46 
47 
48 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
49 
51 :
53  fmtType_(static_cast<unsigned>(vtk::formatType::INLINE_BASE64)),
54  precision_(IOstream::defaultPrecision()),
55  writer_(nullptr)
56 {}
57 
58 
60 (
61  const vtk::outputOptions& opts
62 )
63 :
65  fmtType_(static_cast<unsigned>(opts.fmt())),
66  precision_(opts.precision()),
67  writer_(nullptr)
68 {}
69 
70 
72 :
73  coordSetWriter(options),
74  fmtType_(static_cast<unsigned>(vtk::formatType::INLINE_BASE64)),
75  precision_
76  (
77  options.getOrDefault("precision", IOstream::defaultPrecision())
78  ),
79  writer_(nullptr)
80 {
81  // format: ascii | binary
82  // legacy: true | false
83 
85  opts.ascii
86  (
89  );
90 
91  opts.legacy(options.getOrDefault("legacy", false));
92 
93  // Convert back to raw data type
94  fmtType_ = static_cast<unsigned>(opts.fmt());
95 }
96 
97 
99 (
100  const coordSet& coords,
101  const fileName& outputPath,
102  const dictionary& options
103 )
104 :
105  vtkWriter(options)
106 {
107  open(coords, outputPath);
108 }
109 
110 
112 (
113  const UPtrList<coordSet>& tracks,
114  const fileName& outputPath,
115  const dictionary& options
116 )
117 :
118  vtkWriter(options)
119 {
120  open(tracks, outputPath);
121 }
122 
123 
124 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
125 
127 {
128  close();
129 }
130 
131 
132 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
133 
135 {
136  // 1) rootdir/<TIME>/setName.{vtk|vtp}
137  // 2) rootdir/setName.{vtk|vtp}
138 
139  // From raw unsigned value to vtk::outputOptions
140  vtk::outputOptions opts(static_cast<vtk::formatType>(fmtType_));
141 
142  return getExpectedPath(vtk::polyWriter::ext(opts));
143 }
144 
145 
147 {
148  writer_.clear();
149  coordSetWriter::close(force);
150 }
151 
152 
154 {
155  writer_.clear();
157 }
158 
159 
161 {
162  writer_.clear();
164 }
165 
166 
168 {
169  writer_.clear();
171 }
172 
173 
175 {
176  checkOpen();
177  if (needsUpdate())
178  {
179  writer_.clear();
180  }
181  merge();
182 
183  if (coords_.empty())
184  {
185  return fileName::null;
186  }
187 
188  // From raw unsigned values to vtk::outputOptions
189  vtk::outputOptions opts(static_cast<vtk::formatType>(fmtType_), precision_);
190 
191 
192  // Geometry: rootdir/<TIME>/setName.{vtk|vtp}
193 
194  fileName outputFile = getExpectedPath(vtk::polyWriter::ext(opts));
195 
196  if (verbose_)
197  {
198  Info<< "Writing geometry to " << outputFile << endl;
199  }
200 
201  if (!writer_ && true) // always (non-parallel)
202  {
203  UPtrList<const pointField> points(coords_.size());
204  forAll(coords_, tracki)
205  {
206  points.set(tracki, coords_.get(tracki));
207  }
208 
209  writer_.reset
210  (
211  new vtk::coordSetWriter
212  (
213  points,
214  opts,
215  outputFile,
216  false // serial!
217  )
218  );
219 
220  if (useTracks_ || coords_.size() > 1)
221  {
222  writer_->setElementType(vtk::coordSetWriter::LINE_ELEMENTS);
223  }
224 
225  if (this->hasTime())
226  {
227  // Time name in title
228  writer_->setTime(currTime_);
229  writer_->writeTimeValue();
230  }
231  else
232  {
233  // Set name in title
234  writer_->beginFile(outputPath_.stem());
235  }
236 
237  writer_->writeGeometry();
238  }
239 
240  wroteGeom_ = true;
241  return outputFile;
242 }
243 
244 
245 // * * * * * * * * * * * * * * * Implementation * * * * * * * * * * * * * * * //
246 
247 template<class Type>
248 Foam::fileName Foam::coordSetWriters::vtkWriter::writeTemplate
249 (
250  const word& fieldName,
251  const UPtrList<const Field<Type>>& fieldPtrs
252 )
253 {
254  if (coords_.size() != fieldPtrs.size())
255  {
257  << "Attempted to write field: " << fieldName
258  << " (" << fieldPtrs.size() << " entries) for "
259  << coords_.size() << " sets" << nl
260  << exit(FatalError);
261  }
262 
263  // Open file, writing geometry (if required)
264  fileName outputFile = this->write();
265 
266  if (!nFields_ && writer_->legacy())
267  {
268  // Emit error message, but attempt to recover anyhow
269  nFields_ = 1;
270 
272  << "Using VTK legacy format, but did not define nFields!"
273  << nl
274  << "Assuming nFields=1 (may be incorrect) and continuing..."
275  << nl
276  << " Field " << fieldName << " to " << outputFile << nl;
277 
278  Info<< FatalError;
279  Info<< endl;
280  }
281 
282  writer_->beginPointData(nFields_);
283 
284  writer_->writePointData(fieldName, fieldPtrs);
285 
286  wroteGeom_ = true;
287  return outputFile;
288 }
289 
290 
291 template<class Type>
292 Foam::fileName Foam::coordSetWriters::vtkWriter::writeTemplate
293 (
294  const word& fieldName,
295  const Field<Type>& values
296 )
297 {
298  checkOpen();
299  if (coords_.empty())
300  {
301  return fileName::null;
302  }
303 
304  UPtrList<const Field<Type>> fieldPtrs(repackageFields(values));
305  return writeTemplate(fieldName, fieldPtrs);
306 }
307 
308 
309 template<class Type>
310 Foam::fileName Foam::coordSetWriters::vtkWriter::writeTemplate
311 (
312  const word& fieldName,
313  const List<Field<Type>>& fieldValues
314 )
315 {
316  checkOpen();
317  if (coords_.empty())
318  {
319  return fileName::null;
320  }
321  useTracks_ = true; // Extra safety
322 
323  UPtrList<const Field<Type>> fieldPtrs(repackageFields(fieldValues));
324  return writeTemplate(fieldName, fieldPtrs);
325 }
326 
327 
328 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
329 
330 // Field writing methods
332 
333 
334 // ************************************************************************* //
addToRunTimeSelectionTable(coordSetWriter, abaqusWriter, word)
A class for handling file names.
Definition: fileName.H:72
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:125
error FatalError
Error stream (stdout output on all processes), with additional &#39;FOAM FATAL ERROR&#39; header text and sta...
A list of keyword definitions, which are a keyword followed by a number of values (eg...
Definition: dictionary.H:129
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:598
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition: BitOps.H:56
virtual void close(bool force=false)
Close and reset, clears backend.
virtual ~vtkWriter()
Destructor. Calls close()
constexpr char nl
The newline &#39;\n&#39; character (0x0a)
Definition: Ostream.H:50
"ascii" (normal default)
static const fileName null
An empty fileName.
Definition: fileName.H:111
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:531
defineTypeName(abaqusWriter)
Class to control time during OpenFOAM simulations that is also the top-level objectRegistry.
Definition: Time.H:69
virtual fileName path() const
Expected (characteristic) output file name - information only.
Macros for easy insertion into run-time selection tables.
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:421
Encapsulated combinations of output format options. This is primarily useful when defining the output...
List< T > values(const HashTable< T, Key, Hash > &tbl, const bool doSort=false)
List of values from HashTable, optionally sorted.
Definition: HashOps.H:164
virtual void beginTime(const Time &t)
Begin a time-step.
virtual fileName write()
Write geometry to file.
void write(vtk::formatter &fmt, const Type &val, const label n=1)
Component-wise write of a value (N times)
Convenience macros for instantiating coordSetWriter methods.
defineCoordSetWriterWriteFields(Foam::coordSetWriters::vtkWriter)
Holds list of sampling positions.
Definition: coordSet.H:49
const pointField & points
Generic templated field type.
Definition: Field.H:62
word ext() const
File extension for current format type.
A class for handling words, derived from Foam::string.
Definition: word.H:63
formatType
The output format type for file contents.
Definition: foamVtkCore.H:66
Base class for writing coordSet(s) and tracks with fields.
bool ascii() const noexcept
True if output format is ASCII.
A list of pointers to objects of type <T>, without allocation/deallocation management of the pointers...
Definition: HashTable.H:106
vtk::formatType fmt() const noexcept
The output format type.
virtual void endTime()
End a time-step.
virtual void beginTime(const Time &t)
Begin time step. Clears existing backend.
An instant of time. Contains the time value and name. Uses Foam::Time when formatting the name...
Definition: instant.H:53
An IOstream is an abstract base class for all input/output systems; be they streams, files, token lists etc.
Definition: IOstream.H:82
static streamFormat formatEnum(const word &fmtName, const streamFormat deflt=streamFormat::ASCII)
Lookup streamFormat enum corresponding to the string (ascii | binary).
virtual void endTime()
End time step. Clears existing backend.
bool legacy() const noexcept
True if writer uses legacy file format.
messageStream Info
Information stream (stdout output on master, null elsewhere)
XML inline base64, base64Formatter.
T getOrDefault(const word &keyword, const T &deflt, enum keyType::option matchOpt=keyType::REGEX) const
Find and return a T, or return the given default value. FatalIOError if it is found and the number of...
virtual void close(bool force=false)
Finish output, performing any necessary cleanup.
Namespace for OpenFOAM.