1# -*- coding: utf-8 -*-
2# imageio is distributed under the terms of the (new) BSD License.
3
4"""Read TIFF from FEI SEM microscopes.
5
6Backend Library: internal
7
8This format is based on :mod:`TIFF <imageio.plugins.tifffile>`, and supports the
9same parameters. FEI microscopes append metadata as ASCII text at the end of the
10file, which this reader correctly extracts.
11
12Parameters
13----------
14discard_watermark : bool
15 If True (default), discard the bottom rows of the image, which
16 contain no image data, only a watermark with metadata.
17watermark_height : int
18 The height in pixels of the FEI watermark. The default is 70.
19
20See Also
21--------
22 :mod:`imageio.plugins.tifffile`
23
24"""
25
26
27from .tifffile import TiffFormat
28
29
30class FEISEMFormat(TiffFormat):
31 """See :mod:`imageio.plugins.feisem`"""
32
33 def _can_write(self, request):
34 return False # FEI-SEM only supports reading
35
36 class Reader(TiffFormat.Reader):
37 def _get_data(self, index=0, discard_watermark=True, watermark_height=70):
38 """Get image and metadata from given index.
39
40 FEI images usually (always?) contain a watermark at the
41 bottom of the image, 70 pixels high. We discard this by
42 default as it does not contain any information not present
43 in the metadata.
44 """
45 im, meta = super(FEISEMFormat.Reader, self)._get_data(index)
46 if discard_watermark:
47 im = im[:-watermark_height]
48 return im, meta
49
50 def _get_meta_data(self, index=None):
51 """Read the metadata from an FEI SEM TIFF.
52
53 This metadata is included as ASCII text at the end of the file.
54
55 The index, if provided, is ignored.
56
57 Returns
58 -------
59 metadata : dict
60 Dictionary of metadata.
61 """
62 if hasattr(self, "_fei_meta"):
63 return self._fei_meta
64
65 md = {"root": {}}
66 current_tag = "root"
67 reading_metadata = False
68 filename = self.request.get_local_filename()
69 with open(filename, encoding="utf8", errors="ignore") as fin:
70 for line in fin:
71 if not reading_metadata:
72 if not line.startswith("Date="):
73 continue
74 else:
75 reading_metadata = True
76 line = line.rstrip()
77 if line.startswith("["):
78 current_tag = line.lstrip("[").rstrip("]")
79 md[current_tag] = {}
80 else:
81 if "=" in line: # ignore empty and irrelevant lines
82 key, val = line.split("=", maxsplit=1)
83 for tag_type in (int, float):
84 try:
85 val = tag_type(val)
86 except ValueError:
87 continue
88 else:
89 break
90 md[current_tag][key] = val
91 if not md["root"] and len(md) == 1:
92 raise ValueError("Input file %s contains no FEI metadata." % filename)
93
94 self._fei_meta = md
95 return md