IMP logo
IMP Reference Guide  2.18.0
The Integrative Modeling Platform
ProjectionMask.h
Go to the documentation of this file.
1 /**
2  * \file IMP/em2d/ProjectionMask.h
3  * \brief projection masks
4  * Copyright 2007-2022 IMP Inventors. All rights reserved.
5 */
6 
7 #ifndef IMPEM2D_PROJECTION_MASK_H
8 #define IMPEM2D_PROJECTION_MASK_H
9 
10 #include <IMP/em2d/em2d_config.h>
12 #include "IMP/em2d/CenteredMat.h"
13 #include "IMP/atom/Mass.h"
14 #include "IMP/em/exp.h"
15 #include "IMP/algebra/Vector3D.h"
16 #include "IMP/algebra/Vector2D.h"
17 #include "IMP/algebra/Rotation3D.h"
20 #include "IMP/core/XYZR.h"
21 #include "IMP/Particle.h"
22 #include "IMP/exception.h"
23 #include <complex>
24 #include <boost/shared_ptr.hpp>
25 #include <boost/serialization/access.hpp>
26 #include <boost/serialization/split_free.hpp>
27 
28 IMPEM2D_BEGIN_NAMESPACE
29 
30 class ProjectionMask;
31 class MasksManager;
32 
33 typedef boost::shared_ptr<ProjectionMask> ProjectionMaskPtr;
34 typedef boost::shared_ptr<MasksManager> MasksManagerPtr;
35 
36 //! Mask that contains the projection of a given particles. This matrices
37 //! speed up projecting because the only have to be computed once for a model
38 class IMPEM2DEXPORT ProjectionMask {
39  public:
40  ProjectionMask() {}
41 #if !defined(DOXYGEN) && !defined(SWIG)
42  ProjectionMask(const em::KernelParameters& kparams,
43  double voxelsize, double mass = 1.0);
44 
45  //! Generates the mask
46  /*!
47  \param[in] KP Kernel parameters to employ. See the EM module
48  \param[in] mass Mass to give to the mask
49  */
50  void create(const em::KernelParameters& kparams,
51  double mass = 1.0);
52 #endif
53 
54  //! Adds the values of the mask to a matrix at the given pixel
55  /*!
56  \param[out] m matrix where the values of the mask are added.
57  \param[in] v pixel where to apply the values. Currently used as integer.
58  */
59  void apply(cv::Mat &m, const algebra::Vector2D &v);
60 
61  void show(std::ostream &out = std::cout) const;
62 
63  ~ProjectionMask();
64 
65  protected:
66  int dim_; // dimension of the mask
67  double sq_pixelsize_; // Used to save multiplications
68  cv::Mat data_; // actual matrix with the mask
69 private:
70  friend class boost::serialization::access;
71 
72  template<class Archive> void serialize(Archive &ar, const unsigned int) {
73  ar & dim_ & sq_pixelsize_ & data_;
74  }
75 };
76 
78 
79 IMPEM2D_END_NAMESPACE
80 
81 namespace boost {
82  namespace serialization {
83  template<class Archive> inline void save(
84  Archive &ar, const std::map<double, IMP::em2d::ProjectionMaskPtr> &m,
85  const unsigned int) {
86  size_t sz = m.size();
87  ar << sz;
88  for (const auto &p : m) {
89  ar << p.first;
90  ar << *(p.second);
91  }
92  }
93 
94  template<class Archive> inline void load(
95  Archive &ar, std::map<double, IMP::em2d::ProjectionMaskPtr> &m,
96  const unsigned int) {
97  m.clear();
98  size_t sz;
99  ar >> sz;
100  for (size_t i = 0; i < sz; ++i) {
101  double mass;
102  IMP::em2d::ProjectionMaskPtr ptr(new IMP::em2d::ProjectionMask());
103  ar >> mass;
104  ar >> *ptr;
105  m[mass] = ptr;
106  }
107  }
108 
109  template<class Archive> inline void serialize(
110  Archive &ar, std::map<double, IMP::em2d::ProjectionMaskPtr> &m,
111  const unsigned int version) {
112  boost::serialization::split_free(ar, m, version);
113  }
114  }
115 }
116 
117 IMPEM2D_BEGIN_NAMESPACE
118 
119 // Place a matrix in another
120 // Very ugly but very fast projecting function
121 
122 /*!
123  \param[in] mask matrix to place in m
124  \param[in] m matrix
125  \param[in] v Pixel of the matrix dest where the center of m is put.
126 */
127 inline void do_place(cv::Mat &mask, cv::Mat &m, const algebra::Vector2D &v) {
128 
129  // v is the vector of coordinates respect to the center of the matrix m
130  int vi = algebra::get_rounded(v[0]);
131  int vj = algebra::get_rounded(v[1]);
132 
133  // Centers for the matrix
134  int center[2];
135  center[0] = static_cast<int>(0.5 * m.rows);
136  center[1] = static_cast<int>(0.5 * m.cols);
137 
138  int start[2], end[2];
139  start[0] = -center[0];
140  start[1] = -center[1];
141  end[0] = m.rows - 1 - center[0];
142  end[1] = m.cols - 1 - center[1];
143 
144  // Check range: If the vector is outside the matrix, don't do anything.
145  if (vi < start[0] || vi > end[0]) return;
146  if (vj < start[1] || vj > end[1]) return;
147 
148  // Centers for the mask
149  int mcenter[2];
150  mcenter[0] = static_cast<int>(0.5 * mask.rows);
151  mcenter[1] = static_cast<int>(0.5 * mask.cols);
152 
153  int mstart[2], mend[2];
154  mstart[0] = -mcenter[0];
155  mstart[1] = -mcenter[1];
156  mend[0] = mask.rows - 1 - mcenter[0];
157  mend[1] = mask.cols - 1 - mcenter[1];
158 
159  // Get the admissible range for the mask
160  int start_i = std::max(start[0] - vi, mstart[0]);
161  int start_j = std::max(start[1] - vj, mstart[1]);
162  int end_i = std::min(end[0] - vi, mend[0]);
163  int end_j = std::min(end[1] - vj, mend[1]);
164 
165  int row = vi + center[0];
166  int col = vj + center[1];
167 
168  for (int i = start_i; i <= end_i; ++i) {
169  int p = i + row;
170  for (int j = start_j; j <= end_j; ++j) {
171  m.at<double>(p, j + col) +=
172  mask.at<double>(i + mcenter[0], j + mcenter[1]);
173  }
174  }
175 }
176 
177 //! Management of projection masks
178 class IMPEM2DEXPORT MasksManager {
179  public:
180  MasksManager() {
181  is_setup_ = false;
182  };
183 
184  MasksManager(double resolution, double pixelsize) {
185  setup_kernel(resolution, pixelsize);
186  }
187 
188  //! Initializes the kernel
189  inline void setup_kernel(double resolution, double pixelsize) {
190  kernel_params_ = em::KernelParameters((float)resolution);
191  pixelsize_ = pixelsize;
192  is_setup_ = true;
193  }
194 
195  //! Generates all the masks for a set of particles. This is the function
196  //! you typically want to use
197  void create_masks(const ParticlesTemp &ps);
198 
199  //! Creates the adequate mask for a particle of given mass
200  /*!
201  \param[in] mass of the particle
202  */
203  void create_mask(double mass);
204 
205  //! Returns the adequate mask for a particle of given mass
206  ProjectionMaskPtr find_mask(double mass);
207 
208  void show(std::ostream &out = std::cout) const;
209 
210  unsigned int get_number_of_masks() const { return mass2mask_.size(); }
211 
212  ~MasksManager();
213 
214  protected:
215  // A map to store the masks
216  std::map<double, ProjectionMaskPtr> mass2mask_;
217  // Kernel Params for the particles
218  em::KernelParameters kernel_params_;
219  // Pixel size for the masks
220  double pixelsize_;
221  bool is_setup_;
222 
223 private:
224  friend class boost::serialization::access;
225 
226  template<class Archive> void serialize(Archive &ar, const unsigned int) {
227  ar & mass2mask_ & kernel_params_ & pixelsize_ & is_setup_;
228  }
229 
230 };
231 
233 
234 IMPEM2D_END_NAMESPACE
235 
236 #endif /* IMPEM2D_PROJECTION_MASK_H */
A decorator for particles with mass.
VectorD< 2 > Vector2D
Definition: VectorD.h:417
Calculates and stores Gaussian kernel parameters.
void setup_kernel(double resolution, double pixelsize)
Initializes the kernel.
Simple 2D vector class.
Calculates and stores Gaussian kernel parameters.
Interface with OpenCV Copyright 2007-2022 IMP Inventors. All rights reserved.
Exception definitions and assertions.
An approximation of the exponential function.
A more IMP-like version of the std::vector.
Definition: Vector.h:42
#define IMP_VALUES(Name, PluralName)
Define the type for storing sets of values.
Definition: value_macros.h:23
int get_rounded(const T &x)
Rounds a number to next integer.
Stores and converts spherical coordinates.
Simple 3D rotation class.
Classes to handle individual model particles. (Note that implementation of inline functions is in int...
std::ostream & show(Hierarchy h, std::ostream &out=std::cout)
Print the hierarchy using a given decorator to display each node.
Simple 3D vector class.
void do_place(cv::Mat &mask, cv::Mat &m, const algebra::Vector2D &v)
Decorator for a sphere-like particle.
Management of projection masks.
Decorator for OpenCV matrix to use relative coordinates Copyright 2007-2022 IMP Inventors. All rights reserved.