This is a read only copy of the old FEniCS QA forum. Please visit the new QA forum to ask questions

Writing multiple functions to a single XDMF/HDF5 file

+2 votes

Dear all,

I would like to save multiple functions with different function spaces in a single XDMF file for visualization with Paraview/VisIt (preferably), e.g., a vector function $u$ and a scalar function $p$.

I tried:

xf = XDMFFile("test.xdmf")
xf.write(u)
xf.write(p)

This seems to work, but in Paraview only the first function written can be displayed. While both show up in the properties inspector, only $u$ is actually eligible for plotting.

Any comments on how to get this to work?

Thanks, David

ps: example output:

$ cat test.xdmf

<?xml version="1.0"?>
<Xdmf Version="2.0" xmlns:xi="http://www.w3.org/2001/XInclude">
  <Domain>
    <Grid Name="TimeSeries" GridType="Collection" CollectionType="Temporal">
      <Time TimeType="List">
        <DataItem Format="XML" Dimensions="2"> 0 1</DataItem>
      </Time>
      <Grid Name="grid_1" GridType="Uniform">
        <Topology NumberOfElements="512" TopologyType="Triangle">
          <DataItem Format="HDF" Dimensions="512 3">test.h5:/Mesh/0/topology</DataItem>
        </Topology>
        <Geometry GeometryType="XY">
          <DataItem Format="HDF" Dimensions="289 2">test.h5:/Mesh/0/coordinates</DataItem>
        </Geometry>
        <Attribute Name="f_19" AttributeType="Vector" Center="Node">
          <DataItem Format="HDF" Dimensions="289 3">test.h5:/VisualisationVector/0</DataItem>
        </Attribute>
      </Grid>
      <Grid Name="grid_2" GridType="Uniform">
        <Topology NumberOfElements="512" TopologyType="Triangle">
          <DataItem Format="HDF" Dimensions="512 3">test.h5:/Mesh/1/topology</DataItem>
        </Topology>
        <Geometry GeometryType="XY">
          <DataItem Format="HDF" Dimensions="289 2">test.h5:/Mesh/1/coordinates</DataItem>
        </Geometry>
        <Attribute Name="f_31" AttributeType="Scalar" Center="Node">
          <DataItem Format="HDF" Dimensions="289 1">test.h5:/VisualisationVector/1</DataItem>
        </Attribute>
      </Grid>
    </Grid>
  </Domain>
</Xdmf>

$ h5dump -H test.h5

HDF5 "test.h5" {
GROUP "/" {
   GROUP "Mesh" {
      GROUP "0" {
         DATASET "cell_indices" {
            DATATYPE  H5T_STD_U64LE
            DATASPACE  SIMPLE { ( 512 ) / ( 512 ) }
         }
         DATASET "coordinates" {
            DATATYPE  H5T_IEEE_F64LE
            DATASPACE  SIMPLE { ( 289, 2 ) / ( 289, 2 ) }
         }
         DATASET "topology" {
            DATATYPE  H5T_STD_I64LE
            DATASPACE  SIMPLE { ( 512, 3 ) / ( 512, 3 ) }
            ATTRIBUTE "celltype" {
               DATATYPE  H5T_STRING {
                  STRSIZE 8;
                  STRPAD H5T_STR_NULLTERM;
                  CSET H5T_CSET_ASCII;
                  CTYPE H5T_C_S1;
               }
               DATASPACE  SCALAR
            }
            ATTRIBUTE "partition" {
               DATATYPE  H5T_STD_U64LE
               DATASPACE  SIMPLE { ( 1 ) / ( 1 ) }
            }
         }
      }
      GROUP "1" {
         DATASET "cell_indices" {
            DATATYPE  H5T_STD_U64LE
            DATASPACE  SIMPLE { ( 512 ) / ( 512 ) }
         }
         DATASET "coordinates" {
            DATATYPE  H5T_IEEE_F64LE
            DATASPACE  SIMPLE { ( 289, 2 ) / ( 289, 2 ) }
         }
         DATASET "topology" {
            DATATYPE  H5T_STD_I64LE
            DATASPACE  SIMPLE { ( 512, 3 ) / ( 512, 3 ) }
            ATTRIBUTE "celltype" {
               DATATYPE  H5T_STRING {
                  STRSIZE 8;
                  STRPAD H5T_STR_NULLTERM;
                  CSET H5T_CSET_ASCII;
                  CTYPE H5T_C_S1;
               }
               DATASPACE  SCALAR
            }
            ATTRIBUTE "partition" {
               DATATYPE  H5T_STD_U64LE
               DATASPACE  SIMPLE { ( 1 ) / ( 1 ) }
            }
         }
      }
   }
   GROUP "VisualisationVector" {
      DATASET "0" {
         DATATYPE  H5T_IEEE_F64LE
         DATASPACE  SIMPLE { ( 289, 3 ) / ( 289, 3 ) }
      }
      DATASET "1" {
         DATATYPE  H5T_IEEE_F64LE
         DATASPACE  SIMPLE { ( 289, 1 ) / ( 289, 1 ) }
      }
   }
}
}
asked Sep 29, 2016 by dajuno FEniCS User (4,140 points)

1 Answer

+3 votes
 
Best answer

This doesn't really work well at the moment (but it is definitely something we would like to improve). I think what happens, is that the dataset gets saved as a TimeSeries, and each time-step will represent a field, so t=0 would be u, and t=1 would be p. Probably best to save as separate files, for now. To address this, we need to enrich the interface to XDMFFile.

answered Sep 29, 2016 by chris_richardson FEniCS Expert (31,740 points)
selected Sep 29, 2016 by dajuno

ok, good to know! thanks, that was fast ;)

Using the timeseries functionality to write multiple functions seems to be broken now in dolfin 2016.2.0 anyway. Only the first function is written, the second call to "xf.write(p)" is apparently ignored.

The change seems to be associated with an update in the XDMF format from 2.0 to 3.0. i.e. dolfin 2016.2.0 now writes XDMF 3 files.

An enriched XDMF interface would be handy. Is there a flag for reverting to the former behaviour? (writing XDMF 2.0 with multiple functions encoded as "time series")

Time series now require you to supply a time value, but it does still work, if you do that.
Because of some faulty documentation for Xdmf3, you need to use the Xdmf (not Xdmf3) reader to read it in ParaView.

You're right, I see it now. We can still write multiple functions using xf.write(p,t) with t=0,1,2 etc to emulate the old behaviour.

...