19#include <covfie/core/algebra/affine.hpp>
20#include <covfie/core/backend/primitive/array.hpp>
21#include <covfie/core/backend/transformer/affine.hpp>
22#include <covfie/core/backend/transformer/clamp.hpp>
23#include <covfie/core/backend/transformer/linear.hpp>
24#include <covfie/core/backend/transformer/nearest_neighbour.hpp>
25#include <covfie/core/backend/transformer/strided.hpp>
26#include <covfie/core/field.hpp>
27#include <covfie/core/field_view.hpp>
28#include <covfie/core/parameter_pack.hpp>
29#include <covfie/core/vector.hpp>
39 covfie::backend::strided<covfie::vector::size3, covfie::backend::array<covfie::vector::float3>>;
42 covfie::backend::affine<covfie::backend::clamp<covfie::backend::linear<stored_backend_t>>>>;
45 covfie::backend::clamp<covfie::backend::nearest_neighbour<stored_backend_t>>>>;
49 std::array<float, 3>
min;
50 std::array<float, 3>
max;
51 std::array<std::size_t, 3>
n;
59 for (std::size_t i = 0; i < 3; ++i) {
61 throw std::invalid_argument(
"GridSpec: axis " + std::to_string(i) +
62 " needs at least 2 samples");
64 if (!(spec.
max[i] > spec.
min[i])) {
65 throw std::invalid_argument(
"GridSpec: axis " + std::to_string(i) +
" needs max > min");
74[[nodiscard]]
inline float grid_pos(
float min,
float max, std::size_t n, std::size_t i) {
75 return min +
static_cast<float>(i) * (max - min) /
static_cast<float>(n - 1);
83 covfie::algebra::affine<3> translation =
84 covfie::algebra::affine<3>::translation(-spec.
min[0], -spec.
min[1], -spec.
min[2]);
85 covfie::algebra::affine<3> scaling = covfie::algebra::affine<3>::scaling(
86 static_cast<float>(spec.
n[0] - 1) / (spec.
max[0] - spec.
min[0]),
87 static_cast<float>(spec.
n[1] - 1) / (spec.
max[1] - spec.
min[1]),
88 static_cast<float>(spec.
n[2] - 1) / (spec.
max[2] - spec.
min[2]));
94 using clamp_cfg_t = writer_field_t::backend_t::backend_t::configuration_t;
95 clamp_cfg_t clamp_cfg{};
96 for (std::size_t i = 0; i < 3; ++i) {
97 clamp_cfg.min[i] = 0.0f;
98 clamp_cfg.max[i] = std::nextafter(
static_cast<float>(spec.
n[i] - 1), 0.0f);
102 writer_field_t::backend_t::configuration_t(scaling * translation), std::move(clamp_cfg),
104 writer_field_t::backend_t::backend_t::backend_t::backend_t::configuration_t{
105 spec.
n[0], spec.
n[1], spec.
n[2]}));
Definition covfie_chains.h:36
void validate(GridSpec const &spec)
Throw if spec cannot produce a well-formed grid: every axis needs at least two samples (n - 1 underfl...
Definition covfie_chains.h:58
covfie::backend::strided< covfie::vector::size3, covfie::backend::array< covfie::vector::float3 > > stored_backend_t
Definition covfie_chains.h:39
covfie::field< covfie::backend::affine< covfie::backend::clamp< covfie::backend::nearest_neighbour< stored_backend_t > > > > writer_field_t
Definition covfie_chains.h:45
float grid_pos(float min, float max, std::size_t n, std::size_t i)
Position of sample i on an axis with n samples spanning [min, max].
Definition covfie_chains.h:74
writer_field_t make_writer_field(GridSpec const &spec)
Build an empty writer-chain field over spec, ready to be filled via writer_field_t::view_t::at(x,...
Definition covfie_chains.h:80
covfie::field< covfie::backend::affine< covfie::backend::clamp< covfie::backend::linear< stored_backend_t > > > > reader_field_t
Definition covfie_chains.h:42
Axis-aligned grid: n[i] samples spanning [min[i], max[i]] (mm).
Definition covfie_chains.h:48
std::array< std::size_t, 3 > n
Definition covfie_chains.h:51
std::array< float, 3 > min
Definition covfie_chains.h:49
std::array< float, 3 > max
Definition covfie_chains.h:50