IMP logo
IMP Reference Guide  2.14.0
The Integrative Modeling Platform
SpiderImageReaderWriter.h
Go to the documentation of this file.
1 /**
2  * \file IMP/em2d/SpiderImageReaderWriter.h
3  * \brief Management of Images in Spider format
4  * Copyright 2007-2020 IMP Inventors. All rights reserved.
5 */
6 
7 #ifndef IMPEM2D_SPIDER_IMAGE_READER_WRITER_H
8 #define IMPEM2D_SPIDER_IMAGE_READER_WRITER_H
9 
10 #include "IMP/em2d/em2d_config.h"
13 #include "IMP/em/ImageHeader.h"
15 #include <IMP/algebra/utility.h>
16 #include <IMP/algebra/endian.h>
17 #include <IMP/exception.h>
18 #include <IMP/log_macros.h>
19 #include <IMP/log.h>
20 #include <typeinfo>
21 #include <complex>
22 #include <string>
23 #include <cstdio>
24 #include <iostream>
25 #include <fstream>
26 #include <cstring>
27 
28 IMPEM2D_BEGIN_NAMESPACE
29 
30 //! Class to read and write EM images in Spider format. They are stored in
31 //! the header and data passed as arguments
33  public:
34  String filename_;
35  bool skip_type_check_;
36  bool force_reversed_;
37  bool skip_extra_checkings_;
38 
39  //! Empty constructor. It does not force reversed header and does not
40  //! skip any of the tests
41  /*!
42  * \note reversed is only used in case that the type_check is skipped
43  */
45  skip_type_check_ = false;
46  force_reversed_ = false;
47  skip_extra_checkings_ = false;
48  }
49 
50  //! Full constructor.
51  /*!
52  * \param[in] filename file to read
53  * \param[in] skip_type_check if true, the check for type of image is skipped
54  * \param[in] force_reversed if true, the reverse mode is enforced
55  * for reading and writing
56  * \param[in] skip_extra_checkings if true, the most stringent
57  * tests for consistency of images are skipped when reading
58  */
59  SpiderImageReaderWriter(const String &filename, bool skip_type_check,
60  bool force_reversed, bool skip_extra_checkings) {
61  filename_ = filename;
62  skip_type_check_ = skip_type_check;
63  force_reversed_ = force_reversed;
64  skip_extra_checkings_ = skip_extra_checkings;
65  }
66 
67  void read(const String &filename, em::ImageHeader &header,
68  cv::Mat &data) const {
69  this->read_from_floats(filename, header, data);
70  }
71 
72  void write(const String &filename, em::ImageHeader &header,
73  const cv::Mat &data) const {
74  this->write_to_floats(filename, header, data);
75  }
76 
77  void read_from_ints(const String &, em::ImageHeader &, cv::Mat &) const {}
78 
79  void write_to_ints(const String &, em::ImageHeader &, const cv::Mat &) const {
80  }
81 
82  //! Reads an image file in Spider format and stores the content
83  //! int the header and data parameters
84  /*!
85  \param[in] filename file to read
86  \param[in] header header to store the info
87  \param[in] data a matrix to store the grid of data of the image
88  */
89  void read_from_floats(const String &filename, em::ImageHeader &header,
90  cv::Mat &data) const {
91  IMP_LOG_VERBOSE("reading with SpiderImageReaderWriter" << std::endl);
92  std::ifstream in;
93  in.open(filename.c_str(), std::ios::in | std::ios::binary);
94  if (in.fail() || in.bad()) {
95  IMP_THROW("Error reading from Spider Image " << filename, IOException);
96  }
97  //! The header format is already in Spider format, just read it
98  bool success = header.read(in, skip_type_check_, force_reversed_,
99  skip_extra_checkings_);
100  if (!success) {
101  IMP_THROW("Error reading header from Spider Image " << filename,
102  IOException);
103  }
104  IMP_LOG_VERBOSE("Header of image " << filename << std::endl << header
105  << std::endl);
106  // Adjust size of the matrix according to the header
107  unsigned int rows = (int)header.get_number_of_rows();
108  unsigned int cols = (int)header.get_number_of_columns();
109  data.create(rows, cols, CV_64FC1);
110  // Read with casting
111  float aux;
112  for (cvDoubleMatIterator it = data.begin<double>();
113  it != data.end<double>(); ++it) {
114  if (!(force_reversed_ ^ algebra::get_is_big_endian())) {
115  in.read(reinterpret_cast<char *>(&aux), sizeof(float));
116  } else {
117  algebra::reversed_read(reinterpret_cast<char *>(&aux), sizeof(float), 1,
118  in, true);
119  }
120  (*it) = static_cast<double>(aux);
121  }
122  in.close();
123  }
124 
125  //! Writes an EM image in Spider format
126  /*!
127  * \param[in] filename file to write
128  * \param[in] header header with the image info
129  * \param[in] data a matrix with the grid of data of the image
130  */
131  void write_to_floats(const String &filename, em::ImageHeader &header,
132  const cv::Mat &data) const {
133  std::ofstream out;
134  out.open(filename.c_str(), std::ios::out | std::ios::binary);
135  //! The image header is already in Spider format, just write it
136  header.write(out, force_reversed_ ^ algebra::get_is_big_endian());
137 
138  float aux;
139  for (cvDoubleConstMatIterator it = data.begin<double>();
140  it != data.end<double>(); ++it) {
141  aux = (float)(*it);
142  if (!(force_reversed_ ^ algebra::get_is_big_endian())) {
143  out.write(reinterpret_cast<char *>(&aux), sizeof(float));
144  } else {
145  algebra::reversed_write(reinterpret_cast<char *>(&aux), sizeof(float),
146  1, out, true);
147  }
148  }
149  out.close();
150  }
151 
153 };
154 
155 IMPEM2D_END_NAMESPACE
156 
157 #endif /* IMPEM2D_SPIDER_IMAGE_READER_WRITER_H */
bool get_is_big_endian()
Returns 1 if machine is big endian else 0.
Functions to convert between ImageHeader and DensityHeader Copyright 2007-2020 IMP Inventors...
Class to deal with the header of Electron Microscopy images in IMP.
Definition: ImageHeader.h:28
#define IMP_OBJECT_METHODS(Name)
Define the basic things needed by any Object.
Definition: object_macros.h:25
Virtual class for reader/writers of images.
SpiderImageReaderWriter(const String &filename, bool skip_type_check, bool force_reversed, bool skip_extra_checkings)
Full constructor.
Virtual class for reader/writers of images Copyright 2007-2020 IMP Inventors. All rights reserved...
Interface with OpenCV Copyright 2007-2020 IMP Inventors. All rights reserved.
#define IMP_LOG_VERBOSE(expr)
Definition: log_macros.h:83
Exception definitions and assertions.
void read_from_floats(const String &filename, em::ImageHeader &header, cv::Mat &data) const
An input/output exception.
Definition: exception.h:174
void write(const String &filename, bool force_reversed=false)
Writes the header of a EM image.
Functions to deal with byte order.
Functions to deal with very common math operations.
Logging and error reporting support.
void write_to_floats(const String &filename, em::ImageHeader &header, const cv::Mat &data) const
Writes an EM image in Spider format.
void reversed_read(void *dest, size_t size, size_t nitems, std::ifstream &f, bool reverse)
Reads from file in normal or reverse order.
#define IMP_THROW(message, exception_name)
Throw an exception with a message.
Definition: check_macros.h:50
int read(const String filename, bool skip_type_check=false, bool force_reversed=false, bool skip_extra_checkings=false)
Reads the header of a EM image.
void reversed_write(const void *src, size_t size, size_t nitems, std::ofstream &f, bool reverse=false)
Writes to a file in normal or reversed order.
Header for EM images. Compatible with Spider and Xmipp formats Copyright 2007-2020 IMP Inventors...
Logging and error reporting support.
std::string String
Basic string value.
Definition: types.h:44