8 #ifndef IMPALGEBRA_GRID_UTILITY_H
9 #define IMPALGEBRA_GRID_UTILITY_H
11 #include <IMP/algebra/algebra_config.h>
13 #include "internal/grid_interpolation.h"
15 #include "internal/grid_3d_impl.h"
16 IMPALGEBRA_BEGIN_NAMESPACE
22 template <
int D,
class Storage,
class Value,
class Embedding>
26 internal::get_interpolation_corners(g, pt);
27 Floats values = internal::get_interpolation_values(g, corners);
28 VectorD<D> fraction = internal::get_interpolation_fraction(g, pt);
29 return internal::get_interpolation_value(values, fraction);
39 template <
class Storage,
class Embedding>
42 const Vector3D &v,
const typename Storage::Value &outside = 0) {
44 const Vector3D halfside = g.get_unit_cell() * .5;
45 const Vector3D bottom_sample = g.get_bounding_box().get_corner(0) + halfside;
46 const Vector3D top_sample = g.get_bounding_box().get_corner(1) - halfside;
47 for (
unsigned int i = 0; i < 3; ++i) {
48 if (v[i] < bottom_sample[i] || v[i] >= top_sample[i]) {
53 using namespace internal::trilep_helpers;
56 internal::trilep_helpers::compute_voxel(g, v, ivox, r);
57 typename Storage::Value is[4];
58 for (
unsigned int i = 0; i < 4; ++i) {
60 unsigned int bx = ((i & 2) >> 1);
61 unsigned int by = (i & 1);
63 "Logic error in trilerp");
65 1 - r[2], get_value(g, ivox[0] + bx, ivox[1] + by, ivox[2], outside),
66 get_value(g, ivox[0] + bx, ivox[1] + by, ivox[2] + 1U, outside));
68 typename Storage::Value js[2];
69 for (
unsigned int i = 0; i < 2; ++i) {
75 IMPALGEBRA_END_NAMESPACE
77 #include "internal/grid_3d_impl.h"
85 #define IMP_GRID3D_FOREACH_VOXEL(g, action) \
87 unsigned int next_loop_voxel_index = 0; \
88 const IMP::algebra::Vector3D macro_map_unit_cell = g.get_unit_cell(); \
89 const int macro_map_nx = g.get_number_of_voxels(0); \
90 const int macro_map_ny = g.get_number_of_voxels(1); \
91 const int macro_map_nz = g.get_number_of_voxels(2); \
92 const IMP::algebra::Vector3D macro_map_origin = g.get_origin(); \
93 IMP::algebra::GridIndexD<3> voxel_index; \
94 int *voxel_index_data = voxel_index.access_data().get_data(); \
95 IMP::algebra::Vector3D voxel_center; \
96 for (voxel_index_data[0] = 0; voxel_index_data[0] < macro_map_nx; \
97 ++voxel_index_data[0]) { \
98 voxel_center[0] = macro_map_origin[0] + \
99 (voxel_index_data[0] + .5) * macro_map_unit_cell[0]; \
100 for (voxel_index_data[1] = 0; voxel_index_data[1] < macro_map_ny; \
101 ++voxel_index_data[1]) { \
102 voxel_center[1] = macro_map_origin[1] + \
103 (voxel_index_data[1] + .5) * macro_map_unit_cell[1]; \
104 for (voxel_index_data[2] = 0; voxel_index_data[2] < macro_map_nz; \
105 ++voxel_index_data[2]) { \
106 voxel_center[2] = macro_map_origin[2] + (voxel_index_data[2] + .5) * \
107 macro_map_unit_cell[2]; \
108 unsigned int loop_voxel_index = next_loop_voxel_index; \
109 IMP_UNUSED(loop_voxel_index); \
110 ++next_loop_voxel_index; \
123 #define IMP_GRID3D_FOREACH_SMALLER_EXTENDED_INDEX_RANGE( \
124 grid, center, lower_corner, upper_corner, action) \
126 int voxel_index[3]; \
127 IMP_USAGE_CHECK(lower_corner <= upper_corner, \
128 "Inverted range " << lower_corner << " " << upper_corner); \
129 IMP_USAGE_CHECK(lower_corner <= center, \
130 "Center not in range " << lower_corner << " " << center); \
131 IMP_USAGE_CHECK(center <= upper_corner, "Center not in range " \
132 << center << upper_corner); \
133 for (voxel_index[0] = lower_corner[0]; voxel_index[0] <= upper_corner[0]; \
134 ++voxel_index[0]) { \
135 if (voxel_index[0] > center[0]) break; \
136 for (voxel_index[1] = lower_corner[1]; \
137 voxel_index[1] <= upper_corner[1]; ++voxel_index[1]) { \
138 if (voxel_index[0] == center[0] && voxel_index[1] > center[1]) break; \
139 for (voxel_index[2] = lower_corner[2]; \
140 voxel_index[2] <= upper_corner[2]; ++voxel_index[2]) { \
141 if (voxel_index[0] == center[0] && voxel_index[1] == center[1] && \
142 voxel_index[2] >= center[2]) \
A class to represent a voxel grid.
A class to represent a voxel grid.
A voxel grid in d-dimensional space space.
A Cartesian vector in D-dimensions.
#define IMP_INTERNAL_CHECK(expr, message)
An assertion to check for internal errors in IMP. An IMP::ErrorException will be thrown.
const Storage::Value get_trilinearly_interpolated(const GridD< 3, Storage, typename Storage::Value, Embedding > &g, const Vector3D &v, const typename Storage::Value &outside=0)
Use trilinear interpolation to compute a smoothed value at v.
Value get_linearly_interpolated(const GridD< D, Storage, Value, Embedding > &g, const VectorD< D > &pt)