use nalgebra as na;
type Vec2 = nalgebra::Vector2<f32>;
type Vec3 = nalgebra::Vector3<f32>;
type Vec4 = nalgebra::Vector4<f32>;
type IVec2 = nalgebra::Vector2<i32>;
type IVec4 = nalgebra::Vector4<i32>;
use crate::multilinear::sample_multilinear;
#[repr(C, align(16))]
#[derive(Default, Copy, Clone, Debug)]
pub struct GridSampler
{
pub extents: Vec4,
pub corner: Vec4,
pub resolution: IVec4,
pub cell_size: f32,
}
impl GridSampler
{
pub fn new(corner: &Vec3, extents: &Vec3, cell_size: f32) -> GridSampler
{
let resolution = (extents / cell_size).map(|v| v.ceil());
GridSampler {
extents: Vec4::new(extents.x, extents.y, extents.z, 0.0),
corner: Vec4::new(corner.x, corner.y, corner.z, 0.0),
cell_size,
resolution: IVec4::new(
resolution.x as i32,
resolution.y as i32,
resolution.z as i32,
0,
),
}
}
pub fn resolution(&self) -> IVec4 { self.resolution }
pub fn position_to_grid_coord(&self, pos: &Vec2) -> IVec2
{
let coord: IVec2 =
na::try_convert((pos - self.corner.xy()) / self.cell_size).unwrap();
coord
}
pub fn quantize_position(&self, pos: &Vec2) -> Vec2
{
let coord = IVec2::new(
((pos.x - self.corner.x) / self.cell_size).floor() as i32,
((pos.y - self.corner.y) / self.cell_size).floor() as i32,
);
let res: Vec2 = na::convert(coord);
res * self.cell_size + self.corner.xy()
}
pub fn coord_to_pos(&self, index: &IVec2) -> Vec2
{
let pos: Vec2 = na::convert(*index);
pos * self.cell_size + self.corner.xy()
}
pub fn index_to_coord(&self, index: usize) -> IVec2
{
let resolution = self.resolution();
let x = index as i32 / resolution.y;
let y = index as i32 % resolution.y;
IVec2::new(x, y)
}
pub fn coord_to_index(&self, coord: &IVec2) -> usize
{
let resolution = self.resolution();
let index = (coord.x * resolution.y + coord.y) as usize;
index
}
pub fn bounds(&self) -> (Vec2, Vec2)
{
(self.corner.xy(), self.corner.xy() + self.extents.xy())
}
pub fn linear_sample(&self, pos: &Vec2, data: &[f32]) -> f32
{
sample_multilinear(
&[pos[0], pos[1]],
&[self.corner.x, self.corner.y],
&[self.extents.x, self.extents.y],
self.cell_size,
&data,
)
}
}