Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Document concepts of the new geometry description #612

Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
143 changes: 120 additions & 23 deletions manual/source/design.rst
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ used by NeXus. These are:
Multidimensional arrays and scalars representing the actual data to be stored

:ref:`Design-Attributes`
Attributes containing additional metadata can be assigned to groups, fields,
Attributes containing additional metadata can be assigned to groups, fields,
or :ref:`files <Design-FileAttributes>`.

:ref:`Design-Links`
Expand Down Expand Up @@ -239,7 +239,7 @@ a more descriptive representation of the concept of linking.

Linking in a NeXus file

.. index::
.. index::
! single: target, attribute
single: link, target, attribute
single: address, absolute
Expand All @@ -249,13 +249,13 @@ a more descriptive representation of the concept of linking.

NeXus links are HDF5 hard links with an additional ``target`` attribute.
The ``target`` attribute is added [#]_ for NeXus to distinguish the HDF5 path to the
*original* [#]_ dataset. The value of the ``target`` attribute is the HDF5
*original* [#]_ dataset. The value of the ``target`` attribute is the HDF5
path [#absolute_address]_ to the *original* dataset.

.. [#] When using the NAPI, the ``target`` attribute is added automatically.
When the NAPI is not used to write NeXus/HDF5 files, this attribute must
When the NAPI is not used to write NeXus/HDF5 files, this attribute must
be added. Here are the steps to follow:

#. Get the HDF5 reference ID of the source item (*field*, *group*, or *link*) to be linked.
#. If the ID does not have a ``target`` attribute defined:
#. Get the absolute HDF5 address [#absolute_address]_ of the ID.
Expand All @@ -270,18 +270,18 @@ path [#absolute_address]_ to the *original* dataset.
such as *h5dump*, confusion often occurs over which dataset is
original and which is a link to the original. Actually, both HDF5 paths
point to the exact, same dataset which exists at a specific offset in the HDF5 file.

See the :ref:`FAQ` question: **I'm using links to place data in two places.
Which one should be the data and which one is the link?**

.. [#absolute_address] When using the ``target`` attribute,
.. [#absolute_address] When using the ``target`` attribute,
**always** specify the HDF5 address
as an *absolute** address (starts from the HDF5 root,
such as: ``/entry/instrument/detector/polar_angle``)
such as: ``/entry/instrument/detector/polar_angle``)
rather than a **relative** address (starting from the current group,
such as: ``detector/polar_angle``).

.. [#hdf5_hard_link] HDF5 hard link:
.. [#hdf5_hard_link] HDF5 hard link:
https://support.hdfgroup.org/HDF5/doc/RM/RM_H5L.html#Link-CreateHard

NeXus links are best understood with an example.
Expand Down Expand Up @@ -363,10 +363,10 @@ showing an external file link in HDF5:
TARGETPATH "entry/instrument/detector/data"
}

.. note:: The NAPI code [#]_ makes no ``target`` attribute assignment for
links to external files. It is best to avoid using the
.. note:: The NAPI code [#]_ makes no ``target`` attribute assignment for
links to external files. It is best to avoid using the
``target`` attribute with external file links.

.. Q: So what happens if the object in the external file
has a ``@target`` attribute?

Expand All @@ -375,7 +375,7 @@ showing an external file link in HDF5:

The NAPI maintains a group attribute ``@napimount`` that provides
a URL to a group in another file. More information about the
``@napimount`` attribute is described in the
``@napimount`` attribute is described in the
*NeXus Programmers Reference*. [#]_

.. [#] http://download.nexusformat.org/doc/NeXusIntern.pdf
Expand All @@ -385,9 +385,9 @@ a URL to a group in another file. More information about the
Combining NeXus links and External File Links
---------------------------------------------

Consider the case described in
Consider the case described in
:ref:`Links to Data in External HDF5 Files <h5py-example-external-links>`,
where numerical data are provided in two different HDF5 files and a *master* NeXus HDF5 file links to
where numerical data are provided in two different HDF5 files and a *master* NeXus HDF5 file links to
the data through external file links. HDF5 will not allow hard links to be constructed with these data
objects in the master file. An error such as *Interfile hard links are not allowed* (as generated
from h5py) will arise. This makes sense since there is no such data object in the file.
Expand Down Expand Up @@ -591,7 +591,7 @@ certain applications of NeXus, too. The tool which NeXus uses for the expression
:ref:`Application Definition <application.definitions>`.
A NeXus Application Definition describes which groups and data items have to be present in
a file in order to properly describe an application of NeXus. For example for describing a powder diffraction
experiment.
experiment.
An application definition may also declare terms which are optional in the data file.
Typically an application definition will contain only a small subset of the many groups and fields
defined in NeXus. NeXus application definitions are also expressed in the NeXus Definition Language (NXDL). A tool exists
Expand Down Expand Up @@ -621,10 +621,23 @@ that it is always possible to add more data to a file without breaking its compl
.. index::
! coordinate systems; NeXus

.. _Design-Geometry:

NeXus Geometry
##############

NeXus supports description of the shape, position and orientation of objects in
:ref:`Design-CoordinateSystem`. Position and
orientation can be defined as :ref:`CoordinateTransformations` using the
:ref:`NXtransformations` class. :ref:`ShapeDescriptions` use the :ref:`NXoff_geometry`
or :ref:`NXcylindrical_geometry` class.

You may come across old files which use :ref:`LegacyGeometryDescriptions`.

.. _Design-CoordinateSystem:

NeXus Coordinate Systems
########################
The NeXus Coordinate System
===========================

.. index::
single: geometry
Expand Down Expand Up @@ -669,7 +682,7 @@ Coordinate Transformations

.. index:: transformation matrices

In the recommended way of dealing with geometry NeXus uses a series of
In the recommended way of dealing with geometry NeXus uses a series of
:index:`transformations <coordinate systems; transformations>` to place objects in space.
In this world view, the absolute position of a component or a detector pixel with respect to
the laboratory coordinate system is calculated by applying a series of translations and
Expand Down Expand Up @@ -849,13 +862,97 @@ This is also a nice example of the application of transformation matrices:
#. This also moves the direction of the *z* vector.
Along which you translate the component to place by distance.

.. _ShapeDescriptions:

Legacy Geometry Decriptions
===========================
Shape Descriptions
==================

``NXoff_geometry``
------------------

The shape of instrument components can be described using the :ref:`NXoff_geometry`
class. ``NXoff_geometry`` is a polygon-based description, based on the open OFF format.
Conversion between OFF files and the NeXus description is straightforward. This is
beneficial as existing tools can use, view or manipulate the geometry in OFF files.
CAD software, for example `FreeCAD <https://www.freecadweb.org/>`_, can be used to
define the geometry. 3D rendering tools such as `Geomview <http://www.geomview.org/>`_
can be used to view the geometry. `McStas <http://www.mcstas.org/>`_ can use OFF
files to define the shape of components for scattering simulations.

The example OFF file shown below defines a cube. The first line containing
numbers defines: the number of vertices, the number of faces (polygons) making
up the model's surface, and the number of edges in the mesh. Note, the number of
edges must be present but does not need to be correct
(http://www.geomview.org/docs/html/OFF.html).

.. literalinclude:: examples/cube.off
:tab-width: 4
:linenos:
:language: text

Following the initial line are the xyz coordinates of each vertex. Proceeding
which is the list of faces. Each line defining a face starts with the number of
vertices in that face followed by the sequence number of the composing vertices,
indexed from zero. The vertex indices form a winding order by defining the face
normal by the right-hand rule. The number of vertices in each face need not be
constant; a mesh can comprise of polygons of many different orders.

The list of vertices in an OFF file maps directly to the ``vertices`` dataset in
the :ref:`NXoff_geometry` class. The vertex indices of the face list in the OFF
file occupy the ``winding_order`` dataset of the NeXus class, however the list
is flattened to 1D in order to avoid a ragged-edged dataset, which are not
easy to work with using HDF libraries. A ``faces`` dataset contains the position
of the first entry in ``winding_order`` for each face. The ``NXoff_geometry``
equivalent of the OFF cube example is shown below.

.. literalinclude:: examples/cube_NXoff_geometry.txt
:tab-width: 4
:linenos:
:language: text

``NXcylindrical_geometry``
--------------------------

Although the polygon-based description of :ref:`NXoff_geometry` is very flexible,
it is not ideal for curved shapes when high precision is required since a very
large number of vertices may be necessary. A common example of this is when
describing helium tube, neutron detectors. :ref:`NXcylindrical_geometry` provides
a more concise method of defining shape for such cases.

Like ``NXoff_geometry``, ``NXcylindrical_geometry`` contains a ``vertices``
dataset. The indices of three vertices (**A**, **B**, **C** in :ref:`fig.cylinder_3_points`) in the ``vertices`` dataset are used to
define each cylinder in the ``cylinders`` dataset.

.. compound::

.. _fig.cylinder_3_points:

.. figure:: img/cylinder_3_points.png
:alt: fig.cylinder_3_points
:width: 15%
:align: center

Cylinder definition with three vertices


Detector Shape Descriptions
---------------------------

An ``NXoff_geometry`` or ``NXcylindrical_geometry`` group named ``shape`` can
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The field name added was detector_shape, not shape

be placed in an ``NXdetector`` or ``NXdetector_module`` to define the complete
shape of the detector. Alternatively, the group can be named ``pixel_shape``
and define the shape of a single pixel. In this case, ``x_pixel_offset``,
``y_pixel_offset`` and ``z_pixel_offset`` datasets of the ``NXdetector`` define
how the pixel shape is tiled to form the geometry of the complete detector.

.. _LegacyGeometryDescriptions:

Legacy Geometry Descriptions
============================

The above system of chained transformations is the recommended way of
The above system of chained transformations is the recommended way of
encoding geometry going forward. This section describes the traditional way
this was handled in NeXus, which you may find occasionally in old files.
this was handled in NeXus, which you may find occasionally in old files.


:index:`Coordinate systems <coordinate systems>`
Expand Down
19 changes: 19 additions & 0 deletions manual/source/examples/cube.off
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
OFF
# cube.off
# A cube

8 6 12
1.0 0.0 1.0
0.0 1.0 1.0
-1.0 0.0 1.0
0.0 -1.0 1.0
1.0 0.0 0.0
0.0 1.0 0.0
-1.0 0.0 0.0
0.0 -1.0 0.0
4 0 1 2 3
4 7 4 0 3
4 4 5 1 0
4 5 6 2 1
4 3 2 6 7
4 6 5 4 7
15 changes: 15 additions & 0 deletions manual/source/examples/cube_NXoff_geometry.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
shape : NXoff_geometry
@NX_class = "NXoff_geometry"
vertices =
1.0, 0.0, 1.0
0.0, 1.0 , 1.0
-1.0, 0.0, 1.0
0.0, -1.0, 1.0
1.0, 0.0, 0.0
0.0, 1.0, 0.0
-1.0, 0.0, 0.0
0.0, -1.0, 0.0
faces =
0, 4, 8, 12, 16, 20
winding_order =
0, 1, 2, 3, 7, 4, 0, 3, 4, 5, 1, 0, 5, 6, 2, 1, 3, 2, 6, 7, 6, 5, 4, 7
Binary file added manual/source/img/cylinder_3_points.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.