Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Move Point out of cubic splines module and expand it #12747

Merged
merged 7 commits into from
Mar 28, 2024
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion crates/bevy_color/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -239,7 +239,7 @@ macro_rules! impl_componentwise_point {
}
}

impl bevy_math::cubic_splines::Point for $ty {}
impl bevy_math::VectorSpace for $ty {}
mweatherley marked this conversation as resolved.
Show resolved Hide resolved
};
}

Expand Down
133 changes: 133 additions & 0 deletions crates/bevy_math/src/common_traits.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
use glam::{Quat, Vec2, Vec3, Vec3A, Vec4};
use std::fmt::Debug;
use std::ops::{Add, Div, Mul, Sub};

/// A type that supports the mathematical operations of a vector space, irrespective of dimension.
mweatherley marked this conversation as resolved.
Show resolved Hide resolved
mweatherley marked this conversation as resolved.
Show resolved Hide resolved
pub trait VectorSpace:
Mul<f32, Output = Self>
+ Div<f32, Output = Self>
+ Add<Self, Output = Self>
+ Sub<Self, Output = Self>
+ Default
+ Debug
+ Clone
+ Copy
{
/// Perform vector space linear interpolation between this element and another, based
/// on the parameter `t`. When `t` is `0`, `self` is recovered. When `t` is `1`, `rhs`
/// is recovered.
///
/// Note that the value of `t` is not clamped by this function, so interpolating outside
/// of the interval `[0,1]` is allowed.
#[inline]
fn lerp(&self, rhs: Self, t: f32) -> Self {
*self * (1. - t) + rhs * t
}
}

impl VectorSpace for Quat {}
impl VectorSpace for Vec4 {}
impl VectorSpace for Vec3 {}
impl VectorSpace for Vec3A {}
impl VectorSpace for Vec2 {}
impl VectorSpace for f32 {}

/// A type that supports the operations of a normed vector space; i.e. a norm operation in addition
/// to those of [`VectorSpace`]. The implementor must guarantee that the axioms of a normed vector
/// space are satisfied.
pub trait NormedVectorSpace: VectorSpace {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The mathematician in me also wants to see MetricSpace and InnerProductSpace traits with corresponding blanket impls, but I agree with Alice that we shouldn't add traits until the need arises.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree! I suspect it will come up before too long if someone tries to use NormedVectorSpace and ends up needing a dot product.

/// The size of this element. The return value should always be nonnegative.
fn norm(self) -> f32;

/// The squared norm of this element. Computing this is often faster than computing
/// [`Normed::norm`].
#[inline]
fn norm_squared(self) -> f32 {
self.norm() * self.norm()
}

/// The distance between this element and another, as determined by the norm.
#[inline]
fn distance(self, rhs: Self) -> f32 {
(rhs - self).norm()
}

/// The squared distance between this element and another, as determined by the norm. Note that
/// this is often faster to compute in practice than [`NormedVectorSpace::distance`].
#[inline]
fn distance_squared(self, rhs: Self) -> f32 {
(rhs - self).norm_squared()
}
}

impl NormedVectorSpace for Quat {
#[inline]
fn norm(self) -> f32 {
self.length()
}

#[inline]
fn norm_squared(self) -> f32 {
self.length_squared()
}
}

impl NormedVectorSpace for Vec4 {
#[inline]
fn norm(self) -> f32 {
self.length()
}

#[inline]
fn norm_squared(self) -> f32 {
self.length_squared()
}
}

impl NormedVectorSpace for Vec3 {
#[inline]
fn norm(self) -> f32 {
self.length()
}

#[inline]
fn norm_squared(self) -> f32 {
self.length_squared()
}
}

impl NormedVectorSpace for Vec3A {
#[inline]
fn norm(self) -> f32 {
self.length()
}

#[inline]
fn norm_squared(self) -> f32 {
self.length_squared()
}
}

impl NormedVectorSpace for Vec2 {
#[inline]
fn norm(self) -> f32 {
self.length()
}

#[inline]
fn norm_squared(self) -> f32 {
self.length_squared()
}
}

impl NormedVectorSpace for f32 {
#[inline]
fn norm(self) -> f32 {
self.abs()
}

#[inline]
fn norm_squared(self) -> f32 {
self * self
}
}
Loading
Loading