mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
ENH: provide OpenFOAM/VTK low-level transcription routines
- Zero-copy does not work for several reasons, but this uses the OpenFOAM structures to write VTK-compatible formats into external arrays.
This commit is contained in:
@ -25,6 +25,8 @@ starcd/STARCDMeshWriter.C
|
||||
polyDualMesh/polyDualMesh.C
|
||||
|
||||
vtk/part/foamVtkCells.C
|
||||
vtk/part/foamVtkMeshMaps.C
|
||||
vtk/part/foamVtuSizing.C
|
||||
vtk/output/foamVtkOutput.C
|
||||
|
||||
LIB = $(FOAM_LIBBIN)/libconversion
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd.
|
||||
\\ / A nd | Copyright (C) 2016-2107 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
@ -80,7 +80,7 @@ public:
|
||||
|
||||
//- Write a value component-wise.
|
||||
template<class Type>
|
||||
inline static void write(foamVtkFormatter&, const Type&);
|
||||
inline static void write(foamVtkFormatter& fmt, const Type& val);
|
||||
|
||||
|
||||
//- Write a list of values.
|
||||
@ -88,8 +88,8 @@ public:
|
||||
template<class Type>
|
||||
static void writeList
|
||||
(
|
||||
foamVtkFormatter&,
|
||||
const UList<Type>&
|
||||
foamVtkFormatter& fmt,
|
||||
const UList<Type>& lst
|
||||
);
|
||||
|
||||
|
||||
@ -98,20 +98,29 @@ public:
|
||||
template<class Type>
|
||||
static void writeList
|
||||
(
|
||||
foamVtkFormatter&,
|
||||
const UList<Type>&,
|
||||
foamVtkFormatter& fmt,
|
||||
const UList<Type>& lst,
|
||||
const UList<label>& addressing
|
||||
);
|
||||
|
||||
|
||||
//- Write volField with cell values (including decomposed cells).
|
||||
//- Write internalField for mesh
|
||||
// The output includes the payload size and flush.
|
||||
template<class Type>
|
||||
static void writeField
|
||||
(
|
||||
foamVtkFormatter&,
|
||||
const GeometricField<Type, fvPatchField, volMesh>&,
|
||||
const UList<label>& superCells
|
||||
foamVtkFormatter& fmt,
|
||||
const GeometricField<Type, fvPatchField, volMesh>& vf
|
||||
);
|
||||
|
||||
//- Write internalField based on the cellMap
|
||||
// The output includes the payload size and flush.
|
||||
template<class Type>
|
||||
static void writeField
|
||||
(
|
||||
foamVtkFormatter& fmt,
|
||||
const GeometricField<Type, fvPatchField, volMesh>& vf,
|
||||
const UList<label>& cellMap
|
||||
);
|
||||
|
||||
};
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd.
|
||||
\\ / A nd | Copyright (C) 2016-2107 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
@ -73,19 +73,36 @@ template<class Type>
|
||||
void Foam::foamVtkOutput::writeField
|
||||
(
|
||||
foamVtkFormatter& fmt,
|
||||
const GeometricField<Type, fvPatchField, volMesh>& vf,
|
||||
const UList<label>& superCells
|
||||
const GeometricField<Type, fvPatchField, volMesh>& vf
|
||||
)
|
||||
{
|
||||
const uint64_t payLoad =
|
||||
(
|
||||
(vf.size() + superCells.size())
|
||||
* pTraits<Type>::nComponents * sizeof(float)
|
||||
vf.size() * pTraits<Type>::nComponents * sizeof(float)
|
||||
);
|
||||
|
||||
fmt.writeSize(payLoad);
|
||||
writeList(fmt, vf.internalField());
|
||||
writeList(fmt, vf, superCells);
|
||||
|
||||
fmt.flush();
|
||||
}
|
||||
|
||||
|
||||
template<class Type>
|
||||
void Foam::foamVtkOutput::writeField
|
||||
(
|
||||
foamVtkFormatter& fmt,
|
||||
const GeometricField<Type, fvPatchField, volMesh>& vf,
|
||||
const UList<label>& cellMap
|
||||
)
|
||||
{
|
||||
const uint64_t payLoad =
|
||||
(
|
||||
cellMap.size() * pTraits<Type>::nComponents * sizeof(float)
|
||||
);
|
||||
|
||||
fmt.writeSize(payLoad);
|
||||
writeList(fmt, vf.internalField(), cellMap);
|
||||
|
||||
fmt.flush();
|
||||
}
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2011-2016 OpenCFD Ltd.
|
||||
\\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
@ -25,624 +25,133 @@ License
|
||||
|
||||
#include "foamVtkCells.H"
|
||||
#include "polyMesh.H"
|
||||
#include "cellShape.H"
|
||||
#include "cellModeller.H"
|
||||
|
||||
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
||||
|
||||
void Foam::foamVtkCells::correct()
|
||||
{
|
||||
// Clear derived data
|
||||
// clearGeom();
|
||||
|
||||
const cellModel& tet = *(cellModeller::lookup("tet"));
|
||||
const cellModel& pyr = *(cellModeller::lookup("pyr"));
|
||||
const cellModel& prism = *(cellModeller::lookup("prism"));
|
||||
const cellModel& wedge = *(cellModeller::lookup("wedge"));
|
||||
const cellModel& tetWedge = *(cellModeller::lookup("tetWedge"));
|
||||
const cellModel& hex = *(cellModeller::lookup("hex"));
|
||||
|
||||
const cellShapeList& cellShapes = mesh_.cellShapes();
|
||||
|
||||
// face owner is needed to determine the face orientation
|
||||
const labelList& owner = mesh_.faceOwner();
|
||||
|
||||
// Unique vertex labels per polyhedral
|
||||
HashSet<label> hashUniqId(2*256);
|
||||
|
||||
// =======================
|
||||
// PASS 1: Determine sizes
|
||||
|
||||
label nVertLabels = 0;
|
||||
label nFaceLabels = 0;
|
||||
label nAddPoints = 0;
|
||||
label nAddCells = 0;
|
||||
label nAddVerts = 0;
|
||||
|
||||
forAll(cellShapes, cellI)
|
||||
{
|
||||
const cellShape& shape = cellShapes[cellI];
|
||||
const cellModel& model = shape.model();
|
||||
|
||||
if
|
||||
(
|
||||
model == tet
|
||||
|| model == pyr
|
||||
|| model == prism
|
||||
|| model == hex
|
||||
)
|
||||
{
|
||||
// normal primitives
|
||||
nVertLabels += shape.size();
|
||||
}
|
||||
else if (model == tetWedge && decompose_.requested())
|
||||
{
|
||||
// Treat as squeezed prism (VTK_WEDGE)
|
||||
nVertLabels += 6;
|
||||
}
|
||||
else if (model == wedge && decompose_.requested())
|
||||
{
|
||||
// Treat as squeezed hex
|
||||
nVertLabels += 8;
|
||||
}
|
||||
else if (decompose_.requested())
|
||||
{
|
||||
// Polyhedral: Decompose into tets + pyramids.
|
||||
|
||||
// Count vertices in first decomposed cell
|
||||
bool first = true;
|
||||
|
||||
const cell& cFaces = mesh_.cells()[cellI];
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh_.faces()[cFaces[cFaceI]];
|
||||
|
||||
// Face decomposed into triangles and quads
|
||||
// Tri -> Tet, Quad -> Pyr
|
||||
label nTria = 0, nQuad = 0;
|
||||
f.nTrianglesQuads(mesh_.points(), nTria, nQuad);
|
||||
|
||||
nAddCells += nTria + nQuad;
|
||||
nAddVerts += (nTria * 4) + (nQuad * 5);
|
||||
|
||||
if (first)
|
||||
{
|
||||
const label nvrt = (nQuad ? 5 : 4);
|
||||
nAddCells--;
|
||||
nAddVerts -= nvrt;
|
||||
nVertLabels += nvrt;
|
||||
|
||||
first = false;
|
||||
}
|
||||
}
|
||||
|
||||
++nAddPoints;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Polyhedral: Not decomposed.
|
||||
|
||||
const labelList& cFaces = mesh_.cells()[cellI];
|
||||
|
||||
// establish unique node ids used (only needed for XML)
|
||||
hashUniqId.clear();
|
||||
|
||||
// determing sizing for face stream
|
||||
// number of faces, size of each face, vertices per face
|
||||
// [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh_.faces()[cFaces[cFaceI]];
|
||||
nFaceLabels += f.size();
|
||||
|
||||
forAll(f, fp)
|
||||
{
|
||||
hashUniqId.insert(f[fp]);
|
||||
}
|
||||
}
|
||||
|
||||
nVertLabels += hashUniqId.size();
|
||||
nFaceLabels += 1 + cFaces.size();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// adjust/reserve sizes
|
||||
//
|
||||
|
||||
// Cell types (including added cells) in vtk numbering
|
||||
cellTypes_.setSize(cellShapes.size() + nAddCells);
|
||||
|
||||
// List of vertex labels in VTK ordering
|
||||
vertLabels_.setSize(nVertLabels + nAddVerts);
|
||||
|
||||
vertOffset_.setSize(cellShapes.size() + nAddCells);
|
||||
|
||||
faceLabels_.clear();
|
||||
faceOffset_.clear();
|
||||
if (nFaceLabels)
|
||||
{
|
||||
faceLabels_.setSize(nFaceLabels);
|
||||
|
||||
// only need nCells (without nAddCells)
|
||||
// set to -1 (primitive)
|
||||
faceOffset_.setSize(cellShapes.size(), -1);
|
||||
}
|
||||
|
||||
if (decompose_.requested())
|
||||
{
|
||||
decompose_.addPointCellLabels_.setSize(nAddPoints);
|
||||
decompose_.superCells_.setSize(nAddCells);
|
||||
}
|
||||
|
||||
|
||||
// ======================
|
||||
// PASS 2: Fill in arrays
|
||||
|
||||
// Need this offset later, but only for decomposed polys
|
||||
const label offsetAddVerts = nVertLabels;
|
||||
|
||||
// Reset counters
|
||||
nVertLabels = 0;
|
||||
nFaceLabels = 0;
|
||||
nAddPoints = 0;
|
||||
nAddCells = 0;
|
||||
nAddVerts = 0;
|
||||
|
||||
forAll(cellShapes, cellI)
|
||||
{
|
||||
const cellShape& shape = cellShapes[cellI];
|
||||
const cellModel& model = shape.model();
|
||||
|
||||
if (model == tet)
|
||||
{
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_TETRA;
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels_[nVertLabels++] = shape[i];
|
||||
}
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (model == pyr)
|
||||
{
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_PYRAMID;
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels_[nVertLabels++] = shape[i];
|
||||
}
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (model == hex)
|
||||
{
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_HEXAHEDRON;
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels_[nVertLabels++] = shape[i];
|
||||
}
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (model == prism)
|
||||
{
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_WEDGE;
|
||||
|
||||
// VTK_WEDGE triangles point outwards (swap 1<->2, 4<->5)
|
||||
vertLabels_[nVertLabels++] = shape[0];
|
||||
vertLabels_[nVertLabels++] = shape[2];
|
||||
vertLabels_[nVertLabels++] = shape[1];
|
||||
vertLabels_[nVertLabels++] = shape[3];
|
||||
vertLabels_[nVertLabels++] = shape[5];
|
||||
vertLabels_[nVertLabels++] = shape[4];
|
||||
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (model == tetWedge && decompose_.requested())
|
||||
{
|
||||
// Treat as squeezed prism (VTK_WEDGE)
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_WEDGE;
|
||||
|
||||
vertLabels_[nVertLabels++] = shape[0];
|
||||
vertLabels_[nVertLabels++] = shape[2];
|
||||
vertLabels_[nVertLabels++] = shape[1];
|
||||
vertLabels_[nVertLabels++] = shape[3];
|
||||
vertLabels_[nVertLabels++] = shape[4];
|
||||
vertLabels_[nVertLabels++] = shape[3];
|
||||
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (model == wedge && decompose_.requested())
|
||||
{
|
||||
// Treat as squeezed hex
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_HEXAHEDRON;
|
||||
|
||||
vertLabels_[nVertLabels++] = shape[0];
|
||||
vertLabels_[nVertLabels++] = shape[1];
|
||||
vertLabels_[nVertLabels++] = shape[2];
|
||||
vertLabels_[nVertLabels++] = shape[2];
|
||||
vertLabels_[nVertLabels++] = shape[3];
|
||||
vertLabels_[nVertLabels++] = shape[4];
|
||||
vertLabels_[nVertLabels++] = shape[5];
|
||||
vertLabels_[nVertLabels++] = shape[6];
|
||||
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
else if (decompose_.requested())
|
||||
{
|
||||
// Polyhedral cell - decompose into tet/pyr.
|
||||
|
||||
// Ensure we have the correct orientation for the base of the
|
||||
// primitive cell shape.
|
||||
// If the cell is face owner, the orientation needs to be flipped
|
||||
// to avoid defining negative cells.
|
||||
// VTK doesn't seem to care, but we'll do it anyhow for safety.
|
||||
|
||||
// The new vertex from the cell-centre
|
||||
const label newVertexLabel = mesh_.nPoints() + nAddPoints;
|
||||
|
||||
// Mapping from additional point to cell
|
||||
decompose_.addPointCellLabels_[nAddPoints++] = cellI;
|
||||
|
||||
// Whether to insert cell in place of original or not.
|
||||
bool first = true;
|
||||
|
||||
const labelList& cFaces = mesh_.cells()[cellI];
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh_.faces()[cFaces[cFaceI]];
|
||||
const bool isOwner = (owner[cFaces[cFaceI]] == cellI);
|
||||
|
||||
// Count triangles/quads in decomposition
|
||||
label nTria = 0;
|
||||
label nQuad = 0;
|
||||
f.nTrianglesQuads(mesh_.points(), nTria, nQuad);
|
||||
|
||||
// Do actual decomposition
|
||||
faceList faces3(nTria);
|
||||
faceList faces4(nQuad);
|
||||
nTria = 0, nQuad = 0;
|
||||
f.trianglesQuads(mesh_.points(), nTria, nQuad, faces3, faces4);
|
||||
|
||||
forAll(faces4, fci)
|
||||
{
|
||||
const face& quad = faces4[fci];
|
||||
|
||||
label celLoc;
|
||||
label vrtLoc;
|
||||
|
||||
if (first)
|
||||
{
|
||||
celLoc = cellI;
|
||||
vrtLoc = nVertLabels;
|
||||
nVertLabels += 5;
|
||||
|
||||
vertOffset_[celLoc] = nVertLabels;
|
||||
first = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
celLoc = mesh_.nCells() + nAddCells;
|
||||
vrtLoc = offsetAddVerts + nAddVerts;
|
||||
nAddVerts += 5;
|
||||
|
||||
vertOffset_[celLoc] = nAddVerts;
|
||||
decompose_.superCells_[nAddCells++] = cellI;
|
||||
}
|
||||
|
||||
cellTypes_[celLoc] = foamVtkCore::VTK_PYRAMID;
|
||||
|
||||
// See note above about the orientation.
|
||||
if (isOwner)
|
||||
{
|
||||
vertLabels_[vrtLoc++] = quad[3];
|
||||
vertLabels_[vrtLoc++] = quad[2];
|
||||
vertLabels_[vrtLoc++] = quad[1];
|
||||
vertLabels_[vrtLoc++] = quad[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
vertLabels_[vrtLoc++] = quad[0];
|
||||
vertLabels_[vrtLoc++] = quad[1];
|
||||
vertLabels_[vrtLoc++] = quad[2];
|
||||
vertLabels_[vrtLoc++] = quad[3];
|
||||
}
|
||||
|
||||
vertLabels_[vrtLoc++] = newVertexLabel;
|
||||
}
|
||||
|
||||
forAll(faces3, fci)
|
||||
{
|
||||
const face& tria = faces3[fci];
|
||||
|
||||
label celLoc;
|
||||
label vrtLoc;
|
||||
|
||||
if (first)
|
||||
{
|
||||
celLoc = cellI;
|
||||
vrtLoc = nVertLabels;
|
||||
nVertLabels += 4;
|
||||
|
||||
vertOffset_[celLoc] = nVertLabels;
|
||||
first = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
celLoc = mesh_.nCells() + nAddCells;
|
||||
vrtLoc = offsetAddVerts + nAddVerts;
|
||||
nAddVerts += 4;
|
||||
|
||||
vertOffset_[celLoc] = nAddVerts;
|
||||
decompose_.superCells_[nAddCells++] = cellI;
|
||||
}
|
||||
|
||||
cellTypes_[celLoc] = foamVtkCore::VTK_TETRA;
|
||||
|
||||
// See note above about the orientation.
|
||||
if (isOwner)
|
||||
{
|
||||
vertLabels_[vrtLoc++] = tria[2];
|
||||
vertLabels_[vrtLoc++] = tria[1];
|
||||
vertLabels_[vrtLoc++] = tria[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
vertLabels_[vrtLoc++] = tria[0];
|
||||
vertLabels_[vrtLoc++] = tria[1];
|
||||
vertLabels_[vrtLoc++] = tria[2];
|
||||
}
|
||||
vertLabels_[vrtLoc++] = newVertexLabel;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Polyhedral cell - not decomposed
|
||||
|
||||
hashUniqId.clear(); // unique node ids used (only needed for XML)
|
||||
|
||||
// face-stream
|
||||
// [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
|
||||
cellTypes_[cellI] = foamVtkCore::VTK_POLYHEDRON;
|
||||
const labelList& cFaces = mesh_.cells()[cellI];
|
||||
|
||||
faceLabels_[nFaceLabels++] = cFaces.size();
|
||||
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh_.faces()[cFaces[cFaceI]];
|
||||
const bool isOwner = (owner[cFaces[cFaceI]] == cellI);
|
||||
|
||||
forAll(f, fp)
|
||||
{
|
||||
hashUniqId.insert(f[fp]);
|
||||
}
|
||||
|
||||
// number of labels for this face
|
||||
faceLabels_[nFaceLabels++] = f.size();
|
||||
|
||||
if (isOwner)
|
||||
{
|
||||
forAll(f, fp)
|
||||
{
|
||||
faceLabels_[nFaceLabels++] = f[fp];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// fairly immaterial if we reverse the list
|
||||
// or use face::reverseFace()
|
||||
forAllReverse(f, fp)
|
||||
{
|
||||
faceLabels_[nFaceLabels++] = f[fp];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
faceOffset_[cellI] = nFaceLabels;
|
||||
|
||||
const labelList uniq = hashUniqId.sortedToc();
|
||||
forAll(uniq, i)
|
||||
{
|
||||
vertLabels_[nVertLabels++] = uniq[i];
|
||||
}
|
||||
|
||||
vertOffset_[cellI] = nVertLabels;
|
||||
}
|
||||
}
|
||||
|
||||
// ===========================================
|
||||
// PASS 3: Repair offsets for additional cells
|
||||
|
||||
// Info<<"vertOffset: " << vertOffset_.size() << " VS. " << (mesh_.nCells()) << endl;
|
||||
// Info<<"nAddCells: " << nAddCells << " VS. " << (mesh_.nCells()) << endl;
|
||||
|
||||
if (nAddCells)
|
||||
{
|
||||
const label beg = mesh_.nCells();
|
||||
const label add = vertOffset_[beg-1];
|
||||
|
||||
for (label i = beg; i < vertOffset_.size(); ++i)
|
||||
{
|
||||
vertOffset_[i] += add;
|
||||
}
|
||||
}
|
||||
|
||||
// Some basic programming/sanity checks
|
||||
|
||||
if ((nVertLabels + nAddVerts) != vertOffset_[mesh_.nCells()-1 + nAddCells])
|
||||
{
|
||||
WarningInFunction
|
||||
<< "predicted offsets (" << nVertLabels << " + " << nAddVerts << ") != "
|
||||
<< vertOffset_[mesh_.nCells()-1 + nAddCells]
|
||||
<< endl;
|
||||
}
|
||||
|
||||
if (offsetAddVerts != vertOffset_[mesh_.nCells()-1])
|
||||
{
|
||||
WarningInFunction
|
||||
<< "predicted regular offset " << offsetAddVerts
|
||||
<< " != " << vertOffset_[mesh_.nCells()]
|
||||
<< endl;
|
||||
}
|
||||
|
||||
// nFaceLabels = 0;
|
||||
// nAddPoints = 0;
|
||||
// nAddCells = 0;
|
||||
|
||||
// Pout<<"vertLabels: " << vertLabels_.size() << " vs. " << (nVertLabels + nAddVerts) << endl;
|
||||
// Pout<<"faceLabels: " << faceLabels_.size() << " vs. " << nFaceLabels << endl;
|
||||
#if 0
|
||||
if (decompose_.requested())
|
||||
{
|
||||
Pout<< " Original cells:" << mesh_.nCells()
|
||||
<< " points:" << mesh_.nPoints()
|
||||
<< " Additional cells:" << decompose_.superCells_.size()
|
||||
<< " additional points:" << decompose_.addPointCellLabels_.size()
|
||||
<< nl << endl;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
|
||||
|
||||
Foam::foamVtkCells::decomp::decomp(const bool decomposePoly)
|
||||
Foam::foamVtkCells::foamVtkCells
|
||||
(
|
||||
const contentType output,
|
||||
const bool decompose
|
||||
)
|
||||
:
|
||||
addPointCellLabels_(),
|
||||
superCells_(),
|
||||
pointMap_(),
|
||||
requested_(decomposePoly)
|
||||
foamVtuSizing(),
|
||||
output_(output),
|
||||
decomposeRequest_(decompose),
|
||||
cellTypes_(),
|
||||
vertLabels_(),
|
||||
vertOffset_(),
|
||||
faceLabels_(),
|
||||
faceOffset_(),
|
||||
maps_()
|
||||
{}
|
||||
|
||||
|
||||
Foam::foamVtkCells::foamVtkCells
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const bool decomposePoly,
|
||||
const bool lazy
|
||||
const contentType output,
|
||||
const bool decompose
|
||||
)
|
||||
:
|
||||
mesh_(mesh),
|
||||
cellTypes_(),
|
||||
vertLabels_(),
|
||||
vertOffset_(),
|
||||
faceLabels_(),
|
||||
faceOffset_(),
|
||||
decompose_(decomposePoly),
|
||||
needsUpdate_(true)
|
||||
foamVtkCells(output, decompose)
|
||||
{
|
||||
if (!lazy)
|
||||
{
|
||||
correct();
|
||||
}
|
||||
reset(mesh);
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
|
||||
|
||||
Foam::foamVtkCells::decomp::~decomp()
|
||||
{}
|
||||
|
||||
|
||||
Foam::foamVtkCells::~foamVtkCells()
|
||||
{}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
|
||||
void Foam::foamVtkCells::decomp::clear()
|
||||
void Foam::foamVtkCells::clear()
|
||||
{
|
||||
superCells_.clear();
|
||||
addPointCellLabels_.clear();
|
||||
pointMap_.clear();
|
||||
foamVtuSizing::clear();
|
||||
cellTypes_.clear();
|
||||
vertLabels_.clear();
|
||||
vertOffset_.clear();
|
||||
faceLabels_.clear();
|
||||
faceOffset_.clear();
|
||||
|
||||
maps_.clear();
|
||||
}
|
||||
|
||||
|
||||
Foam::label Foam::foamVtkCells::nFieldPoints() const
|
||||
void Foam::foamVtkCells::reset(const polyMesh& mesh)
|
||||
{
|
||||
return mesh_.nPoints() + decompose_.addPointCellLabels_.size();
|
||||
}
|
||||
foamVtuSizing::reset(mesh, decomposeRequest_);
|
||||
|
||||
cellTypes_.setSize(nFieldCells());
|
||||
vertLabels_.setSize(slotSize(output_, slotType::CELLS));
|
||||
vertOffset_.setSize(slotSize(output_, slotType::CELLS_OFFSETS));
|
||||
faceLabels_.setSize(slotSize(output_, slotType::FACES));
|
||||
faceOffset_.setSize(slotSize(output_, slotType::FACES_OFFSETS));
|
||||
|
||||
Foam::label Foam::foamVtkCells::legacyCellPayLoad() const
|
||||
{
|
||||
label payLoad = cellTypes_.size();
|
||||
|
||||
if (faceOffset_.size())
|
||||
switch (output_)
|
||||
{
|
||||
// also has polys with face streams
|
||||
|
||||
label begVert = 0;
|
||||
label begFace = 0;
|
||||
|
||||
forAll(faceOffset_, i)
|
||||
{
|
||||
label endFace = faceOffset_[i];
|
||||
label endVert = vertOffset_[i];
|
||||
|
||||
if (endFace > 0)
|
||||
{
|
||||
// poly with face stream
|
||||
payLoad += endFace - begFace;
|
||||
|
||||
begFace = endFace;
|
||||
}
|
||||
else
|
||||
{
|
||||
// primitive without face stream
|
||||
payLoad += endVert - begVert;
|
||||
}
|
||||
begVert = endVert;
|
||||
}
|
||||
case contentType::LEGACY:
|
||||
populateLegacy
|
||||
(
|
||||
mesh,
|
||||
cellTypes_,
|
||||
vertLabels_,
|
||||
maps_
|
||||
);
|
||||
break;
|
||||
case contentType::XML:
|
||||
populateXml
|
||||
(
|
||||
mesh,
|
||||
cellTypes_,
|
||||
vertLabels_,
|
||||
vertOffset_,
|
||||
faceLabels_,
|
||||
faceOffset_,
|
||||
maps_
|
||||
);
|
||||
break;
|
||||
case contentType::INTERNAL:
|
||||
populateInternal
|
||||
(
|
||||
mesh,
|
||||
cellTypes_,
|
||||
vertLabels_,
|
||||
vertOffset_,
|
||||
faceLabels_,
|
||||
faceOffset_,
|
||||
maps_
|
||||
);
|
||||
break;
|
||||
}
|
||||
else if (vertOffset_.size())
|
||||
{
|
||||
// primitives only, trivial
|
||||
payLoad += vertOffset_[vertOffset_.size()-1];
|
||||
}
|
||||
|
||||
return payLoad;
|
||||
}
|
||||
|
||||
|
||||
bool Foam::foamVtkCells::needsUpdate() const
|
||||
void Foam::foamVtkCells::reset
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const enum contentType output,
|
||||
const bool decompose
|
||||
)
|
||||
{
|
||||
return needsUpdate_;
|
||||
output_ = output;
|
||||
decomposeRequest_ = decompose;
|
||||
|
||||
reset(mesh);
|
||||
}
|
||||
|
||||
|
||||
bool Foam::foamVtkCells::expire()
|
||||
void Foam::foamVtkCells::renumberCells(const UList<label>& mapping)
|
||||
{
|
||||
// Clear any stored topologies
|
||||
|
||||
// Clear derived data
|
||||
// clearGeom();
|
||||
|
||||
// already marked as expired
|
||||
if (needsUpdate_)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
needsUpdate_ = true;
|
||||
return true;
|
||||
maps_.renumberCells(mapping);
|
||||
}
|
||||
|
||||
|
||||
bool Foam::foamVtkCells::update()
|
||||
void Foam::foamVtkCells::renumberPoints(const UList<label>& mapping)
|
||||
{
|
||||
if (!needsUpdate_)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
correct();
|
||||
|
||||
needsUpdate_ = false;
|
||||
return true;
|
||||
maps_.renumberPoints(mapping);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2011-2016 OpenCFD Ltd.
|
||||
\\ / A nd | Copyright (C) 2011-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
@ -25,53 +25,32 @@ Class
|
||||
Foam::foamVtkCells
|
||||
|
||||
Description
|
||||
The deep-copy description of an OpenFOAM volume mesh in data structures
|
||||
corresponding to an VTK UnstructuredGrid, including the possiblity of
|
||||
A deep-copy description of an OpenFOAM volume mesh in data structures
|
||||
suitable for VTK UnstructuredGrid, including the possibility of
|
||||
decomposing polyhedral cells into primitive cell types.
|
||||
|
||||
Knowledge of the vtkUnstructuredGrid and the corresponding \c .vtu
|
||||
xml file-format aids in understanding this class.
|
||||
For flexibilty, support for the legacy vtk file-format is also provided.
|
||||
The class can be used for the VTK xml format, legacy format, as well as a
|
||||
VTK internal representation. The internal representation is somewhat
|
||||
related to the xml format, but not entirely.
|
||||
|
||||
Primitive cell types are straighforward, polyhedral cells are represented
|
||||
by a face stream:
|
||||
\verbatim
|
||||
[nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
\endverbatim
|
||||
|
||||
For the legacy format, the face stream is simply passed as vertex labels
|
||||
(connectivity).
|
||||
|
||||
For the xml format, the face stream is saved separately:
|
||||
\verbatim
|
||||
"connectivity"
|
||||
== the unique vertex labels used by the cell (optionally sorted).
|
||||
|
||||
"offsets":
|
||||
== offset + sizeof(connectivity)
|
||||
|
||||
"faces":
|
||||
[nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
|
||||
"faceoffsets":
|
||||
== faceoffsets + sizeof(faces)
|
||||
\endverbatim
|
||||
|
||||
The storage of "connectivity" and "offsets" strongly resembles a
|
||||
CompactListList, but the "offsets" point to the end of the respective
|
||||
sub-lists.
|
||||
SeeAlso
|
||||
Foam::foamVtuSizing
|
||||
|
||||
SourceFiles
|
||||
foamVtkCells.C
|
||||
foamVtkCellsI.H
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef foamVtkCells_H
|
||||
#define foamVtkCells_H
|
||||
|
||||
#include "foamVtkMeshMaps.H"
|
||||
#include "foamVtuSizing.H"
|
||||
#include "foamVtkCore.H"
|
||||
#include "DynamicList.H"
|
||||
#include "SubList.H"
|
||||
#include "labelList.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
@ -83,119 +62,48 @@ namespace Foam
|
||||
class polyMesh;
|
||||
|
||||
/*---------------------------------------------------------------------------*\
|
||||
Class foamVtkCells Declaration
|
||||
Class foamVtkCells Declaration
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
class foamVtkCells
|
||||
:
|
||||
public fileFormats::foamVtkCore
|
||||
public fileFormats::foamVtkCore,
|
||||
public foamVtuSizing
|
||||
{
|
||||
public:
|
||||
|
||||
//- Bookkeeping for polyhedral cell decomposition
|
||||
class decomp
|
||||
{
|
||||
private:
|
||||
friend foamVtkCells;
|
||||
|
||||
// Private data
|
||||
|
||||
//- Cell-centre labels for additional points of decomposed cells
|
||||
DynamicList<label> addPointCellLabels_;
|
||||
|
||||
//- Label of original cell for decomposed cells
|
||||
DynamicList<label> superCells_;
|
||||
|
||||
//- Point labels for subsetted meshes
|
||||
DynamicList<label> pointMap_;
|
||||
|
||||
//- Track if decomposition was requested
|
||||
const bool requested_;
|
||||
|
||||
|
||||
// Private Member Functions
|
||||
|
||||
//- Disallow default bitwise copy construct
|
||||
decomp(const decomp&) = delete;
|
||||
|
||||
//- Disallow default bitwise assignment
|
||||
void operator=(const decomp&) = delete;
|
||||
|
||||
public:
|
||||
|
||||
// Constructors
|
||||
|
||||
//- Construct null
|
||||
decomp(const bool decomposePoly = false);
|
||||
|
||||
|
||||
//- Destructor
|
||||
~decomp();
|
||||
|
||||
|
||||
// Member Functions
|
||||
|
||||
// Access
|
||||
|
||||
//- Polyhedral decomposition requested
|
||||
inline bool requested() const;
|
||||
|
||||
//- Polyhedral decomposition used
|
||||
inline bool used() const;
|
||||
|
||||
//- Label of original cell for decomposed cells
|
||||
inline const labelList& superCells() const;
|
||||
|
||||
//- Cell-centre labels for additional points of decomposed cells
|
||||
inline const labelList& addPointCellLabels() const;
|
||||
|
||||
//- Point labels for subsetted meshes
|
||||
inline const labelList& pointMap() const;
|
||||
|
||||
|
||||
// Edit
|
||||
|
||||
//- Clear
|
||||
void clear();
|
||||
};
|
||||
|
||||
|
||||
private:
|
||||
|
||||
// Private data
|
||||
|
||||
//- Reference to underlying mesh or mesh sub-set
|
||||
const polyMesh& mesh_;
|
||||
// Requested output types
|
||||
|
||||
//- Output content type
|
||||
contentType output_;
|
||||
|
||||
//- Bookkeeping for polyhedral cell decomposition
|
||||
bool decomposeRequest_;
|
||||
|
||||
// Storage of output
|
||||
|
||||
//- Cell types (including added cells) in vtk numbering
|
||||
// Range is 1-255
|
||||
List<uint8_t> cellTypes_;
|
||||
|
||||
//- Vertices per cell (including added cells) in vtk ordering
|
||||
DynamicList<label> vertLabels_;
|
||||
List<label> vertLabels_;
|
||||
|
||||
//- Vertices per cell (including added cells) in vtk ordering
|
||||
DynamicList<label> vertOffset_;
|
||||
//- Connectivity (vertices) offset for the end of each cell
|
||||
List<label> vertOffset_;
|
||||
|
||||
//- Face lists per polyhedral cell
|
||||
DynamicList<label> faceLabels_;
|
||||
List<label> faceLabels_;
|
||||
|
||||
//- Face label offsets
|
||||
DynamicList<label> faceOffset_;
|
||||
List<label> faceOffset_;
|
||||
|
||||
//- Bookkeeping for polyhedral cell decomposition
|
||||
decomp decompose_;
|
||||
|
||||
//- Needs update
|
||||
bool needsUpdate_;
|
||||
|
||||
foamVtkMeshMaps maps_;
|
||||
|
||||
|
||||
// Private Member Functions
|
||||
|
||||
//- Create the geometry
|
||||
void correct();
|
||||
|
||||
//- Disallow default bitwise copy construct
|
||||
foamVtkCells(const foamVtkCells&) = delete;
|
||||
|
||||
@ -208,13 +116,20 @@ public:
|
||||
// Constructors
|
||||
|
||||
//- Construct from components.
|
||||
// Optionally with polyhedral decomposition and/or lazy evaluation.
|
||||
// A 'lazy' evaluation avoids fully creation within the constructor.
|
||||
// Optionally with polyhedral decomposition.
|
||||
foamVtkCells
|
||||
(
|
||||
const polyMesh&,
|
||||
const bool decomposePoly = false,
|
||||
const bool lazy = false
|
||||
const enum contentType output = contentType::XML,
|
||||
const bool decompose = false
|
||||
);
|
||||
|
||||
//- Construct from components and create the output information
|
||||
// immediately
|
||||
foamVtkCells
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const enum contentType output = contentType::XML,
|
||||
const bool decompose = false
|
||||
);
|
||||
|
||||
|
||||
@ -224,113 +139,68 @@ public:
|
||||
|
||||
// Member Functions
|
||||
|
||||
// Access
|
||||
// Access
|
||||
|
||||
//- Query the poly decompose flag.
|
||||
inline bool decomposeRequested() const;
|
||||
//- The output content type
|
||||
inline enum contentType content() const;
|
||||
|
||||
//- Values for "connectivity" (XML) or basis for "CELLS" (legacy)
|
||||
// In the legacy format, the size (offset) must be prefixed.
|
||||
inline const labelList& vertLabels() const;
|
||||
//- Query the polyhedral decompose requested flag.
|
||||
inline bool decomposeRequested() const;
|
||||
|
||||
//- Values for "offsets" (XML)
|
||||
// or sizes to prefix for for "CELLS" (legacy)
|
||||
inline const labelList& vertOffsets() const;
|
||||
//- True if no cellTypes are populated.
|
||||
inline bool empty() const;
|
||||
|
||||
//- Values for "types" (XML) and "CELL_TYPES" (legacy)
|
||||
inline const List<uint8_t>& cellTypes() const;
|
||||
|
||||
//- Values for "faces" (XML)
|
||||
inline const labelList& faceLabels() const;
|
||||
|
||||
//- Values for "faceoffsets" (XML)
|
||||
inline const labelList& faceOffsets() const;
|
||||
|
||||
//- Additional point addressing (from added point to original cell)
|
||||
inline const labelList& addPointCellLabels() const;
|
||||
|
||||
//- Additional cells mapping (from added cell to original cell)
|
||||
inline const labelList& superCells() const;
|
||||
//- The size of populated cellTypes.
|
||||
inline label size() const;
|
||||
|
||||
|
||||
//- Number of field cells
|
||||
inline label nFieldCells() const;
|
||||
// Edit
|
||||
|
||||
//- Number of field points
|
||||
label nFieldPoints() const;
|
||||
//- Reset all sizes to zero.
|
||||
void clear();
|
||||
|
||||
//- The field size for legacy "CELLS".
|
||||
// In the legacy format, the size (offset) must be prefixed.
|
||||
label legacyCellPayLoad() const;
|
||||
//- Create the geometry using the previously requested output and
|
||||
// decomposition types.
|
||||
void reset(const polyMesh& mesh);
|
||||
|
||||
//- Respecify requested output and decomposition type prior to
|
||||
// creating the geometry
|
||||
void reset
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const enum contentType output,
|
||||
const bool decompose
|
||||
);
|
||||
|
||||
//- Renumber cell ids to account for subset meshes
|
||||
void renumberCells(const UList<label>& mapping);
|
||||
|
||||
//- Renumber point ids to account for subset meshes
|
||||
void renumberPoints(const UList<label>& mapping);
|
||||
|
||||
|
||||
//- Does the mapping need an update?
|
||||
bool needsUpdate() const;
|
||||
// Storage Access
|
||||
|
||||
//- Mark as needing an update.
|
||||
// May also free up unneeded data.
|
||||
// Return false if it was already marked as expired.
|
||||
bool expire();
|
||||
//- Values for "types" (XML) and "CELL_TYPES" (legacy)
|
||||
inline const List<uint8_t>& cellTypes() const;
|
||||
|
||||
//- Update the description (and decomposition) as required.
|
||||
// Do nothing (and return false) if no update was required
|
||||
bool update();
|
||||
//- Values for "connectivity" (XML) or "CELLS" (legacy)
|
||||
inline const labelList& vertLabels() const;
|
||||
|
||||
//- Values for "offsets" (XML only)
|
||||
inline const labelList& vertOffsets() const;
|
||||
|
||||
//- The const_iterator for foamVtkCells
|
||||
class const_iterator
|
||||
{
|
||||
friend class foamVtkCells;
|
||||
//- Values for "faces" (XML only)
|
||||
inline const labelList& faceLabels() const;
|
||||
|
||||
protected:
|
||||
//- Values for "faceoffset" (XML only)
|
||||
inline const labelList& faceOffsets() const;
|
||||
|
||||
// Protected Data
|
||||
//- Additional point addressing (from added point to original cell)
|
||||
inline const labelList& addPointCellLabels() const;
|
||||
|
||||
//- Reference to parent list
|
||||
const foamVtkCells& parent_;
|
||||
|
||||
//- Element index
|
||||
label index_;
|
||||
|
||||
//- Begin of connectivity sub-list
|
||||
mutable label begVert_;
|
||||
|
||||
//- Begin of faces sub-list
|
||||
mutable label begFace_;
|
||||
|
||||
//- On-demand legacy pointer
|
||||
mutable autoPtr<SubList<label>> legacy_;
|
||||
|
||||
|
||||
// Constructors
|
||||
|
||||
//- Construct begin/end iterator
|
||||
inline const_iterator
|
||||
(
|
||||
const foamVtkCells&,
|
||||
bool isEnd = false
|
||||
);
|
||||
|
||||
public:
|
||||
|
||||
// Member operators
|
||||
|
||||
//- On-demand legacy cell labels (primitive or faces)
|
||||
inline const labelUList& legacyCell() const;
|
||||
|
||||
//- Compare position
|
||||
inline bool operator!=(const const_iterator&) const;
|
||||
|
||||
//- Pre-increment iterator
|
||||
inline const_iterator& operator++();
|
||||
};
|
||||
|
||||
|
||||
//- const_iterator set to the beginning
|
||||
inline const_iterator begin() const;
|
||||
|
||||
//- const_iterator set to beyond the end
|
||||
inline const_iterator end() const;
|
||||
//- Original cell ids for all cells (regular and decomposed).
|
||||
inline const labelList& cellMap() const;
|
||||
|
||||
};
|
||||
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd.
|
||||
\\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
@ -25,44 +25,37 @@ License
|
||||
|
||||
#include "foamVtkCells.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
inline bool Foam::foamVtkCells::decomp::requested() const
|
||||
|
||||
inline enum Foam::foamVtkCells::contentType Foam::foamVtkCells::content() const
|
||||
{
|
||||
return requested_;
|
||||
}
|
||||
|
||||
|
||||
inline bool Foam::foamVtkCells::decomp::used() const
|
||||
{
|
||||
return !superCells_.empty();
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::decomp::superCells() const
|
||||
{
|
||||
return superCells_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::decomp::addPointCellLabels() const
|
||||
{
|
||||
return addPointCellLabels_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::decomp::pointMap() const
|
||||
{
|
||||
return pointMap_;
|
||||
return output_;
|
||||
}
|
||||
|
||||
|
||||
inline bool Foam::foamVtkCells::decomposeRequested() const
|
||||
{
|
||||
return decompose_.requested();
|
||||
return decomposeRequest_;
|
||||
}
|
||||
|
||||
|
||||
inline bool Foam::foamVtkCells::empty() const
|
||||
{
|
||||
return cellTypes_.empty();
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtkCells::size() const
|
||||
{
|
||||
return cellTypes_.size();
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::List<uint8_t>&
|
||||
Foam::foamVtkCells::cellTypes() const
|
||||
{
|
||||
return cellTypes_;
|
||||
}
|
||||
|
||||
|
||||
@ -80,13 +73,6 @@ Foam::foamVtkCells::vertOffsets() const
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::List<uint8_t>&
|
||||
Foam::foamVtkCells::cellTypes() const
|
||||
{
|
||||
return cellTypes_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::faceLabels() const
|
||||
{
|
||||
@ -104,135 +90,14 @@ Foam::foamVtkCells::faceOffsets() const
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::addPointCellLabels() const
|
||||
{
|
||||
return decompose_.addPointCellLabels();
|
||||
return maps_.additionalIds();
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkCells::superCells() const
|
||||
Foam::foamVtkCells::cellMap() const
|
||||
{
|
||||
return decompose_.superCells();
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label
|
||||
Foam::foamVtkCells::nFieldCells() const
|
||||
{
|
||||
return cellTypes_.size();
|
||||
}
|
||||
|
||||
|
||||
inline Foam::foamVtkCells::const_iterator
|
||||
Foam::foamVtkCells::begin() const
|
||||
{
|
||||
return const_iterator(*this);
|
||||
}
|
||||
|
||||
|
||||
inline Foam::foamVtkCells::const_iterator
|
||||
Foam::foamVtkCells::end() const
|
||||
{
|
||||
return const_iterator(*this, true);
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Iterators * * * * * * * * * * * * * * * * //
|
||||
|
||||
inline Foam::foamVtkCells::const_iterator::const_iterator
|
||||
(
|
||||
const foamVtkCells& cells,
|
||||
bool isEnd
|
||||
)
|
||||
:
|
||||
parent_(cells),
|
||||
index_(0),
|
||||
begVert_(0),
|
||||
begFace_(0),
|
||||
legacy_()
|
||||
{
|
||||
if (isEnd)
|
||||
{
|
||||
index_ = parent_.vertOffsets().size();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
inline
|
||||
Foam::foamVtkCells::const_iterator&
|
||||
Foam::foamVtkCells::const_iterator::operator++()
|
||||
{
|
||||
++index_;
|
||||
legacy_.clear();
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
inline
|
||||
const Foam::UList<Foam::label>&
|
||||
Foam::foamVtkCells::const_iterator::legacyCell() const
|
||||
{
|
||||
if
|
||||
(
|
||||
legacy_.valid()
|
||||
|| index_ >= parent_.vertOffsets().size()
|
||||
)
|
||||
{
|
||||
return legacy_();
|
||||
}
|
||||
|
||||
const label endVert = parent_.vertOffsets()[index_];
|
||||
|
||||
const label endFace =
|
||||
(
|
||||
parent_.faceOffsets().size()
|
||||
? parent_.faceOffsets()[index_]
|
||||
: -1
|
||||
);
|
||||
|
||||
if (endFace > 0)
|
||||
{
|
||||
// poly with face stream
|
||||
|
||||
legacy_.reset
|
||||
(
|
||||
new SubList<label>
|
||||
(
|
||||
parent_.faceLabels(),
|
||||
endFace - begFace_,
|
||||
begFace_
|
||||
)
|
||||
);
|
||||
|
||||
begFace_ = endFace;
|
||||
}
|
||||
else
|
||||
{
|
||||
// primitive without face stream
|
||||
legacy_.reset
|
||||
(
|
||||
new SubList<label>
|
||||
(
|
||||
parent_.vertLabels(),
|
||||
endVert - begVert_,
|
||||
begVert_
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
begVert_ = endVert;
|
||||
|
||||
return legacy_();
|
||||
}
|
||||
|
||||
|
||||
inline bool
|
||||
Foam::foamVtkCells::const_iterator::operator!=
|
||||
(
|
||||
const const_iterator& rhs
|
||||
) const
|
||||
{
|
||||
return (index_ != rhs.index_);
|
||||
return maps_.cellMap();
|
||||
}
|
||||
|
||||
|
||||
|
||||
44
src/conversion/vtk/part/foamVtkMeshMaps.C
Normal file
44
src/conversion/vtk/part/foamVtkMeshMaps.C
Normal file
@ -0,0 +1,44 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "foamVtkMeshMaps.H"
|
||||
#include "ListOps.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
void Foam::foamVtkMeshMaps::renumberCells(const UList<label>& mapping)
|
||||
{
|
||||
inplaceRenumber(mapping, cellMap_);
|
||||
inplaceRenumber(mapping, additionalIds_);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtkMeshMaps::renumberPoints(const UList<label>& mapping)
|
||||
{
|
||||
inplaceRenumber(mapping, pointMap_);
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
139
src/conversion/vtk/part/foamVtkMeshMaps.H
Normal file
139
src/conversion/vtk/part/foamVtkMeshMaps.H
Normal file
@ -0,0 +1,139 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Class
|
||||
Foam::foamVtkMeshMaps
|
||||
|
||||
Description
|
||||
Bookkeeping for mesh subsetting and/or polyhedral cell decomposition.
|
||||
|
||||
The cellMap is a local-to-global lookup for normal and decomposed cells.
|
||||
The pointMap is an optional local-to-global lookup for point ids.
|
||||
The additional ids is typically used to store the cell-centre labels
|
||||
for additional points of decomposed cells
|
||||
|
||||
SourceFiles
|
||||
foamVtkMeshMapsI.H
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef foamVtkMeshMaps_H
|
||||
#define foamVtkMeshMaps_H
|
||||
|
||||
#include "DynamicList.H"
|
||||
#include "labelList.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
namespace Foam
|
||||
{
|
||||
|
||||
/*---------------------------------------------------------------------------*\
|
||||
Class foamVtkMeshMaps Declaration
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
class foamVtkMeshMaps
|
||||
{
|
||||
// Private data
|
||||
|
||||
//- Original cell ids for all cells (regular and decomposed)
|
||||
DynamicList<label> cellMap_;
|
||||
|
||||
//- Point labels for subsetted meshes
|
||||
DynamicList<label> pointMap_;
|
||||
|
||||
//- Any additional (user) labels.
|
||||
// Eg, cell-centre labels for additional points of decomposed cells
|
||||
DynamicList<label> additionalIds_;
|
||||
|
||||
public:
|
||||
|
||||
// Constructors
|
||||
|
||||
//- Construct null
|
||||
inline foamVtkMeshMaps(const label size = 0);
|
||||
|
||||
|
||||
//- Destructor
|
||||
inline ~foamVtkMeshMaps();
|
||||
|
||||
|
||||
// Member Functions
|
||||
|
||||
// Access
|
||||
|
||||
//- Original cell ids for all cells (regular and decomposed).
|
||||
// A regular mesh comprising only primitive cell types, this will just
|
||||
// be an identity list. However, for subsetted meshes and decomposed
|
||||
// cells this becomes a useful means of mapping from the original mesh.
|
||||
inline const labelList& cellMap() const;
|
||||
|
||||
//- Point labels for subsetted meshes
|
||||
inline const labelList& pointMap() const;
|
||||
|
||||
//- Any additional (user) labels.
|
||||
// Eg, cell-centre labels for additional points of decomposed cells
|
||||
inline const labelList& additionalIds() const;
|
||||
|
||||
|
||||
// Edit
|
||||
|
||||
//- Clear
|
||||
inline void clear();
|
||||
|
||||
//- Renumber cell ids to account for subset meshes
|
||||
void renumberCells(const UList<label>& mapping);
|
||||
|
||||
//- Renumber point ids to account for subset meshes
|
||||
void renumberPoints(const UList<label>& mapping);
|
||||
|
||||
|
||||
//- Original cell ids for all cells (regular and decomposed).
|
||||
// A regular mesh comprising only primitive cell types, this will just
|
||||
// be an identity list. However, for subsetted meshes and decomposed
|
||||
// cells this becomes a useful means of mapping from the original mesh.
|
||||
inline DynamicList<label>& cellMap();
|
||||
|
||||
//- Point labels for subsetted meshes
|
||||
inline DynamicList<label>& pointMap();
|
||||
|
||||
//- Any additional (user) labels.
|
||||
// Eg, cell-centre labels for additional points of decomposed cells
|
||||
inline DynamicList<label>& additionalIds();
|
||||
|
||||
};
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
} // End namespace Foam
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#include "foamVtkMeshMapsI.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#endif
|
||||
|
||||
// ************************************************************************* //
|
||||
96
src/conversion/vtk/part/foamVtkMeshMapsI.H
Normal file
96
src/conversion/vtk/part/foamVtkMeshMapsI.H
Normal file
@ -0,0 +1,96 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "foamVtkMeshMaps.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
|
||||
|
||||
inline Foam::foamVtkMeshMaps::foamVtkMeshMaps(const label size)
|
||||
:
|
||||
cellMap_(size),
|
||||
pointMap_(size),
|
||||
additionalIds_(size)
|
||||
{}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
|
||||
|
||||
inline Foam::foamVtkMeshMaps::~foamVtkMeshMaps()
|
||||
{}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
inline void Foam::foamVtkMeshMaps::clear()
|
||||
{
|
||||
cellMap_.clear();
|
||||
pointMap_.clear();
|
||||
additionalIds_.clear();
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkMeshMaps::cellMap() const
|
||||
{
|
||||
return cellMap_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::DynamicList<Foam::label>&
|
||||
Foam::foamVtkMeshMaps::cellMap()
|
||||
{
|
||||
return cellMap_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkMeshMaps::pointMap() const
|
||||
{
|
||||
return pointMap_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::DynamicList<Foam::label>&
|
||||
Foam::foamVtkMeshMaps::pointMap()
|
||||
{
|
||||
return pointMap_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::labelList&
|
||||
Foam::foamVtkMeshMaps::additionalIds() const
|
||||
{
|
||||
return additionalIds_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::DynamicList<Foam::label>&
|
||||
Foam::foamVtkMeshMaps::additionalIds()
|
||||
{
|
||||
return additionalIds_;
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
578
src/conversion/vtk/part/foamVtuSizing.C
Normal file
578
src/conversion/vtk/part/foamVtuSizing.C
Normal file
@ -0,0 +1,578 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "foamVtuSizing.H"
|
||||
#include "foamVtkCore.H"
|
||||
#include "polyMesh.H"
|
||||
#include "cellShape.H"
|
||||
#include "cellModeller.H"
|
||||
|
||||
// only used in this file
|
||||
#include "foamVtuSizingTemplates.C"
|
||||
|
||||
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
||||
|
||||
void Foam::foamVtuSizing::presizeMaps(foamVtkMeshMaps& maps) const
|
||||
{
|
||||
maps.cellMap().setSize(this->nFieldCells());
|
||||
maps.additionalIds().setSize(this->nAddPoints());
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
|
||||
|
||||
Foam::foamVtuSizing::foamVtuSizing
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const bool decompose
|
||||
)
|
||||
{
|
||||
clear();
|
||||
reset(mesh, decompose);
|
||||
}
|
||||
|
||||
|
||||
Foam::foamVtuSizing::foamVtuSizing()
|
||||
{
|
||||
clear();
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
|
||||
|
||||
Foam::foamVtuSizing::~foamVtuSizing()
|
||||
{}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
void Foam::foamVtuSizing::reset
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const bool decompose
|
||||
)
|
||||
{
|
||||
const cellModel& tet = *(cellModeller::lookup("tet"));
|
||||
const cellModel& pyr = *(cellModeller::lookup("pyr"));
|
||||
const cellModel& prism = *(cellModeller::lookup("prism"));
|
||||
const cellModel& wedge = *(cellModeller::lookup("wedge"));
|
||||
const cellModel& tetWedge = *(cellModeller::lookup("tetWedge"));
|
||||
const cellModel& hex = *(cellModeller::lookup("hex"));
|
||||
|
||||
const cellShapeList& shapes = mesh.cellShapes();
|
||||
|
||||
// Unique vertex labels per polyhedral
|
||||
HashSet<label> hashUniqId(2*256);
|
||||
|
||||
decompose_ = decompose;
|
||||
nCells_ = mesh.nCells();
|
||||
nPoints_ = mesh.nPoints();
|
||||
nAddCells_ = 0;
|
||||
nAddVerts_ = 0;
|
||||
|
||||
nCellsPoly_ = nCells_;
|
||||
nVertLabels_ = 0;
|
||||
nFaceLabels_ = 0;
|
||||
nVertPoly_ = 0;
|
||||
|
||||
forAll(shapes, celli)
|
||||
{
|
||||
const cellShape& shape = shapes[celli];
|
||||
const cellModel& model = shape.model();
|
||||
|
||||
if
|
||||
(
|
||||
model == tet
|
||||
|| model == pyr
|
||||
|| model == prism
|
||||
|| model == hex
|
||||
)
|
||||
{
|
||||
// Normal primitive - not a poly
|
||||
--nCellsPoly_;
|
||||
nVertLabels_ += shape.size();
|
||||
}
|
||||
else if (model == tetWedge && decompose)
|
||||
{
|
||||
nVertLabels_ += 6; // Treat as squeezed prism (VTK_WEDGE)
|
||||
}
|
||||
else if (model == wedge && decompose)
|
||||
{
|
||||
nVertLabels_ += 8; // Treat as squeezed hex
|
||||
}
|
||||
else if (decompose)
|
||||
{
|
||||
// Polyhedral: Decompose into tets + pyramids.
|
||||
++nAddPoints_;
|
||||
|
||||
// Count vertices into first decomposed cell
|
||||
bool first = true;
|
||||
|
||||
const cell& cFaces = mesh.cells()[celli];
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh.faces()[cFaces[cFaceI]];
|
||||
|
||||
// Face decomposed into triangles and quads
|
||||
// Tri -> Tet, Quad -> Pyr
|
||||
label nTria = 0, nQuad = 0;
|
||||
f.nTrianglesQuads(mesh.points(), nTria, nQuad);
|
||||
|
||||
nAddCells_ += nTria + nQuad;
|
||||
nAddVerts_ += (nTria * 4) + (nQuad * 5);
|
||||
|
||||
if (first)
|
||||
{
|
||||
first = false;
|
||||
--nAddCells_;
|
||||
|
||||
const label nvrt = (nQuad ? 5 : 4);
|
||||
nAddVerts_ -= nvrt;
|
||||
nVertLabels_ += nvrt;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Polyhedral: Not decomposed
|
||||
|
||||
const labelList& cFaces = mesh.cells()[celli];
|
||||
|
||||
// Unique node ids used (only needed for XML)
|
||||
hashUniqId.clear();
|
||||
|
||||
// Face stream sizing:
|
||||
// number of faces, size of each face, vertices per face
|
||||
// [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh.faces()[cFaces[cFaceI]];
|
||||
nFaceLabels_ += f.size();
|
||||
|
||||
hashUniqId.insert(f);
|
||||
}
|
||||
|
||||
// Legacy format only uses the face-stream.
|
||||
// - track what *NOT* to use for legacy
|
||||
nVertLabels_ += hashUniqId.size();
|
||||
nVertPoly_ += hashUniqId.size();
|
||||
|
||||
nFaceLabels_ += 1 + cFaces.size();
|
||||
}
|
||||
}
|
||||
|
||||
// decompose requested and needed
|
||||
decompose_ = (decompose && nCellsPoly_);
|
||||
}
|
||||
|
||||
|
||||
Foam::label Foam::foamVtuSizing::slotSize
|
||||
(
|
||||
const enum contentType output,
|
||||
const enum slotType slot
|
||||
) const
|
||||
{
|
||||
switch (output)
|
||||
{
|
||||
case contentType::LEGACY:
|
||||
{
|
||||
switch (slot)
|
||||
{
|
||||
case slotType::CELLS:
|
||||
// legacy uses connectivity for primitives, but directly
|
||||
// stores face streams into connectivity as well.
|
||||
// size-prefix per cell
|
||||
return
|
||||
(
|
||||
nVertLabels() + nAddVerts() - nVertPoly() // primitives
|
||||
+ nFaceLabels() // face-stream (poly)
|
||||
+ nFieldCells() // nFieldCells (size prefix)
|
||||
);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case contentType::XML:
|
||||
{
|
||||
switch (slot)
|
||||
{
|
||||
case slotType::CELLS:
|
||||
return (nVertLabels() + nAddVerts());
|
||||
break;
|
||||
|
||||
case slotType::CELLS_OFFSETS:
|
||||
return nFieldCells();
|
||||
break;
|
||||
|
||||
case slotType::FACES:
|
||||
return nFaceLabels();
|
||||
break;
|
||||
|
||||
case slotType::FACES_OFFSETS:
|
||||
return nFaceLabels() ? nFieldCells() : 0;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case contentType::INTERNAL:
|
||||
{
|
||||
switch (slot)
|
||||
{
|
||||
case slotType::CELLS:
|
||||
// size-prefix per cell
|
||||
return (nVertLabels() + nAddVerts() + nFieldCells());
|
||||
break;
|
||||
|
||||
case slotType::CELLS_OFFSETS:
|
||||
return nFieldCells();
|
||||
break;
|
||||
|
||||
case slotType::FACES:
|
||||
return nFaceLabels();
|
||||
break;
|
||||
|
||||
case slotType::FACES_OFFSETS:
|
||||
return nFaceLabels() ? nFieldCells() : 0;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateLegacy
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<label>& vertLabels,
|
||||
foamVtkMeshMaps& maps
|
||||
) const
|
||||
{
|
||||
// Leave as zero-sized so that populateArrays doesn't fill it.
|
||||
List<label> unused;
|
||||
|
||||
presizeMaps(maps);
|
||||
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
vertLabels,
|
||||
unused, // offsets
|
||||
unused, // faces
|
||||
unused, // facesOffsets
|
||||
contentType::LEGACY,
|
||||
maps.cellMap(),
|
||||
maps.additionalIds()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateXml
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<label>& connectivity,
|
||||
UList<label>& offsets,
|
||||
UList<label>& faces,
|
||||
UList<label>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const
|
||||
{
|
||||
presizeMaps(maps);
|
||||
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::XML,
|
||||
maps.cellMap(),
|
||||
maps.additionalIds()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<int>& connectivity,
|
||||
UList<int>& offsets,
|
||||
UList<int>& faces,
|
||||
UList<int>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const
|
||||
{
|
||||
presizeMaps(maps);
|
||||
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
maps.cellMap(),
|
||||
maps.additionalIds()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long>& connectivity,
|
||||
UList<long>& offsets,
|
||||
UList<long>& faces,
|
||||
UList<long>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const
|
||||
{
|
||||
presizeMaps(maps);
|
||||
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
maps.cellMap(),
|
||||
maps.additionalIds()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long long>& connectivity,
|
||||
UList<long long>& offsets,
|
||||
UList<long long>& faces,
|
||||
UList<long long>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const
|
||||
{
|
||||
presizeMaps(maps);
|
||||
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
maps.cellMap(),
|
||||
maps.additionalIds()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<int>& connectivity,
|
||||
UList<int>& offsets,
|
||||
UList<int>& faces,
|
||||
UList<int>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const
|
||||
{
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
cellMap,
|
||||
addPointsIds
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long>& connectivity,
|
||||
UList<long>& offsets,
|
||||
UList<long>& faces,
|
||||
UList<long>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const
|
||||
{
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
cellMap,
|
||||
addPointsIds
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long long>& connectivity,
|
||||
UList<long long>& offsets,
|
||||
UList<long long>& faces,
|
||||
UList<long long>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const
|
||||
{
|
||||
populateArrays
|
||||
(
|
||||
mesh,
|
||||
*this,
|
||||
cellTypes,
|
||||
connectivity,
|
||||
offsets,
|
||||
faces,
|
||||
facesOffsets,
|
||||
contentType::INTERNAL,
|
||||
cellMap,
|
||||
addPointsIds
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::clear()
|
||||
{
|
||||
decompose_ = false;
|
||||
nCells_ = 0;
|
||||
nPoints_ = 0;
|
||||
nVertLabels_ = 0;
|
||||
|
||||
nFaceLabels_ = 0;
|
||||
nCellsPoly_ = 0;
|
||||
nVertPoly_ = 0;
|
||||
|
||||
nAddCells_ = 0;
|
||||
nAddPoints_ = 0;
|
||||
nAddVerts_ = 0;
|
||||
}
|
||||
|
||||
|
||||
void Foam::foamVtuSizing::info(Ostream& os) const
|
||||
{
|
||||
os << "nFieldCells:" << nFieldCells();
|
||||
if (nAddCells_)
|
||||
{
|
||||
os << " (" << nCells_
|
||||
<< "+" << nAddCells_ << ")";
|
||||
}
|
||||
else
|
||||
{
|
||||
os << " (poly:" << nCellsPoly_ << ")";
|
||||
}
|
||||
|
||||
os << " nFieldPoints:" << nFieldPoints();
|
||||
if (nAddPoints_)
|
||||
{
|
||||
os << " (" << nPoints_ << "+" << nAddPoints_ << ")";
|
||||
}
|
||||
|
||||
os << " nVertLabels:" << (nVertLabels_ + nAddVerts_);
|
||||
if (nAddVerts_)
|
||||
{
|
||||
os << " (" << nVertLabels_ << "+" << nAddVerts_ << ")";
|
||||
}
|
||||
else if (nVertPoly_)
|
||||
{
|
||||
os << " (poly:" << nVertPoly_ << ")";
|
||||
}
|
||||
|
||||
os << " nFaceLabels:" << nFaceLabels_;
|
||||
os << " legacy-count:" << sizeLegacy();
|
||||
}
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
|
||||
|
||||
bool Foam::foamVtuSizing::operator==(const foamVtuSizing& rhs) const
|
||||
{
|
||||
return
|
||||
(
|
||||
decompose() == rhs.decompose()
|
||||
&& nCells() == rhs.nCells()
|
||||
&& nPoints() == rhs.nPoints()
|
||||
&& nVertLabels() == rhs.nVertLabels()
|
||||
&& nFaceLabels() == rhs.nFaceLabels()
|
||||
&& nCellsPoly() == rhs.nCellsPoly()
|
||||
&& nVertPoly() == rhs.nVertPoly()
|
||||
&& nAddCells() == rhs.nAddCells()
|
||||
&& nAddPoints() == rhs.nAddPoints()
|
||||
&& nAddVerts() == rhs.nAddVerts()
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
bool Foam::foamVtuSizing::operator!=(const foamVtuSizing& rhs) const
|
||||
{
|
||||
return !operator==(rhs);
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
408
src/conversion/vtk/part/foamVtuSizing.H
Normal file
408
src/conversion/vtk/part/foamVtuSizing.H
Normal file
@ -0,0 +1,408 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Class
|
||||
Foam::foamVtuSizing
|
||||
|
||||
Description
|
||||
Sizing descriptions and routines for transcribing an OpenFOAM volume mesh
|
||||
into a VTK unstructured grid, with possible decomposition of polyhedral
|
||||
cells into primitive cell types.
|
||||
|
||||
This class is intended to populate externally allocated arrays with content
|
||||
that is compatible with what VTK expects. This approach allows an improved
|
||||
separation of the OpenFOAM mesh description and the storage, and allows
|
||||
support of alternative storage containers (eg, std::vector, vtkDataArray).
|
||||
The ideal goal would be a zero-copy mechanism, but this does not work for
|
||||
several reasons:
|
||||
\par
|
||||
- OpenFOAM and VTK have different point ordering for prism
|
||||
- polyhedral decomposition
|
||||
- face-stream are required for VTK
|
||||
- VTK internal storage includes list size as part of the data
|
||||
- VTK includes storage may be a different base size (eg, long long)
|
||||
compared to the OpenFOAM label.
|
||||
|
||||
\par Data Entries (slots)
|
||||
|
||||
These are the storage entries normally associate with each output-type:
|
||||
\table
|
||||
legacy output
|
||||
\c types | vtk cell type (1-255)
|
||||
\c cells | nLabels and unique vertex labels used by the cell, or
|
||||
| [nLabels nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
\endtable
|
||||
|
||||
\table
|
||||
xml output
|
||||
\c types | vtk cell type (1-255)
|
||||
\c connectivity | unique vertex labels used by the cell
|
||||
\c offsets | end offset for each of \c connectivity
|
||||
\c faces | face stream for polyhedral cells
|
||||
| [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
\c faceoffsets | end offset for each of \c faces, with -1 for primitive cells
|
||||
\endtable
|
||||
|
||||
\table
|
||||
internal storage
|
||||
\c types | vtk cell type (1-255)
|
||||
\c connectivity | nLabels and unique vertex labels used by the cell
|
||||
\c location | begin location for each of \c connectivity
|
||||
\c faces | face stream for polyhedral cells
|
||||
| [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
\c facelocation | begin location for each of \c faces, with -1 for primitive cells
|
||||
\endtable
|
||||
|
||||
The VTK storage concept for "connectivity" and "faces" somewhat resemble
|
||||
a CompactListList.
|
||||
|
||||
SourceFiles
|
||||
foamVtuSizing.C
|
||||
foamVtuSizingI.H
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef foamVtuSizing_H
|
||||
#define foamVtuSizing_H
|
||||
|
||||
#include "label.H"
|
||||
#include "labelList.H"
|
||||
#include "foamVtkMeshMaps.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
namespace Foam
|
||||
{
|
||||
|
||||
// Forward declaration of classes
|
||||
class polyMesh;
|
||||
|
||||
/*---------------------------------------------------------------------------*\
|
||||
Class foamVtuSizing Declaration
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
class foamVtuSizing
|
||||
{
|
||||
public:
|
||||
|
||||
// Public data
|
||||
|
||||
//- Types of content that the storage may represent
|
||||
enum contentType
|
||||
{
|
||||
LEGACY, //!< Legacy VTK content
|
||||
XML, //!< XML (VTU) content
|
||||
INTERNAL //!< Internal vtkUnstructuredGrid content
|
||||
};
|
||||
|
||||
//- The storage 'slots' required
|
||||
enum slotType
|
||||
{
|
||||
CELLS, //!< Cell connectivity (ALL)
|
||||
CELLS_OFFSETS, //!< Begin (XML) or end (INTERNAL) offsets into cells
|
||||
FACES, //!< Face-stream (XML, INTERNAL)
|
||||
FACES_OFFSETS //!< Begin (XML) or end (INTERNAL) offsets into faces
|
||||
};
|
||||
|
||||
private:
|
||||
|
||||
// Private Member Data
|
||||
|
||||
//- Polyhedral decomposition requested
|
||||
bool decompose_;
|
||||
|
||||
//- Number of cells in the mesh
|
||||
label nCells_;
|
||||
|
||||
//- Number of points in the mesh
|
||||
label nPoints_;
|
||||
|
||||
//- Number of vertex labels to represent the mesh
|
||||
label nVertLabels_;
|
||||
|
||||
// Polyhedrals
|
||||
|
||||
//- Number of polyhedral face labels for the mesh
|
||||
label nFaceLabels_;
|
||||
|
||||
//- Number of polyhedral cells (informational)
|
||||
label nCellsPoly_;
|
||||
|
||||
//- Number of vertex labels used by polyhedrals
|
||||
label nVertPoly_;
|
||||
|
||||
// Decomposed polyhedrals
|
||||
|
||||
//- Number of additional (decomposed) cells for the mesh
|
||||
label nAddCells_;
|
||||
|
||||
//- Number of additional (decomposed) points for the mesh
|
||||
label nAddPoints_;
|
||||
|
||||
//- Number of additional (decomposed) vertices for the mesh
|
||||
label nAddVerts_;
|
||||
|
||||
|
||||
// Private Member Functions
|
||||
|
||||
//- set-size for cellMap and additionalIds
|
||||
void presizeMaps(foamVtkMeshMaps& maps) const;
|
||||
|
||||
//- Populate lists for internal VTK representation
|
||||
template<class LabelType, class LabelType2>
|
||||
static void populateArrays
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const foamVtuSizing& sizing,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<LabelType>& vertLabels,
|
||||
UList<LabelType>& vertOffset,
|
||||
UList<LabelType>& faceLabels,
|
||||
UList<LabelType>& faceOffset,
|
||||
const enum contentType output,
|
||||
UList<LabelType2>& cellMap,
|
||||
UList<LabelType2>& addPointsIds
|
||||
);
|
||||
|
||||
// Allow default bitwise copy/assignment
|
||||
|
||||
public:
|
||||
|
||||
// Constructors
|
||||
|
||||
//- Construct null.
|
||||
foamVtuSizing();
|
||||
|
||||
//- Construct sizes by analyzing the mesh,
|
||||
// optionally with polyhedral decomposition.
|
||||
foamVtuSizing(const polyMesh& mesh, const bool decompose=false);
|
||||
|
||||
|
||||
//- Destructor
|
||||
~foamVtuSizing();
|
||||
|
||||
|
||||
// Member Functions
|
||||
|
||||
// Edit
|
||||
|
||||
//- Construct sizes by analyzing the mesh,
|
||||
// optionally with polyhedral decomposition.
|
||||
void reset(const polyMesh& mesh, const bool decompose=false);
|
||||
|
||||
//- Reset all sizes to zero.
|
||||
void clear();
|
||||
|
||||
|
||||
// Access
|
||||
|
||||
//- Query the decompose flag
|
||||
inline bool decompose() const;
|
||||
|
||||
//- Number of cells for the mesh
|
||||
inline label nCells() const;
|
||||
|
||||
//- Number of points for the mesh
|
||||
inline label nPoints() const;
|
||||
|
||||
//- Number of vertex labels for the mesh
|
||||
inline label nVertLabels() const;
|
||||
|
||||
//- Number of polyhedral face labels for the mesh
|
||||
inline label nFaceLabels() const;
|
||||
|
||||
//- Number of polyhedral cells for the mesh
|
||||
inline label nCellsPoly() const;
|
||||
|
||||
//- Number of vertex labels for polyhedral cells of the mesh
|
||||
inline label nVertPoly() const;
|
||||
|
||||
//- Number of additional (decomposed) cells for the mesh
|
||||
inline label nAddCells() const;
|
||||
|
||||
//- Number of additional (decomposed) points for the mesh
|
||||
inline label nAddPoints() const;
|
||||
|
||||
//- Number of additional (decomposed) vertices for the mesh
|
||||
inline label nAddVerts() const;
|
||||
|
||||
|
||||
//- Number of field cells = nCells + nAddCells
|
||||
inline label nFieldCells() const;
|
||||
|
||||
//- Number of field points = nPoints + nAddPoints
|
||||
inline label nFieldPoints() const;
|
||||
|
||||
|
||||
// Derived sizes
|
||||
|
||||
//- Return the required size for the storage slot
|
||||
label slotSize
|
||||
(
|
||||
const enum contentType output,
|
||||
const enum slotType slot
|
||||
) const;
|
||||
|
||||
|
||||
//- The calculated size for legacy storage
|
||||
inline label sizeLegacy() const;
|
||||
|
||||
//- The calculated size for legacy storage of the specified slot
|
||||
inline label sizeLegacy(const enum slotType slot) const;
|
||||
|
||||
//- The calculated size for xml storage of the specified slot
|
||||
inline label sizeXml(const enum slotType slot) const;
|
||||
|
||||
//- The calculated size for vtk-internal storage of the specified slot
|
||||
inline label sizeInternal(const enum slotType slot) const;
|
||||
|
||||
|
||||
// Utilty routines
|
||||
|
||||
//- Populate lists for Legacy output
|
||||
void populateLegacy
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<label>& connectivity,
|
||||
foamVtkMeshMaps& maps
|
||||
) const;
|
||||
|
||||
//- Populate lists for XML output
|
||||
void populateXml
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<label>& connectivity,
|
||||
UList<label>& offsets,
|
||||
UList<label>& faces,
|
||||
UList<label>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<int>& connectivity,
|
||||
UList<int>& offsets,
|
||||
UList<int>& faces,
|
||||
UList<int>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long>& connectivity,
|
||||
UList<long>& offsets,
|
||||
UList<long>& faces,
|
||||
UList<long>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long long>& connectivity,
|
||||
UList<long long>& offsets,
|
||||
UList<long long>& faces,
|
||||
UList<long long>& facesOffsets,
|
||||
foamVtkMeshMaps& maps
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<int>& connectivity,
|
||||
UList<int>& offsets,
|
||||
UList<int>& faces,
|
||||
UList<int>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long>& connectivity,
|
||||
UList<long>& offsets,
|
||||
UList<long>& faces,
|
||||
UList<long>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const;
|
||||
|
||||
//- Populate lists for Internal VTK format
|
||||
void populateInternal
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<long long>& connectivity,
|
||||
UList<long long>& offsets,
|
||||
UList<long long>& faces,
|
||||
UList<long long>& facesOffsets,
|
||||
UList<label>& cellMap,
|
||||
UList<label>& addPointsIds
|
||||
) const;
|
||||
|
||||
|
||||
// Write
|
||||
|
||||
//- Report some information
|
||||
void info(Ostream& os) const;
|
||||
|
||||
|
||||
// Member Operators
|
||||
|
||||
//- Test equality
|
||||
bool operator==(const foamVtuSizing& rhs) const;
|
||||
|
||||
//- Test inequality
|
||||
bool operator!=(const foamVtuSizing& rhs) const;
|
||||
|
||||
};
|
||||
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
} // End namespace Foam
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#include "foamVtuSizingI.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#endif
|
||||
|
||||
// ************************************************************************* //
|
||||
135
src/conversion/vtk/part/foamVtuSizingI.H
Normal file
135
src/conversion/vtk/part/foamVtuSizingI.H
Normal file
@ -0,0 +1,135 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "foamVtuSizing.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
inline bool Foam::foamVtuSizing::decompose() const
|
||||
{
|
||||
return decompose_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nCells() const
|
||||
{
|
||||
return nCells_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nPoints() const
|
||||
{
|
||||
return nPoints_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nVertLabels() const
|
||||
{
|
||||
return nVertLabels_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nFaceLabels() const
|
||||
{
|
||||
return nFaceLabels_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nCellsPoly() const
|
||||
{
|
||||
return nCellsPoly_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nVertPoly() const
|
||||
{
|
||||
return nVertPoly_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nAddCells() const
|
||||
{
|
||||
return nAddCells_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nAddPoints() const
|
||||
{
|
||||
return nAddPoints_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nAddVerts() const
|
||||
{
|
||||
return nAddVerts_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nFieldCells() const
|
||||
{
|
||||
return nCells_ + nAddCells_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::nFieldPoints() const
|
||||
{
|
||||
return nPoints_ + nAddPoints_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::sizeLegacy() const
|
||||
{
|
||||
return slotSize(contentType::LEGACY, slotType::CELLS);
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::sizeLegacy
|
||||
(
|
||||
const enum slotType slot
|
||||
) const
|
||||
{
|
||||
return slotSize(contentType::LEGACY, slot);
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::sizeXml
|
||||
(
|
||||
const enum slotType slot
|
||||
) const
|
||||
{
|
||||
return slotSize(contentType::XML, slot);
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::foamVtuSizing::sizeInternal
|
||||
(
|
||||
const enum slotType slot
|
||||
) const
|
||||
{
|
||||
return slotSize(contentType::INTERNAL, slot);
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
670
src/conversion/vtk/part/foamVtuSizingTemplates.C
Normal file
670
src/conversion/vtk/part/foamVtuSizingTemplates.C
Normal file
@ -0,0 +1,670 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "foamVtuSizing.H"
|
||||
#include "foamVtkCore.H"
|
||||
#include "polyMesh.H"
|
||||
#include "cellShape.H"
|
||||
#include "cellModeller.H"
|
||||
|
||||
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
||||
|
||||
template<class LabelType, class LabelType2>
|
||||
void Foam::foamVtuSizing::populateArrays
|
||||
(
|
||||
const polyMesh& mesh,
|
||||
const foamVtuSizing& sizing,
|
||||
UList<uint8_t>& cellTypes,
|
||||
UList<LabelType>& vertLabels,
|
||||
UList<LabelType>& vertOffset,
|
||||
UList<LabelType>& faceLabels,
|
||||
UList<LabelType>& faceOffset,
|
||||
const enum contentType output,
|
||||
UList<LabelType2>& cellMap,
|
||||
UList<LabelType2>& addPointsIds
|
||||
)
|
||||
{
|
||||
using vtkTypes = fileFormats::foamVtkCore::vtkTypes;
|
||||
|
||||
// STAGE 1: Verify storage sizes
|
||||
|
||||
if (cellTypes.size() != sizing.nFieldCells())
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " cellTypes size=" << cellTypes.size()
|
||||
<< " expected " << sizing.nFieldCells()
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if (cellMap.size() != sizing.nFieldCells())
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " cellMap size=" << cellMap.size()
|
||||
<< " expected " << sizing.nFieldCells()
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if (addPointsIds.size() != sizing.nAddPoints())
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " addPointsIds size=" << addPointsIds.size()
|
||||
<< " expected " << sizing.nAddPoints()
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
// Prefix vertLabels with the size too?
|
||||
// Also use as the size of the prefixed information
|
||||
const int prefix = (output != contentType::XML) ? 1 : 0;
|
||||
|
||||
switch (output)
|
||||
{
|
||||
case contentType::LEGACY:
|
||||
{
|
||||
if (vertLabels.size() != sizing.sizeLegacy())
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " legacy size=" << vertLabels.size()
|
||||
<< " expected " << sizing.sizeLegacy()
|
||||
<< exit(FatalError);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case contentType::XML:
|
||||
{
|
||||
// XML uses connectivity/offset pair.
|
||||
if
|
||||
(
|
||||
vertLabels.size()
|
||||
!= sizing.sizeXml(slotType::CELLS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " connectivity size=" << vertLabels.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeXml(slotType::CELLS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if
|
||||
(
|
||||
vertOffset.size()
|
||||
!= sizing.sizeXml(slotType::CELLS_OFFSETS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " offsets size=" << vertOffset.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeXml(slotType::CELLS_OFFSETS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if (sizing.nFaceLabels())
|
||||
{
|
||||
if
|
||||
(
|
||||
faceLabels.size()
|
||||
!= sizing.sizeXml(slotType::FACES)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " faces size=" << faceLabels.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeXml(slotType::FACES)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if
|
||||
(
|
||||
faceOffset.size()
|
||||
!= sizing.sizeXml(slotType::FACES_OFFSETS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " facesOffsets size=" << faceOffset.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeXml(slotType::FACES_OFFSETS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case contentType::INTERNAL:
|
||||
{
|
||||
// VTK-internal connectivity/offset pair.
|
||||
if
|
||||
(
|
||||
vertLabels.size()
|
||||
!= sizing.sizeInternal(slotType::CELLS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " connectivity size=" << vertLabels.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeInternal(slotType::CELLS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if
|
||||
(
|
||||
vertOffset.size()
|
||||
!= sizing.sizeInternal(slotType::CELLS_OFFSETS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " offsets size=" << vertOffset.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeInternal(slotType::CELLS_OFFSETS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if (sizing.nFaceLabels())
|
||||
{
|
||||
if
|
||||
(
|
||||
faceLabels.size()
|
||||
!= sizing.sizeInternal(slotType::FACES)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " faces size=" << faceLabels.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeInternal(slotType::FACES)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
if
|
||||
(
|
||||
faceOffset.size()
|
||||
!= sizing.sizeInternal(slotType::FACES_OFFSETS)
|
||||
)
|
||||
{
|
||||
FatalErrorInFunction
|
||||
<< " facesOffsets size=" << faceOffset.size()
|
||||
<< " expected "
|
||||
<< sizing.sizeInternal(slotType::FACES_OFFSETS)
|
||||
<< exit(FatalError);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
faceOffset = -1;
|
||||
|
||||
const cellModel& tet = *(cellModeller::lookup("tet"));
|
||||
const cellModel& pyr = *(cellModeller::lookup("pyr"));
|
||||
const cellModel& prism = *(cellModeller::lookup("prism"));
|
||||
const cellModel& wedge = *(cellModeller::lookup("wedge"));
|
||||
const cellModel& tetWedge = *(cellModeller::lookup("tetWedge"));
|
||||
const cellModel& hex = *(cellModeller::lookup("hex"));
|
||||
|
||||
const cellShapeList& shapes = mesh.cellShapes();
|
||||
|
||||
// face owner is needed to determine the face orientation
|
||||
const labelList& owner = mesh.faceOwner();
|
||||
|
||||
// Unique vertex labels per polyhedral
|
||||
HashSet<label> hashUniqId(2*256);
|
||||
|
||||
// Index into vertLabels, faceLabels for normal cells
|
||||
label nVertLabels = 0;
|
||||
label nFaceLabels = 0;
|
||||
|
||||
// Index into vertLabels for decomposed polys
|
||||
label nVertDecomp = sizing.nVertLabels() + prefix*sizing.nCells();
|
||||
|
||||
// Placement of decomposed cells
|
||||
label nCellDecomp = mesh.nCells();
|
||||
|
||||
// Placement of additional point labels
|
||||
label nPointDecomp = 0;
|
||||
|
||||
// Non-decomposed polyhedral are represented as a face-stream.
|
||||
// For legacy format, this stream replaces the normal connectivity
|
||||
// information. Use references to alias where the face output should land.
|
||||
|
||||
UList<LabelType>& faceOutput =
|
||||
(
|
||||
output == contentType::LEGACY
|
||||
? vertLabels
|
||||
: faceLabels
|
||||
);
|
||||
|
||||
label& faceIndexer =
|
||||
(
|
||||
output == contentType::LEGACY
|
||||
? nVertLabels
|
||||
: nFaceLabels
|
||||
);
|
||||
|
||||
// ===========================================
|
||||
// STAGE 2: Rewrite in VTK form
|
||||
// During this stage, the vertOffset contains the *size* associated with
|
||||
// the per-cell vertLabels entries, and the faceOffset contains the *size*
|
||||
// associated with the per-cell faceLabels.
|
||||
|
||||
forAll(shapes, celli)
|
||||
{
|
||||
const cellShape& shape = shapes[celli];
|
||||
const cellModel& model = shape.model();
|
||||
|
||||
cellMap[celli] = celli;
|
||||
|
||||
if (model == tet)
|
||||
{
|
||||
cellTypes[celli] = vtkTypes::VTK_TETRA;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = shape.size();
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape.size();
|
||||
}
|
||||
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape[i];
|
||||
}
|
||||
}
|
||||
else if (model == pyr)
|
||||
{
|
||||
cellTypes[celli] = vtkTypes::VTK_PYRAMID;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = shape.size();
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape.size();
|
||||
}
|
||||
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape[i];
|
||||
}
|
||||
}
|
||||
else if (model == hex)
|
||||
{
|
||||
cellTypes[celli] = vtkTypes::VTK_HEXAHEDRON;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = shape.size();
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape.size();
|
||||
}
|
||||
|
||||
forAll(shape, i)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape[i];
|
||||
}
|
||||
}
|
||||
else if (model == prism)
|
||||
{
|
||||
cellTypes[celli] = vtkTypes::VTK_WEDGE;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = shape.size();
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = shape.size();
|
||||
}
|
||||
|
||||
// VTK_WEDGE triangles point outwards (swap 1<->2, 4<->5)
|
||||
vertLabels[nVertLabels++] = shape[0];
|
||||
vertLabels[nVertLabels++] = shape[2];
|
||||
vertLabels[nVertLabels++] = shape[1];
|
||||
vertLabels[nVertLabels++] = shape[3];
|
||||
vertLabels[nVertLabels++] = shape[5];
|
||||
vertLabels[nVertLabels++] = shape[4];
|
||||
}
|
||||
else if (model == tetWedge && sizing.decompose())
|
||||
{
|
||||
// Treat as squeezed prism
|
||||
cellTypes[celli] = vtkTypes::VTK_WEDGE;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = 6;
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = 6;
|
||||
}
|
||||
|
||||
vertLabels[nVertLabels++] = shape[0];
|
||||
vertLabels[nVertLabels++] = shape[2];
|
||||
vertLabels[nVertLabels++] = shape[1];
|
||||
vertLabels[nVertLabels++] = shape[3];
|
||||
vertLabels[nVertLabels++] = shape[4];
|
||||
vertLabels[nVertLabels++] = shape[3];
|
||||
}
|
||||
else if (model == wedge && sizing.decompose())
|
||||
{
|
||||
// Treat as squeezed hex
|
||||
cellTypes[celli] = vtkTypes::VTK_HEXAHEDRON;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celli] = 8;
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = 8;
|
||||
}
|
||||
|
||||
vertLabels[nVertLabels++] = shape[0];
|
||||
vertLabels[nVertLabels++] = shape[1];
|
||||
vertLabels[nVertLabels++] = shape[2];
|
||||
vertLabels[nVertLabels++] = shape[2];
|
||||
vertLabels[nVertLabels++] = shape[3];
|
||||
vertLabels[nVertLabels++] = shape[4];
|
||||
vertLabels[nVertLabels++] = shape[5];
|
||||
vertLabels[nVertLabels++] = shape[6];
|
||||
}
|
||||
else if (sizing.decompose())
|
||||
{
|
||||
// Polyhedral cell - decompose into tet/pyr.
|
||||
|
||||
// Ensure we have the correct orientation for the base of the
|
||||
// primitive cell shape.
|
||||
// If the cell is face owner, the orientation needs to be flipped
|
||||
// to avoid defining negative cells.
|
||||
// VTK may not care, but we'll do it anyhow for safety.
|
||||
|
||||
// Mapping from additional point to cell, and the new vertex from
|
||||
// the cell-centre
|
||||
const label newVertexLabel = mesh.nPoints() + nPointDecomp;
|
||||
|
||||
addPointsIds[nPointDecomp++] = celli;
|
||||
|
||||
// Whether to insert cell in place of original or not.
|
||||
bool first = true;
|
||||
|
||||
const labelList& cFaces = mesh.cells()[celli];
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh.faces()[cFaces[cFaceI]];
|
||||
const bool isOwner = (owner[cFaces[cFaceI]] == celli);
|
||||
|
||||
// Count triangles/quads in decomposition
|
||||
label nTria = 0, nQuad = 0;
|
||||
f.nTrianglesQuads(mesh.points(), nTria, nQuad);
|
||||
|
||||
// Do actual decomposition
|
||||
faceList faces3(nTria);
|
||||
faceList faces4(nQuad);
|
||||
nTria = 0, nQuad = 0;
|
||||
f.trianglesQuads(mesh.points(), nTria, nQuad, faces3, faces4);
|
||||
|
||||
forAll(faces4, fci)
|
||||
{
|
||||
// Quad becomes a pyramid
|
||||
const face& quad = faces4[fci];
|
||||
const label nShapePoints = 5; // pyr (5 vertices)
|
||||
|
||||
label celLoc, vrtLoc;
|
||||
if (first)
|
||||
{
|
||||
first = false;
|
||||
celLoc = celli;
|
||||
vrtLoc = nVertLabels;
|
||||
nVertLabels += prefix + nShapePoints;
|
||||
}
|
||||
else
|
||||
{
|
||||
celLoc = nCellDecomp++;
|
||||
vrtLoc = nVertDecomp;
|
||||
nVertDecomp += prefix + nShapePoints;
|
||||
}
|
||||
cellMap[celLoc] = celli;
|
||||
|
||||
cellTypes[celLoc] = vtkTypes::VTK_PYRAMID;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celLoc] = nShapePoints;
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[vrtLoc++] = nShapePoints;
|
||||
}
|
||||
|
||||
// See note above about the orientation.
|
||||
if (isOwner)
|
||||
{
|
||||
vertLabels[vrtLoc++] = quad[3];
|
||||
vertLabels[vrtLoc++] = quad[2];
|
||||
vertLabels[vrtLoc++] = quad[1];
|
||||
vertLabels[vrtLoc++] = quad[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
vertLabels[vrtLoc++] = quad[0];
|
||||
vertLabels[vrtLoc++] = quad[1];
|
||||
vertLabels[vrtLoc++] = quad[2];
|
||||
vertLabels[vrtLoc++] = quad[3];
|
||||
}
|
||||
|
||||
vertLabels[vrtLoc++] = newVertexLabel; // apex
|
||||
}
|
||||
|
||||
forAll(faces3, fci)
|
||||
{
|
||||
// Triangle becomes a tetrahedral
|
||||
const face& tria = faces3[fci];
|
||||
const label nShapePoints = 4; // tet (4 vertices)
|
||||
|
||||
label celLoc, vrtLoc;
|
||||
if (first)
|
||||
{
|
||||
first = false;
|
||||
celLoc = celli;
|
||||
vrtLoc = nVertLabels;
|
||||
nVertLabels += prefix + nShapePoints;
|
||||
}
|
||||
else
|
||||
{
|
||||
celLoc = nCellDecomp++;
|
||||
vrtLoc = nVertDecomp;
|
||||
nVertDecomp += prefix + nShapePoints;
|
||||
}
|
||||
cellMap[celLoc] = celli;
|
||||
|
||||
cellTypes[celLoc] = vtkTypes::VTK_TETRA;
|
||||
if (vertOffset.size())
|
||||
{
|
||||
vertOffset[celLoc] = nShapePoints;
|
||||
}
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[vrtLoc++] = nShapePoints;
|
||||
}
|
||||
|
||||
cellTypes[celLoc] = vtkTypes::VTK_TETRA;
|
||||
|
||||
// See note above about the orientation.
|
||||
if (isOwner)
|
||||
{
|
||||
vertLabels[vrtLoc++] = tria[2];
|
||||
vertLabels[vrtLoc++] = tria[1];
|
||||
vertLabels[vrtLoc++] = tria[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
vertLabels[vrtLoc++] = tria[0];
|
||||
vertLabels[vrtLoc++] = tria[1];
|
||||
vertLabels[vrtLoc++] = tria[2];
|
||||
}
|
||||
vertLabels[vrtLoc++] = newVertexLabel; // apex
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Polyhedral cell - not decomposed
|
||||
hashUniqId.clear(); // unique node ids used (XML, INTERNAL)
|
||||
|
||||
// face-stream
|
||||
// [nFaces, nFace0Pts, id1, id2, ..., nFace1Pts, id1, id2, ...]
|
||||
cellTypes[celli] = vtkTypes::VTK_POLYHEDRON;
|
||||
const labelList& cFaces = mesh.cells()[celli];
|
||||
|
||||
const label startLabel = faceIndexer;
|
||||
|
||||
if (output == contentType::LEGACY)
|
||||
{
|
||||
faceOutput[startLabel] = 0; // placeholder for size
|
||||
++faceIndexer;
|
||||
}
|
||||
|
||||
faceOutput[faceIndexer++] = cFaces.size();
|
||||
|
||||
forAll(cFaces, cFaceI)
|
||||
{
|
||||
const face& f = mesh.faces()[cFaces[cFaceI]];
|
||||
const bool isOwner = (owner[cFaces[cFaceI]] == celli);
|
||||
|
||||
forAll(f, fp)
|
||||
{
|
||||
hashUniqId.insert(f[fp]);
|
||||
}
|
||||
|
||||
// number of labels for this face
|
||||
faceOutput[faceIndexer++] = f.size();
|
||||
|
||||
if (isOwner)
|
||||
{
|
||||
forAll(f, fp)
|
||||
{
|
||||
faceOutput[faceIndexer++] = f[fp];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// fairly immaterial if we reverse the list
|
||||
// or use face::reverseFace()
|
||||
forAllReverse(f, fp)
|
||||
{
|
||||
faceOutput[faceIndexer++] = f[fp];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (output == contentType::LEGACY)
|
||||
{
|
||||
// Update size for legacy face stream
|
||||
faceOutput[startLabel] = (faceIndexer - startLabel);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Size for face stream
|
||||
faceOffset[celli] = (faceIndexer - startLabel);
|
||||
|
||||
vertOffset[celli] = hashUniqId.size();
|
||||
if (prefix)
|
||||
{
|
||||
vertLabels[nVertLabels++] = hashUniqId.size();
|
||||
}
|
||||
|
||||
const labelList uniq = hashUniqId.sortedToc();
|
||||
forAll(uniq, i)
|
||||
{
|
||||
vertLabels[nVertLabels++] = uniq[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ===========================================
|
||||
// STAGE 3: Adjust vertOffset for all cells
|
||||
// A second pass is needed for several reasons.
|
||||
// - Additional (decomposed) cells are placed out of sequence
|
||||
// - Internal format has the size prefixed, XML format does not.
|
||||
// - XML format expects end-offsets, Internal expects begin-offsets
|
||||
|
||||
switch (output)
|
||||
{
|
||||
case contentType::LEGACY: // nothing to do
|
||||
break;
|
||||
|
||||
case contentType::XML:
|
||||
{
|
||||
// No prefix, determine end offsets
|
||||
// vertOffset[0] already contains its size
|
||||
for (label i = 1; i < vertOffset.size(); ++i)
|
||||
{
|
||||
vertOffset[i] += vertOffset[i-1];
|
||||
}
|
||||
|
||||
if (sizing.nFaceLabels())
|
||||
{
|
||||
// End face offsets, leaving -1 untouched
|
||||
label prev = 0;
|
||||
forAll(faceOffset, i)
|
||||
{
|
||||
const label sz = faceOffset[i];
|
||||
if (sz > 0)
|
||||
{
|
||||
prev += sz;
|
||||
faceOffset[i] = prev;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case contentType::INTERNAL:
|
||||
{
|
||||
// Has prefix, determine begin offsets
|
||||
label beg = 0;
|
||||
forAll(vertOffset, i)
|
||||
{
|
||||
const label sz = vertOffset[i];
|
||||
vertOffset[i] = beg;
|
||||
beg += 1 + sz;
|
||||
}
|
||||
|
||||
// Begin face offsets, leaving -1 untouched
|
||||
if (sizing.nFaceLabels())
|
||||
{
|
||||
beg = 0;
|
||||
forAll(faceOffset, i)
|
||||
{
|
||||
const label sz = faceOffset[i];
|
||||
if (sz > 0)
|
||||
{
|
||||
faceOffset[i] = beg;
|
||||
beg += sz;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
Reference in New Issue
Block a user