starcdSurfaceWriter.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 OpenFOAM Foundation
9  Copyright (C) 2015-2022 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 "starcdSurfaceWriter.H"
30 #include "ListOps.H"
31 #include "OFstream.H"
32 #include "OSspecific.H"
33 #include "MeshedSurfaceProxy.H"
34 #include "surfaceWriterMethods.H"
36 
37 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
38 
39 namespace Foam
40 {
41 namespace surfaceWriters
42 {
43  defineTypeName(starcdWriter);
44  addToRunTimeSelectionTable(surfaceWriter, starcdWriter, word);
45  addToRunTimeSelectionTable(surfaceWriter, starcdWriter, wordDict);
46 }
47 }
48 
49 // * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
50 
51 namespace Foam
52 {
53  // Emit each component
54  template<class Type>
55  static inline void writeData(Ostream& os, const Type& val)
56  {
57  for (direction cmpt=0; cmpt < pTraits<Type>::nComponents; ++cmpt)
58  {
59  os << ' ' << component(val, cmpt);
60  }
61  os << nl;
62  }
63 
64 } // End namespace Foam
65 
66 
67 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
68 
70 :
71  surfaceWriter(),
72  streamOpt_()
73 {}
74 
75 
77 (
78  const dictionary& options
79 )
80 :
81  surfaceWriter(options),
82  streamOpt_
83  (
85  IOstreamOption::compressionEnum("compression", options)
86  )
87 {}
88 
89 
91 (
92  const meshedSurf& surf,
93  const fileName& outputPath,
94  bool parallel,
95  const dictionary& options
96 )
97 :
98  starcdWriter(options)
99 {
100  open(surf, outputPath, parallel);
101 }
102 
103 
105 (
106  const pointField& points,
107  const faceList& faces,
108  const fileName& outputPath,
109  bool parallel,
110  const dictionary& options
111 )
112 :
113  starcdWriter(options)
114 {
115  open(points, faces, outputPath, parallel);
116 }
117 
118 
119 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
120 
122 {
123  checkOpen();
124 
125  // Geometry: rootdir/<TIME>/surfaceName.{inp,cel,vrt}
126 
127  fileName outputFile = outputPath_;
128  if (useTimeDir() && !timeName().empty())
129  {
130  // Splice in time-directory
131  outputFile = outputPath_.path() / timeName() / outputPath_.name();
132  }
133  outputFile.ext("inp");
134 
135  if (verbose_)
136  {
137  Info<< "Writing geometry to " << outputFile << endl;
138  }
139 
140  // const meshedSurf& surf = surface();
141  const meshedSurfRef& surf = adjustSurface();
142 
143  if (UPstream::master() || !parallel_)
144  {
145  if (!isDir(outputFile.path()))
146  {
147  mkDir(outputFile.path());
148  }
149 
150  const labelUList& origFaceIds = surf.faceIds();
151 
152  // Face ids (if possible)
153  const labelUList& elemIds =
154  (
155  !ListOps::found(origFaceIds, lessOp1<label>(0))
156  ? origFaceIds
157  : labelUList::null()
158  );
159 
160  MeshedSurfaceProxy<face>
161  (
162  surf.points(),
163  surf.faces(),
164  UList<surfZone>::null(), // one zone
165  labelUList::null(), // no faceMap
166  elemIds // face ids
167  ).write
168  (
169  outputFile,
170  "starcd", // Canonical selection name
171  streamOpt_
172  );
173  }
174 
175  wroteGeom_ = true;
176  return outputFile;
177 }
178 
179 
180 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
181 
182 template<class Type>
183 Foam::fileName Foam::surfaceWriters::starcdWriter::writeTemplate
184 (
185  const word& fieldName,
186  const Field<Type>& localValues
187 )
188 {
189  // Separate geometry
190  if (!wroteGeom_)
191  {
192  write();
193  }
194 
195  checkOpen();
196 
197  // Field: rootdir/<TIME>/<field>_surfaceName.usr
198 
199  fileName outputFile = outputPath_.path();
200  if (useTimeDir() && !timeName().empty())
201  {
202  // Splice in time-directory
203  outputFile /= timeName();
204  }
205 
206  // Append <field>_surfaceName.usr
207  outputFile /= fieldName + '_' + outputPath_.name();
208  outputFile.ext("usr");
209 
210  // Implicit geometry merge()
211  tmp<Field<Type>> tfield = adjustField(fieldName, mergeField(localValues));
212 
213  if (verbose_)
214  {
215  Info<< " to " << outputFile << endl;
216  }
217 
218 
219  // const meshedSurf& surf = surface();
220  const meshedSurfRef& surf = adjustSurface();
221 
222  if (UPstream::master() || !parallel_)
223  {
224  const auto& values = tfield();
225 
226  if (!isDir(outputFile.path()))
227  {
228  mkDir(outputFile.path());
229  }
230 
231  OFstream os(outputFile, streamOpt_);
232 
233  const labelUList& elemIds = surf.faceIds();
234 
235  // Possible to use faceIds?
236  const bool useOrigFaceIds =
237  (
238  elemIds.size() == values.size()
239  && !ListOps::found(elemIds, lessOp1<label>(0))
240  );
241 
242  label faceIndex = 0;
243 
244  // No header, just write values
245  for (const Type& val : values)
246  {
247  const label elemId =
248  (useOrigFaceIds ? elemIds[faceIndex] : faceIndex);
249 
250  os << (elemId + 1); // 1-based ids
251  writeData(os, val);
252  ++faceIndex;
253  }
254  }
255 
256  wroteGeom_ = true;
257  return outputFile;
258 }
259 
260 
261 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
262 
263 // Field writing methods
265 
266 
267 // ************************************************************************* //
uint8_t direction
Definition: direction.H:46
A class for handling file names.
Definition: fileName.H:72
static void writeData(Ostream &os, const Type &val)
A list of keyword definitions, which are a keyword followed by a number of values (eg...
Definition: dictionary.H:129
bool found(const ListType &input, const UnaryPredicate &pred, const label start=0)
Same as found_if.
Definition: ListOps.H:826
constexpr char nl
The newline &#39;\n&#39; character (0x0a)
Definition: Ostream.H:50
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:531
A surfaceWriter for STARCD files.
::Foam::direction nComponents(const expressions::valueTypeCode) noexcept
The number of components associated with given valueTypeCode.
Definition: exprTraits.C:40
A simple container for options an IOstream can normally have.
static std::string path(const std::string &str)
Return directory path name (part before last /)
Definition: fileNameI.H:169
word ext() const
Return file name extension (part after last .)
Definition: fileNameI.H:211
Macros for easy insertion into run-time selection tables.
UList< label > labelUList
A UList of labels.
Definition: UList.H:78
Abstract definition of a meshed surface defined by faces and points.
Definition: meshedSurf.H:43
Various functions to operate on Lists.
bool isDir(const fileName &name, const bool followLink=true)
Does the name exist as a DIRECTORY in the file system?
Definition: POSIX.C:860
List< T > values(const HashTable< T, Key, Hash > &tbl, const bool doSort=false)
List of values from HashTable, optionally sorted.
Definition: HashOps.H:164
Functions used by OpenFOAM that are specific to POSIX compliant operating systems and need to be repl...
word timeName
Definition: getTimeIndex.H:3
void write(vtk::formatter &fmt, const Type &val, const label n=1)
Component-wise write of a value (N times)
bool mkDir(const fileName &pathName, mode_t mode=0777)
Make a directory and return an error if it could not be created.
Definition: POSIX.C:614
const pointField & points
A class for handling words, derived from Foam::string.
Definition: word.H:63
An Ostream is an abstract base class for all output systems (streams, files, token lists...
Definition: Ostream.H:56
OBJstream os(runTime.globalPath()/outputName)
static const UList< label > & null()
Return a UList reference to a nullObject.
Definition: UListI.H:90
virtual fileName write()
Write surface geometry to file.
Convenience macros for instantiating surfaceWriter methods.
defineTypeName(abaqusWriter)
defineSurfaceWriterWriteFields(Foam::surfaceWriters::starcdWriter)
static bool master(const label communicator=worldComm)
True if process corresponds to the master rank in the communicator.
Definition: UPstream.H:1082
messageStream Info
Information stream (stdout output on master, null elsewhere)
Base class for surface writers.
addToRunTimeSelectionTable(surfaceWriter, abaqusWriter, word)
void component(FieldField< Field, typename FieldField< Field, Type >::cmptType > &sf, const FieldField< Field, Type > &f, const direction d)
Namespace for OpenFOAM.