Commit a9bf69b5 authored by Mark Olesen's avatar Mark Olesen

ENH: suppress surface Face-id field if writer manages that itself (#1600)

- for CAE formats such as abaqus, nastran, starcd, etc, the element id
  is already part of the output format itself. For these cases, there
  is no use in generating an additional "Ids" field.

ENH: add code to ignore negative face ids

- these will arise from very special cases, such as when a
  solid element and side are encoded into a single integer.

BUG: starcd surface values output did not use original face ids
parent a001c0d2
...@@ -32,6 +32,7 @@ License ...@@ -32,6 +32,7 @@ License
#include "mapPolyMesh.H" #include "mapPolyMesh.H"
#include "volFields.H" #include "volFields.H"
#include "HashOps.H" #include "HashOps.H"
#include "ListOps.H"
#include "Time.H" #include "Time.H"
#include "UIndirectList.H" #include "UIndirectList.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
...@@ -168,12 +169,18 @@ void Foam::sampledSurfaces::countFields() ...@@ -168,12 +169,18 @@ void Foam::sampledSurfaces::countFields()
forAll(*this, surfi) forAll(*this, surfi)
{ {
const sampledSurface& s = (*this)[surfi]; const sampledSurface& s = (*this)[surfi];
surfaceWriter& outWriter = writers_[surfi];
writers_[surfi].nFields() = outWriter.nFields() =
( (
nVolumeFields nVolumeFields
+ (s.withSurfaceFields() ? nSurfaceFields : 0) + (s.withSurfaceFields() ? nSurfaceFields : 0)
+ ((s.hasFaceIds() && !s.interpolate()) ? 1 : 0) +
(
// Face-id field, but not if the writer manages that itself
!s.interpolate() && s.hasFaceIds() && !outWriter.usesFaceIds()
? 1 : 0
)
); );
} }
} }
...@@ -319,7 +326,7 @@ bool Foam::sampledSurfaces::read(const dictionary& dict) ...@@ -319,7 +326,7 @@ bool Foam::sampledSurfaces::read(const dictionary& dict)
const dictionary& surfDict = dEntry.dict(); const dictionary& surfDict = dEntry.dict();
autoPtr<sampledSurface> surf = autoPtr<sampledSurface> surf =
sampledSurface::New sampledSurface::New
( (
dEntry.keyword(), dEntry.keyword(),
mesh_, mesh_,
...@@ -555,20 +562,29 @@ bool Foam::sampledSurfaces::performAction(unsigned request) ...@@ -555,20 +562,29 @@ bool Foam::sampledSurfaces::performAction(unsigned request)
outWriter.beginTime(obr_.time()); outWriter.beginTime(obr_.time());
// Write original ids // Face-id field, but not if the writer manages that itself
if (s.hasFaceIds() && !s.interpolate()) if (!s.interpolate() && s.hasFaceIds() && !outWriter.usesFaceIds())
{ {
// This is still quite horrible. // This is still quite horrible.
Field<label> ids(s.faceIds()); Field<label> ids(s.faceIds());
ids += label(1); // From 0-based to 1-based
writeSurface if
( (
outWriter, returnReduce
ids, (
"Ids" !ListOps::found(ids, lessOp1<label>(0)),
); andOp<bool>()
)
)
{
// From 0-based to 1-based, provided there are no
// negative ids (eg, encoded solid/side)
ids += label(1);
}
writeSurface(outWriter, ids, "Ids");
} }
} }
} }
......
...@@ -26,10 +26,10 @@ License ...@@ -26,10 +26,10 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "ABAQUSsurfaceFormat.H" #include "ABAQUSsurfaceFormat.H"
#include "ListOps.H"
#include "IFstream.H" #include "IFstream.H"
#include "IOmanip.H" #include "IOmanip.H"
#include "faceTraits.H" #include "faceTraits.H"
#include "stringOps.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
...@@ -267,13 +267,17 @@ void Foam::fileFormats::ABAQUSsurfaceFormat<Face>::write ...@@ -267,13 +267,17 @@ void Foam::fileFormats::ABAQUSsurfaceFormat<Face>::write
const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1); const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1);
// Possible to use faceIds? // Possible to use faceIds?
// - cannot if there are negative ids (eg, encoded solid/side)
bool useOrigFaceIds = bool useOrigFaceIds =
(!useFaceMap && elemIds.size() == faceLst.size()); (
!useFaceMap
&& elemIds.size() == faceLst.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
);
// Not possible with on-the-fly face decomposition
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// Not possible with on-the-fly face decomposition
for (const auto& f : faceLst) for (const auto& f : faceLst)
{ {
if (f.size() > 4) if (f.size() > 4)
......
...@@ -27,6 +27,7 @@ License ...@@ -27,6 +27,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "NASsurfaceFormat.H" #include "NASsurfaceFormat.H"
#include "ListOps.H"
#include "IFstream.H" #include "IFstream.H"
#include "IOmanip.H" #include "IOmanip.H"
#include "faceTraits.H" #include "faceTraits.H"
...@@ -458,13 +459,17 @@ void Foam::fileFormats::NASsurfaceFormat<Face>::write ...@@ -458,13 +459,17 @@ void Foam::fileFormats::NASsurfaceFormat<Face>::write
const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1); const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1);
// Possible to use faceIds? // Possible to use faceIds?
// - cannot if there are negative ids (eg, encoded solid/side)
bool useOrigFaceIds = bool useOrigFaceIds =
(!useFaceMap && elemIds.size() == faceLst.size()); (
!useFaceMap
&& elemIds.size() == faceLst.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
);
// Not possible with on-the-fly face decomposition
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// Not possible with on-the-fly face decomposition
for (const auto& f : faceLst) for (const auto& f : faceLst)
{ {
if (f.size() > 4) if (f.size() > 4)
......
...@@ -284,11 +284,12 @@ void Foam::fileFormats::STARCDsurfaceFormat<Face>::write ...@@ -284,11 +284,12 @@ void Foam::fileFormats::STARCDsurfaceFormat<Face>::write
const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1); const bool useFaceMap = (surf.useFaceMap() && zones.size() > 1);
// Possible to use faceIds? // Possible to use faceIds?
// - cannot if there are negative ids (eg, encoded solid/side)
const bool useOrigFaceIds = const bool useOrigFaceIds =
( (
!useFaceMap !useFaceMap
&& surf.useFaceIds()
&& elemIds.size() == faceLst.size() && elemIds.size() == faceLst.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
); );
......
...@@ -29,6 +29,7 @@ License ...@@ -29,6 +29,7 @@ License
#include "nastranSurfaceWriter.H" #include "nastranSurfaceWriter.H"
#include "Pair.H" #include "Pair.H"
#include "IOmanip.H" #include "IOmanip.H"
#include "ListOps.H"
#include "OSspecific.H" #include "OSspecific.H"
#include "surfaceWriterMethods.H" #include "surfaceWriterMethods.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
...@@ -214,11 +215,15 @@ void Foam::surfaceWriters::nastranWriter::writeGeometry ...@@ -214,11 +215,15 @@ void Foam::surfaceWriters::nastranWriter::writeGeometry
const labelList& elemIds = surf.faceIds(); const labelList& elemIds = surf.faceIds();
// Possible to use faceIds? // Possible to use faceIds?
bool useOrigFaceIds = (elemIds.size() == faces.size()); bool useOrigFaceIds =
(
elemIds.size() == faces.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
);
// Not possible with on-the-fly face decomposition
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// Not possible with on-the-fly face decomposition
for (const auto& f : faces) for (const auto& f : faces)
{ {
if (f.size() > 4) if (f.size() > 4)
...@@ -258,7 +263,6 @@ void Foam::surfaceWriters::nastranWriter::writeGeometry ...@@ -258,7 +263,6 @@ void Foam::surfaceWriters::nastranWriter::writeGeometry
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// When available and not decomposed
elemId = elemIds[facei]; elemId = elemIds[facei];
} }
......
...@@ -254,6 +254,12 @@ public: ...@@ -254,6 +254,12 @@ public:
// Member Functions // Member Functions
//- Format uses faceIds as part of its output
virtual bool usesFaceIds() const // override
{
return true;
}
//- Write surface geometry to file. //- Write surface geometry to file.
virtual fileName write(); // override virtual fileName write(); // override
......
...@@ -28,6 +28,7 @@ License ...@@ -28,6 +28,7 @@ License
#include "OFstream.H" #include "OFstream.H"
#include "IOmanip.H" #include "IOmanip.H"
#include "ListOps.H"
#include "OSspecific.H" #include "OSspecific.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
...@@ -254,13 +255,13 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate ...@@ -254,13 +255,13 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
// Regular (undecomposed) faces // Regular (undecomposed) faces
const faceList& faces = surf.faces(); const faceList& faces = surf.faces();
const labelList& elemIds = surf.faceIds(); const labelUList& elemIds = surf.faceIds();
// Possible to use faceIds? // Possible to use faceIds?
// Not possible with on-the-fly face decomposition
const bool useOrigFaceIds = const bool useOrigFaceIds =
( (
elemIds.size() == faces.size() elemIds.size() == faces.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
&& decompFaces.empty() && decompFaces.empty()
); );
...@@ -273,7 +274,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate ...@@ -273,7 +274,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
{ {
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// When available and not decomposed
elemId = elemIds[facei]; elemId = elemIds[facei];
} }
...@@ -324,7 +324,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate ...@@ -324,7 +324,6 @@ Foam::fileName Foam::surfaceWriters::nastranWriter::writeTemplate
{ {
if (useOrigFaceIds) if (useOrigFaceIds)
{ {
// When available and not decomposed
elemId = elemIds[facei]; elemId = elemIds[facei];
} }
......
...@@ -27,6 +27,7 @@ License ...@@ -27,6 +27,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "starcdSurfaceWriter.H" #include "starcdSurfaceWriter.H"
#include "ListOps.H"
#include "OFstream.H" #include "OFstream.H"
#include "OSspecific.H" #include "OSspecific.H"
#include "MeshedSurfaceProxy.H" #include "MeshedSurfaceProxy.H"
...@@ -53,7 +54,7 @@ namespace Foam ...@@ -53,7 +54,7 @@ namespace Foam
template<class Type> template<class Type>
static inline void writeData(Ostream& os, const Type& val) static inline void writeData(Ostream& os, const Type& val)
{ {
for (direction cmpt=0; cmpt < pTraits<Type>::nComponents; ++cmpt) for (direction cmpt=0; cmpt < pTraits<Type>::nComponents; ++cmpt)
{ {
os << ' ' << component(val, cmpt); os << ' ' << component(val, cmpt);
} }
...@@ -145,13 +146,23 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::write() ...@@ -145,13 +146,23 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::write()
mkDir(outputFile.path()); mkDir(outputFile.path());
} }
const labelUList& origFaceIds = surf.faceIds();
// Face ids (if possible)
const labelUList& elemIds =
(
!ListOps::found(origFaceIds, lessOp1<label>(0))
? origFaceIds
: labelUList::null()
);
MeshedSurfaceProxy<face> MeshedSurfaceProxy<face>
( (
surf.points(), surf.points(),
surf.faces(), surf.faces(),
UList<surfZone>::null(), // one zone UList<surfZone>::null(), // one zone
labelUList::null(), // no faceMap labelUList::null(), // no faceMap
surf.faceIds() // with face ids (if possible) elemIds // face ids
).write ).write
( (
outputFile, outputFile,
...@@ -204,6 +215,8 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::writeTemplate ...@@ -204,6 +215,8 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::writeTemplate
// geometry merge() implicit // geometry merge() implicit
tmp<Field<Type>> tfield = mergeField(localValues); tmp<Field<Type>> tfield = mergeField(localValues);
const meshedSurf& surf = surface();
if (Pstream::master() || !parallel_) if (Pstream::master() || !parallel_)
{ {
const auto& values = tfield(); const auto& values = tfield();
...@@ -215,16 +228,26 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::writeTemplate ...@@ -215,16 +228,26 @@ Foam::fileName Foam::surfaceWriters::starcdWriter::writeTemplate
OFstream os(outputFile, streamOpt_); OFstream os(outputFile, streamOpt_);
// 1-based ids const labelUList& elemIds = surf.faceIds();
label elemId = 1;
// Possible to use faceIds?
const bool useOrigFaceIds =
(
elemIds.size() == values.size()
&& !ListOps::found(elemIds, lessOp1<label>(0))
);
label faceIndex = 0;
// No header, just write values // No header, just write values
for (const Type& val : values) for (const Type& val : values)
{ {
os << elemId; const label elemId =
writeData(os, val); (useOrigFaceIds ? elemIds[faceIndex] : faceIndex);
++elemId; os << (elemId + 1); // 1-based ids
writeData(os, val);
++faceIndex;
} }
} }
......
...@@ -159,6 +159,12 @@ public: ...@@ -159,6 +159,12 @@ public:
return true; return true;
} }
//- Format uses faceIds as part of its output
virtual bool usesFaceIds() const // override
{
return true;
}
//- Write surface geometry to file. //- Write surface geometry to file.
virtual fileName write(); // override virtual fileName write(); // override
......
...@@ -300,6 +300,14 @@ public: ...@@ -300,6 +300,14 @@ public:
return false; return false;
} }
//- True if the writer format uses faceIds as part of its output.
// Element ids are used by various CAE formats
// (abaqus, nastran, starcd, ...)
virtual bool usesFaceIds() const
{
return false;
}
// Bookkeeping // Bookkeeping
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment