mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
ENH: improvements for nastran surface writer
- select default nastran PLOAD2 or PLOAD4 based on field type. Default to PLOAD2 for scalar types and PLOAD4 for vectors etc. - relocate nastran SHELL/MAT cards. Previously wrote at the end of the file, now emit when writing the geometry itself. This improves modularity (of code and files) - initial support for common geometry file for nastran
This commit is contained in:
@ -303,15 +303,12 @@ void Foam::surfaceWriters::nastranWriter::writeGeometry
|
||||
// The end offset, which is the next begin offset
|
||||
decompOffsets[facei+1] = decompFaces.size();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Foam::Ostream& Foam::surfaceWriters::nastranWriter::writeFooter
|
||||
(
|
||||
Ostream& os,
|
||||
const meshedSurf& surf
|
||||
) const
|
||||
{
|
||||
//
|
||||
// SHELL/MAT information
|
||||
//
|
||||
|
||||
// Zone id have been used for the PID. Find unique values.
|
||||
|
||||
labelList pidsUsed = labelHashSet(surf.zoneIds()).sortedToc();
|
||||
@ -339,7 +336,7 @@ Foam::Ostream& Foam::surfaceWriters::nastranWriter::writeFooter
|
||||
|
||||
const label MID = 1;
|
||||
|
||||
writeKeyword(os, "MAT1") << separator_;
|
||||
writeKeyword(os, "MAT1") << separator_;
|
||||
writeValue(os, MID);
|
||||
|
||||
for (label i = 0; i < 7; ++i)
|
||||
@ -349,8 +346,6 @@ Foam::Ostream& Foam::surfaceWriters::nastranWriter::writeFooter
|
||||
writeValue(os, "");
|
||||
}
|
||||
os << nl;
|
||||
|
||||
return os;
|
||||
}
|
||||
|
||||
|
||||
@ -361,6 +356,7 @@ Foam::surfaceWriters::nastranWriter::nastranWriter()
|
||||
surfaceWriter(),
|
||||
writeFormat_(fieldFormat::SHORT),
|
||||
fieldMap_(),
|
||||
commonGeometry_(false),
|
||||
geometryScale_(1),
|
||||
fieldScale_(),
|
||||
separator_()
|
||||
@ -383,6 +379,7 @@ Foam::surfaceWriters::nastranWriter::nastranWriter
|
||||
)
|
||||
),
|
||||
fieldMap_(),
|
||||
commonGeometry_(options.getOrDefault("commonGeometry", false)),
|
||||
geometryScale_(options.getOrDefault<scalar>("scale", 1)),
|
||||
fieldScale_(options.subOrEmptyDict("fieldScale")),
|
||||
separator_()
|
||||
@ -470,9 +467,7 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::write()
|
||||
OFstream os(outputFile);
|
||||
fileFormats::NASCore::setPrecision(os, writeFormat_);
|
||||
|
||||
os << "TITLE=OpenFOAM " << outputPath_.name()
|
||||
<< " mesh" << nl
|
||||
<< '$' << nl
|
||||
os << "TITLE=OpenFOAM " << outputPath_.name() << " geometry" << nl
|
||||
<< "BEGIN BULK" << nl;
|
||||
|
||||
labelList decompOffsets;
|
||||
@ -480,8 +475,7 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::write()
|
||||
|
||||
writeGeometry(os, surf, decompOffsets, decompFaces);
|
||||
|
||||
writeFooter(os, surf)
|
||||
<< "ENDDATA" << nl;
|
||||
os << "ENDDATA" << nl;
|
||||
}
|
||||
|
||||
wroteGeom_ = true;
|
||||
|
||||
@ -33,10 +33,11 @@ Description
|
||||
The formatOptions for nastran:
|
||||
\table
|
||||
Property | Description | Required | Default
|
||||
fields | field pairs for PLOAD2, PLOAD4 | yes |
|
||||
fields | field pairs for PLOAD2/PLOAD4 | yes |
|
||||
format | short / long / free | no | long
|
||||
scale | output geometry scaling | no | 1
|
||||
fieldScale | output field scaling (dictionary) | no | empty
|
||||
commonGeometry | use separate geometry files | no | false
|
||||
\endtable
|
||||
|
||||
For example,
|
||||
@ -45,7 +46,7 @@ Description
|
||||
{
|
||||
nastran
|
||||
{
|
||||
// OpenFOAM field name to NASTRAN field name
|
||||
// OpenFOAM field name to NASTRAN load types
|
||||
fields
|
||||
(
|
||||
(pMean PLOAD2)
|
||||
@ -71,7 +72,7 @@ Description
|
||||
\subheading Geometry
|
||||
\verbatim
|
||||
rootdir
|
||||
`-- timeName
|
||||
`-- <time>
|
||||
|-- surfaceName0.{nas}
|
||||
`-- surfaceName1.{nas}
|
||||
\endverbatim
|
||||
@ -79,17 +80,18 @@ Description
|
||||
\subheading Fields
|
||||
\verbatim
|
||||
rootdir
|
||||
`-- timeName
|
||||
`-- <time>
|
||||
`-- field0
|
||||
| |-- surfaceName0.{nas}
|
||||
| `-- surfaceName1.{nas}
|
||||
| |-- surfaceName0.{bdf}
|
||||
| `-- surfaceName1.{bdf}
|
||||
`-- field1
|
||||
|-- surfaceName0.{nas}
|
||||
`-- surfaceName1.{nas}
|
||||
|-- surfaceName0.{bdf}
|
||||
`-- surfaceName1.{bdf}
|
||||
\endverbatim
|
||||
|
||||
Note
|
||||
Output variable scaling does not apply to integer types such as Ids.
|
||||
Field pairs default to PLOAD2 for scalars and PLOAD4 for vectors etc.
|
||||
|
||||
SourceFiles
|
||||
nastranSurfaceWriter.C
|
||||
@ -138,6 +140,9 @@ private:
|
||||
//- Mapping from field name to data format enumeration
|
||||
HashTable<loadFormat> fieldMap_;
|
||||
|
||||
//- Use common geometry file
|
||||
bool commonGeometry_;
|
||||
|
||||
//- Output geometry scaling
|
||||
const scalar geometryScale_;
|
||||
|
||||
@ -169,6 +174,7 @@ private:
|
||||
) const;
|
||||
|
||||
//- Write the surface mesh geometry, tracking face decomposition
|
||||
// Includes SHELL/MAT information
|
||||
//
|
||||
// \param decompOffsets begin/end offsets (size+1) into decompFaces
|
||||
// \param decompFaces Non tri/quad decomposed into triangles
|
||||
@ -187,9 +193,6 @@ private:
|
||||
const word& keyword
|
||||
) const;
|
||||
|
||||
//- Write the footer information
|
||||
Ostream& writeFooter(Ostream& os, const meshedSurf& surf) const;
|
||||
|
||||
//- Write a formatted value to the output stream
|
||||
template<class Type>
|
||||
Ostream& writeValue(Ostream& os, const Type& value) const;
|
||||
|
||||
@ -145,22 +145,59 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
const Field<Type>& localValues
|
||||
)
|
||||
{
|
||||
checkOpen();
|
||||
// Geometry changed since last output? Capture now before any merging.
|
||||
/// const bool geomChanged = (!upToDate_);
|
||||
|
||||
if (!fieldMap_.found(fieldName))
|
||||
// Separate geometry, when commonGeometry = true
|
||||
if (!wroteGeom_ && commonGeometry_)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< "No mapping found between field " << fieldName
|
||||
<< " and corresponding Nastran field. Available types are:"
|
||||
<< fieldMap_
|
||||
<< exit(FatalError);
|
||||
|
||||
return fileName::null;
|
||||
write();
|
||||
}
|
||||
|
||||
const loadFormat format(fieldMap_[fieldName]);
|
||||
checkOpen();
|
||||
|
||||
// Field: rootdir/<TIME>/field/surfaceName.nas
|
||||
const loadFormat format
|
||||
(
|
||||
fieldMap_.lookup
|
||||
(
|
||||
fieldName,
|
||||
// Default format
|
||||
(
|
||||
pTraits<Type>::nComponents == 1
|
||||
? loadFormat::PLOAD2
|
||||
: loadFormat::PLOAD4
|
||||
)
|
||||
)
|
||||
);
|
||||
|
||||
if
|
||||
(
|
||||
!std::is_integral<Type>::value // Handle 'Ids' etc silently
|
||||
&& !fieldMap_.empty()
|
||||
&& !fieldMap_.found(fieldName)
|
||||
)
|
||||
{
|
||||
WarningInFunction
|
||||
<< "No mapping found between field " << fieldName
|
||||
<< " and corresponding Nastran field. Available types:"
|
||||
<< fieldMap_ << nl;
|
||||
}
|
||||
|
||||
// Emit any common warnings
|
||||
if (format == loadFormat::PLOAD2 && pTraits<Type>::nComponents != 1)
|
||||
{
|
||||
WarningInFunction
|
||||
<< fileFormats::NASCore::loadFormatNames[format]
|
||||
<< " cannot be used for higher rank values"
|
||||
<< " - reverting to mag()" << endl;
|
||||
}
|
||||
|
||||
|
||||
// Common geometry
|
||||
// Field: rootdir/<TIME>/<field>_surfaceName.bdf
|
||||
|
||||
// Embedded geometry
|
||||
// Field: rootdir/<TIME>/<field>/surfaceName.bdf
|
||||
|
||||
fileName outputFile = outputPath_.path();
|
||||
if (useTimeDir() && !timeName().empty())
|
||||
@ -168,8 +205,23 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
// Splice in time-directory
|
||||
outputFile /= timeName();
|
||||
}
|
||||
outputFile /= fieldName / outputPath_.name();
|
||||
outputFile.ext("nas");
|
||||
|
||||
fileName geomFileName;
|
||||
if (commonGeometry_)
|
||||
{
|
||||
// Common geometry
|
||||
geomFileName = outputPath_.name().ext("nas");
|
||||
|
||||
// Append <field>_surfaceName.bdf
|
||||
outputFile /= fieldName + '_' + outputPath_.name();
|
||||
}
|
||||
else
|
||||
{
|
||||
// Embedded geometry
|
||||
// Use sub-directory
|
||||
outputFile /= fieldName / outputPath_.name();
|
||||
}
|
||||
outputFile.ext("bdf");
|
||||
|
||||
|
||||
// Output scaling for the variable, but not for integer types.
|
||||
@ -193,16 +245,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
}
|
||||
|
||||
|
||||
// Emit any common warnings
|
||||
if (format == loadFormat::PLOAD2 && pTraits<Type>::nComponents != 1)
|
||||
{
|
||||
WarningInFunction
|
||||
<< fileFormats::NASCore::loadFormatNames[format]
|
||||
<< " cannot be used for higher rank values"
|
||||
<< " - reverting to mag()" << endl;
|
||||
}
|
||||
|
||||
|
||||
// Implicit geometry merge()
|
||||
tmp<Field<Type>> tfield = mergeField(localValues) * varScale;
|
||||
|
||||
@ -224,8 +266,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
DynamicList<face> decompFaces;
|
||||
|
||||
|
||||
// Could handle separate geometry here
|
||||
|
||||
OFstream os(outputFile);
|
||||
fileFormats::NASCore::setPrecision(os, writeFormat_);
|
||||
|
||||
@ -238,17 +278,31 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
<< "$ TIME " << timeName() << nl;
|
||||
}
|
||||
|
||||
os << '$' << nl
|
||||
<< "TIME " << timeValue << nl
|
||||
<< '$' << nl
|
||||
os << "TIME " << timeValue << nl
|
||||
<< nl
|
||||
<< "BEGIN BULK" << nl;
|
||||
|
||||
if (commonGeometry_)
|
||||
{
|
||||
os << "INCLUDE '" << geomFileName.c_str() << "'" << nl;
|
||||
|
||||
writeGeometry(os, surf, decompOffsets, decompFaces);
|
||||
|
||||
// Geometry already written (or suppressed)
|
||||
// - still need decomposition information
|
||||
fileFormats::NASCore::faceDecomposition
|
||||
(
|
||||
surf.points(),
|
||||
surf.faces(),
|
||||
decompOffsets,
|
||||
decompFaces
|
||||
);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Write geometry
|
||||
writeGeometry(os, surf, decompOffsets, decompFaces);
|
||||
}
|
||||
|
||||
// Write field
|
||||
|
||||
os << '$' << nl
|
||||
<< "$ Field data" << nl
|
||||
<< '$' << nl;
|
||||
@ -345,8 +399,7 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
|
||||
}
|
||||
}
|
||||
|
||||
writeFooter(os, surf)
|
||||
<< "ENDDATA" << endl;
|
||||
os << "ENDDATA" << endl;
|
||||
}
|
||||
|
||||
wroteGeom_ = true;
|
||||
|
||||
Reference in New Issue
Block a user