You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

80 lines
2.1 KiB

  1. from pims import FramesSequenceND, Frame
  2. from nd2reader.exc import NoImageError
  3. from nd2reader.nd2parser import ND2Parser
  4. class ND2Reader(FramesSequenceND):
  5. """
  6. PIMS wrapper for the ND2 parser
  7. """
  8. def __init__(self, filename):
  9. self.filename = filename
  10. # first use the parser to parse the file
  11. self._fh = open(filename, "rb")
  12. self._parser = ND2Parser(self._fh)
  13. # Setup metadata
  14. self.metadata = self._parser.metadata
  15. # Set data type
  16. self._dtype = self._parser.get_dtype_from_metadata()
  17. # Setup the axes
  18. self._setup_axes()
  19. @classmethod
  20. def class_exts(cls):
  21. """
  22. So PIMS open function can use this reader for opening .nd2 files
  23. :return:
  24. """
  25. return {'nd2'} | super(ND2Reader, cls).class_exts()
  26. def close(self):
  27. """
  28. Correctly close the file handle
  29. :return:
  30. """
  31. if self._fh is not None:
  32. self._fh.close()
  33. def get_frame_2D(self, c, t, z):
  34. """
  35. Gets a given frame using the parser
  36. :param c:
  37. :param t:
  38. :param z:
  39. :return:
  40. """
  41. c_name = self.metadata["channels"][c]
  42. try:
  43. image = self._parser.get_image_by_attributes(t, 0, c_name, z, self.metadata["width"],
  44. self.metadata["height"])
  45. except (TypeError, NoImageError):
  46. return Frame([])
  47. else:
  48. return image
  49. @property
  50. def pixel_type(self):
  51. """
  52. Return the pixel data type
  53. :return:
  54. """
  55. return self._dtype
  56. def _setup_axes(self):
  57. """
  58. Setup the xyctz axes, iterate over t axis by default
  59. :return:
  60. """
  61. self._init_axis('x', self.metadata["width"])
  62. self._init_axis('y', self.metadata["height"])
  63. self._init_axis('c', len(self.metadata["channels"]))
  64. self._init_axis('t', len(self.metadata["frames"]))
  65. self._init_axis('z', len(self.metadata["z_levels"]))
  66. # provide the default
  67. self.iter_axes = 't'