Skip to main content

rs_math3d/
vector.rs

1// Copyright 2020-Present (c) Raja Lehtihet & Wael El Oraiby
2//
3// Redistribution and use in source and binary forms, with or without
4// modification, are permitted provided that the following conditions are met:
5//
6// 1. Redistributions of source code must retain the above copyright notice,
7// this list of conditions and the following disclaimer.
8//
9// 2. Redistributions in binary form must reproduce the above copyright notice,
10// this list of conditions and the following disclaimer in the documentation
11// and/or other materials provided with the distribution.
12//
13// 3. Neither the name of the copyright holder nor the names of its contributors
14// may be used to endorse or promote products derived from this software without
15// specific prior written permission.
16//
17// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
21// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27// POSSIBILITY OF SUCH DAMAGE.
28//! Vector mathematics module providing 2D, 3D, and 4D vector operations.
29//!
30//! This module provides generic vector types and operations for computer graphics
31//! and linear algebra applications. All vectors support standard arithmetic operations,
32//! dot products, and component-wise operations.
33//!
34//! Integer vectors are supported for storage and discrete geometry. Operations that
35//! require fractional results, such as normalization, are available only through
36//! [`FloatVector`].
37//!
38//! # Examples
39//!
40//! ```
41//! use rs_math3d::vector::{FloatVector, Vector, Vector3};
42//!
43//! let v1 = Vector3::new(1.0, 2.0, 3.0);
44//! let v2 = Vector3::new(4.0, 5.0, 6.0);
45//!
46//! // Vector addition
47//! let sum = v1 + v2;
48//!
49//! // Dot product
50//! let dot = Vector3::dot(&v1, &v2);
51//!
52//! // Normalization
53//! let normalized = v1.normalize();
54//! ```
55
56use crate::scalar::*;
57use core::ops::{Add, Div, Mul, Neg, Rem, Sub};
58use num_traits::Zero;
59
60/// Generic vector trait defining common vector operations.
61///
62/// This trait provides the foundation for all vector types, defining
63/// operations like addition, subtraction, dot product, and component-wise operations.
64///
65/// # Mathematical Operations
66///
67/// For vectors **v** and **w**, and scalar `s`:
68/// - Addition: **v** + **w** = (v₁ + w₁, v₂ + w₂, ...)
69/// - Subtraction: **v** - **w** = (v₁ - w₁, v₂ - w₂, ...)
70/// - Scalar multiplication: s**v** = (sv₁, sv₂, ...)
71/// - Dot product: **v** · **w** = v₁w₁ + v₂w₂ + ...
72pub trait Vector<T: Scalar, Rhs = Self, Output = Self>:
73    Add<Rhs, Output = Output>
74    + Sub<Rhs, Output = Output>
75    + Mul<Rhs, Output = Output>
76    + Mul<T, Output = Output>
77    + Div<Rhs, Output = Output>
78    + Div<T, Output = Output>
79    + Neg<Output = Output>
80    + Clone
81    + Copy
82{
83    /// Returns the zero vector (all components are zero).
84    fn zero() -> Self;
85
86    /// Adds two vectors component-wise.
87    fn add_vv(l: &Self, r: &Self) -> Self;
88
89    /// Subtracts two vectors component-wise.
90    fn sub_vv(l: &Self, r: &Self) -> Self;
91
92    /// Multiplies two vectors component-wise (Hadamard product).
93    fn mul_vv(l: &Self, r: &Self) -> Self;
94
95    /// Divides two vectors component-wise.
96    fn div_vv(l: &Self, r: &Self) -> Self;
97
98    /// Multiplies a vector by a scalar.
99    fn mul_vs(l: &Self, r: T) -> Self;
100
101    /// Divides a vector by a scalar.
102    fn div_vs(l: &Self, r: T) -> Self;
103
104    /// Computes the remainder of component-wise division.
105    fn rem_vv(l: &Self, r: &Self) -> Self;
106
107    /// Computes the dot product of two vectors.
108    ///
109    /// For vectors **v** and **w**:
110    /// ```text
111    /// v · w = Σᵢ vᵢwᵢ
112    /// ```
113    fn dot(l: &Self, r: &Self) -> T;
114
115    /// Returns a vector with the minimum components from both vectors.
116    fn min(l: &Self, r: &Self) -> Self;
117
118    /// Returns a vector with the maximum components from both vectors.
119    fn max(l: &Self, r: &Self) -> Self;
120}
121
122/// Trait for vectors with floating-point components.
123///
124/// Extends the base `Vector` trait with operations that require
125/// floating-point arithmetic, such as length calculation and normalization.
126pub trait FloatVector<T: FloatScalar>: Vector<T> {
127    /// Computes the Euclidean length (magnitude) of the vector.
128    ///
129    /// For vector **v**:
130    /// ```text
131    /// ||v|| = √(v₁² + v₂² + ... + vₙ²)
132    /// ```
133    fn length(&self) -> T;
134
135    /// Returns a unit vector in the same direction.
136    ///
137    /// For vector **v**:
138    /// ```text
139    /// v̂ = v / ||v||
140    /// ```
141    ///
142    /// # Note
143    /// Returns NaN or Inf components if the vector has zero length.
144    fn normalize(&self) -> Self;
145
146    /// Computes the Euclidean distance between two vectors.
147    ///
148    /// For vectors **v** and **w**:
149    /// ```text
150    /// d(v, w) = ||v - w||
151    /// ```
152    fn distance(l: &Self, r: &Self) -> T;
153
154    /// Computes the squared length (avoids a square root).
155    ///
156    /// ```text
157    /// ||v||² = v · v
158    /// ```
159    fn length_squared(&self) -> T {
160        Self::dot(self, self)
161    }
162
163    /// Returns a normalized vector or `None` when the length is too small.
164    fn try_normalize(&self, epsilon: T) -> Option<Self> {
165        let len_sq = self.length_squared();
166        if len_sq <= epsilon * epsilon {
167            None
168        } else {
169            Some(*self / len_sq.tsqrt())
170        }
171    }
172
173    /// Returns a normalized vector or the zero vector when too small.
174    fn normalize_or_zero(&self, epsilon: T) -> Self {
175        self.try_normalize(epsilon).unwrap_or_else(Self::zero)
176    }
177
178    /// Normalizes using a precomputed inverse length (e.g., from rsqrt).
179    fn normalize_with_inv_len(&self, inv_len: T) -> Self {
180        *self * inv_len
181    }
182
183    /// Normalizes with precomputed length squared and inverse length.
184    fn try_normalize_with_inv_len(&self, len_sq: T, inv_len: T, epsilon: T) -> Option<Self> {
185        if len_sq <= epsilon * epsilon {
186            None
187        } else {
188            Some(*self * inv_len)
189        }
190    }
191}
192
193macro_rules! implVecScalar {
194    ($vecName:ident, $scalar:ident) => {
195        impl Mul<$vecName<$scalar>> for $scalar {
196            type Output = $vecName<$scalar>;
197
198            fn mul(self, rhs: $vecName<$scalar>) -> Self::Output {
199                $vecName::mul_vs(&rhs, self)
200            }
201        }
202    };
203}
204
205macro_rules! vector_field_doc {
206    (x) => {
207        "X component."
208    };
209    (y) => {
210        "Y component."
211    };
212    (z) => {
213        "Z component."
214    };
215    (w) => {
216        "W component."
217    };
218}
219
220macro_rules! implVector {
221    ($(#[$meta:meta])* $vecName:ident, $($field:ident)*) => {
222        $(#[$meta])*
223        #[repr(C)]
224        #[derive(Copy, Clone, Debug, Default)]
225        pub struct $vecName<T> { $(#[doc = vector_field_doc!($field)] pub $field: T),* }
226
227        impl<T: Scalar> $vecName<T> {
228            /// Creates a vector from components.
229            pub fn new($($field:T),*) -> Self { Self { $($field: $field),* } }
230        }
231
232        impl<T> $vecName<T>
233        where
234            T: Copy + num_traits::ToPrimitive,
235        {
236            /// Attempts to cast each component into another numeric type.
237            pub fn try_cast<U>(&self) -> Option<$vecName<U>>
238            where
239                U: Scalar + num_traits::NumCast,
240            {
241                Some($vecName {
242                    $($field: num_traits::NumCast::from(self.$field)?),*
243                })
244            }
245        }
246
247        impl<T: Scalar> Vector<T> for $vecName<T> {
248            fn zero() -> Self { Self { $($field: <T as Zero>::zero()),* } }
249            fn dot  (l: &Self, r: &Self) -> T { $(l.$field * r.$field +)* <T as Zero>::zero() }
250            fn add_vv(l: &Self, r: &Self) -> Self { Self::new($(l.$field + r.$field),*) }
251            fn sub_vv(l: &Self, r: &Self) -> Self { Self::new($(l.$field - r.$field),*) }
252            fn mul_vv(l: &Self, r: &Self) -> Self { Self::new($(l.$field * r.$field),*) }
253            fn div_vv(l: &Self, r: &Self) -> Self { Self::new($(l.$field / r.$field),*) }
254            fn mul_vs(l: &Self, r: T) -> Self { Self::new($(l.$field * r),*) }
255            fn div_vs(l: &Self, r: T) -> Self { Self::new($(l.$field / r),*) }
256            fn rem_vv(l: &Self, r: &Self) -> Self { Self::new($(l.$field % r.$field),*) }
257            fn min(l: &Self, r: &Self) -> Self { Self::new($(T::min(l.$field, r.$field)),*) }
258            fn max(l: &Self, r: &Self) -> Self { Self::new($(T::max(l.$field, r.$field)),*) }
259        }
260
261        impl<T> Add for $vecName<T> where T: Scalar {
262            type Output = $vecName<T>;
263
264            fn add(self, rhs: Self) -> Self::Output {
265                Self { $($field: self.$field + rhs.$field),* }
266            }
267        }
268
269        impl<T> Sub for $vecName<T> where T: Scalar {
270            type Output = $vecName<T>;
271
272            fn sub(self, rhs: Self) -> Self::Output {
273                Self { $($field: self.$field - rhs.$field),* }
274            }
275        }
276
277        impl<T> Mul for $vecName<T> where T: Scalar {
278            type Output = $vecName<T>;
279
280            fn mul(self, rhs: Self) -> Self::Output {
281                Self { $($field: self.$field * rhs.$field),* }
282            }
283        }
284
285        impl<T> Mul<T> for $vecName<T> where T:Scalar {
286            type Output = $vecName<T>;
287
288            fn mul(self, rhs: T) -> Self::Output {
289                Self { $($field: self.$field * rhs),* }
290            }
291        }
292
293        implVecScalar!($vecName, f32);
294        implVecScalar!($vecName, f64);
295        implVecScalar!($vecName, i32);
296        implVecScalar!($vecName, i64);
297
298        impl<T> Div for $vecName<T> where T:Scalar {
299            type Output = $vecName<T>;
300
301            fn div(self, rhs: Self) -> Self::Output {
302                Self { $($field: self.$field / rhs.$field),* }
303            }
304        }
305
306        impl<T> Div<T> for $vecName<T> where T:Scalar {
307            type Output = $vecName<T>;
308
309            fn div(self, rhs: T) -> Self::Output {
310                Self { $($field: self.$field / rhs),* }
311            }
312        }
313
314        impl<T> Rem for $vecName<T> where T: Scalar {
315            type Output = $vecName<T>;
316
317            fn rem(self, rhs: $vecName<T>) -> Self::Output {
318                Self { $($field: self.$field % rhs.$field),* }
319            }
320        }
321
322        impl<T> Rem<T> for $vecName<T> where T:Scalar {
323            type Output = $vecName<T>;
324
325            fn rem(self, rhs: T) -> Self::Output {
326                Self { $($field: self.$field % rhs),* }
327            }
328        }
329
330        impl<T: Scalar> Neg for $vecName<T> {
331            type Output = $vecName<T>;
332            fn neg(self) -> Self::Output {
333                Self { $($field: -self.$field),* }
334            }
335        }
336    };
337}
338
339macro_rules! implFloatVector {
340    ($vecName:ident) => {
341        impl<T: FloatScalar> FloatVector<T> for $vecName<T> {
342            fn length(&self) -> T {
343                Self::dot(self, self).tsqrt()
344            }
345            fn normalize(&self) -> Self {
346                let len = Self::length(self);
347                *self / len
348            }
349            fn distance(l: &Self, r: &Self) -> T {
350                Self::length(&(*r - *l))
351            }
352        }
353    };
354}
355
356/// Trait for computing the cross product of 3D vectors.
357///
358/// The cross product is only defined for 3D vectors and produces
359/// a vector perpendicular to both input vectors.
360pub trait CrossProduct {
361    /// Computes the cross product of two vectors.
362    ///
363    /// For 3D vectors **v** and **w**:
364    /// ```text
365    /// v × w = (v₂w₃ - v₃w₂, v₃w₁ - v₁w₃, v₁w₂ - v₂w₁)
366    /// ```
367    ///
368    /// The resulting vector is perpendicular to both input vectors,
369    /// with magnitude ||v|| ||w|| sin(θ), where θ is the angle between them.
370    fn cross(l: &Self, r: &Self) -> Self;
371}
372
373implVector!(
374    /// A 2D vector with x and y components.
375    ///
376    /// # Examples
377    /// ```
378    /// use rs_math3d::vector::Vector2;
379    ///
380    /// let v = Vector2::new(3.0, 4.0);
381    /// assert_eq!(v.x, 3.0);
382    /// assert_eq!(v.y, 4.0);
383    /// ```
384    Vector2,
385    x y
386);
387
388implVector!(
389    /// A 3D vector with x, y, and z components.
390    ///
391    /// # Examples
392    /// ```
393    /// use rs_math3d::vector::{Vector3, CrossProduct};
394    ///
395    /// let v1 = Vector3::new(1.0, 0.0, 0.0);
396    /// let v2 = Vector3::new(0.0, 1.0, 0.0);
397    /// let cross = Vector3::cross(&v1, &v2);
398    /// // Result is (0, 0, 1) - the z-axis
399    /// ```
400    Vector3,
401    x y z
402);
403
404implVector!(
405    /// A 4D vector with x, y, z, and w components.
406    ///
407    /// Often used for homogeneous coordinates in 3D graphics.
408    ///
409    /// # Examples
410    /// ```
411    /// use rs_math3d::vector::Vector4;
412    ///
413    /// let v = Vector4::new(1.0, 2.0, 3.0, 1.0);
414    /// // w=1 for positions, w=0 for directions
415    /// ```
416    Vector4,
417    x y z w
418);
419
420implFloatVector!(Vector2);
421implFloatVector!(Vector3);
422implFloatVector!(Vector4);
423
424impl<T> CrossProduct for Vector3<T>
425where
426    T: Scalar,
427{
428    /// Computes the cross product of two 3D vectors.
429    ///
430    /// The cross product **v** × **w** produces a vector perpendicular
431    /// to both **v** and **w**, following the right-hand rule.
432    ///
433    /// # Properties
434    /// - Anti-commutative: **v** × **w** = -(**w** × **v**)
435    /// - Distributive: **v** × (**w** + **u**) = **v** × **w** + **v** × **u**
436    /// - **v** × **v** = **0**
437    fn cross(l: &Vector3<T>, r: &Vector3<T>) -> Vector3<T> {
438        Vector3::new(
439            l.y * r.z - l.z * r.y,
440            l.z * r.x - l.x * r.z,
441            l.x * r.y - l.y * r.x,
442        )
443    }
444}
445
446/// Trait for 2D swizzle operations on vectors.
447///
448/// Provides methods to rearrange and duplicate vector components
449/// into 2D vectors using familiar shader-style syntax.
450pub trait Swizzle2<T: Scalar> {
451    /// Returns a vector with components (x, x).
452    fn xx(&self) -> Vector2<T>;
453    /// Returns a vector with components (x, y).
454    fn xy(&self) -> Vector2<T>;
455    /// Returns a vector with components (x, z).
456    fn xz(&self) -> Vector2<T>;
457    /// Returns a vector with components (y, x).
458    fn yx(&self) -> Vector2<T>;
459    /// Returns a vector with components (y, y).
460    fn yy(&self) -> Vector2<T>;
461    /// Returns a vector with components (y, z).
462    fn yz(&self) -> Vector2<T>;
463    /// Returns a vector with components (z, x).
464    fn zx(&self) -> Vector2<T>;
465    /// Returns a vector with components (z, y).
466    fn zy(&self) -> Vector2<T>;
467    /// Returns a vector with components (z, z).
468    fn zz(&self) -> Vector2<T>;
469}
470
471macro_rules! swizzle_field {
472    ($s:ident, x) => {
473        $s.x
474    };
475    ($s:ident, y) => {
476        $s.y
477    };
478    ($s:ident, z) => {
479        $s.z
480    };
481    ($s:ident, zero) => {
482        <T as Zero>::zero()
483    };
484}
485
486macro_rules! impl_swizzle2 {
487    ($vec:ident, $x:tt, $y:tt, $z:tt) => {
488        impl<T: Scalar> Swizzle2<T> for $vec<T> {
489            fn xx(&self) -> Vector2<T> {
490                Vector2::new(swizzle_field!(self, $x), swizzle_field!(self, $x))
491            }
492            fn xy(&self) -> Vector2<T> {
493                Vector2::new(swizzle_field!(self, $x), swizzle_field!(self, $y))
494            }
495            fn xz(&self) -> Vector2<T> {
496                Vector2::new(swizzle_field!(self, $x), swizzle_field!(self, $z))
497            }
498            fn yx(&self) -> Vector2<T> {
499                Vector2::new(swizzle_field!(self, $y), swizzle_field!(self, $x))
500            }
501            fn yy(&self) -> Vector2<T> {
502                Vector2::new(swizzle_field!(self, $y), swizzle_field!(self, $y))
503            }
504            fn yz(&self) -> Vector2<T> {
505                Vector2::new(swizzle_field!(self, $y), swizzle_field!(self, $z))
506            }
507            fn zx(&self) -> Vector2<T> {
508                Vector2::new(swizzle_field!(self, $z), swizzle_field!(self, $x))
509            }
510            fn zy(&self) -> Vector2<T> {
511                Vector2::new(swizzle_field!(self, $z), swizzle_field!(self, $y))
512            }
513            fn zz(&self) -> Vector2<T> {
514                Vector2::new(swizzle_field!(self, $z), swizzle_field!(self, $z))
515            }
516        }
517    };
518}
519
520impl_swizzle2!(Vector2, x, y, zero);
521impl_swizzle2!(Vector3, x, y, z);
522impl_swizzle2!(Vector4, x, y, z);
523
524/// Trait for 3D swizzle operations on vectors.
525///
526/// Provides methods to rearrange and duplicate vector components
527/// into 3D vectors using familiar shader-style syntax.
528pub trait Swizzle3<T: Scalar> {
529    /// Returns a vector with components (x, x, x).
530    fn xxx(&self) -> Vector3<T>;
531    /// Returns a vector with components (x, x, y).
532    fn xxy(&self) -> Vector3<T>;
533    /// Returns a vector with components (x, x, z).
534    fn xxz(&self) -> Vector3<T>;
535    /// Returns a vector with components (x, y, x).
536    fn xyx(&self) -> Vector3<T>;
537    /// Returns a vector with components (x, y, y).
538    fn xyy(&self) -> Vector3<T>;
539    /// Returns a vector with components (x, y, z).
540    fn xyz(&self) -> Vector3<T>;
541    /// Returns a vector with components (x, z, x).
542    fn xzx(&self) -> Vector3<T>;
543    /// Returns a vector with components (x, z, y).
544    fn xzy(&self) -> Vector3<T>;
545    /// Returns a vector with components (x, z, z).
546    fn xzz(&self) -> Vector3<T>;
547
548    /// Returns a vector with components (y, x, x).
549    fn yxx(&self) -> Vector3<T>;
550    /// Returns a vector with components (y, x, y).
551    fn yxy(&self) -> Vector3<T>;
552    /// Returns a vector with components (y, x, z).
553    fn yxz(&self) -> Vector3<T>;
554    /// Returns a vector with components (y, y, x).
555    fn yyx(&self) -> Vector3<T>;
556    /// Returns a vector with components (y, y, y).
557    fn yyy(&self) -> Vector3<T>;
558    /// Returns a vector with components (y, y, z).
559    fn yyz(&self) -> Vector3<T>;
560    /// Returns a vector with components (y, z, x).
561    fn yzx(&self) -> Vector3<T>;
562    /// Returns a vector with components (y, z, y).
563    fn yzy(&self) -> Vector3<T>;
564    /// Returns a vector with components (y, z, z).
565    fn yzz(&self) -> Vector3<T>;
566
567    /// Returns a vector with components (z, x, x).
568    fn zxx(&self) -> Vector3<T>;
569    /// Returns a vector with components (z, x, y).
570    fn zxy(&self) -> Vector3<T>;
571    /// Returns a vector with components (z, x, z).
572    fn zxz(&self) -> Vector3<T>;
573    /// Returns a vector with components (z, y, x).
574    fn zyx(&self) -> Vector3<T>;
575    /// Returns a vector with components (z, y, y).
576    fn zyy(&self) -> Vector3<T>;
577    /// Returns a vector with components (z, y, z).
578    fn zyz(&self) -> Vector3<T>;
579    /// Returns a vector with components (z, z, x).
580    fn zzx(&self) -> Vector3<T>;
581    /// Returns a vector with components (z, z, y).
582    fn zzy(&self) -> Vector3<T>;
583    /// Returns a vector with components (z, z, z).
584    fn zzz(&self) -> Vector3<T>;
585}
586
587macro_rules! impl_swizzle3 {
588    ($vec:ident, $x:tt, $y:tt, $z:tt) => {
589        impl<T: Scalar> Swizzle3<T> for $vec<T> {
590            fn xxx(&self) -> Vector3<T> {
591                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $x), swizzle_field!(self, $x))
592            }
593            fn xxy(&self) -> Vector3<T> {
594                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $x), swizzle_field!(self, $y))
595            }
596            fn xxz(&self) -> Vector3<T> {
597                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $x), swizzle_field!(self, $z))
598            }
599            fn xyx(&self) -> Vector3<T> {
600                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $y), swizzle_field!(self, $x))
601            }
602            fn xyy(&self) -> Vector3<T> {
603                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $y), swizzle_field!(self, $y))
604            }
605            fn xyz(&self) -> Vector3<T> {
606                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $y), swizzle_field!(self, $z))
607            }
608            fn xzx(&self) -> Vector3<T> {
609                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $z), swizzle_field!(self, $x))
610            }
611            fn xzy(&self) -> Vector3<T> {
612                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $z), swizzle_field!(self, $y))
613            }
614            fn xzz(&self) -> Vector3<T> {
615                Vector3::new(swizzle_field!(self, $x), swizzle_field!(self, $z), swizzle_field!(self, $z))
616            }
617
618            fn yxx(&self) -> Vector3<T> {
619                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $x), swizzle_field!(self, $x))
620            }
621            fn yxy(&self) -> Vector3<T> {
622                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $x), swizzle_field!(self, $y))
623            }
624            fn yxz(&self) -> Vector3<T> {
625                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $x), swizzle_field!(self, $z))
626            }
627            fn yyx(&self) -> Vector3<T> {
628                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $y), swizzle_field!(self, $x))
629            }
630            fn yyy(&self) -> Vector3<T> {
631                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $y), swizzle_field!(self, $y))
632            }
633            fn yyz(&self) -> Vector3<T> {
634                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $y), swizzle_field!(self, $z))
635            }
636            fn yzx(&self) -> Vector3<T> {
637                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $z), swizzle_field!(self, $x))
638            }
639            fn yzy(&self) -> Vector3<T> {
640                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $z), swizzle_field!(self, $y))
641            }
642            fn yzz(&self) -> Vector3<T> {
643                Vector3::new(swizzle_field!(self, $y), swizzle_field!(self, $z), swizzle_field!(self, $z))
644            }
645
646            fn zxx(&self) -> Vector3<T> {
647                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $x), swizzle_field!(self, $x))
648            }
649            fn zxy(&self) -> Vector3<T> {
650                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $x), swizzle_field!(self, $y))
651            }
652            fn zxz(&self) -> Vector3<T> {
653                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $x), swizzle_field!(self, $z))
654            }
655            fn zyx(&self) -> Vector3<T> {
656                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $y), swizzle_field!(self, $x))
657            }
658            fn zyy(&self) -> Vector3<T> {
659                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $y), swizzle_field!(self, $y))
660            }
661            fn zyz(&self) -> Vector3<T> {
662                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $y), swizzle_field!(self, $z))
663            }
664            fn zzx(&self) -> Vector3<T> {
665                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $z), swizzle_field!(self, $x))
666            }
667            fn zzy(&self) -> Vector3<T> {
668                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $z), swizzle_field!(self, $y))
669            }
670            fn zzz(&self) -> Vector3<T> {
671                Vector3::new(swizzle_field!(self, $z), swizzle_field!(self, $z), swizzle_field!(self, $z))
672            }
673        }
674    };
675}
676
677impl_swizzle3!(Vector3, x, y, z);
678impl_swizzle3!(Vector4, x, y, z);
679
680#[cfg(test)]
681mod tests {
682    use super::*;
683    use crate::scalar::{FloatScalar, EPS_F32};
684
685    #[test]
686    pub fn test() {
687        let f1 = Vector2 { x: 1.0, y: 2.0 };
688        let f2 = Vector2 { x: 3.0, y: 4.0 };
689        let out = f1 + f2;
690        assert_eq!(out.x, 4.0);
691        assert_eq!(out.y, 6.0);
692
693        let f22: Vector2<f32> = 2.0 * f2;
694        let f23: Vector2<f32> = f2 * 2.0;
695
696        assert_eq!(f22.x, 6.0);
697        assert_eq!(f22.y, 8.0);
698        assert_eq!(f23.x, f22.x);
699        assert_eq!(f23.y, f22.y);
700    }
701
702    #[test]
703    fn test_vector_normalization() {
704        // Test normal case
705        let v = Vector3::<f32>::new(3.0, 4.0, 0.0);
706        let nv = v.normalize();
707        let len = nv.length();
708        assert!((len - 1.0).abs() < f32::epsilon());
709
710        // Test zero vector normalization (should handle gracefully)
711        let v_zero = Vector3::<f32>::new(0.0, 0.0, 0.0);
712        let nv_zero = v_zero.normalize();
713        // When normalizing zero vector, we get NaN or Inf components
714        // The current implementation divides by zero, resulting in inf/nan
715        assert!(nv_zero.x.is_infinite() || nv_zero.x.is_nan());
716
717        // Test already normalized vector
718        let v_unit = Vector3::<f32>::new(1.0, 0.0, 0.0);
719        let nv_unit = v_unit.normalize();
720        assert!((nv_unit.x - 1.0).abs() < f32::epsilon());
721        assert!((nv_unit.y).abs() < f32::epsilon());
722        assert!((nv_unit.z).abs() < f32::epsilon());
723    }
724
725    #[test]
726    fn test_vector_try_normalize() {
727        let v = Vector3::<f32>::new(3.0, 4.0, 0.0);
728        let nv = v.try_normalize(EPS_F32).expect("should normalize");
729        assert!((nv.length() - 1.0).abs() < 0.001);
730
731        let zero = Vector3::<f32>::zero();
732        assert!(zero.try_normalize(EPS_F32).is_none());
733        let zero_norm = zero.normalize_or_zero(EPS_F32);
734        assert_eq!(zero_norm.x, 0.0);
735        assert_eq!(zero_norm.y, 0.0);
736        assert_eq!(zero_norm.z, 0.0);
737
738        let len_sq = v.length_squared();
739        let inv_len = 1.0f32 / len_sq.tsqrt();
740        let nv_fast = v.normalize_with_inv_len(inv_len);
741        assert!((nv_fast.length() - 1.0).abs() < 0.001);
742
743        let nv_fast_try = v
744            .try_normalize_with_inv_len(len_sq, inv_len, EPS_F32)
745            .expect("should normalize");
746        assert!((nv_fast_try.length() - 1.0).abs() < 0.001);
747        assert!(zero.try_normalize_with_inv_len(0.0, 0.0, EPS_F32).is_none());
748    }
749
750    #[test]
751    fn test_vector_length() {
752        let v2 = Vector2::<f32>::new(3.0, 4.0);
753        assert!((v2.length() - 5.0).abs() < f32::epsilon());
754
755        let v3 = Vector3::<f32>::new(2.0, 3.0, 6.0);
756        assert!((v3.length() - 7.0).abs() < f32::epsilon());
757
758        let v4 = Vector4::<f32>::new(1.0, 2.0, 2.0, 0.0);
759        assert!((v4.length() - 3.0).abs() < f32::epsilon());
760
761        // Test zero vector
762        let v_zero = Vector3::<f32>::zero();
763        assert_eq!(v_zero.length(), 0.0);
764    }
765
766    #[test]
767    fn test_vector_dot_product() {
768        let v1 = Vector3::<f32>::new(1.0, 2.0, 3.0);
769        let v2 = Vector3::<f32>::new(4.0, 5.0, 6.0);
770        let dot = Vector3::dot(&v1, &v2);
771        assert_eq!(dot, 32.0); // 1*4 + 2*5 + 3*6 = 32
772
773        // Test orthogonal vectors
774        let v_ortho1 = Vector3::<f32>::new(1.0, 0.0, 0.0);
775        let v_ortho2 = Vector3::<f32>::new(0.0, 1.0, 0.0);
776        assert_eq!(Vector3::dot(&v_ortho1, &v_ortho2), 0.0);
777
778        // Test dot product with itself equals length squared
779        let self_dot = Vector3::dot(&v1, &v1);
780        let len_squared = v1.length() * v1.length();
781        assert!((self_dot - len_squared).abs() < 0.0001);
782    }
783
784    #[test]
785    fn test_vector_cross_product() {
786        // Test standard basis vectors
787        let x = Vector3::<f32>::new(1.0, 0.0, 0.0);
788        let y = Vector3::<f32>::new(0.0, 1.0, 0.0);
789        let z = Vector3::<f32>::new(0.0, 0.0, 1.0);
790
791        let x_cross_y = Vector3::cross(&x, &y);
792        assert!((x_cross_y.x - z.x).abs() < f32::epsilon());
793        assert!((x_cross_y.y - z.y).abs() < f32::epsilon());
794        assert!((x_cross_y.z - z.z).abs() < f32::epsilon());
795
796        let y_cross_z = Vector3::cross(&y, &z);
797        assert!((y_cross_z.x - x.x).abs() < f32::epsilon());
798        assert!((y_cross_z.y - x.y).abs() < f32::epsilon());
799        assert!((y_cross_z.z - x.z).abs() < f32::epsilon());
800
801        let z_cross_x = Vector3::cross(&z, &x);
802        assert!((z_cross_x.x - y.x).abs() < f32::epsilon());
803        assert!((z_cross_x.y - y.y).abs() < f32::epsilon());
804        assert!((z_cross_x.z - y.z).abs() < f32::epsilon());
805
806        // Test anti-commutativity: a × b = -(b × a)
807        let a = Vector3::<f32>::new(1.0, 2.0, 3.0);
808        let b = Vector3::<f32>::new(4.0, 5.0, 6.0);
809        let a_cross_b = Vector3::cross(&a, &b);
810        let b_cross_a = Vector3::cross(&b, &a);
811        assert!((a_cross_b.x + b_cross_a.x).abs() < f32::epsilon());
812        assert!((a_cross_b.y + b_cross_a.y).abs() < f32::epsilon());
813        assert!((a_cross_b.z + b_cross_a.z).abs() < f32::epsilon());
814
815        // Test cross product with itself is zero
816        let self_cross = Vector3::cross(&a, &a);
817        assert!(self_cross.x.abs() < f32::epsilon());
818        assert!(self_cross.y.abs() < f32::epsilon());
819        assert!(self_cross.z.abs() < f32::epsilon());
820    }
821
822    #[test]
823    fn test_vector_distance() {
824        let v1 = Vector3::<f32>::new(1.0, 2.0, 3.0);
825        let v2 = Vector3::<f32>::new(4.0, 6.0, 3.0);
826        let dist = Vector3::distance(&v1, &v2);
827        assert!((dist - 5.0).abs() < f32::epsilon()); // sqrt(9 + 16 + 0) = 5
828
829        // Distance to itself should be zero
830        let self_dist = Vector3::distance(&v1, &v1);
831        assert!(self_dist.abs() < f32::epsilon());
832    }
833
834    #[test]
835    fn test_vector_min_max() {
836        let v1 = Vector3::<f32>::new(1.0, 5.0, 3.0);
837        let v2 = Vector3::<f32>::new(4.0, 2.0, 6.0);
838
839        let v_min = Vector3::min(&v1, &v2);
840        assert_eq!(v_min.x, 1.0);
841        assert_eq!(v_min.y, 2.0);
842        assert_eq!(v_min.z, 3.0);
843
844        let v_max = Vector3::max(&v1, &v2);
845        assert_eq!(v_max.x, 4.0);
846        assert_eq!(v_max.y, 5.0);
847        assert_eq!(v_max.z, 6.0);
848    }
849
850    #[test]
851    fn test_vector_arithmetic() {
852        let v1 = Vector3::<f32>::new(1.0, 2.0, 3.0);
853        let v2 = Vector3::<f32>::new(4.0, 5.0, 6.0);
854
855        // Addition
856        let sum = v1 + v2;
857        assert_eq!(sum.x, 5.0);
858        assert_eq!(sum.y, 7.0);
859        assert_eq!(sum.z, 9.0);
860
861        // Subtraction
862        let diff = v2 - v1;
863        assert_eq!(diff.x, 3.0);
864        assert_eq!(diff.y, 3.0);
865        assert_eq!(diff.z, 3.0);
866
867        // Component-wise multiplication
868        let prod = v1 * v2;
869        assert_eq!(prod.x, 4.0);
870        assert_eq!(prod.y, 10.0);
871        assert_eq!(prod.z, 18.0);
872
873        // Component-wise division
874        let div = v2 / v1;
875        assert_eq!(div.x, 4.0);
876        assert_eq!(div.y, 2.5);
877        assert_eq!(div.z, 2.0);
878
879        // Scalar multiplication
880        let scaled = v1 * 2.0;
881        assert_eq!(scaled.x, 2.0);
882        assert_eq!(scaled.y, 4.0);
883        assert_eq!(scaled.z, 6.0);
884
885        // Scalar division
886        let divided = v2 / 2.0;
887        assert_eq!(divided.x, 2.0);
888        assert_eq!(divided.y, 2.5);
889        assert_eq!(divided.z, 3.0);
890
891        // Negation
892        let neg = -v1;
893        assert_eq!(neg.x, -1.0);
894        assert_eq!(neg.y, -2.0);
895        assert_eq!(neg.z, -3.0);
896    }
897
898    #[test]
899    fn test_swizzle_operations() {
900        let v2 = Vector2::<f32>::new(1.0, 2.0);
901
902        assert_eq!(v2.xx().x, 1.0);
903        assert_eq!(v2.xx().y, 1.0);
904
905        assert_eq!(v2.xy().x, 1.0);
906        assert_eq!(v2.xy().y, 2.0);
907
908        assert_eq!(v2.yx().x, 2.0);
909        assert_eq!(v2.yx().y, 1.0);
910
911        assert_eq!(v2.yy().x, 2.0);
912        assert_eq!(v2.yy().y, 2.0);
913
914        let v2_xz = v2.xz();
915        assert_eq!(v2_xz.x, 1.0);
916        assert_eq!(v2_xz.y, 0.0);
917
918        let v3 = Vector3::<f32>::new(1.0, 2.0, 3.0);
919
920        assert_eq!(v3.xz().x, 1.0);
921        assert_eq!(v3.xz().y, 3.0);
922
923        assert_eq!(v3.zy().x, 3.0);
924        assert_eq!(v3.zy().y, 2.0);
925
926        let v3_swizzle = v3.zyx();
927        assert_eq!(v3_swizzle.x, 3.0);
928        assert_eq!(v3_swizzle.y, 2.0);
929        assert_eq!(v3_swizzle.z, 1.0);
930
931        let v4 = Vector4::<f32>::new(1.0, 2.0, 3.0, 4.0);
932        let v4_xz = v4.xz();
933        assert_eq!(v4_xz.x, 1.0);
934        assert_eq!(v4_xz.y, 3.0);
935        let v4_swizzle = v4.zyx();
936        assert_eq!(v4_swizzle.x, 3.0);
937        assert_eq!(v4_swizzle.y, 2.0);
938        assert_eq!(v4_swizzle.z, 1.0);
939    }
940
941    #[test]
942    fn test_vector_rem_operation() {
943        let v1 = Vector3::<i32>::new(10, 15, 20);
944        let v2 = Vector3::<i32>::new(3, 4, 6);
945
946        let rem = v1 % v2;
947        assert_eq!(rem.x, 1); // 10 % 3 = 1
948        assert_eq!(rem.y, 3); // 15 % 4 = 3
949        assert_eq!(rem.z, 2); // 20 % 6 = 2
950
951        let v3 = Vector3::<i32>::new(10, 15, 20);
952        let rem_scalar = v3 % 7;
953        assert_eq!(rem_scalar.x, 3); // 10 % 7 = 3
954        assert_eq!(rem_scalar.y, 1); // 15 % 7 = 1
955        assert_eq!(rem_scalar.z, 6); // 20 % 7 = 6
956    }
957
958    #[test]
959    fn test_vector_try_cast() {
960        let vi = Vector3::<i32>::new(1, 2, 3);
961        let vf = vi
962            .try_cast::<f32>()
963            .expect("integer vector should cast to f32");
964        assert_eq!(vf.x, 1.0);
965        assert_eq!(vf.y, 2.0);
966        assert_eq!(vf.z, 3.0);
967    }
968}