ENH: improve internal bookkeeping in paraview readers

- has the selected values directly and use these lookup names to store
  directly into a hash. This replaces several parallel lists of
  decomp information etc and makes it easier.
This commit is contained in:
Mark Olesen
2017-05-14 21:42:59 +02:00
parent 09f0cfd5c7
commit cf5ebd82db
10 changed files with 431 additions and 331 deletions

View File

@ -47,6 +47,20 @@ License
namespace Foam
{
defineTypeNameAndDebug(vtkPVFoam, 0);
// file-scope
static word updateStateName(polyMesh::readUpdateState state)
{
switch (state)
{
case polyMesh::UNCHANGED: return "UNCHANGED";
case polyMesh::POINTS_MOVED: return "POINTS_MOVED";
case polyMesh::TOPO_CHANGE: return "TOPO_CHANGE";
case polyMesh::TOPO_PATCH_CHANGE: return "TOPO_PATCH_CHANGE";
};
return "UNKNOWN";
}
}
@ -138,27 +152,15 @@ int Foam::vtkPVFoam::setTime(int nRequest, const double requestTimes[])
<< ", nearestIndex = " << nearestIndex << endl;
}
// see what has changed
// See what has changed
if (timeIndex_ != nearestIndex)
{
timeIndex_ = nearestIndex;
runTime.setTime(Times[nearestIndex], nearestIndex);
// the fields change each time
// When the changes, so do the fields
fieldsChanged_ = true;
if (meshPtr_)
{
if (meshPtr_->readUpdate() != polyMesh::UNCHANGED)
{
meshChanged_ = true;
}
}
else
{
meshChanged_ = true;
}
meshState_ = meshPtr_ ? meshPtr_->readUpdate() : polyMesh::TOPO_CHANGE;
reader_->UpdateProgress(0.05);
@ -171,7 +173,7 @@ int Foam::vtkPVFoam::setTime(int nRequest, const double requestTimes[])
Info<< "<end> setTime() - selectedTime="
<< Times[nearestIndex].name() << " index=" << timeIndex_
<< "/" << Times.size()
<< " meshChanged=" << Switch(meshChanged_)
<< " meshUpdateState=" << updateStateName(meshState_)
<< " fieldsChanged=" << Switch(fieldsChanged_) << endl;
}
@ -179,7 +181,20 @@ int Foam::vtkPVFoam::setTime(int nRequest, const double requestTimes[])
}
Foam::word Foam::vtkPVFoam::getPartName(const int partId)
Foam::word Foam::vtkPVFoam::getPartName(const int partId) const
{
if (selectedPartIds_.found(partId))
{
return getFoamName(selectedPartIds_[partId]);
}
else
{
return word::null;
}
}
Foam::word Foam::vtkPVFoam::getReaderPartName(const int partId) const
{
return getFoamName(reader_->GetPartArrayName(partId));
}
@ -199,7 +214,7 @@ Foam::vtkPVFoam::vtkPVFoam
meshRegion_(polyMesh::defaultRegion),
meshDir_(polyMesh::meshSubDir),
timeIndex_(-1),
meshChanged_(true),
meshState_(polyMesh::TOPO_CHANGE),
fieldsChanged_(true),
rangeVolume_("unzoned"),
rangePatches_("patch"),
@ -334,7 +349,7 @@ void Foam::vtkPVFoam::updateInfo()
// time of the vtkDataArraySelection, but the qt/paraview proxy
// layer doesn't care about that anyhow.
stringList enabledEntries;
HashSet<string> enabledEntries;
if (!partSelection->GetNumberOfArrays() && !meshPtr_)
{
// enable 'internalMesh' on the first call
@ -356,10 +371,10 @@ void Foam::vtkPVFoam::updateInfo()
updateInfoZones(partSelection);
updateInfoLagrangian(partSelection);
// restore the enabled selections
// Adjust/restore the enabled selections
setSelectedArrayEntries(partSelection, enabledEntries);
if (meshChanged_)
if (meshState_ != polyMesh::UNCHANGED)
{
fieldsChanged_ = true;
}
@ -408,37 +423,48 @@ void Foam::vtkPVFoam::Update
}
vtkDataArraySelection* selection = reader_->GetPartSelection();
label nElem = selection->GetNumberOfArrays();
const int n = selection->GetNumberOfArrays();
if (partStatus_.size() != nElem)
// All previously selected (enabled) names
HashSet<string> original;
forAllConstIters(selectedPartIds_, iter)
{
partStatus_.setSize(nElem);
partStatus_ = false;
meshChanged_ = true;
original.insert(iter.object());
}
// this needs fixing if we wish to re-use the datasets
partDataset_.setSize(nElem);
partDataset_ = -1;
selectedPartIds_.clear();
// Read the selected mesh parts (zones, patches ...) and add to list
forAll(partStatus_, partId)
for (int id=0; id < n; ++id)
{
const int setting = selection->GetArraySetting(partId);
string str(selection->GetArrayName(id));
bool status = selection->GetArraySetting(id);
if (partStatus_[partId] != setting)
if (status)
{
partStatus_[partId] = setting;
meshChanged_ = true;
selectedPartIds_.set(id, str); // id -> name
if (!original.erase(str))
{
// New part, or newly enabled
//? meshChanged_ = true;
}
}
else
{
if (original.erase(str))
{
// Part disappeared, or newly disabled
//? meshChanged_ = true;
}
}
if (debug > 1)
{
Info<< " part[" << partId << "] = "
<< partStatus_[partId]
<< " : " << selection->GetArrayName(partId) << endl;
Info<< " part[" << id << "] = " << status
<< " : " << str << nl;
}
}
if (debug)
{
Info<< "<end> updateMeshPartsStatus" << endl;
@ -467,8 +493,7 @@ void Foam::vtkPVFoam::Update
if (debug)
{
Info<< "Creating OpenFOAM mesh for region " << meshRegion_
<< " at time=" << dbPtr_().timeName()
<< endl;
<< " at time=" << dbPtr_().timeName() << endl;
}
@ -483,7 +508,7 @@ void Foam::vtkPVFoam::Update
)
);
meshChanged_ = true;
meshState_ = polyMesh::TOPO_CHANGE; // New mesh
}
else
{
@ -502,6 +527,20 @@ void Foam::vtkPVFoam::Update
reader_->UpdateProgress(0.4);
// Update cached, saved, unneed values:
HashSet<string> nowActive;
forAllConstIters(selectedPartIds_, iter)
{
nowActive.insert(iter.object());
}
// Dispose of unneeded components
cachedVtp_.retain(nowActive);
cachedVtu_.retain(nowActive);
// Reset (expire) dataset ids
partDataset_.clear();
// Convert meshes - start port0 at block=0
int blockNo = 0;
@ -549,21 +588,12 @@ void Foam::vtkPVFoam::Update
}
reader_->UpdateProgress(0.95);
meshChanged_ = fieldsChanged_ = false;
fieldsChanged_ = false;
meshState_ = polyMesh::UNCHANGED;
// Standard memory cleanup
forAll(regionVtus_, i)
{
regionVtus_[i].clear();
}
forAll(zoneVtus_, i)
{
zoneVtus_[i].clear();
}
forAll(csetVtus_, i)
{
csetVtus_[i].clear();
}
cachedVtp_.clear();
cachedVtu_.clear();
}

View File

@ -160,7 +160,17 @@ class vtkPVFoam
}
};
typedef polyDecomp foamVtuData;
//- Bookkeeping for vtkPolyData
class foamVtpData
{
};
//- Bookkeeping for vtkUnstructuredGrid
class foamVtuData
:
public polyDecomp
{
};
// Private Data
@ -184,20 +194,26 @@ class vtkPVFoam
int timeIndex_;
//- Track changes in mesh geometry
bool meshChanged_;
enum polyMesh::readUpdateState meshState_;
//- Track changes in fields
bool fieldsChanged_;
//- Selected geometrical parts (internalMesh, patches, ...)
boolList partStatus_;
//- The index of selected parts mapped to their names
Map<string> selectedPartIds_;
//- Datasets corresponding to selected geometrical pieces
// a negative number indicates that no vtkmesh exists for this piece
labelList partDataset_;
Map<label> partDataset_;
//- Any information for 2D (VTP) geometries
HashTable<foamVtpData, string> cachedVtp_;
//- Cell maps and other information for 3D (VTU) geometries
HashTable<foamVtuData, string> cachedVtu_;
//- First instance and size of various mesh parts
// used to index into partStatus_ and partDataset_
// used to index into selectedPartIds and thus indirectly into
// cachedVtp, cachedVtu and partDataset
arrayRange rangeVolume_;
arrayRange rangePatches_;
arrayRange rangeLagrangian_;
@ -208,16 +224,6 @@ class vtkPVFoam
arrayRange rangeFaceSets_;
arrayRange rangePointSets_;
//- Decomposed cells information (mesh regions)
// TODO: regions
List<foamVtuData> regionVtus_;
//- Decomposed cells information (cellZone meshes)
List<foamVtuData> zoneVtus_;
//- Decomposed cells information (cellSet meshes)
List<foamVtuData> csetVtus_;
//- List of patch names for rendering to window
List<vtkSmartPointer<vtkTextActor>> patchTextActors_;
@ -230,19 +236,24 @@ class vtkPVFoam
// Update information helper functions
//- Internal mesh info
void updateInfoInternalMesh(vtkDataArraySelection*);
void updateInfoInternalMesh(vtkDataArraySelection* select);
//- Lagrangian info
void updateInfoLagrangian(vtkDataArraySelection*);
void updateInfoLagrangian(vtkDataArraySelection* select);
//- Patch info
void updateInfoPatches(vtkDataArraySelection*, stringList&);
//- Patch info, modifies enabledEntries
void updateInfoPatches
(
vtkDataArraySelection* select,
HashSet<string>& enabledEntries
);
//- Set info
void updateInfoSets(vtkDataArraySelection*);
void updateInfoSets(vtkDataArraySelection* select);
//- Zone info
void updateInfoZones(vtkDataArraySelection*);
void updateInfoZones(vtkDataArraySelection* select);
//- Get non-empty zone names for zoneType from file
wordList getZoneNames(const word& zoneType) const;
@ -395,8 +406,7 @@ class vtkPVFoam
const GeometricField<Type, fvPatchField, volMesh>& fld,
autoPtr<GeometricField<Type, pointPatchField, pointMesh>>& ptfPtr,
vtkMultiBlockDataSet* output,
const arrayRange& range,
const List<foamVtuData>& vtuDataList
const arrayRange& range
);
//- Lagrangian fields - all types
@ -423,8 +433,7 @@ class vtkPVFoam
(
const GeometricField<Type, pointPatchField, pointMesh>& pfld,
vtkMultiBlockDataSet* output,
const arrayRange& range,
const List<foamVtuData>& vtuDataList
const arrayRange& range
);
//- Point field
@ -447,8 +456,12 @@ class vtkPVFoam
const hashedWordList& retain
);
//- Get the first word from selectedPartIds_
word getPartName(const int partId) const;
//- Get the first word from the reader 'parts' selection
word getPartName(const int partId);
word getReaderPartName(const int partId) const;
// Constructors

View File

@ -84,8 +84,7 @@ void Foam::vtkPVFoam::convertVolField
fld,
ptfPtr,
output,
rangeVolume_,
regionVtus_
rangeVolume_
);
// Convert activated cellZones
@ -94,8 +93,7 @@ void Foam::vtkPVFoam::convertVolField
fld,
ptfPtr,
output,
rangeCellZones_,
zoneVtus_
rangeCellZones_
);
// Convert activated cellSets
@ -104,21 +102,30 @@ void Foam::vtkPVFoam::convertVolField
fld,
ptfPtr,
output,
rangeCellSets_,
csetVtus_
rangeCellSets_
);
//
// Convert patches - if activated
// - skip field conversion for groups
//
for (auto partId : rangePatches_)
{
if
(
!selectedPartIds_.found(partId)
|| selectedPartIds_[partId].startsWith("group/")
)
{
continue;
}
const word patchName = getPartName(partId);
const label datasetNo = partDataset_[partId];
const label datasetNo = partDataset_.lookup(partId, -1);
const label patchId = patches.findPatchID(patchName);
if (!partStatus_[partId] || patchId < 0)
if (patchId < 0)
{
continue;
}
@ -199,10 +206,15 @@ void Foam::vtkPVFoam::convertVolField
//
for (auto partId : rangeFaceZones_)
{
const word zoneName = getPartName(partId);
const label datasetNo = partDataset_[partId];
if (!selectedPartIds_.found(partId))
{
continue;
}
if (!partStatus_[partId] || datasetNo < 0)
const word zoneName = getPartName(partId);
const label datasetNo = partDataset_.lookup(partId, -1);
if (datasetNo < 0)
{
continue;
}
@ -239,14 +251,14 @@ void Foam::vtkPVFoam::convertVolField
//
for (auto partId : rangeFaceSets_)
{
const word selectName = getPartName(partId);
const label datasetNo = partDataset_[partId];
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const word selectName = getPartName(partId);
const label datasetNo = partDataset_.lookup(partId, -1);
vtkPolyData* vtkmesh = getDataFromBlock<vtkPolyData>
(
output, rangeFaceSets_, datasetNo
@ -373,23 +385,23 @@ void Foam::vtkPVFoam::convertVolFieldBlock
const GeometricField<Type, fvPatchField, volMesh>& fld,
autoPtr<GeometricField<Type, pointPatchField, pointMesh>>& ptfPtr,
vtkMultiBlockDataSet* output,
const arrayRange& range,
const List<foamVtuData>& vtuDataList
const arrayRange& range
)
{
for (auto partId : range)
{
const label datasetNo = partDataset_[partId];
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
const label datasetNo = partDataset_.lookup(partId, -1);
vtkUnstructuredGrid* vtkmesh =
getDataFromBlock<vtkUnstructuredGrid>(output, range, datasetNo);
if (!vtkmesh)
if (!vtkmesh || !cachedVtu_.found(longName))
{
continue;
}
@ -397,13 +409,17 @@ void Foam::vtkPVFoam::convertVolFieldBlock
vtkSmartPointer<vtkFloatArray> cdata = convertVolFieldToVTK
(
fld,
vtuDataList[datasetNo]
cachedVtu_[longName]
);
vtkmesh->GetCellData()->AddArray(cdata);
if (ptfPtr.valid())
{
convertPointField(vtkmesh, ptfPtr(), fld, vtuDataList[datasetNo]);
convertPointField
(
vtkmesh, ptfPtr(), fld,
cachedVtu_[longName]
);
}
}
}
@ -446,44 +462,53 @@ void Foam::vtkPVFoam::convertPointFields
GeometricField<Type, pointPatchField, pointMesh> pfld(*iter(), pMesh);
// Convert activated internalMesh regions
// Convert internalMesh (if selected)
convertPointFieldBlock
(
pfld,
output,
rangeVolume_,
regionVtus_
rangeVolume_
);
// Convert activated cellZones
// Convert (selected) cellZones
convertPointFieldBlock
(
pfld,
output,
rangeCellZones_,
zoneVtus_
rangeCellZones_
);
// Convert activated cellSets
// Convert (selected) cellSets
convertPointFieldBlock
(
pfld,
output,
rangeCellSets_,
csetVtus_
rangeCellSets_
);
//
// Convert patches - if activated
// Convert patches (if selected)
//
for (auto partId : rangePatches_)
{
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
if (longName.startsWith("group/"))
{
// Skip patch-groups
continue;
}
const word patchName = getPartName(partId);
const label datasetNo = partDataset_[partId];
const label datasetNo = partDataset_.lookup(partId, -1);
const label patchId = patches.findPatchID(patchName);
if (!partStatus_[partId] || patchId < 0)
if (patchId < 0)
{
continue;
}
@ -506,15 +531,20 @@ void Foam::vtkPVFoam::convertPointFields
}
//
// Convert faceZones - if activated
// Convert (selected) faceZones
//
for (auto partId : rangeFaceZones_)
{
if (!selectedPartIds_.found(partId))
{
continue;
}
const word zoneName = getPartName(partId);
const label datasetNo = partDataset_[partId];
const label datasetNo = partDataset_.lookup(partId, -1);
const label zoneId = mesh.faceZones().findZoneID(zoneName);
if (!partStatus_[partId] || zoneId < 0)
if (zoneId < 0)
{
continue;
}
@ -552,34 +582,35 @@ void Foam::vtkPVFoam::convertPointFieldBlock
(
const GeometricField<Type, pointPatchField, pointMesh>& pfld,
vtkMultiBlockDataSet* output,
const arrayRange& range,
const List<foamVtuData>& vtuDataList
const arrayRange& range
)
{
for (auto partId : range)
{
const label datasetNo = partDataset_[partId];
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
const label datasetNo = partDataset_.lookup(partId, -1);
vtkUnstructuredGrid* vtkmesh = getDataFromBlock<vtkUnstructuredGrid>
(
output, range, datasetNo
);
if (vtkmesh)
if (!vtkmesh || !cachedVtu_.found(longName))
{
convertPointField
(
vtkmesh,
pfld,
GeometricField<Type, fvPatchField, volMesh>::null(),
vtuDataList[datasetNo]
cachedVtu_[longName]
);
}
}
}
@ -878,16 +909,16 @@ Foam::vtkPVFoam::convertVolFieldToVTK
}
float vec[nComp];
forAll(cellMap, i)
forAll(cellMap, idx)
{
const Type& t = fld[cellMap[i]];
const Type& t = fld[cellMap[idx]];
for (direction d=0; d<nComp; ++d)
{
vec[d] = component(t, d);
}
foamPvFields::remapTuple<Type>(vec);
fldData->SetTuple(i, vec);
fldData->SetTuple(idx, vec);
}
return fldData;

View File

@ -226,10 +226,15 @@ void Foam::vtkPVFoam::convertLagrangianFields
for (auto partId : range)
{
const word cloudName = getPartName(partId);
const label datasetNo = partDataset_[partId];
if (!selectedPartIds_.found(partId))
{
continue;
}
if (!partStatus_[partId] || datasetNo < 0)
const word cloudName = getPartName(partId);
const label datasetNo = partDataset_.lookup(partId, -1);
if (datasetNo < 0)
{
continue;
}

View File

@ -53,9 +53,6 @@ void Foam::vtkPVFoam::convertMeshVolume
label datasetNo = 0; // restart at dataset 0
const fvMesh& mesh = *meshPtr_;
// resize for decomposed polyhedra
regionVtus_.setSize(range.size());
if (debug)
{
Info<< "<beg> convertMeshVolume" << endl;
@ -66,23 +63,24 @@ void Foam::vtkPVFoam::convertMeshVolume
// this looks like more than one part, but it isn't
for (auto partId : range)
{
const word partName = "internalMesh";
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
const word partName = getPartName(partId);
vtkSmartPointer<vtkUnstructuredGrid> vtkmesh = volumeVTKMesh
(
mesh,
regionVtus_[datasetNo]
cachedVtu_(longName)
);
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, partName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -119,20 +117,20 @@ void Foam::vtkPVFoam::convertMeshLagrangian
for (auto partId : range)
{
const word cloudName = getPartName(partId);
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const word cloudName = getPartName(partId);
vtkSmartPointer<vtkPolyData> vtkmesh =
lagrangianVTKMesh(mesh, cloudName);
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, cloudName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -170,30 +168,28 @@ void Foam::vtkPVFoam::convertMeshPatches
for (auto partId : range)
{
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const word patchName = getPartName(partId);
labelHashSet
patchIds(patches.patchSet(List<wordRe>(1, wordRe(patchName))));
if (debug)
{
Info<< "Creating VTK mesh for patches [" << patchIds <<"] "
<< patchName << endl;
}
const auto& longName = selectedPartIds_[partId];
const word partName = getPartName(partId);
vtkSmartPointer<vtkPolyData> vtkmesh;
if (patchIds.size() == 1)
{
vtkmesh = patchVTKMesh(patchName, patches[patchIds.begin().key()]);
}
else
if (longName.startsWith("group/"))
{
// Patch group. Collect patch faces.
const labelList& patchIds =
patches.groupPatchIDs().lookup(partName, labelList());
if (debug)
{
Info<< "Creating VTK mesh for patches [" << patchIds <<"] "
<< longName << endl;
}
label sz = 0;
for (auto id : patchIds)
{
@ -210,23 +206,37 @@ void Foam::vtkPVFoam::convertMeshPatches
}
}
uindirectPrimitivePatch pp
(
UIndirectList<face>
if (faceLabels.size())
{
uindirectPrimitivePatch pp
(
mesh.faces(),
faceLabels
),
mesh.points()
);
UIndirectList<face>(mesh.faces(), faceLabels),
mesh.points()
);
vtkmesh = patchVTKMesh(patchName, pp);
vtkmesh = patchVTKMesh(partName, pp);
}
}
else
{
const label patchId = patches.findPatchID(partName);
if (debug)
{
Info<< "Creating VTK mesh for patch [" << patchId <<"] "
<< partName << endl;
}
if (patchId >= 0)
{
vtkmesh = patchVTKMesh(partName, patches[patchId]);
}
}
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, patchName);
partDataset_[partId] = datasetNo++;
addToBlock(output, vtkmesh, range, datasetNo, partName);
partDataset_.set(partId, datasetNo++);
}
}
@ -255,9 +265,6 @@ void Foam::vtkPVFoam::convertMeshCellZones
label datasetNo = 0; // restart at dataset 0
const fvMesh& mesh = *meshPtr_;
// resize for decomposed polyhedra
zoneVtus_.setSize(range.size());
if (range.empty())
{
return;
@ -272,10 +279,16 @@ void Foam::vtkPVFoam::convertMeshCellZones
const cellZoneMesh& zMesh = mesh.cellZones();
for (auto partId : range)
{
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
const word zoneName = getPartName(partId);
const label zoneId = zMesh.findZoneID(zoneName);
if (!partStatus_[partId] || zoneId < 0)
if (zoneId < 0)
{
continue;
}
@ -292,28 +305,28 @@ void Foam::vtkPVFoam::convertMeshCellZones
vtkSmartPointer<vtkUnstructuredGrid> vtkmesh = volumeVTKMesh
(
subsetter.subMesh(),
zoneVtus_[datasetNo]
cachedVtu_(longName)
);
if (vtkmesh)
{
// cellMap + addPointCellLabels must contain global cell ids
// Convert cellMap, addPointCellLabels to global cell ids
inplaceRenumber
(
subsetter.cellMap(),
zoneVtus_[datasetNo].cellMap()
cachedVtu_[longName].cellMap()
);
inplaceRenumber
(
subsetter.cellMap(),
zoneVtus_[datasetNo].additionalIds()
cachedVtu_[longName].additionalIds()
);
// copy pointMap as well, otherwise pointFields fail
zoneVtus_[datasetNo].pointMap() = subsetter.pointMap();
cachedVtu_[longName].pointMap() = subsetter.pointMap();
addToBlock(output, vtkmesh, range, datasetNo, zoneName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -342,9 +355,6 @@ void Foam::vtkPVFoam::convertMeshCellSets
label datasetNo = 0; // restart at dataset 0
const fvMesh& mesh = *meshPtr_;
// resize for decomposed polyhedra
csetVtus_.setSize(range.size());
if (debug)
{
Info<< "<beg> convertMeshCellSets" << endl;
@ -353,13 +363,14 @@ void Foam::vtkPVFoam::convertMeshCellSets
for (auto partId : range)
{
const word partName = getPartName(partId);
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const auto& longName = selectedPartIds_[partId];
const word partName = getPartName(partId);
if (debug)
{
Info<< "Creating VTK mesh for cellSet=" << partName << endl;
@ -372,28 +383,28 @@ void Foam::vtkPVFoam::convertMeshCellSets
vtkSmartPointer<vtkUnstructuredGrid> vtkmesh = volumeVTKMesh
(
subsetter.subMesh(),
csetVtus_[datasetNo]
cachedVtu_(longName)
);
if (vtkmesh)
{
// cellMap + addPointCellLabels must contain global cell ids
// Convert cellMap, addPointCellLabels to global cell ids
inplaceRenumber
(
subsetter.cellMap(),
csetVtus_[datasetNo].cellMap()
cachedVtu_[longName].cellMap()
);
inplaceRenumber
(
subsetter.cellMap(),
csetVtus_[datasetNo].additionalIds()
cachedVtu_[longName].additionalIds()
);
// copy pointMap as well, otherwise pointFields fail
csetVtus_[datasetNo].pointMap() = subsetter.pointMap();
cachedVtu_[longName].pointMap() = subsetter.pointMap();
addToBlock(output, vtkmesh, range, datasetNo, partName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -436,10 +447,15 @@ void Foam::vtkPVFoam::convertMeshFaceZones
const faceZoneMesh& zMesh = mesh.faceZones();
for (auto partId : range)
{
if (!selectedPartIds_.found(partId))
{
continue;
}
const word zoneName = getPartName(partId);
const label zoneId = zMesh.findZoneID(zoneName);
if (!partStatus_[partId] || zoneId < 0)
if (zoneId < 0)
{
continue;
}
@ -456,7 +472,7 @@ void Foam::vtkPVFoam::convertMeshFaceZones
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, zoneName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -493,26 +509,24 @@ void Foam::vtkPVFoam::convertMeshFaceSets
for (auto partId : range)
{
const word partName = getPartName(partId);
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const word partName = getPartName(partId);
if (debug)
{
Info<< "Creating VTK mesh for faceSet=" << partName << endl;
}
// faces in sorted order for more reliability
const labelList faceLabels = faceSet(mesh, partName).sortedToc();
uindirectPrimitivePatch p
(
UIndirectList<face>
(
mesh.faces(),
faceSet(mesh, partName).sortedToc()
),
UIndirectList<face>(mesh.faces(), faceLabels),
mesh.points()
);
@ -527,7 +541,7 @@ void Foam::vtkPVFoam::convertMeshFaceSets
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, partName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
@ -567,10 +581,15 @@ void Foam::vtkPVFoam::convertMeshPointZones
const pointZoneMesh& zMesh = mesh.pointZones();
for (auto partId : range)
{
if (!selectedPartIds_.found(partId))
{
continue;
}
const word zoneName = getPartName(partId);
const label zoneId = zMesh.findZoneID(zoneName);
if (!partStatus_[partId] || zoneId < 0)
if (zoneId < 0)
{
continue;
}
@ -600,7 +619,7 @@ void Foam::vtkPVFoam::convertMeshPointZones
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, zoneName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}
}
@ -619,7 +638,6 @@ void Foam::vtkPVFoam::convertMeshPointZones
}
void Foam::vtkPVFoam::convertMeshPointSets
(
vtkMultiBlockDataSet* output,
@ -639,13 +657,13 @@ void Foam::vtkPVFoam::convertMeshPointSets
for (auto partId : range)
{
const word partName = getPartName(partId);
if (!partStatus_[partId])
if (!selectedPartIds_.found(partId))
{
continue;
}
const word partName = getPartName(partId);
if (debug)
{
Info<< "Creating VTK mesh for pointSet=" << partName << endl;
@ -676,7 +694,7 @@ void Foam::vtkPVFoam::convertMeshPointSets
if (vtkmesh)
{
addToBlock(output, vtkmesh, range, datasetNo, partName);
partDataset_[partId] = datasetNo++;
partDataset_.set(partId, datasetNo++);
}
}

View File

@ -136,7 +136,7 @@ Foam::wordList Foam::vtkPVFoam::getZoneNames(const word& zoneType) const
void Foam::vtkPVFoam::updateInfoInternalMesh
(
vtkDataArraySelection* arraySelection
vtkDataArraySelection* select
)
{
if (debug)
@ -146,8 +146,8 @@ void Foam::vtkPVFoam::updateInfoInternalMesh
// Determine mesh parts (internalMesh, patches...)
//- Add internal mesh as first entry
rangeVolume_.reset(arraySelection->GetNumberOfArrays(), 1);
arraySelection->AddArray("internalMesh");
rangeVolume_.reset(select->GetNumberOfArrays(), 1);
select->AddArray("internalMesh");
if (debug)
{
@ -158,7 +158,7 @@ void Foam::vtkPVFoam::updateInfoInternalMesh
void Foam::vtkPVFoam::updateInfoLagrangian
(
vtkDataArraySelection* arraySelection
vtkDataArraySelection* select
)
{
if (debug)
@ -167,7 +167,6 @@ void Foam::vtkPVFoam::updateInfoLagrangian
<< " " << dbPtr_->timePath()/cloud::prefix << endl;
}
// use the db directly since this might be called without a mesh,
// but the region must get added back in
fileName lagrangianPrefix(cloud::prefix);
@ -182,11 +181,11 @@ void Foam::vtkPVFoam::updateInfoLagrangian
readDir(dbPtr_->timePath()/lagrangianPrefix, fileName::DIRECTORY)
);
rangeLagrangian_.reset(arraySelection->GetNumberOfArrays());
rangeLagrangian_.reset(select->GetNumberOfArrays());
forAll(cloudDirs, cloudi)
{
// Add cloud to GUI list
arraySelection->AddArray
select->AddArray
(
("lagrangian/" + cloudDirs[cloudi]).c_str()
);
@ -202,8 +201,8 @@ void Foam::vtkPVFoam::updateInfoLagrangian
void Foam::vtkPVFoam::updateInfoPatches
(
vtkDataArraySelection* arraySelection,
stringList& enabledEntries
vtkDataArraySelection* select,
HashSet<string>& enabledEntries
)
{
if (debug)
@ -212,14 +211,13 @@ void Foam::vtkPVFoam::updateInfoPatches
<< " [meshPtr=" << (meshPtr_ ? "set" : "null") << "]" << endl;
}
HashSet<string> enabledEntriesSet(enabledEntries);
rangePatches_.reset(arraySelection->GetNumberOfArrays());
rangePatches_.reset(select->GetNumberOfArrays());
if (meshPtr_)
{
const polyBoundaryMesh& patches = meshPtr_->boundaryMesh();
const HashTable<labelList>& groups = patches.groupPatchIDs();
DynamicList<string> displayNames(groups.size());
// Add (non-zero) patch groups to the list of mesh parts
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@ -243,29 +241,38 @@ void Foam::vtkPVFoam::updateInfoPatches
// Valid patch if nFace > 0 - add patch to GUI list
const string dpyName = "group/" + groupName;
arraySelection->AddArray(dpyName.c_str());
++rangePatches_;
displayNames.append(dpyName);
if (enabledEntriesSet.found(dpyName))
// Optionally replace group with patch name selections
// - must remove the group from the select itself, otherwise
// it can toggle on, but not toggle off very well
if
(
!reader_->GetShowGroupsOnly()
&& enabledEntries.erase(dpyName)
)
{
if (!reader_->GetShowGroupsOnly())
for (auto patchId : patchIDs)
{
enabledEntriesSet.erase(dpyName);
for (auto patchId : patchIDs)
const polyPatch& pp = patches[patchId];
if (pp.size())
{
const polyPatch& pp = patches[patchId];
if (pp.size())
{
enabledEntriesSet.insert
(
"patch/" + pp.name()
);
}
enabledEntries.insert
(
"patch/" + pp.name()
);
}
}
}
}
// Sort group names
Foam::sort(displayNames);
for (const auto& name : displayNames)
{
select->AddArray(name.c_str());
++rangePatches_;
}
// Add (non-zero) patches to the list of mesh parts
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@ -279,7 +286,7 @@ void Foam::vtkPVFoam::updateInfoPatches
if (pp.size())
{
// Add patch to GUI list
arraySelection->AddArray
select->AddArray
(
("patch/" + pp.name()).c_str()
);
@ -308,36 +315,24 @@ void Foam::vtkPVFoam::updateInfoPatches
false
);
// this should only ever fail if the mesh region doesn't exist
// This should only ever fail if the mesh region doesn't exist
if (ioObj.typeHeaderOk<polyBoundaryMesh>(true, false))
{
polyBoundaryMeshEntries patchEntries(ioObj);
// Read patches and determine sizes
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
// Read patches, determine sizes and patch groups
wordList names(patchEntries.size());
labelList sizes(patchEntries.size());
forAll(patchEntries, patchi)
{
const dictionary& patchDict = patchEntries[patchi].dict();
sizes[patchi] = readLabel(patchDict.lookup("nFaces"));
names[patchi] = patchEntries[patchi].keyword();
}
// Add (non-zero) patch groups to the list of mesh parts
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
HashTable<labelHashSet> groups(patchEntries.size());
HashTable<labelHashSet> groups(2*patchEntries.size());
forAll(patchEntries, patchi)
{
const dictionary& patchDict = patchEntries[patchi].dict();
wordList groupNames;
sizes[patchi] = readLabel(patchDict.lookup("nFaces"));
names[patchi] = patchEntries[patchi].keyword();
if
(
sizes[patchi] // Valid patch if nFace > 0
@ -351,26 +346,31 @@ void Foam::vtkPVFoam::updateInfoPatches
}
}
// Add (non-zero) patch groups to the list of mesh parts
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
DynamicList<string> displayNames(groups.size());
forAllConstIters(groups, iter)
{
const auto& groupName = iter.key();
const auto& patchIDs = iter.object();
const string dpyName = "group/" + groupName;
arraySelection->AddArray(dpyName.c_str());
++rangePatches_;
displayNames.append(dpyName);
// Optionally replace with patch name selection
// Optionally replace group with patch name selections
// - must remove the group from the select itself, otherwise
// it can toggle on, but not toggle off very well
if
(
enabledEntriesSet.found(dpyName)
&& !reader_->GetShowGroupsOnly()
!reader_->GetShowGroupsOnly()
&& enabledEntries.erase(dpyName)
)
{
enabledEntriesSet.erase(dpyName);
for (auto patchId : patchIDs)
{
enabledEntriesSet.insert
enabledEntries.insert
(
"patch/" + names[patchId]
);
@ -378,6 +378,13 @@ void Foam::vtkPVFoam::updateInfoPatches
}
}
// Sort group names
Foam::sort(displayNames);
for (const auto& name : displayNames)
{
select->AddArray(name.c_str());
++rangePatches_;
}
// Add (non-zero) patches to the list of mesh parts
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@ -389,7 +396,7 @@ void Foam::vtkPVFoam::updateInfoPatches
// Valid patch if nFace > 0 - add patch to GUI list
if (sizes[patchi])
{
arraySelection->AddArray
select->AddArray
(
("patch/" + names[patchi]).c_str()
);
@ -400,9 +407,6 @@ void Foam::vtkPVFoam::updateInfoPatches
}
}
// Update enabled entries in case of group selection
enabledEntries = enabledEntriesSet.toc();
if (debug)
{
Info<< "<end> updateInfoPatches" << endl;
@ -412,7 +416,7 @@ void Foam::vtkPVFoam::updateInfoPatches
void Foam::vtkPVFoam::updateInfoZones
(
vtkDataArraySelection* arraySelection
vtkDataArraySelection* select
)
{
if (!reader_->GetIncludeZones())
@ -440,10 +444,10 @@ void Foam::vtkPVFoam::updateInfoZones
namesLst = getZoneNames("cellZones");
}
rangeCellZones_.reset(arraySelection->GetNumberOfArrays());
rangeCellZones_.reset(select->GetNumberOfArrays());
forAll(namesLst, elemI)
{
arraySelection->AddArray
select->AddArray
(
("cellZone/" + namesLst[elemI]).c_str()
);
@ -463,10 +467,10 @@ void Foam::vtkPVFoam::updateInfoZones
namesLst = getZoneNames("faceZones");
}
rangeFaceZones_.reset(arraySelection->GetNumberOfArrays());
rangeFaceZones_.reset(select->GetNumberOfArrays());
forAll(namesLst, elemI)
{
arraySelection->AddArray
select->AddArray
(
("faceZone/" + namesLst[elemI]).c_str()
);
@ -486,10 +490,10 @@ void Foam::vtkPVFoam::updateInfoZones
namesLst = getZoneNames("pointZones");
}
rangePointZones_.reset(arraySelection->GetNumberOfArrays());
rangePointZones_.reset(select->GetNumberOfArrays());
forAll(namesLst, elemI)
{
arraySelection->AddArray
select->AddArray
(
("pointZone/" + namesLst[elemI]).c_str()
);
@ -505,7 +509,7 @@ void Foam::vtkPVFoam::updateInfoZones
void Foam::vtkPVFoam::updateInfoSets
(
vtkDataArraySelection* arraySelection
vtkDataArraySelection* select
)
{
if (!reader_->GetIncludeSets())
@ -545,26 +549,26 @@ void Foam::vtkPVFoam::updateInfoSets
}
rangeCellSets_.reset(arraySelection->GetNumberOfArrays());
rangeCellSets_.reset(select->GetNumberOfArrays());
rangeCellSets_ += addToSelection<cellSet>
(
arraySelection,
select,
objects,
"cellSet/"
);
rangeFaceSets_.reset(arraySelection->GetNumberOfArrays());
rangeFaceSets_.reset(select->GetNumberOfArrays());
rangeFaceSets_ += addToSelection<faceSet>
(
arraySelection,
select,
objects,
"faceSet/"
);
rangePointSets_.reset(arraySelection->GetNumberOfArrays());
rangePointSets_.reset(select->GetNumberOfArrays());
rangePointSets_ += addToSelection<pointSet>
(
arraySelection,
select,
objects,
"pointSet/"
);
@ -586,8 +590,8 @@ void Foam::vtkPVFoam::updateInfoLagrangianFields
Info<< "<beg> updateInfoLagrangianFields" << endl;
}
// preserve the enabled selections
stringList enabledEntries = getSelectedArrayEntries(select);
// Preserve the enabled selections
HashSet<string> enabledEntries = getSelectedArrayEntries(select);
select->RemoveAllArrays();
// TODO - currently only get fields from ONE cloud
@ -600,8 +604,9 @@ void Foam::vtkPVFoam::updateInfoLagrangianFields
return;
}
int partId = range.start();
word cloudName = getPartName(partId);
// Add Lagrangian fields even if particles are not enabled?
const int partId = range.start();
const word cloudName = getReaderPartName(partId);
// use the db directly since this might be called without a mesh,
// but the region must get added back in
@ -625,7 +630,7 @@ void Foam::vtkPVFoam::updateInfoLagrangianFields
addToSelection<IOField<symmTensor>>(select, objects);
addToSelection<IOField<tensor>>(select, objects);
// restore the enabled selections
// Restore the enabled selections
setSelectedArrayEntries(select, enabledEntries);
if (debug > 1)

View File

@ -45,7 +45,7 @@ void Foam::vtkPVFoam::updateInfoFields
<< endl;
}
stringList enabledEntries;
HashSet<string> enabledEntries;
if (!select->GetNumberOfArrays() && !meshPtr_)
{
// enable 'p' and 'U' only on the first call
@ -126,7 +126,7 @@ void Foam::vtkPVFoam::updateInfoFields
);
// restore the enabled selections
// Restore the enabled selections
setSelectedArrayEntries(select, enabledEntries);
if (debug)

View File

@ -303,10 +303,11 @@ void Foam::vtkPVblockMesh::updateInfo()
vtkDataArraySelection* blockSelection = reader_->GetBlockSelection();
vtkDataArraySelection* edgeSelection = reader_->GetCurvedEdgesSelection();
// preserve the enabled selections if possible
stringList enabledParts;
stringList enabledEdges;
const bool firstTime = (!blockSelection->GetNumberOfArrays() && !meshPtr_);
// Preserve the enabled selections if possible
HashSet<string> enabledParts;
HashSet<string> enabledEdges;
if (!firstTime)
{
enabledParts = getSelectedArrayEntries(blockSelection);
@ -326,7 +327,7 @@ void Foam::vtkPVblockMesh::updateInfo()
// Update curved edges list
updateInfoEdges(edgeSelection);
// restore the enabled selections
// Restore the enabled selections
if (!firstTime)
{
setSelectedArrayEntries(blockSelection, enabledParts);

View File

@ -194,22 +194,22 @@ Foam::hashedWordList Foam::foamPvCore::getSelected
}
Foam::stringList Foam::foamPvCore::getSelectedArrayEntries
Foam::HashSet<Foam::string>
Foam::foamPvCore::getSelectedArrayEntries
(
vtkDataArraySelection* select
)
{
stringList selections(select->GetNumberOfArrays());
label nElem = 0;
const int n = select->GetNumberOfArrays();
HashSet<string> selections(2*n);
forAll(selections, elemI)
for (int i=0; i < n; ++i)
{
if (select->GetArraySetting(elemI))
if (select->GetArraySetting(i))
{
selections[nElem++] = select->GetArrayName(elemI);
selections.insert(select->GetArrayName(i));
}
}
selections.setSize(nElem);
if (debug > 1)
{
@ -221,9 +221,9 @@ Foam::stringList Foam::foamPvCore::getSelectedArrayEntries
}
Info<< " )\nselected(";
forAll(selections, elemI)
for (auto k : selections)
{
Info<< " " << selections[elemI];
Info<< " " << k;
}
Info<< " )\n";
}
@ -232,65 +232,61 @@ Foam::stringList Foam::foamPvCore::getSelectedArrayEntries
}
Foam::stringList Foam::foamPvCore::getSelectedArrayEntries
Foam::HashSet<Foam::string>
Foam::foamPvCore::getSelectedArrayEntries
(
vtkDataArraySelection* select,
const arrayRange& selector
const arrayRange& slice
)
{
stringList selections(selector.size());
label nElem = 0;
const int n = select->GetNumberOfArrays();
HashSet<string> enabled(2*n);
for (auto i : selector)
for (auto i : slice)
{
if (select->GetArraySetting(i))
{
selections[nElem++] = select->GetArrayName(i);
enabled.insert(select->GetArrayName(i));
}
}
selections.setSize(nElem);
if (debug > 1)
{
Info<< "available(";
for (auto i : selector)
for (auto i : slice)
{
Info<< " \"" << select->GetArrayName(i) << "\"";
}
Info<< " )\nselected(";
forAll(selections, elemI)
for (auto k : enabled)
{
Info<< " " << selections[elemI];
Info<< " " << k;
}
Info<< " )\n";
}
return selections;
return enabled;
}
void Foam::foamPvCore::setSelectedArrayEntries
(
vtkDataArraySelection* select,
const stringList& selections
const HashSet<string>& enabled
)
{
const int n = select->GetNumberOfArrays();
// disable everything not explicitly enabled
select->DisableAllArrays();
// Loop through entries, setting values from selectedEntries
// Loop through entries, enabling as required
for (int i=0; i < n; ++i)
{
const string arrayName(select->GetArrayName(i));
forAll(selections, elemI)
const char* arrayName = select->GetArrayName(i);
if (enabled.found(arrayName))
{
if (selections[elemI] == arrayName)
{
select->EnableArray(arrayName.c_str());
break;
}
select->EnableArray(arrayName);
}
}
}

View File

@ -39,6 +39,7 @@ SourceFiles
#include "pointList.H"
#include "wordList.H"
#include "Hash.H"
#include "HashSet.H"
#include "hashedWordList.H"
#include "labelRange.H"
@ -208,25 +209,25 @@ public:
);
//- Retrieve the current selections
static stringList getSelectedArrayEntries
//- Retrieve the currently enabled selections
static HashSet<string> getSelectedArrayEntries
(
vtkDataArraySelection* select
);
//- Retrieve a sub-list of the current selections
static stringList getSelectedArrayEntries
//- Retrieve a sub-list of the currently enabled selections
static HashSet<string> getSelectedArrayEntries
(
vtkDataArraySelection* select,
const arrayRange& selector
const arrayRange& slice
);
//- Set selection(s)
//- Enable the selection(s)
static void setSelectedArrayEntries
(
vtkDataArraySelection* select,
const stringList& selections
const HashSet<string>& enabled
);