Skip to content

Commit

Permalink
Add snapped to integer vectors
Browse files Browse the repository at this point in the history
  • Loading branch information
joriskleiber committed Jun 16, 2024
1 parent feff365 commit 7da3b4d
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 25 deletions.
2 changes: 2 additions & 0 deletions godot-core/src/builtin/vectors/vector2i.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ impl_vector_fns!(Vector2i, glam::IVec2, i32, (x, y));
impl_vector2x_fns!(Vector2i, i32);

impl Vector2i {
impl_integer_vector_fns!(x, y);

/// Constructs a new `Vector2i` from a [`Vector2`]. The floating point coordinates will be truncated.
#[inline]
pub const fn from_vector2(v: Vector2) -> Self {
Expand Down
2 changes: 2 additions & 0 deletions godot-core/src/builtin/vectors/vector3i.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ impl_vector_fns!(Vector3i, glam::IVec3, i32, (x, y, z));
impl_vector3x_fns!(Vector3i, i32);

impl Vector3i {
impl_integer_vector_fns!(x, y, z);

/// Constructs a new `Vector3i` from a [`Vector3`]. The floating point coordinates will be truncated.
#[inline]
pub const fn from_vector3(v: Vector3) -> Self {
Expand Down
2 changes: 2 additions & 0 deletions godot-core/src/builtin/vectors/vector4i.rs
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ impl_vector_fns!(Vector4i, glam::IVec4, i32, (x, y, z, w));
impl_vector4x_fns!(Vector4i, i32);

impl Vector4i {
impl_integer_vector_fns!(x, y, z, w);

/// Constructs a new `Vector4i` from a [`Vector4`]. The floating point coordinates will be
/// truncated.
#[inline]
Expand Down
37 changes: 36 additions & 1 deletion godot-core/src/builtin/vectors/vector_macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -457,6 +457,42 @@ macro_rules! impl_vector_fns {
}
}

/// Implements functions that are present only on integer vectors.
macro_rules! impl_integer_vector_fns {
(
// Names of the components, for example `x, y`.
$($comp:ident),*
) => {
/// A new vector with each component snapped to the closest multiple of the corresponding
/// component in `step`.
pub fn snapped(self, step: Self) -> Self {
#[inline]
fn snap_one(mut value: i32, step: i32) -> i32 {
if step != 0 {
let a = value + step / 2;

// manual implement `a.div_floor(step)` since Rust's native method is still unstable, as of 1.79.0
let mut d = a / step;
let r = a % step;
if (r > 0 && step < 0) || (r < 0 && step > 0) {
d -= 1;
}

value = step * d;
}

value
}

Self::new(
$(
snap_one(self.$comp, step.$comp)
),*
)
}
};
}

/// Implements functions that are present only on floating-point vectors.
macro_rules! impl_float_vector_fns {
(
Expand Down Expand Up @@ -612,7 +648,6 @@ macro_rules! impl_float_vector_fns {

/// A new vector with each component snapped to the closest multiple of the corresponding
/// component in `step`.
// TODO: also implement for integer vectors
#[inline]
pub fn snapped(self, step: Self) -> Self {
Self::new(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -102,11 +102,10 @@ fn sign() {
assert_eq!(b.sign(), b.as_inner().sign());
}

// TODO: implement snapped for integer vectors
// #[itest]
// fn snapped() {
// let a = Vector2i::new(12, 34);
// let b = Vector2i::new(5, -5);

// assert_eq!(a.snapped(b), a.as_inner().snapped(b));
// }
#[itest]
fn snapped() {
let a = Vector2i::new(12, 34);
let b = Vector2i::new(5, -5);

assert_eq!(a.snapped(b), a.as_inner().snapped(b));
}
Original file line number Diff line number Diff line change
Expand Up @@ -99,11 +99,10 @@ fn sign() {
assert_eq!(b.sign(), b.as_inner().sign());
}

// TODO: implement snapped for integer vectors
// #[itest]
// fn snapped() {
// let a = Vector3i::new(12, 34, 56);
// let b = Vector3i::new(5, -5, 6);

// assert_eq!(a.snapped(b), a.as_inner().snapped(b));
// }
#[itest]
fn snapped() {
let a = Vector3i::new(12, 34, -56);
let b = Vector3i::new(5, -5, 6);

assert_eq!(a.snapped(b), a.as_inner().snapped(b));
}
Original file line number Diff line number Diff line change
Expand Up @@ -103,11 +103,10 @@ fn sign() {
assert_eq!(b.sign(), b.as_inner().sign());
}

// TODO: implement snapped for integer vectors
// #[itest]
// fn snapped() {
// let a = Vector4i::new(12, 34, 56, 78);
// let b = Vector4i::new(5, -5, 6, -6);

// assert_eq!(a.snapped(b), a.as_inner().snapped(b));
// }
#[itest]
fn snapped() {
let a = Vector4i::new(12, 34, 56, -78);
let b = Vector4i::new(5, -5, 6, 6);

assert_eq!(a.snapped(b), a.as_inner().snapped(b));
}

0 comments on commit 7da3b4d

Please sign in to comment.