|
- #![allow(dead_code)]
-
- use std::convert::{AsMut, AsRef};
- use std::fmt::{Debug, Formatter, Result as FmtResult};
- use std::ops::{Add, Deref, DerefMut, Mul, Sub};
-
- #[cfg(feature = "serde")]
- use serde::{
- de::{Deserialize, Deserializer, Error},
- ser::{Serialize, Serializer},
- };
-
- pub use super::{
- angle::Angle,
- numeric::{Float, Numeric},
- };
-
- macro_rules! first_ptr {
- ($this:ident, $first:ident $(, $other:ident)*) => {
- unsafe { &$this.$first }
- };
- }
-
- macro_rules! define_vec {
- ($Name:ident, $size:tt, $($T:ident => $i:tt => $f:ident),*) => {
- #[repr(C, packed)]
- pub struct $Name<T> {
- $(pub $f: T,)+
- }
-
- impl<T> $Name<T> {
- #[inline]
- pub const fn new($($f: T,)+) -> Self {
- Self { $($f,)+ }
- }
-
- #[inline]
- pub fn as_ptr(&self) -> * const T {
- first_ptr!(self $(, $f)+)
- }
- }
-
- impl<T> Default for $Name<T>
- where
- T: Default
- {
- #[inline]
- fn default() -> Self {
- Self {
- $($f: T::default(),)+
- }
- }
- }
-
- impl<T> Debug for $Name<T>
- where
- T: Debug
- {
- fn fmt(&self, fmt: &mut Formatter<'_>) -> FmtResult {
- fmt.debug_list().entries(self.as_ref().iter()).finish()
- }
- }
-
- impl<T, S> PartialEq<$Name<S>> for $Name<T>
- where
- S: PartialEq<T>,
- {
- fn eq(&self, other: &$Name<S>) -> bool {
- unsafe { true $(&& other.$f.eq(&self.$f))+ }
- }
- }
-
- impl<T> Eq for $Name<T>
- where
- T: Eq
- { }
-
- impl<T> Deref for $Name<T> {
- type Target = [T; $size];
-
- #[inline]
- fn deref(&self) -> &Self::Target {
- self.as_ref()
- }
- }
-
- impl<T> DerefMut for $Name<T> {
- #[inline]
- fn deref_mut(&mut self) -> &mut Self::Target {
- self.as_mut()
- }
- }
-
- impl<T> AsRef<[T; $size]> for $Name<T> {
- #[inline]
- fn as_ref(&self) -> &[T; $size] {
- unsafe {
- let raw: * const _ = self;
- let raw = raw as * const [T; $size];
-
- &*raw
- }
- }
- }
-
- impl<T> AsMut<[T; $size]> for $Name<T> {
- #[inline]
- fn as_mut(&mut self) -> &mut [T; $size] {
- unsafe {
- let raw: * mut _ = self;
- let raw = raw as * mut [T; $size];
-
- &mut *raw
- }
- }
- }
-
- impl<T> Clone for $Name<T>
- where
- T: Clone
- {
- #[inline]
- fn clone(&self) -> Self {
- unsafe {
- Self {
- $($f: self.$f.clone(),)+
- }
- }
- }
- }
-
- impl<T> Copy for $Name<T>
- where
- T: Copy
- { }
-
- impl<T> From<[T; $size]> for $Name<T>
- where
- T: Copy,
- {
- #[inline]
- fn from(arr: [T; $size]) -> Self {
- Self {
- $($f: arr[$i],)+
- }
- }
- }
-
- impl<T> From<T> for $Name<T>
- where
- T: Copy,
- {
- #[inline]
- fn from(value: T) -> Self {
- Self {
- $($f: value,)+
- }
- }
- }
-
- impl<T> From<($($T,)+)> for $Name<T> {
- #[inline]
- fn from(($($f,)+): ($($T,)+)) -> Self {
- Self {
- $($f,)+
- }
- }
- }
-
- #[cfg(feature = "serde")]
- impl<T> Serialize for $Name<T>
- where
- T: Serialize,
- {
- fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
- where
- S: Serializer
- {
- unsafe { vec![$(&self.$f,)+].serialize(serializer) }
- }
- }
-
- #[cfg(feature = "serde")]
- impl<'de, T> Deserialize<'de> for $Name<T>
- where
- T: Deserialize<'de>,
- {
- fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
- where
- D: Deserializer<'de>
- {
- let mut data = Vec::<T>::deserialize(deserializer)?.into_iter();
-
- Ok(Self {
- $($f: data.next().ok_or_else(|| D::Error::custom("Vector is missing some elements!"))?,)+
- })
- }
- }
- };
- }
-
- define_vec!(Vector2, 2, T => 0 => x, T => 1 => y);
- define_vec!(Vector3, 3, T => 0 => x, T => 1 => y, T => 2 => z);
- define_vec!(Vector4, 4, T => 0 => x, T => 1 => y, T => 2 => z, T => 3 => w);
-
- pub type Vector2f = Vector2<gl::GLfloat>;
- pub type Vector3f = Vector3<gl::GLfloat>;
- pub type Vector4f = Vector4<gl::GLfloat>;
-
- pub type Vector2d = Vector2<gl::GLdouble>;
- pub type Vector3d = Vector3<gl::GLdouble>;
- pub type Vector4d = Vector4<gl::GLdouble>;
-
- pub type Vector2i = Vector2<gl::GLint>;
- pub type Vector3i = Vector3<gl::GLint>;
- pub type Vector4i = Vector4<gl::GLint>;
-
- /* Vector2 */
-
- impl<T> Vector2<T>
- where
- T: Numeric,
- {
- #[inline]
- pub fn multiply(mut self, v: T) -> Self {
- self.x = self.x * v;
- self.y = self.y * v;
-
- self
- }
-
- #[inline]
- pub fn length_sqr(&self) -> T {
- self.x * self.x + self.y * self.y
- }
-
- #[inline]
- pub fn length(&self) -> T {
- Numeric::sqrt(self.length_sqr())
- }
-
- #[inline]
- pub fn normalize(mut self) -> Self {
- let len = self.length();
-
- self.x = self.x / len;
- self.y = self.y / len;
-
- self
- }
-
- #[inline]
- pub fn scalar(&self, other: &Self) -> T {
- self.x * other.x + self.y * other.y
- }
- }
-
- impl<T> Vector2<T>
- where
- T: Float,
- {
- #[inline]
- pub fn angle(&self, other: &Self) -> Angle<T> {
- let s = self.scalar(other);
- let l1 = self.length();
- let l2 = self.length();
-
- Angle::Rad(T::acos(s / (l1 + l2)))
- }
-
- #[inline]
- pub fn angle2(&self, other: &Self) -> Angle<T> {
- Angle::Rad(T::atan2(
- other.x * self.y - other.y * self.x,
- other.x * self.x + other.y * self.y,
- ))
- }
- }
-
- impl<T> Add for Vector2<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn add(mut self, other: Self) -> Self::Output {
- self.x = self.x + other.x;
- self.y = self.y + other.y;
-
- self
- }
- }
-
- impl<T> Sub for Vector2<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn sub(mut self, other: Self) -> Self::Output {
- self.x = self.x - other.x;
- self.y = self.y - other.y;
-
- self
- }
- }
-
- impl<T> Mul for Vector2<T>
- where
- T: Numeric,
- {
- type Output = T;
-
- #[inline]
- fn mul(self, rhs: Self) -> Self::Output {
- self.scalar(&rhs)
- }
- }
-
- impl<T> Mul<T> for Vector2<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn mul(self, rhs: T) -> Self::Output {
- self.multiply(rhs)
- }
- }
-
- /* Vector3 */
-
- impl<T> Vector3<T>
- where
- T: Numeric,
- {
- #[inline]
- pub fn multiply(mut self, v: T) -> Self {
- self.x = self.x * v;
- self.y = self.y * v;
- self.z = self.z * v;
-
- self
- }
-
- #[inline]
- pub fn length_sqr(&self) -> T {
- self.x * self.x + self.y * self.y + self.z * self.z
- }
-
- #[inline]
- pub fn length(&self) -> T {
- Numeric::sqrt(self.length_sqr())
- }
-
- #[inline]
- pub fn normalize(mut self) -> Self {
- let len = self.length();
-
- self.x = self.x / len;
- self.y = self.y / len;
- self.z = self.z / len;
-
- self
- }
-
- #[inline]
- pub fn scalar(&self, other: &Self) -> T {
- self.x * other.x + self.y * other.y + self.z * other.z
- }
-
- #[inline]
- pub fn cross(&self, other: &Self) -> Self {
- Self {
- x: self.y * other.z - self.z * other.y,
- y: self.z * other.x - self.x * other.z,
- z: self.x * other.y - self.y * other.x,
- }
- }
- }
-
- impl<T> Vector3<T>
- where
- T: Float,
- {
- #[inline]
- pub fn angle(&self, other: &Self) -> Angle<T> {
- let s = self.scalar(other);
- let l1 = self.length();
- let l2 = self.length();
-
- Angle::Rad(T::acos(s / (l1 + l2)))
- }
- }
-
- impl<T> Add for Vector3<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn add(mut self, other: Self) -> Self::Output {
- self.x = self.x + other.x;
- self.y = self.y + other.y;
- self.z = self.z + other.z;
-
- self
- }
- }
-
- impl<T> Sub for Vector3<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn sub(mut self, other: Self) -> Self::Output {
- self.x = self.x - other.x;
- self.y = self.y - other.y;
- self.z = self.z - other.z;
-
- self
- }
- }
-
- impl<T> Mul for Vector3<T>
- where
- T: Numeric,
- {
- type Output = T;
-
- #[inline]
- fn mul(self, rhs: Self) -> Self::Output {
- self.scalar(&rhs)
- }
- }
-
- impl<T> Mul<T> for Vector3<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn mul(self, rhs: T) -> Self::Output {
- self.multiply(rhs)
- }
- }
-
- /* Vector4 */
-
- impl<T> Vector4<T>
- where
- T: Numeric,
- {
- #[inline]
- pub fn multiply(mut self, v: T) -> Self {
- self.x = self.x * v;
- self.y = self.y * v;
- self.z = self.z * v;
-
- self
- }
-
- #[inline]
- pub fn length_sqr(self) -> T {
- self.xyz().length_sqr()
- }
-
- #[inline]
- pub fn length(self) -> T {
- self.xyz().length()
- }
-
- #[inline]
- pub fn normalize(mut self) -> Self {
- let len = self.length();
-
- if unsafe { !Numeric::is_zero(&self.w) } {
- self.x = self.x / self.w;
- self.y = self.y / self.w;
- self.z = self.z / self.w;
- } else {
- self.x = Numeric::zero();
- self.y = Numeric::zero();
- self.z = Numeric::zero();
- }
-
- self.x = self.x / len;
- self.y = self.y / len;
- self.z = self.z / len;
- self.w = Numeric::one();
-
- self
- }
-
- #[inline]
- pub fn scalar(&self, other: &Self) -> T {
- self.xyz().scalar(&other.xyz())
- }
-
- #[inline]
- pub fn cross(&self, other: &Self) -> Self {
- (self.xyz().cross(&other.xyz()), Numeric::one()).into()
- }
-
- #[inline]
- pub fn xyz(self) -> Vector3<T> {
- if unsafe { Numeric::is_zero(&self.w) } {
- Vector3 {
- x: Numeric::zero(),
- y: Numeric::zero(),
- z: Numeric::zero(),
- }
- } else {
- Vector3 {
- x: self.x / self.w,
- y: self.y / self.w,
- z: self.z / self.w,
- }
- }
- }
- }
-
- impl<T> Vector4<T>
- where
- T: Float,
- {
- #[inline]
- pub fn angle(&self, other: &Self) -> Angle<T> {
- self.xyz().angle(&other.xyz())
- }
- }
-
- impl<T> Add for Vector4<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn add(self, other: Self) -> Self::Output {
- (self.xyz() + other.xyz(), T::one()).into()
- }
- }
-
- impl<T> Sub for Vector4<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn sub(self, other: Self) -> Self::Output {
- (self.xyz() - other.xyz(), T::one()).into()
- }
- }
-
- impl<T> Mul for Vector4<T>
- where
- T: Numeric,
- {
- type Output = T;
-
- fn mul(self, rhs: Self) -> Self::Output {
- self.scalar(&rhs)
- }
- }
-
- impl<T> Mul<T> for Vector4<T>
- where
- T: Numeric,
- {
- type Output = Self;
-
- #[inline]
- fn mul(self, rhs: T) -> Self::Output {
- self.multiply(rhs)
- }
- }
-
- impl<T> From<(Vector3<T>, T)> for Vector4<T> {
- fn from((vec3, w): (Vector3<T>, T)) -> Self {
- Self {
- x: vec3.x,
- y: vec3.y,
- z: vec3.z,
- w,
- }
- }
- }
-
- #[cfg(test)]
- mod tests {
- use super::*;
-
- #[test]
- fn add() {
- let v1 = Vector2f::from((1.0, 0.0));
- let v2 = Vector2f::from((0.0, 1.0));
- let ex = Vector2f::from((1.0, 1.0));
-
- assert_eq!(ex, v1 + v2);
-
- let v1 = Vector3f::from((1.0, 0.0, 1.8));
- let v2 = Vector3f::from((0.0, 2.0, 1.2));
- let ex = Vector3f::from((1.0, 2.0, 3.0));
-
- assert_eq!(ex, v1 + v2);
-
- let v1 = Vector4f::from((1.0, 0.0, 1.8, 0.5));
- let v2 = Vector4f::from((0.0, 2.0, 1.2, 1.0));
- let ex = Vector4f::from((2.0, 2.0, 4.8, 1.0));
-
- assert_eq!(ex, v1 + v2);
- }
-
- #[test]
- fn sub() {
- let v1 = Vector2f::from((1.0, 0.0));
- let v2 = Vector2f::from((0.0, 1.0));
- let ex = Vector2f::from((1.0, -1.0));
-
- assert_eq!(ex, v1 - v2);
-
- let v1 = Vector3d::from((1.0, 0.0, 1.75));
- let v2 = Vector3d::from((0.0, 2.0, 1.0));
- let ex = Vector3d::from((1.0, -2.0, 0.75));
-
- assert_eq!(ex, v1 - v2);
-
- let v1 = Vector4d::from((1.0, 0.0, 1.0, 0.5));
- let v2 = Vector4d::from((0.0, 2.0, -2.0, 1.0));
- let ex = Vector4d::from((2.0, -2.0, 4.0, 1.0));
-
- assert_eq!(ex, v1 - v2);
- }
-
- #[test]
- fn multiply() {
- let v1 = Vector2f::from((1.0, 0.0)).multiply(2.0);
- let ex = Vector2f::from((2.0, 0.0));
-
- assert_eq!(ex, v1);
-
- let v1 = Vector3d::from((1.0, 0.0, 1.75)).multiply(2.0);
- let ex = Vector3d::from((2.0, 0.0, 3.5));
-
- assert_eq!(ex, v1);
-
- let v1 = Vector4d::from((1.0, 0.0, 0.5, 0.5)).multiply(3.0);
- let ex = Vector4d::from((3.0, 0.0, 1.5, 0.5));
-
- assert_eq!(ex, v1);
- }
-
- #[test]
- fn scalar() {
- let v1 = Vector2f::from((1.0, 0.0));
- let v2 = Vector2f::from((0.0, 1.0));
-
- assert_eq!(0.0, v1.scalar(&v2));
-
- let v1 = Vector3f::from((1.0, 0.0, 0.0));
- let v2 = Vector3f::from((0.0, 1.0, 0.0));
-
- assert_eq!(0.0, v1.scalar(&v2));
-
- let v1 = Vector4f::from((3.0, 0.0, 0.0, 1.0));
- let v2 = Vector4f::from((0.0, 2.0, 0.0, 0.8));
-
- assert_eq!(0.0, v1.scalar(&v2));
- }
-
- #[test]
- fn normalize() {
- let v1 = Vector2f::from((1.0, 0.0)).normalize();
- let ex = Vector2f::from((1.0, 0.0));
-
- assert_eq!(ex, v1);
-
- let v1 = Vector3d::from((1.0, 0.0, 1.75)).normalize();
- let ex = Vector3d::from((0.49613893835683387, 0.0, 0.8682431421244593));
-
- assert_eq!(ex, v1);
-
- let v1 = Vector4d::from((1.0, 0.0, 0.5, 0.5)).normalize();
- let ex = Vector4d::from((0.8944271909999159, 0.0, 0.4472135954999579, 1.0));
-
- assert_eq!(ex, v1);
- }
-
- #[test]
- fn cross() {
- let v1 = Vector3d::from((1.0, 0.0, 0.0));
- let v2 = Vector3d::from((0.0, 1.0, 0.0));
- let ex = Vector3d::from((0.0, 0.0, 1.0));
-
- assert_eq!(ex, v1.cross(&v2));
-
- let v1 = Vector4d::from((1.0, 0.0, 0.0, 0.5));
- let v2 = Vector4d::from((0.0, 3.0, 0.0, 1.0));
- let ex = Vector4d::from((0.0, 0.0, 6.0, 1.0));
-
- assert_eq!(ex, v1.cross(&v2));
- }
- }
|