Skip to content

Commit

Permalink
Merge pull request #371 from hakonanes/oxford-binary-format-reader
Browse files Browse the repository at this point in the history
Add reader of EBSD patterns from Oxford binary .ebsp files
  • Loading branch information
hakonanes committed Jun 21, 2021
2 parents 9a98a55 + f72fe5c commit 4992625
Show file tree
Hide file tree
Showing 27 changed files with 506 additions and 23 deletions.
3 changes: 3 additions & 0 deletions doc/changelog.rst
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@ Contributors

Added
-----
- Reader for EBSD patterns stored in Oxford Instrument's binary .ebsp file
format, uncompressed and with intensities as 8-bit unsigned integers.
(`#? <https://github.com/pyxem/kikuchipy/pull/?>`_)
- Unit testing of docstring examples.
(`#350 <https://github.com/pyxem/kikuchipy/pull/350>`_)
- Support for Python 3.9.
Expand Down
54 changes: 51 additions & 3 deletions doc/load_save_data.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -507,11 +507,12 @@
"| ------------------------------- | ---- | ----- |\n",
"| Bruker Nano h5ebsd | Yes | No |\n",
"| EDAX TSL h5ebsd | Yes | No |\n",
"| EMsoft simulated EBSD HDF5 | Yes | No |\n",
"| EMsoft EBSD master pattern HDF5 | Yes | No |\n",
"| kikuchipy h5ebsd | Yes | Yes |\n",
"| NORDIF binary | Yes | Yes |\n",
"| NORDIF calibration patterns | Yes | No |\n",
"| EMsoft simulated EBSD HDF5 | Yes | No |\n",
"| EMsoft EBSD master pattern HDF5 | Yes | No |\n",
"| Oxford Instruments binary | Yes | No |\n",
"\n",
"<div class=\"alert alert-info\">\n",
"\n",
Expand Down Expand Up @@ -552,7 +553,7 @@
"metadata": {},
"outputs": [],
"source": [
"kikuchipy_ebsd = \"kikuchipy/patterns.h5\"\n",
"kikuchipy_ebsd = \"kikuchipy_h5ebsd/patterns.h5\"\n",
"s_awsm, s2 = kp.load(\n",
" filename=datadir + kikuchipy_ebsd,\n",
" scan_group_names=[\"My awes0m4 Xcan #! with a long title\", \"Scan 2\"]\n",
Expand Down Expand Up @@ -853,6 +854,53 @@
"details of the underlying theory."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Oxford Instrument's binary\n",
"\n",
"Patterns stored in the Oxford Instruments binary .ebsp file format, uncompressed\n",
"and with intensities as 8-bit unsigned integer, can be read by providing the\n",
"navigation shape (number of map rows, number of map columns), which is not\n",
"stored explicitly in the file"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"oxford_binary_path = datadir + \"oxford_binary/\"\n",
"s_oxford = kp.load(filename=oxford_binary_path + \"patterns.ebsp\",\n",
" navigation_shape=(3, 3),\n",
")\n",
"s_oxford"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Here, the Oxford Instruments binary\n",
"[file_reader()](reference.rst#kikuchipy.io.plugins.oxford_binary.file_reader) is\n",
"called. If the navigation shape is not known, the number of patterns in the file\n",
"can be guessed by the reader from inspecting the file header. The returned\n",
"signal will then have a single navigation dimension the size of the number of\n",
"patterns"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"s_oxford2 = kp.load(filename=oxford_binary_path + \"patterns.ebsp\")\n",
"s_oxford2"
]
},
{
"cell_type": "markdown",
"metadata": {},
Expand Down
9 changes: 9 additions & 0 deletions doc/reference.rst
Original file line number Diff line number Diff line change
Expand Up @@ -308,6 +308,7 @@ plugins
nordif_calibration_patterns
emsoft_ebsd
emsoft_ebsd_master_pattern
oxford_binary

The plugins import patterns and parameters from file formats into
:class:`~kikuchipy.signals.EBSD` or
Expand Down Expand Up @@ -355,6 +356,14 @@ emsoft_ebsd_master_pattern
:undoc-members:
:show-inheritance:

oxford_binary
~~~~~~~~~~~~~

.. automodule:: kikuchipy.io.plugins.oxford_binary
:members:
:undoc-members:
:show-inheritance:

....

pattern
Expand Down
2 changes: 1 addition & 1 deletion kikuchipy/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -409,4 +409,4 @@ def doctest_setup_teardown(request):
@pytest.fixture(autouse=True)
def import_to_namespace(doctest_namespace):
DIR_PATH = os.path.dirname(__file__)
doctest_namespace["DATA_DIR"] = os.path.join(DIR_PATH, "data/kikuchipy")
doctest_namespace["DATA_DIR"] = os.path.join(DIR_PATH, "data/kikuchipy_h5ebsd")
4 changes: 2 additions & 2 deletions kikuchipy/data/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@
see :doc:`open datasets <open_datasets>`.
"""

from pathlib import Path
import os
from pathlib import Path
from typing import Union

import pooch as ppooch
Expand Down Expand Up @@ -111,7 +111,7 @@ def nickel_ebsd_small(**kwargs) -> EBSD:
signal : EBSD
EBSD signal.
"""
return _load(filename="data/kikuchipy/patterns.h5", **kwargs)
return _load(filename="data/kikuchipy_h5ebsd/patterns.h5", **kwargs)


def nickel_ebsd_master_pattern_small(**kwargs) -> EBSDMasterPattern:
Expand Down
2 changes: 1 addition & 1 deletion kikuchipy/data/_registry.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@

# fmt: off
registry = {
"data/kikuchipy/patterns.h5": "7a99ce88174c725f5407b6fcc1eab0c4255694ca8e6029fde7f372f3ab40897f",
"data/kikuchipy_h5ebsd/patterns.h5": "7a99ce88174c725f5407b6fcc1eab0c4255694ca8e6029fde7f372f3ab40897f",
"data/emsoft_ebsd_master_pattern/ni_mc_mp_20kv_uint8_gzip_opts9.h5": "8a7c1fb471d9ce750f0332a154e87cf41eed7529be508548e0c0f51ec6f92bc2",
"data/nickel_ebsd_large/patterns.h5": "3ea6e729c3adfdea9dce461806f011c24bf70b011dcf4d90a23a6aa29f15872c",
"data/silicon_ebsd_moving_screen/si_in.h5": "de57b8ef7213420af694c191c939f44818979b3db9873e74cc85cabde824b7eb",
Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
File renamed without changes.
File renamed without changes.
68 changes: 68 additions & 0 deletions kikuchipy/data/oxford_binary/create_oxford_binary_file.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
# -*- coding: utf-8 -*-
# Copyright 2019-2021 The kikuchipy developers
#
# This file is part of kikuchipy.
#
# kikuchipy 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.
#
# kikuchipy 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 kikuchipy. If not, see <http://www.gnu.org/licenses/>.

import os

import numpy as np

import kikuchipy as kp


s = kp.data.nickel_ebsd_small()

sr, sc = s.axes_manager.signal_shape[::-1]
n_pixels = sr * sc
nr, nc = s.axes_manager.navigation_shape[::-1]
n_patterns = nr * nc

dir_data = os.path.abspath(os.path.dirname(__file__))
fname = os.path.join(dir_data, "patterns.ebsp")
file = open(fname, mode="w")

# Write file header: 8 bytes with ?
file_header = np.ones(1, dtype=np.int64)
file_header.tofile(file)

# Pattern header: 16 bytes with pattern height, pattern width and ?
pattern_header_size = 16
pattern_header = np.zeros(8, dtype=np.uint16)
pattern_header[2] = sr
pattern_header[4] = sc

# Pattern footer: 18 bytes with ?
pattern_footer_size = 18
pattern_footer = np.zeros(9, dtype=np.uint16)

# Write pattern positions: 8 bytes per position
pattern_positions = np.arange(n_patterns, dtype=np.int64)
pattern_positions *= pattern_header_size + n_pixels + pattern_footer_size
pattern_positions += file_header.nbytes + n_patterns * 8
# Shift positions one step to the right
new_order = np.roll(np.arange(n_patterns), 1)
pattern_positions = pattern_positions[new_order]
pattern_positions.tofile(file)

# Write patterns with header and footer
pattern_data = s.data
for i in new_order:
r, c = np.unravel_index(i, (nr, nc))
pattern_header.tofile(file)
pattern_data[r, c].tofile(file)
pattern_footer.tofile(file)

file.close()
Binary file added kikuchipy/data/oxford_binary/patterns.ebsp
Binary file not shown.
2 changes: 1 addition & 1 deletion kikuchipy/generators/tests/test_virtual_bse_generator.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
from kikuchipy.signals import EBSD, LazyEBSD, VirtualBSEImage

DIR_PATH = os.path.dirname(__file__)
KIKUCHIPY_FILE = os.path.join(DIR_PATH, "../../data/kikuchipy/patterns.h5")
KIKUCHIPY_FILE = os.path.join(DIR_PATH, "../../data/kikuchipy_h5ebsd/patterns.h5")

matplotlib.use("Agg") # For plotting

Expand Down
2 changes: 2 additions & 0 deletions kikuchipy/io/_io.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
h5ebsd,
nordif,
nordif_calibration_patterns,
oxford_binary,
)
from kikuchipy.io._util import _get_input_bool, _ensure_directory

Expand All @@ -44,6 +45,7 @@
h5ebsd,
nordif,
nordif_calibration_patterns,
oxford_binary,
]

default_write_ext = set()
Expand Down
2 changes: 2 additions & 0 deletions kikuchipy/io/plugins/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,11 +23,13 @@
emsoft_ebsd_master_pattern,
h5ebsd,
nordif,
oxford_binary,
)

__all__ = [
"emsoft_ebsd",
"emsoft_ebsd_master_pattern",
"h5ebsd",
"nordif",
"oxford_binary",
]
2 changes: 1 addition & 1 deletion kikuchipy/io/plugins/nordif_calibration_patterns.py
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ def _get_coordinates(filename: str) -> List[Tuple[int, int]]:
raise ValueError(err)
xy = []
for line in content[l_start + 1 :]:
match = re.search("Calibration \((.*)\)", line)
match = re.search(r"Calibration \((.*)\)", line)
try:
match = match.group(1)
match = match.split(",")
Expand Down
Loading

0 comments on commit 4992625

Please sign in to comment.