nastranSurfaceWriter.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) 2012-2013 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 "nastranSurfaceWriter.H"
27 #include "IOmanip.H"
28 #include "Tuple2.H"
30 
31 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
32 
33 namespace Foam
34 {
35  makeSurfaceWriterType(nastranSurfaceWriter);
36  addToRunTimeSelectionTable(surfaceWriter, nastranSurfaceWriter, wordDict);
37 
38  // create write methods
39  defineSurfaceWriterWriteFields(nastranSurfaceWriter);
40 
41  template<>
43  {
44  "short",
45  "long",
46  "free"
47  };
48 
51 }
52 
53 
54 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
55 
56 void Foam::nastranSurfaceWriter::formatOS(OFstream& os) const
57 {
59 
60  // capitalise the E marker
61  os.setf(ios_base::uppercase);
62 
63  label prec = 0;
64  label offset = 7;
65  switch (writeFormat_)
66  {
67  case (wfShort):
68  case (wfFree):
69  {
70  prec = 8 - offset;
71  break;
72  }
73  case (wfLong):
74  {
75  prec = 16 - offset;
76  break;
77  }
78  default:
79  {
80  }
81  }
82 
83  os.precision(prec);
84 }
85 
86 
87 void Foam::nastranSurfaceWriter::writeCoord
88 (
89  const point& p,
90  const label pointI,
91  OFstream& os
92 ) const
93 {
94  // Fixed short/long formats:
95  // 1 GRID
96  // 2 ID : point ID - requires starting index of 1
97  // 3 CP : co-ordinate system ID (blank)
98  // 4 X1 : point x cp-ordinate
99  // 5 X2 : point x cp-ordinate
100  // 6 X3 : point x cp-ordinate
101  // 7 CD : co-ordinate system for displacements (blank)
102  // 8 PS : single point constraints (blank)
103  // 9 SEID : super-element ID
104 
105  switch (writeFormat_)
106  {
107  case wfShort:
108  {
109  os.setf(ios_base::left);
110  os << setw(8) << "GRID";
111  os.unsetf(ios_base::left);
112  os.setf(ios_base::right);
113  os << setw(8) << pointI + 1
114  << " "
115  << setw(8) << p.x()
116  << setw(8) << p.y()
117  << setw(8) << p.z()
118  << nl;
119  os.unsetf(ios_base::right);
120 
121  break;
122  }
123  case wfLong:
124  {
125  os.setf(ios_base::left);
126  os << setw(8) << "GRID*";
127  os.unsetf(ios_base::left);
128  os.setf(ios_base::right);
129  os << setw(16) << pointI + 1
130  << " "
131  << setw(16) << p.x()
132  << setw(16) << p.y()
133  << nl;
134  os.unsetf(ios_base::right);
135  os.setf(ios_base::left);
136  os << setw(8) << "*";
137  os.unsetf(ios_base::left);
138  os.setf(ios_base::right);
139  os << setw(16) << p.z()
140  << nl;
141  os.unsetf(ios_base::right);
142 
143  break;
144  }
145  case wfFree:
146  {
147  os << "GRID"
148  << ',' << pointI + 1
149  << ','
150  << ',' << p.x()
151  << ',' << p.y()
152  << ',' << p.z()
153  << nl;
154 
155  break;
156  }
157  default:
158  {
160  (
161  "void Foam::nastranSurfaceWriter::writeCoord"
162  "("
163  "Ostream&, "
164  "const point&"
165  ") const"
166  ) << "Unknown writeFormat enumeration" << abort(FatalError);
167  }
168  }
169 }
170 
171 void Foam::nastranSurfaceWriter::writeFace
172 (
173  const word& faceType,
174  const labelList& facePts,
175  label& nFace,
176  OFstream& os
177 ) const
178 {
179  // Only valid surface elements are CTRIA3 and CQUAD4
180 
181  // Fixed short/long formats:
182  // 1 CQUAD4
183  // 2 EID : element ID
184  // 3 PID : property element ID; default = EID (blank)
185  // 4 G1 : grid point index - requires starting index of 1
186  // 5 G2 : grid point index
187  // 6 G3 : grid point index
188  // 7 G4 : grid point index
189  // 8 onwards - not used
190 
191  // For CTRIA3 elements, cols 7 onwards are not used
192 
193  switch (writeFormat_)
194  {
195  case wfShort:
196  {
197  os.setf(ios_base::left);
198  os << setw(8) << faceType;
199  os.unsetf(ios_base::left);
200  os.setf(ios_base::right);
201  os << setw(8) << nFace++
202  << " ";
203 
204  forAll(facePts, i)
205  {
206  os << setw(8) << facePts[i] + 1;
207  }
208 
209  os << nl;
210  os.unsetf(ios_base::right);
211 
212  break;
213  }
214  case wfLong:
215  {
216  os.setf(ios_base::left);
217  os << setw(8) << word(faceType + "*");
218  os.unsetf(ios_base::left);
219  os.setf(ios_base::right);
220  os << setw(16) << nFace++
221  << " ";
222 
223  forAll(facePts, i)
224  {
225  os << setw(16) << facePts[i] + 1;
226  if (i == 1)
227  {
228  os << nl;
229  os.unsetf(ios_base::right);
230  os.setf(ios_base::left);
231  os << setw(8) << "*";
232  os.unsetf(ios_base::left);
233  os.setf(ios_base::right);
234  }
235  }
236 
237  os << nl;
238  os.unsetf(ios_base::right);
239 
240  break;
241  }
242  case wfFree:
243  {
244  os << faceType << ','
245  << ++nFace << ',';
246 
247  forAll(facePts, i)
248  {
249  os << ',' << facePts[i] + 1;
250  }
251 
252  os << nl;
253 
254  break;
255  }
256  default:
257  {
259  (
260  "void Foam::nastranSurfaceWriter::writeFace"
261  "("
262  "const word&"
263  "const labelList&"
264  "label&"
265  "Ostream&, "
266  ") const"
267  ) << "Unknown writeFormat enumeration" << abort(FatalError);
268  }
269  }
270 
271 }
272 
273 
274 void Foam::nastranSurfaceWriter::writeGeometry
275 (
276  const pointField& points,
277  const faceList& faces,
278  List<DynamicList<face> >& decomposedFaces,
279  OFstream& os
280 ) const
281 {
282  // write points
283 
284  os << "$" << nl
285  << "$ Points" << nl
286  << "$" << nl;
287 
288  forAll(points, pointI)
289  {
290  writeCoord(points[pointI], pointI, os);
291  }
292 
293 
294  // write faces
295 
296  os << "$" << nl
297  << "$ Faces" << nl
298  << "$" << nl;
299 
300  label nFace = 1;
301 
302  forAll(faces, faceI)
303  {
304  const face& f = faces[faceI];
305 
306  if (f.size() == 3)
307  {
308  writeFace("CTRIA3", faces[faceI], nFace, os);
309  decomposedFaces[faceI].append(faces[faceI]);
310  }
311  else if (f.size() == 4)
312  {
313  writeFace("CQUAD4", faces[faceI], nFace, os);
314  decomposedFaces[faceI].append(faces[faceI]);
315  }
316  else
317  {
318  // decompose poly face into tris
319  label nTri = 0;
320  faceList triFaces;
321  f.triangles(points, nTri, triFaces);
322 
323  forAll(triFaces, triI)
324  {
325  writeFace("CTRIA3", triFaces[triI], nFace, os);
326  decomposedFaces[faceI].append(triFaces[triI]);
327  }
328  }
329  }
330 }
331 
332 
333 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
334 
336 :
337  surfaceWriter(),
338  writeFormat_(wfShort),
339  fieldMap_(),
340  scale_(1.0)
341 {}
342 
343 
345 :
346  surfaceWriter(),
347  writeFormat_(wfLong),
348  fieldMap_(),
349  scale_(options.lookupOrDefault("scale", 1.0))
350 {
351  if (options.found("format"))
352  {
353  writeFormat_ = writeFormatNames_.read(options.lookup("format"));
354  }
355 
356  List<Tuple2<word, word> > fieldSet(options.lookup("fields"));
357 
358  forAll(fieldSet, i)
359  {
360  fieldMap_.insert(fieldSet[i].first(), fieldSet[i].second());
361  }
362 }
363 
364 
365 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
366 
368 {}
369 
370 
371 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
372 
374 (
375  const fileName& outputDir,
376  const fileName& surfaceName,
377  const pointField& points,
378  const faceList& faces,
379  const bool verbose
380 ) const
381 {
382  if (!isDir(outputDir))
383  {
384  mkDir(outputDir);
385  }
386 
387  OFstream os(outputDir/surfaceName + ".dat");
388  formatOS(os);
389 
390  if (verbose)
391  {
392  Info<< "Writing nastran file to " << os.name() << endl;
393  }
394 
395  os << "TITLE=OpenFOAM " << surfaceName.c_str() << " mesh" << nl
396  << "$" << nl
397  << "BEGIN BULK" << nl;
398 
399  List<DynamicList<face> > decomposedFaces(faces.size());
400 
401  writeGeometry(points, faces, decomposedFaces, os);
402 
403  if (!isDir(outputDir))
404  {
405  mkDir(outputDir);
406  }
407 
408  os << "ENDDATA" << endl;
409 }
410 
411 
412 // ************************************************************************* //
Output to file stream.
Definition: OFstream.H:81
nastranSurfaceWriter()
Construct null.
bool found(const word &, bool recursive=false, bool patternMatch=true) const
Search dictionary for given keyword.
Definition: dictionary.C:306
labelList f(nPoints)
void unsetf(const ios_base::fmtflags uf)
Unset flags of stream.
Definition: IOstream.H:512
Convenience macros for instantiating writer methods for surfaceWriter classes.
A class for handling words, derived from string.
Definition: word.H:59
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
defineSurfaceWriterWriteFields(nastranSurfaceWriter)
void size(const label)
Override size to be inconsistent with allocated storage.
Definition: ListI.H:76
messageStream Info
A list of keyword definitions, which are a keyword followed by any number of values (e...
Definition: dictionary.H:137
Namespace for OpenFOAM.
A face is a list of labels corresponding to mesh vertices.
Definition: face.H:75
virtual ~nastranSurfaceWriter()
Destructor.
static const char nl
Definition: Ostream.H:260
const Cmpt & y() const
Definition: VectorI.H:71
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:251
virtual int precision() const
Get precision of output field.
Definition: OSstream.C:290
const fileName & name() const
Return the name of the stream.
Definition: OFstream.H:118
Base class for surface writers.
Definition: surfaceWriter.H:54
#define forAll(list, i)
Definition: UList.H:421
const Cmpt & x() const
Definition: VectorI.H:65
Omanip< int > setw(const int i)
Definition: IOmanip.H:199
virtual void write(const fileName &outputDir, const fileName &surfaceName, const pointField &points, const faceList &faces, const bool verbose=false) const
Write single surface geometry to file.
const Cmpt & z() const
Definition: VectorI.H:77
errorManip< error > abort(error &err)
Definition: errorManip.H:131
Istream and Ostream manipulators taking arguments.
Initialise the NamedEnum HashTable from the static list of names.
Definition: NamedEnum.H:52
#define FatalErrorIn(functionName)
Report an error message using Foam::FatalError.
Definition: error.H:314
bool isDir(const fileName &)
Does the name exist as a DIRECTORY in the file system?
Definition: POSIX.C:616
A 1D vector of objects of type <T> that resizes itself as necessary to accept the new objects...
Definition: DynamicList.H:56
ITstream & lookup(const word &, bool recursive=false, bool patternMatch=true) const
Find and return an entry data stream.
Definition: dictionary.C:452
error FatalError
A class for handling file names.
Definition: fileName.H:69
makeSurfaceWriterType(dxSurfaceWriter)
ios_base::fmtflags setf(const ios_base::fmtflags f)
Set flags of stream.
Definition: IOstream.H:496
IOstream & scientific(IOstream &io)
Definition: IOstream.H:582
bool mkDir(const fileName &, mode_t=0777)
Make a directory and return an error if it could not be created.
Definition: POSIX.C:420
label triangles(const pointField &points, label &triI, faceList &triFaces) const
Split into triangles using existing points.
Definition: face.C:835
Enum read(Istream &) const
Read a word from Istream and return the corresponding.
Definition: NamedEnum.C:61
addToRunTimeSelectionTable(ensightPart, ensightPartCells, istream)
static const NamedEnum< writeFormat, 3 > writeFormatNames_