Hi @lgivord ,
Thanks for your response! Yes, I am able to write a non-temporal partitioned data set collection, as follows:
# this works
def write_vtk_hdf_nontransient(path: Path):
sphere = vtkSphereSource()
sphere.SetThetaResolution(20)
sphere.SetPhiResolution(20)
sphere.Update()
surf_polydata = sphere.GetOutput()
# Convert surface to unstructured grid (for demo)
tri_filter = vtkTriangleFilter()
tri_filter.SetInputData(surf_polydata)
tri_filter.Update()
volume_ugrid = vtkUnstructuredGrid()
volume_ugrid.ShallowCopy(tri_filter.GetOutput())
# Create a surface mesh (PolyData) as-is
surface = surf_polydata
# Create a vtkPartitionedDataSetCollection
pdc = vtkPartitionedDataSetCollection()
pdc.Initialize()
# Partition 0 = volume mesh
pdc.SetNumberOfPartitionedDataSets(2)
pdc.SetNumberOfPartitions(0, 1)
pdc.SetNumberOfPartitions(1, 1)
pdc.SetPartition(0, 0, volume_ugrid)
pdc.GetMetaData(0).Set(vtkDataObject.FIELD_NAME(), "Volume")
# Partition 1 = surface mesh
pdc.SetPartition(1, 0, surface)
pdc.GetMetaData(1).Set(vtkDataObject.FIELD_NAME(), "Surface")
assembly = vtkDataAssembly()
root = assembly.GetRootNode()
assembly.AddNode("Volume", root)
assembly.AddNode("Surface", root)
pdc.SetDataAssembly(assembly)
writer = vtkHDFWriter()
writer.SetFileName(str(path))
# Important: set input as the PDC
writer.SetInputDataObject(pdc)
writer.Write()
return pdc
As for the temporal dataset, I’m currently using the pipeline defined in How to write time dependent data in VTKHDF files because I want to replicate this except using vtkhdfwriter. Here’s the complete code that I currently have (this code does not work properly, this is what I’m trying to fix):
# this does not work properly
from pathlib import Path
def write_transient_pds(path: Path | None):
sphere0 = vtkSphereSource()
sphere0.SetPhiResolution(30)
sphere0.SetThetaResolution(30)
sphere0.SetRadius(10)
sphere1 = vtkSphereSource()
sphere1.SetPhiResolution(30)
sphere1.SetThetaResolution(30)
sphere1.SetRadius(10)
sphere1.SetCenter(15, 15, 15)
# store the spheres in a single partitioned data set
groupDataSets = vtkGroupDataSetsFilter()
groupDataSets.AddInputConnection(sphere0.GetOutputPort())
groupDataSets.AddInputConnection(sphere1.GetOutputPort())
groupDataSets.SetOutputTypeToPartitionedDataSetCollection()
# generate time steps
timeSteps = vtkGenerateTimeSteps()
timeSteps.SetInputConnection(groupDataSets.GetOutputPort())
timeValues = np.linspace(0.0, 2*np.pi, 100, endpoint=False)
timeSteps.SetTimeStepValues(100, timeValues)
# generate fields
addFields = vtkSpatioTemporalHarmonicsAttribute()
harmonics = np.array([
[1.0, 1.0, 0.6283, 0.6283, 0.6283, 0.0],
[3.0, 1.0, 0.6283, 0.0, 0.0, 1.5708],
[2.0, 2.0, 0.0, 0.6283, 0.0, 3.1416],
[1.0, 3.0, 0.0, 0.0, 0.6283, 4.7124]
])
for iH in range(harmonics.shape[0]):
addFields.AddHarmonic(harmonics[iH, 0],
harmonics[iH, 1],
harmonics[iH, 2],
harmonics[iH, 3],
harmonics[iH, 4],
harmonics[iH, 5])
addFields.SetInputConnection(timeSteps.GetOutputPort())
# warp spheres
warp = vtkWarpScalar()
warp.SetInputConnection(addFields.GetOutputPort())
warp.SetInputArrayToProcess(0, 0, 0,
vtkDataObject.FIELD_ASSOCIATION_POINTS,
'SpatioTemporalHarmonics')
warp.Update()
"""
# pdsc = warp.GetOutputDataObject(0)
# assembly = vtkDataAssembly()
# root = assembly.GetRootNode()
# assembly.AddNode("sphere1", root)
# assembly.AddNode("sphere2", root)
# pdsc.SetDataAssembly(assembly)
"""
if path:
writer = vtkHDFWriter()
writer.SetFileName(str(path))
# Important: set input as the PDC
# writer.SetInputDataObject(pdsc)
writer.SetInputConnection(warp.GetOutputPort())
writer.SetWriteAllTimeSteps(True)
writer.Write()
# return pdsc
return warp
One change from the original blog post is that I changed the vtkGroupDataSetsFilter
output to pdc rather than just partitioned data set. Another two observations:
- If I pass the warp object, the vtkhdf writer dies.
- If I extract the output data object from the warp object and persist that, then the persisted object isn’t temporal.
Also, for reference, I have a working example of a temporal polydata using vtkhdfwriter:
# this works
def write_simple_temporal_sphere(output_path: str):
# 1. Create a basic sphere
sphere = vtkSphereSource()
sphere.SetRadius(10)
sphere.SetThetaResolution(30)
sphere.SetPhiResolution(30)
# 2. Generate 2 time steps (e.g., t = 0 and pi)
time_gen = vtkGenerateTimeSteps()
time_gen.SetInputConnection(sphere.GetOutputPort())
time_gen.SetTimeStepValues(2, [0.0, np.pi])
# 3. Add time-varying field with one harmonic
harmonics = vtkSpatioTemporalHarmonicsAttribute()
harmonics.SetInputConnection(time_gen.GetOutputPort())
harmonics.AddHarmonic(1, 0, 0.5, 0.5, 0.5, 0.0) # magnitude, frequency, direction, phase
# 4. Warp the mesh using the harmonic field
warp = vtkWarpScalar()
warp.SetInputConnection(harmonics.GetOutputPort())
warp.SetInputArrayToProcess(0, 0, 0, vtkDataObject.FIELD_ASSOCIATION_POINTS, "SpatioTemporalHarmonics")
# 5. Write to .vtkhdf with all timesteps
writer = vtkHDFWriter()
writer.SetInputConnection(warp.GetOutputPort())
writer.SetFileName(output_path)
writer.SetWriteAllTimeSteps(True)
writer.Write()
So tl;dr: I’m able to write a temporal polydata and I’m able to write a nontemporal partitioned dataset collection, but I don’t know how to write a temporal partitioned dataset collection to vtkhdf. Let me know what additional info I can provide.
Thanks again!