glam/f32/sse2/
vec3a.rs

1// Generated from vec.rs.tera template. Edit the template, not the generated file.
2
3use crate::{f32::math, sse2::*, BVec3, BVec3A, FloatExt, Quat, Vec2, Vec3, Vec4};
4
5use core::fmt;
6use core::iter::{Product, Sum};
7use core::{f32, ops::*};
8
9#[cfg(target_arch = "x86")]
10use core::arch::x86::*;
11#[cfg(target_arch = "x86_64")]
12use core::arch::x86_64::*;
13
14#[cfg(feature = "zerocopy")]
15use zerocopy_derive::*;
16
17#[repr(C)]
18union UnionCast {
19    a: [f32; 4],
20    v: Vec3A,
21}
22
23/// Creates a 3-dimensional vector.
24#[inline(always)]
25#[must_use]
26pub const fn vec3a(x: f32, y: f32, z: f32) -> Vec3A {
27    Vec3A::new(x, y, z)
28}
29
30/// A 3-dimensional vector.
31///
32/// SIMD vector types are used for storage on supported platforms for better
33/// performance than the [`Vec3`] type.
34///
35/// It is possible to convert between [`Vec3`] and [`Vec3A`] types using [`From`]
36/// or [`Into`] trait implementations.
37///
38/// This type is 16 byte aligned.
39#[derive(Clone, Copy)]
40#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))]
41#[cfg_attr(
42    feature = "zerocopy",
43    derive(FromBytes, Immutable, IntoBytes, KnownLayout)
44)]
45#[repr(transparent)]
46pub struct Vec3A(pub(crate) __m128);
47
48impl Vec3A {
49    /// All zeroes.
50    pub const ZERO: Self = Self::splat(0.0);
51
52    /// All ones.
53    pub const ONE: Self = Self::splat(1.0);
54
55    /// All negative ones.
56    pub const NEG_ONE: Self = Self::splat(-1.0);
57
58    /// All `f32::MIN`.
59    pub const MIN: Self = Self::splat(f32::MIN);
60
61    /// All `f32::MAX`.
62    pub const MAX: Self = Self::splat(f32::MAX);
63
64    /// All `f32::NAN`.
65    pub const NAN: Self = Self::splat(f32::NAN);
66
67    /// All `f32::INFINITY`.
68    pub const INFINITY: Self = Self::splat(f32::INFINITY);
69
70    /// All `f32::NEG_INFINITY`.
71    pub const NEG_INFINITY: Self = Self::splat(f32::NEG_INFINITY);
72
73    /// A unit vector pointing along the positive X axis.
74    pub const X: Self = Self::new(1.0, 0.0, 0.0);
75
76    /// A unit vector pointing along the positive Y axis.
77    pub const Y: Self = Self::new(0.0, 1.0, 0.0);
78
79    /// A unit vector pointing along the positive Z axis.
80    pub const Z: Self = Self::new(0.0, 0.0, 1.0);
81
82    /// A unit vector pointing along the negative X axis.
83    pub const NEG_X: Self = Self::new(-1.0, 0.0, 0.0);
84
85    /// A unit vector pointing along the negative Y axis.
86    pub const NEG_Y: Self = Self::new(0.0, -1.0, 0.0);
87
88    /// A unit vector pointing along the negative Z axis.
89    pub const NEG_Z: Self = Self::new(0.0, 0.0, -1.0);
90
91    /// The unit axes.
92    pub const AXES: [Self; 3] = [Self::X, Self::Y, Self::Z];
93
94    /// Vec3A uses Rust Portable SIMD
95    pub const USES_CORE_SIMD: bool = false;
96    /// Vec3A uses Arm NEON
97    pub const USES_NEON: bool = false;
98    /// Vec3A uses scalar math
99    pub const USES_SCALAR_MATH: bool = false;
100    /// Vec3A uses Intel SSE2
101    pub const USES_SSE2: bool = true;
102    /// Vec3A uses WebAssembly 128-bit SIMD
103    pub const USES_WASM_SIMD: bool = false;
104    #[deprecated(since = "0.31.0", note = "Renamed to USES_WASM_SIMD")]
105    pub const USES_WASM32_SIMD: bool = false;
106
107    /// Creates a new vector.
108    #[inline(always)]
109    #[must_use]
110    pub const fn new(x: f32, y: f32, z: f32) -> Self {
111        unsafe { UnionCast { a: [x, y, z, z] }.v }
112    }
113
114    /// Creates a vector with all elements set to `v`.
115    #[inline]
116    #[must_use]
117    pub const fn splat(v: f32) -> Self {
118        unsafe { UnionCast { a: [v; 4] }.v }
119    }
120
121    /// Returns a vector containing each element of `self` modified by a mapping function `f`.
122    #[inline]
123    #[must_use]
124    pub fn map<F>(self, f: F) -> Self
125    where
126        F: Fn(f32) -> f32,
127    {
128        Self::new(f(self.x), f(self.y), f(self.z))
129    }
130
131    /// Creates a vector from the elements in `if_true` and `if_false`, selecting which to use
132    /// for each element of `self`.
133    ///
134    /// A true element in the mask uses the corresponding element from `if_true`, and false
135    /// uses the element from `if_false`.
136    #[inline]
137    #[must_use]
138    pub fn select(mask: BVec3A, if_true: Self, if_false: Self) -> Self {
139        Self(unsafe {
140            _mm_or_ps(
141                _mm_andnot_ps(mask.0, if_false.0),
142                _mm_and_ps(if_true.0, mask.0),
143            )
144        })
145    }
146
147    /// Creates a new vector from an array.
148    #[inline]
149    #[must_use]
150    pub const fn from_array(a: [f32; 3]) -> Self {
151        Self::new(a[0], a[1], a[2])
152    }
153
154    /// Converts `self` to `[x, y, z]`
155    #[inline]
156    #[must_use]
157    pub const fn to_array(&self) -> [f32; 3] {
158        unsafe { *(self as *const Self as *const [f32; 3]) }
159    }
160
161    /// Creates a vector from the first 3 values in `slice`.
162    ///
163    /// # Panics
164    ///
165    /// Panics if `slice` is less than 3 elements long.
166    #[inline]
167    #[must_use]
168    pub const fn from_slice(slice: &[f32]) -> Self {
169        assert!(slice.len() >= 3);
170        Self::new(slice[0], slice[1], slice[2])
171    }
172
173    /// Writes the elements of `self` to the first 3 elements in `slice`.
174    ///
175    /// # Panics
176    ///
177    /// Panics if `slice` is less than 3 elements long.
178    #[inline]
179    pub fn write_to_slice(self, slice: &mut [f32]) {
180        slice[..3].copy_from_slice(&self.to_array());
181    }
182
183    /// Creates a [`Vec3A`] from the `x`, `y` and `z` elements of `self` discarding `w`.
184    ///
185    /// On architectures where SIMD is supported such as SSE2 on `x86_64` this conversion is a noop.
186    #[inline]
187    #[must_use]
188    pub fn from_vec4(v: Vec4) -> Self {
189        Self(v.0)
190    }
191
192    /// Creates a 4D vector from `self` and the given `w` value.
193    #[inline]
194    #[must_use]
195    pub fn extend(self, w: f32) -> Vec4 {
196        Vec4::new(self.x, self.y, self.z, w)
197    }
198
199    /// Creates a 2D vector from the `x` and `y` elements of `self`, discarding `z`.
200    ///
201    /// Truncation may also be performed by using [`self.xy()`][crate::swizzles::Vec3Swizzles::xy()].
202    #[inline]
203    #[must_use]
204    pub fn truncate(self) -> Vec2 {
205        use crate::swizzles::Vec3Swizzles;
206        self.xy()
207    }
208
209    /// Projects a homogeneous coordinate to 3D space by performing perspective divide.
210    ///
211    /// # Panics
212    ///
213    /// Will panic if `v.w` is `0` when `glam_assert` is enabled.
214    #[inline]
215    #[must_use]
216    pub fn from_homogeneous(v: Vec4) -> Self {
217        glam_assert!(v.w != 0.0);
218        Self::from_vec4(v) / v.w
219    }
220
221    /// Creates a homogeneous coordinate from `self`, equivalent to `self.extend(1.0)`.
222    #[inline]
223    #[must_use]
224    pub fn to_homogeneous(self) -> Vec4 {
225        self.extend(1.0)
226    }
227
228    // Converts `self` to a `Vec3`.
229    #[inline]
230    #[must_use]
231    pub fn to_vec3(self) -> Vec3 {
232        Vec3::from(self)
233    }
234
235    /// Creates a 3D vector from `self` with the given value of `x`.
236    #[inline]
237    #[must_use]
238    pub fn with_x(mut self, x: f32) -> Self {
239        self.x = x;
240        self
241    }
242
243    /// Creates a 3D vector from `self` with the given value of `y`.
244    #[inline]
245    #[must_use]
246    pub fn with_y(mut self, y: f32) -> Self {
247        self.y = y;
248        self
249    }
250
251    /// Creates a 3D vector from `self` with the given value of `z`.
252    #[inline]
253    #[must_use]
254    pub fn with_z(mut self, z: f32) -> Self {
255        self.z = z;
256        self
257    }
258
259    /// Computes the dot product of `self` and `rhs`.
260    #[inline]
261    #[must_use]
262    pub fn dot(self, rhs: Self) -> f32 {
263        unsafe { dot3(self.0, rhs.0) }
264    }
265
266    /// Returns a vector where every component is the dot product of `self` and `rhs`.
267    #[inline]
268    #[must_use]
269    pub fn dot_into_vec(self, rhs: Self) -> Self {
270        Self(unsafe { dot3_into_m128(self.0, rhs.0) })
271    }
272
273    /// Computes the cross product of `self` and `rhs`.
274    #[inline]
275    #[must_use]
276    pub fn cross(self, rhs: Self) -> Self {
277        unsafe {
278            // x  <-  a.y*b.z - a.z*b.y
279            // y  <-  a.z*b.x - a.x*b.z
280            // z  <-  a.x*b.y - a.y*b.x
281            // We can save a shuffle by grouping it in this wacky order:
282            // (self.zxy() * rhs - self * rhs.zxy()).zxy()
283            let lhszxy = _mm_shuffle_ps(self.0, self.0, 0b01_01_00_10);
284            let rhszxy = _mm_shuffle_ps(rhs.0, rhs.0, 0b01_01_00_10);
285            let lhszxy_rhs = _mm_mul_ps(lhszxy, rhs.0);
286            let rhszxy_lhs = _mm_mul_ps(rhszxy, self.0);
287            let sub = _mm_sub_ps(lhszxy_rhs, rhszxy_lhs);
288            Self(_mm_shuffle_ps(sub, sub, 0b01_01_00_10))
289        }
290    }
291
292    /// Returns a vector containing the minimum values for each element of `self` and `rhs`.
293    ///
294    /// In other words this computes `[min(x, rhs.x), min(self.y, rhs.y), ..]`.
295    ///
296    /// NaN propogation does not follow IEEE 754-2008 semantics for minNum and may differ on
297    /// different SIMD architectures.
298    #[inline]
299    #[must_use]
300    pub fn min(self, rhs: Self) -> Self {
301        Self(unsafe { _mm_min_ps(self.0, rhs.0) })
302    }
303
304    /// Returns a vector containing the maximum values for each element of `self` and `rhs`.
305    ///
306    /// In other words this computes `[max(self.x, rhs.x), max(self.y, rhs.y), ..]`.
307    ///
308    /// NaN propogation does not follow IEEE 754-2008 semantics for maxNum and may differ on
309    /// different SIMD architectures.
310    #[inline]
311    #[must_use]
312    pub fn max(self, rhs: Self) -> Self {
313        Self(unsafe { _mm_max_ps(self.0, rhs.0) })
314    }
315
316    /// Component-wise clamping of values, similar to [`f32::clamp`].
317    ///
318    /// Each element in `min` must be less-or-equal to the corresponding element in `max`.
319    ///
320    /// NaN propogation does not follow IEEE 754-2008 semantics and may differ on
321    /// different SIMD architectures.
322    ///
323    /// # Panics
324    ///
325    /// Will panic if `min` is greater than `max` when `glam_assert` is enabled.
326    #[inline]
327    #[must_use]
328    pub fn clamp(self, min: Self, max: Self) -> Self {
329        glam_assert!(min.cmple(max).all(), "clamp: expected min <= max");
330        self.max(min).min(max)
331    }
332
333    /// Returns the horizontal minimum of `self`.
334    ///
335    /// In other words this computes `min(x, y, ..)`.
336    ///
337    /// NaN propogation does not follow IEEE 754-2008 semantics and may differ on
338    /// different SIMD architectures.
339    #[inline]
340    #[must_use]
341    pub fn min_element(self) -> f32 {
342        unsafe {
343            let v = self.0;
344            let v = _mm_min_ps(v, _mm_shuffle_ps(v, v, 0b01_01_10_10));
345            let v = _mm_min_ps(v, _mm_shuffle_ps(v, v, 0b00_00_00_01));
346            _mm_cvtss_f32(v)
347        }
348    }
349
350    /// Returns the horizontal maximum of `self`.
351    ///
352    /// In other words this computes `max(x, y, ..)`.
353    ///
354    /// NaN propogation does not follow IEEE 754-2008 semantics and may differ on
355    /// different SIMD architectures.
356    #[inline]
357    #[must_use]
358    pub fn max_element(self) -> f32 {
359        unsafe {
360            let v = self.0;
361            let v = _mm_max_ps(v, _mm_shuffle_ps(v, v, 0b00_00_10_10));
362            let v = _mm_max_ps(v, _mm_shuffle_ps(v, v, 0b00_00_00_01));
363            _mm_cvtss_f32(v)
364        }
365    }
366
367    /// Returns the index of the first minimum element of `self`.
368    #[doc(alias = "argmin")]
369    #[inline]
370    #[must_use]
371    pub fn min_position(self) -> usize {
372        let mut min = self.x;
373        let mut index = 0;
374        if self.y < min {
375            min = self.y;
376            index = 1;
377        }
378        if self.z < min {
379            index = 2;
380        }
381        index
382    }
383
384    /// Returns the index of the first maximum element of `self`.
385    #[doc(alias = "argmax")]
386    #[inline]
387    #[must_use]
388    pub fn max_position(self) -> usize {
389        let mut max = self.x;
390        let mut index = 0;
391        if self.y > max {
392            max = self.y;
393            index = 1;
394        }
395        if self.z > max {
396            index = 2;
397        }
398        index
399    }
400
401    /// Returns the sum of all elements of `self`.
402    ///
403    /// In other words, this computes `self.x + self.y + ..`.
404    #[inline]
405    #[must_use]
406    pub fn element_sum(self) -> f32 {
407        unsafe {
408            let v = self.0;
409            let v = _mm_add_ps(v, _mm_shuffle_ps(v, Self::ZERO.0, 0b00_11_00_01));
410            let v = _mm_add_ps(v, _mm_shuffle_ps(v, v, 0b00_00_00_10));
411            _mm_cvtss_f32(v)
412        }
413    }
414
415    /// Returns the product of all elements of `self`.
416    ///
417    /// In other words, this computes `self.x * self.y * ..`.
418    #[inline]
419    #[must_use]
420    pub fn element_product(self) -> f32 {
421        unsafe {
422            let v = self.0;
423            let v = _mm_mul_ps(v, _mm_shuffle_ps(v, Self::ONE.0, 0b00_11_00_01));
424            let v = _mm_mul_ps(v, _mm_shuffle_ps(v, v, 0b00_00_00_10));
425            _mm_cvtss_f32(v)
426        }
427    }
428
429    /// Returns a vector mask containing the result of a `==` comparison for each element of
430    /// `self` and `rhs`.
431    ///
432    /// In other words, this computes `[self.x == rhs.x, self.y == rhs.y, ..]` for all
433    /// elements.
434    #[inline]
435    #[must_use]
436    pub fn cmpeq(self, rhs: Self) -> BVec3A {
437        BVec3A(unsafe { _mm_cmpeq_ps(self.0, rhs.0) })
438    }
439
440    /// Returns a vector mask containing the result of a `!=` comparison for each element of
441    /// `self` and `rhs`.
442    ///
443    /// In other words this computes `[self.x != rhs.x, self.y != rhs.y, ..]` for all
444    /// elements.
445    #[inline]
446    #[must_use]
447    pub fn cmpne(self, rhs: Self) -> BVec3A {
448        BVec3A(unsafe { _mm_cmpneq_ps(self.0, rhs.0) })
449    }
450
451    /// Returns a vector mask containing the result of a `>=` comparison for each element of
452    /// `self` and `rhs`.
453    ///
454    /// In other words this computes `[self.x >= rhs.x, self.y >= rhs.y, ..]` for all
455    /// elements.
456    #[inline]
457    #[must_use]
458    pub fn cmpge(self, rhs: Self) -> BVec3A {
459        BVec3A(unsafe { _mm_cmpge_ps(self.0, rhs.0) })
460    }
461
462    /// Returns a vector mask containing the result of a `>` comparison for each element of
463    /// `self` and `rhs`.
464    ///
465    /// In other words this computes `[self.x > rhs.x, self.y > rhs.y, ..]` for all
466    /// elements.
467    #[inline]
468    #[must_use]
469    pub fn cmpgt(self, rhs: Self) -> BVec3A {
470        BVec3A(unsafe { _mm_cmpgt_ps(self.0, rhs.0) })
471    }
472
473    /// Returns a vector mask containing the result of a `<=` comparison for each element of
474    /// `self` and `rhs`.
475    ///
476    /// In other words this computes `[self.x <= rhs.x, self.y <= rhs.y, ..]` for all
477    /// elements.
478    #[inline]
479    #[must_use]
480    pub fn cmple(self, rhs: Self) -> BVec3A {
481        BVec3A(unsafe { _mm_cmple_ps(self.0, rhs.0) })
482    }
483
484    /// Returns a vector mask containing the result of a `<` comparison for each element of
485    /// `self` and `rhs`.
486    ///
487    /// In other words this computes `[self.x < rhs.x, self.y < rhs.y, ..]` for all
488    /// elements.
489    #[inline]
490    #[must_use]
491    pub fn cmplt(self, rhs: Self) -> BVec3A {
492        BVec3A(unsafe { _mm_cmplt_ps(self.0, rhs.0) })
493    }
494
495    /// Returns a vector containing the absolute value of each element of `self`.
496    #[inline]
497    #[must_use]
498    pub fn abs(self) -> Self {
499        Self(unsafe { crate::sse2::m128_abs(self.0) })
500    }
501
502    /// Returns a vector with elements representing the sign of `self`.
503    ///
504    /// - `1.0` if the number is positive, `+0.0` or `INFINITY`
505    /// - `-1.0` if the number is negative, `-0.0` or `NEG_INFINITY`
506    /// - `NAN` if the number is `NAN`
507    #[inline]
508    #[must_use]
509    pub fn signum(self) -> Self {
510        let result = Self(unsafe { _mm_or_ps(_mm_and_ps(self.0, Self::NEG_ONE.0), Self::ONE.0) });
511        let mask = self.is_nan_mask();
512        Self::select(mask, self, result)
513    }
514
515    /// Returns a vector with signs of `rhs` and the magnitudes of `self`.
516    #[inline]
517    #[must_use]
518    pub fn copysign(self, rhs: Self) -> Self {
519        let mask = Self::splat(-0.0);
520        Self(unsafe { _mm_or_ps(_mm_and_ps(rhs.0, mask.0), _mm_andnot_ps(mask.0, self.0)) })
521    }
522
523    /// Returns a bitmask with the lowest 3 bits set to the sign bits from the elements of `self`.
524    ///
525    /// A negative element results in a `1` bit and a positive element in a `0` bit.  Element `x` goes
526    /// into the first lowest bit, element `y` into the second, etc.
527    ///
528    /// An element is negative if it has a negative sign, including -0.0, NaNs with negative sign
529    /// bit and negative infinity.
530    #[inline]
531    #[must_use]
532    pub fn is_negative_bitmask(self) -> u32 {
533        unsafe { (_mm_movemask_ps(self.0) as u32) & 0x7 }
534    }
535
536    /// Returns `true` if, and only if, all elements are finite.  If any element is either
537    /// `NaN`, positive or negative infinity, this will return `false`.
538    #[inline]
539    #[must_use]
540    pub fn is_finite(self) -> bool {
541        self.is_finite_mask().all()
542    }
543
544    /// Performs `is_finite` on each element of self, returning a vector mask of the results.
545    ///
546    /// In other words, this computes `[x.is_finite(), y.is_finite(), ...]`.
547    #[inline]
548    #[must_use]
549    pub fn is_finite_mask(self) -> BVec3A {
550        BVec3A(unsafe { _mm_cmplt_ps(crate::sse2::m128_abs(self.0), Self::INFINITY.0) })
551    }
552
553    /// Returns `true` if any elements are `NaN`.
554    #[inline]
555    #[must_use]
556    pub fn is_nan(self) -> bool {
557        self.is_nan_mask().any()
558    }
559
560    /// Performs `is_nan` on each element of self, returning a vector mask of the results.
561    ///
562    /// In other words, this computes `[x.is_nan(), y.is_nan(), ...]`.
563    #[inline]
564    #[must_use]
565    pub fn is_nan_mask(self) -> BVec3A {
566        BVec3A(unsafe { _mm_cmpunord_ps(self.0, self.0) })
567    }
568
569    /// Computes the length of `self`.
570    #[doc(alias = "magnitude")]
571    #[inline]
572    #[must_use]
573    pub fn length(self) -> f32 {
574        unsafe {
575            let dot = dot3_in_x(self.0, self.0);
576            _mm_cvtss_f32(_mm_sqrt_ps(dot))
577        }
578    }
579
580    /// Computes the squared length of `self`.
581    ///
582    /// This is faster than `length()` as it avoids a square root operation.
583    #[doc(alias = "magnitude2")]
584    #[inline]
585    #[must_use]
586    pub fn length_squared(self) -> f32 {
587        self.dot(self)
588    }
589
590    /// Computes `1.0 / length()`.
591    ///
592    /// For valid results, `self` must _not_ be of length zero.
593    #[inline]
594    #[must_use]
595    pub fn length_recip(self) -> f32 {
596        unsafe {
597            let dot = dot3_in_x(self.0, self.0);
598            _mm_cvtss_f32(_mm_div_ps(Self::ONE.0, _mm_sqrt_ps(dot)))
599        }
600    }
601
602    /// Computes the Euclidean distance between two points in space.
603    #[inline]
604    #[must_use]
605    pub fn distance(self, rhs: Self) -> f32 {
606        (self - rhs).length()
607    }
608
609    /// Compute the squared euclidean distance between two points in space.
610    #[inline]
611    #[must_use]
612    pub fn distance_squared(self, rhs: Self) -> f32 {
613        (self - rhs).length_squared()
614    }
615
616    /// Returns the element-wise quotient of [Euclidean division] of `self` by `rhs`.
617    #[inline]
618    #[must_use]
619    pub fn div_euclid(self, rhs: Self) -> Self {
620        Self::new(
621            math::div_euclid(self.x, rhs.x),
622            math::div_euclid(self.y, rhs.y),
623            math::div_euclid(self.z, rhs.z),
624        )
625    }
626
627    /// Returns the element-wise remainder of [Euclidean division] of `self` by `rhs`.
628    ///
629    /// [Euclidean division]: f32::rem_euclid
630    #[inline]
631    #[must_use]
632    pub fn rem_euclid(self, rhs: Self) -> Self {
633        Self::new(
634            math::rem_euclid(self.x, rhs.x),
635            math::rem_euclid(self.y, rhs.y),
636            math::rem_euclid(self.z, rhs.z),
637        )
638    }
639
640    /// Returns `self` normalized to length 1.0.
641    ///
642    /// For valid results, `self` must be finite and _not_ of length zero, nor very close to zero.
643    ///
644    /// See also [`Self::try_normalize()`] and [`Self::normalize_or_zero()`].
645    ///
646    /// # Panics
647    ///
648    /// Will panic if the resulting normalized vector is not finite when `glam_assert` is enabled.
649    #[inline]
650    #[must_use]
651    pub fn normalize(self) -> Self {
652        unsafe {
653            let length = _mm_sqrt_ps(dot3_into_m128(self.0, self.0));
654            #[allow(clippy::let_and_return)]
655            let normalized = Self(_mm_div_ps(self.0, length));
656            glam_assert!(normalized.is_finite());
657            normalized
658        }
659    }
660
661    /// Returns `self` normalized to length 1.0 if possible, else returns `None`.
662    ///
663    /// In particular, if the input is zero (or very close to zero), or non-finite,
664    /// the result of this operation will be `None`.
665    ///
666    /// See also [`Self::normalize_or_zero()`].
667    #[inline]
668    #[must_use]
669    pub fn try_normalize(self) -> Option<Self> {
670        let rcp = self.length_recip();
671        if rcp.is_finite() && rcp > 0.0 {
672            Some(self * rcp)
673        } else {
674            None
675        }
676    }
677
678    /// Returns `self` normalized to length 1.0 if possible, else returns a
679    /// fallback value.
680    ///
681    /// In particular, if the input is zero (or very close to zero), or non-finite,
682    /// the result of this operation will be the fallback value.
683    ///
684    /// See also [`Self::try_normalize()`].
685    #[inline]
686    #[must_use]
687    pub fn normalize_or(self, fallback: Self) -> Self {
688        let rcp = self.length_recip();
689        if rcp.is_finite() && rcp > 0.0 {
690            self * rcp
691        } else {
692            fallback
693        }
694    }
695
696    /// Returns `self` normalized to length 1.0 if possible, else returns zero.
697    ///
698    /// In particular, if the input is zero (or very close to zero), or non-finite,
699    /// the result of this operation will be zero.
700    ///
701    /// See also [`Self::try_normalize()`].
702    #[inline]
703    #[must_use]
704    pub fn normalize_or_zero(self) -> Self {
705        self.normalize_or(Self::ZERO)
706    }
707
708    /// Returns `self` normalized to length 1.0 and the length of `self`.
709    ///
710    /// If `self` is zero length then `(Self::X, 0.0)` is returned.
711    #[inline]
712    #[must_use]
713    pub fn normalize_and_length(self) -> (Self, f32) {
714        let length = self.length();
715        let rcp = 1.0 / length;
716        if rcp.is_finite() && rcp > 0.0 {
717            (self * rcp, length)
718        } else {
719            (Self::X, 0.0)
720        }
721    }
722
723    /// Returns whether `self` is length `1.0` or not.
724    ///
725    /// Uses a precision threshold of approximately `1e-4`.
726    #[inline]
727    #[must_use]
728    pub fn is_normalized(self) -> bool {
729        math::abs(self.length_squared() - 1.0) <= 2e-4
730    }
731
732    /// Returns the vector projection of `self` onto `rhs`.
733    ///
734    /// `rhs` must be of non-zero length.
735    ///
736    /// # Panics
737    ///
738    /// Will panic if `rhs` is zero length when `glam_assert` is enabled.
739    #[inline]
740    #[must_use]
741    pub fn project_onto(self, rhs: Self) -> Self {
742        let other_len_sq_rcp = rhs.dot(rhs).recip();
743        glam_assert!(other_len_sq_rcp.is_finite());
744        rhs * self.dot(rhs) * other_len_sq_rcp
745    }
746
747    /// Returns the vector rejection of `self` from `rhs`.
748    ///
749    /// The vector rejection is the vector perpendicular to the projection of `self` onto
750    /// `rhs`, in rhs words the result of `self - self.project_onto(rhs)`.
751    ///
752    /// `rhs` must be of non-zero length.
753    ///
754    /// # Panics
755    ///
756    /// Will panic if `rhs` has a length of zero when `glam_assert` is enabled.
757    #[doc(alias("plane"))]
758    #[inline]
759    #[must_use]
760    pub fn reject_from(self, rhs: Self) -> Self {
761        self - self.project_onto(rhs)
762    }
763
764    /// Returns the vector projection of `self` onto `rhs`.
765    ///
766    /// `rhs` must be normalized.
767    ///
768    /// # Panics
769    ///
770    /// Will panic if `rhs` is not normalized when `glam_assert` is enabled.
771    #[inline]
772    #[must_use]
773    pub fn project_onto_normalized(self, rhs: Self) -> Self {
774        glam_assert!(rhs.is_normalized());
775        rhs * self.dot(rhs)
776    }
777
778    /// Returns the vector rejection of `self` from `rhs`.
779    ///
780    /// The vector rejection is the vector perpendicular to the projection of `self` onto
781    /// `rhs`, in rhs words the result of `self - self.project_onto(rhs)`.
782    ///
783    /// `rhs` must be normalized.
784    ///
785    /// # Panics
786    ///
787    /// Will panic if `rhs` is not normalized when `glam_assert` is enabled.
788    #[doc(alias("plane"))]
789    #[inline]
790    #[must_use]
791    pub fn reject_from_normalized(self, rhs: Self) -> Self {
792        self - self.project_onto_normalized(rhs)
793    }
794
795    /// Returns a vector containing the nearest integer to a number for each element of `self`.
796    /// Round half-way cases away from 0.0.
797    #[inline]
798    #[must_use]
799    pub fn round(self) -> Self {
800        Self(unsafe { m128_round(self.0) })
801    }
802
803    /// Returns a vector containing the largest integer less than or equal to a number for each
804    /// element of `self`.
805    #[inline]
806    #[must_use]
807    pub fn floor(self) -> Self {
808        Self(unsafe { m128_floor(self.0) })
809    }
810
811    /// Returns a vector containing the smallest integer greater than or equal to a number for
812    /// each element of `self`.
813    #[inline]
814    #[must_use]
815    pub fn ceil(self) -> Self {
816        Self(unsafe { m128_ceil(self.0) })
817    }
818
819    /// Returns a vector containing the integer part each element of `self`. This means numbers are
820    /// always truncated towards zero.
821    #[inline]
822    #[must_use]
823    pub fn trunc(self) -> Self {
824        Self(unsafe { m128_trunc(self.0) })
825    }
826
827    /// Returns a vector containing `0.0` if `rhs < self` and 1.0 otherwise.
828    ///
829    /// Similar to glsl's step(edge, x), which translates into edge.step(x)
830    #[inline]
831    #[must_use]
832    pub fn step(self, rhs: Self) -> Self {
833        Self::select(rhs.cmplt(self), Self::ZERO, Self::ONE)
834    }
835
836    /// Returns a vector containing all elements of `self` clamped to the range of `[0, 1]`.
837    #[inline]
838    #[must_use]
839    pub fn saturate(self) -> Self {
840        self.clamp(Self::ZERO, Self::ONE)
841    }
842
843    /// Returns a vector containing the fractional part of the vector as `self - self.trunc()`.
844    ///
845    /// Note that this differs from the GLSL implementation of `fract` which returns
846    /// `self - self.floor()`.
847    ///
848    /// Note that this is fast but not precise for large numbers.
849    #[inline]
850    #[must_use]
851    pub fn fract(self) -> Self {
852        self - self.trunc()
853    }
854
855    /// Returns a vector containing the fractional part of the vector as `self - self.floor()`.
856    ///
857    /// Note that this differs from the Rust implementation of `fract` which returns
858    /// `self - self.trunc()`.
859    ///
860    /// Note that this is fast but not precise for large numbers.
861    #[inline]
862    #[must_use]
863    pub fn fract_gl(self) -> Self {
864        self - self.floor()
865    }
866
867    /// Returns a vector containing `e^self` (the exponential function) for each element of
868    /// `self`.
869    #[inline]
870    #[must_use]
871    pub fn exp(self) -> Self {
872        Self::new(math::exp(self.x), math::exp(self.y), math::exp(self.z))
873    }
874
875    /// Returns a vector containing `2^self` for each element of `self`.
876    #[inline]
877    #[must_use]
878    pub fn exp2(self) -> Self {
879        Self::new(math::exp2(self.x), math::exp2(self.y), math::exp2(self.z))
880    }
881
882    /// Returns a vector containing the natural logarithm for each element of `self`.
883    /// This returns NaN when the element is negative and negative infinity when the element is zero.
884    #[inline]
885    #[must_use]
886    pub fn ln(self) -> Self {
887        Self::new(math::ln(self.x), math::ln(self.y), math::ln(self.z))
888    }
889
890    /// Returns a vector containing the base 2 logarithm for each element of `self`.
891    /// This returns NaN when the element is negative and negative infinity when the element is zero.
892    #[inline]
893    #[must_use]
894    pub fn log2(self) -> Self {
895        Self::new(math::log2(self.x), math::log2(self.y), math::log2(self.z))
896    }
897
898    /// Returns a vector containing each element of `self` raised to the power of `n`.
899    #[inline]
900    #[must_use]
901    pub fn powf(self, n: f32) -> Self {
902        Self::new(
903            math::powf(self.x, n),
904            math::powf(self.y, n),
905            math::powf(self.z, n),
906        )
907    }
908
909    /// Returns a vector containing the square root for each element of `self`.
910    /// This returns NaN when the element is negative.
911    #[inline]
912    #[must_use]
913    pub fn sqrt(self) -> Self {
914        Self::new(math::sqrt(self.x), math::sqrt(self.y), math::sqrt(self.z))
915    }
916
917    /// Returns a vector containing the cosine for each element of `self`.
918    #[inline]
919    #[must_use]
920    pub fn cos(self) -> Self {
921        Self::new(math::cos(self.x), math::cos(self.y), math::cos(self.z))
922    }
923
924    /// Returns a vector containing the sine for each element of `self`.
925    #[inline]
926    #[must_use]
927    pub fn sin(self) -> Self {
928        Self::new(math::sin(self.x), math::sin(self.y), math::sin(self.z))
929    }
930
931    /// Returns a tuple of two vectors containing the sine and cosine for each element of `self`.
932    #[inline]
933    #[must_use]
934    pub fn sin_cos(self) -> (Self, Self) {
935        let (sin_x, cos_x) = math::sin_cos(self.x);
936        let (sin_y, cos_y) = math::sin_cos(self.y);
937        let (sin_z, cos_z) = math::sin_cos(self.z);
938
939        (
940            Self::new(sin_x, sin_y, sin_z),
941            Self::new(cos_x, cos_y, cos_z),
942        )
943    }
944
945    /// Returns a vector containing the reciprocal `1.0/n` of each element of `self`.
946    #[inline]
947    #[must_use]
948    pub fn recip(self) -> Self {
949        Self(unsafe { _mm_div_ps(Self::ONE.0, self.0) })
950    }
951
952    /// Performs a linear interpolation between `self` and `rhs` based on the value `s`.
953    ///
954    /// When `s` is `0.0`, the result will be equal to `self`.  When `s` is `1.0`, the result
955    /// will be equal to `rhs`. When `s` is outside of range `[0, 1]`, the result is linearly
956    /// extrapolated.
957    #[doc(alias = "mix")]
958    #[inline]
959    #[must_use]
960    pub fn lerp(self, rhs: Self, s: f32) -> Self {
961        self * (1.0 - s) + rhs * s
962    }
963
964    /// Moves towards `rhs` based on the value `d`.
965    ///
966    /// When `d` is `0.0`, the result will be equal to `self`. When `d` is equal to
967    /// `self.distance(rhs)`, the result will be equal to `rhs`. Will not go past `rhs`.
968    #[inline]
969    #[must_use]
970    pub fn move_towards(self, rhs: Self, d: f32) -> Self {
971        let a = rhs - self;
972        let len = a.length();
973        if len <= d || len <= 1e-4 {
974            return rhs;
975        }
976        self + a / len * d
977    }
978
979    /// Calculates the midpoint between `self` and `rhs`.
980    ///
981    /// The midpoint is the average of, or halfway point between, two vectors.
982    /// `a.midpoint(b)` should yield the same result as `a.lerp(b, 0.5)`
983    /// while being slightly cheaper to compute.
984    #[inline]
985    pub fn midpoint(self, rhs: Self) -> Self {
986        (self + rhs) * 0.5
987    }
988
989    /// Returns true if the absolute difference of all elements between `self` and `rhs` is
990    /// less than or equal to `max_abs_diff`.
991    ///
992    /// This can be used to compare if two vectors contain similar elements. It works best when
993    /// comparing with a known value. The `max_abs_diff` that should be used used depends on
994    /// the values being compared against.
995    ///
996    /// For more see
997    /// [comparing floating point numbers](https://randomascii.wordpress.com/2012/02/25/comparing-floating-point-numbers-2012-edition/).
998    #[inline]
999    #[must_use]
1000    pub fn abs_diff_eq(self, rhs: Self, max_abs_diff: f32) -> bool {
1001        self.sub(rhs).abs().cmple(Self::splat(max_abs_diff)).all()
1002    }
1003
1004    /// Returns a vector with a length no less than `min` and no more than `max`.
1005    ///
1006    /// # Panics
1007    ///
1008    /// Will panic if `min` is greater than `max`, or if either `min` or `max` is negative, when `glam_assert` is enabled.
1009    #[inline]
1010    #[must_use]
1011    pub fn clamp_length(self, min: f32, max: f32) -> Self {
1012        glam_assert!(0.0 <= min);
1013        glam_assert!(min <= max);
1014        let length_sq = self.length_squared();
1015        if length_sq < min * min {
1016            min * (self / math::sqrt(length_sq))
1017        } else if length_sq > max * max {
1018            max * (self / math::sqrt(length_sq))
1019        } else {
1020            self
1021        }
1022    }
1023
1024    /// Returns a vector with a length no more than `max`.
1025    ///
1026    /// # Panics
1027    ///
1028    /// Will panic if `max` is negative when `glam_assert` is enabled.
1029    #[inline]
1030    #[must_use]
1031    pub fn clamp_length_max(self, max: f32) -> Self {
1032        glam_assert!(0.0 <= max);
1033        let length_sq = self.length_squared();
1034        if length_sq > max * max {
1035            max * (self / math::sqrt(length_sq))
1036        } else {
1037            self
1038        }
1039    }
1040
1041    /// Returns a vector with a length no less than `min`.
1042    ///
1043    /// # Panics
1044    ///
1045    /// Will panic if `min` is negative when `glam_assert` is enabled.
1046    #[inline]
1047    #[must_use]
1048    pub fn clamp_length_min(self, min: f32) -> Self {
1049        glam_assert!(0.0 <= min);
1050        let length_sq = self.length_squared();
1051        if length_sq < min * min {
1052            min * (self / math::sqrt(length_sq))
1053        } else {
1054            self
1055        }
1056    }
1057
1058    /// Fused multiply-add. Computes `(self * a) + b` element-wise with only one rounding
1059    /// error, yielding a more accurate result than an unfused multiply-add.
1060    ///
1061    /// Using `mul_add` *may* be more performant than an unfused multiply-add if the target
1062    /// architecture has a dedicated fma CPU instruction. However, this is not always true,
1063    /// and will be heavily dependant on designing algorithms with specific target hardware in
1064    /// mind.
1065    #[inline]
1066    #[must_use]
1067    pub fn mul_add(self, a: Self, b: Self) -> Self {
1068        #[cfg(target_feature = "fma")]
1069        unsafe {
1070            Self(_mm_fmadd_ps(self.0, a.0, b.0))
1071        }
1072        #[cfg(not(target_feature = "fma"))]
1073        Self::new(
1074            math::mul_add(self.x, a.x, b.x),
1075            math::mul_add(self.y, a.y, b.y),
1076            math::mul_add(self.z, a.z, b.z),
1077        )
1078    }
1079
1080    /// Returns the reflection vector for a given incident vector `self` and surface normal
1081    /// `normal`.
1082    ///
1083    /// `normal` must be normalized.
1084    ///
1085    /// # Panics
1086    ///
1087    /// Will panic if `normal` is not normalized when `glam_assert` is enabled.
1088    #[inline]
1089    #[must_use]
1090    pub fn reflect(self, normal: Self) -> Self {
1091        glam_assert!(normal.is_normalized());
1092        self - 2.0 * self.dot(normal) * normal
1093    }
1094
1095    /// Returns the refraction direction for a given incident vector `self`, surface normal
1096    /// `normal` and ratio of indices of refraction, `eta`. When total internal reflection occurs,
1097    /// a zero vector will be returned.
1098    ///
1099    /// `self` and `normal` must be normalized.
1100    ///
1101    /// # Panics
1102    ///
1103    /// Will panic if `self` or `normal` is not normalized when `glam_assert` is enabled.
1104    #[inline]
1105    #[must_use]
1106    pub fn refract(self, normal: Self, eta: f32) -> Self {
1107        glam_assert!(self.is_normalized());
1108        glam_assert!(normal.is_normalized());
1109        let n_dot_i = normal.dot(self);
1110        let k = 1.0 - eta * eta * (1.0 - n_dot_i * n_dot_i);
1111        if k >= 0.0 {
1112            eta * self - (eta * n_dot_i + math::sqrt(k)) * normal
1113        } else {
1114            Self::ZERO
1115        }
1116    }
1117
1118    /// Returns the angle (in radians) between two vectors in the range `[0, +Ï€]`.
1119    ///
1120    /// The inputs do not need to be unit vectors however they must be non-zero.
1121    #[inline]
1122    #[must_use]
1123    pub fn angle_between(self, rhs: Self) -> f32 {
1124        math::acos_approx(
1125            self.dot(rhs)
1126                .div(math::sqrt(self.length_squared().mul(rhs.length_squared()))),
1127        )
1128    }
1129
1130    /// Rotates around the x axis by `angle` (in radians).
1131    #[inline]
1132    #[must_use]
1133    pub fn rotate_x(self, angle: f32) -> Self {
1134        let (sina, cosa) = math::sin_cos(angle);
1135        Self::new(
1136            self.x,
1137            self.y * cosa - self.z * sina,
1138            self.y * sina + self.z * cosa,
1139        )
1140    }
1141
1142    /// Rotates around the y axis by `angle` (in radians).
1143    #[inline]
1144    #[must_use]
1145    pub fn rotate_y(self, angle: f32) -> Self {
1146        let (sina, cosa) = math::sin_cos(angle);
1147        Self::new(
1148            self.x * cosa + self.z * sina,
1149            self.y,
1150            self.x * -sina + self.z * cosa,
1151        )
1152    }
1153
1154    /// Rotates around the z axis by `angle` (in radians).
1155    #[inline]
1156    #[must_use]
1157    pub fn rotate_z(self, angle: f32) -> Self {
1158        let (sina, cosa) = math::sin_cos(angle);
1159        Self::new(
1160            self.x * cosa - self.y * sina,
1161            self.x * sina + self.y * cosa,
1162            self.z,
1163        )
1164    }
1165
1166    /// Rotates around `axis` by `angle` (in radians).
1167    ///
1168    /// The axis must be a unit vector.
1169    ///
1170    /// # Panics
1171    ///
1172    /// Will panic if `axis` is not normalized when `glam_assert` is enabled.
1173    #[inline]
1174    #[must_use]
1175    pub fn rotate_axis(self, axis: Self, angle: f32) -> Self {
1176        Quat::from_axis_angle(axis.into(), angle) * self
1177    }
1178
1179    /// Rotates towards `rhs` up to `max_angle` (in radians).
1180    ///
1181    /// When `max_angle` is `0.0`, the result will be equal to `self`. When `max_angle` is equal to
1182    /// `self.angle_between(rhs)`, the result will be parallel to `rhs`. If `max_angle` is negative,
1183    /// rotates towards the exact opposite of `rhs`. Will not go past the target.
1184    #[inline]
1185    #[must_use]
1186    pub fn rotate_towards(self, rhs: Self, max_angle: f32) -> Self {
1187        let angle_between = self.angle_between(rhs);
1188        // When `max_angle < 0`, rotate no further than `PI` radians away
1189        let angle = max_angle.clamp(angle_between - core::f32::consts::PI, angle_between);
1190        let axis = self
1191            .cross(rhs)
1192            .try_normalize()
1193            .unwrap_or_else(|| self.any_orthogonal_vector().normalize());
1194        Quat::from_axis_angle(axis.into(), angle) * self
1195    }
1196
1197    /// Returns some vector that is orthogonal to the given one.
1198    ///
1199    /// The input vector must be finite and non-zero.
1200    ///
1201    /// The output vector is not necessarily unit length. For that use
1202    /// [`Self::any_orthonormal_vector()`] instead.
1203    #[inline]
1204    #[must_use]
1205    pub fn any_orthogonal_vector(self) -> Self {
1206        // This can probably be optimized
1207        if math::abs(self.x) > math::abs(self.y) {
1208            Self::new(-self.z, 0.0, self.x) // self.cross(Self::Y)
1209        } else {
1210            Self::new(0.0, self.z, -self.y) // self.cross(Self::X)
1211        }
1212    }
1213
1214    /// Returns any unit vector that is orthogonal to the given one.
1215    ///
1216    /// The input vector must be unit length.
1217    ///
1218    /// # Panics
1219    ///
1220    /// Will panic if `self` is not normalized when `glam_assert` is enabled.
1221    #[inline]
1222    #[must_use]
1223    pub fn any_orthonormal_vector(self) -> Self {
1224        glam_assert!(self.is_normalized());
1225        // From https://graphics.pixar.com/library/OrthonormalB/paper.pdf
1226        let sign = math::signum(self.z);
1227        let a = -1.0 / (sign + self.z);
1228        let b = self.x * self.y * a;
1229        Self::new(b, sign + self.y * self.y * a, -self.y)
1230    }
1231
1232    /// Given a unit vector return two other vectors that together form an orthonormal
1233    /// basis. That is, all three vectors are orthogonal to each other and are normalized.
1234    ///
1235    /// # Panics
1236    ///
1237    /// Will panic if `self` is not normalized when `glam_assert` is enabled.
1238    #[inline]
1239    #[must_use]
1240    pub fn any_orthonormal_pair(self) -> (Self, Self) {
1241        glam_assert!(self.is_normalized());
1242        // From https://graphics.pixar.com/library/OrthonormalB/paper.pdf
1243        let sign = math::signum(self.z);
1244        let a = -1.0 / (sign + self.z);
1245        let b = self.x * self.y * a;
1246        (
1247            Self::new(1.0 + sign * self.x * self.x * a, sign * b, -sign * self.x),
1248            Self::new(b, sign + self.y * self.y * a, -self.y),
1249        )
1250    }
1251
1252    /// Performs a spherical linear interpolation between `self` and `rhs` based on the value `s`.
1253    ///
1254    /// When `s` is `0.0`, the result will be equal to `self`.  When `s` is `1.0`, the result
1255    /// will be equal to `rhs`. When `s` is outside of range `[0, 1]`, the result is linearly
1256    /// extrapolated.
1257    #[inline]
1258    #[must_use]
1259    pub fn slerp(self, rhs: Self, s: f32) -> Self {
1260        let self_length = self.length();
1261        let rhs_length = rhs.length();
1262        // Cosine of the angle between the vectors [-1, 1], or NaN if either vector has a zero length
1263        let dot = self.dot(rhs) / (self_length * rhs_length);
1264        // If dot is close to 1 or -1, or is NaN the calculations for t1 and t2 break down
1265        if math::abs(dot) < 1.0 - 3e-7 {
1266            // Angle between the vectors [0, +Ï€]
1267            let theta = math::acos_approx(dot);
1268            // Sine of the angle between vectors [0, 1]
1269            let sin_theta = math::sin(theta);
1270            let t1 = math::sin(theta * (1. - s));
1271            let t2 = math::sin(theta * s);
1272
1273            // Interpolate vector lengths
1274            let result_length = self_length.lerp(rhs_length, s);
1275            // Scale the vectors to the target length and interpolate them
1276            return (self * (result_length / self_length) * t1
1277                + rhs * (result_length / rhs_length) * t2)
1278                * sin_theta.recip();
1279        }
1280        if dot < 0.0 {
1281            // Vectors are almost parallel in opposing directions
1282
1283            // Create a rotation from self to rhs along some axis
1284            let axis = self.any_orthogonal_vector().normalize().into();
1285            let rotation = Quat::from_axis_angle(axis, core::f32::consts::PI * s);
1286            // Interpolate vector lengths
1287            let result_length = self_length.lerp(rhs_length, s);
1288            rotation * self * (result_length / self_length)
1289        } else {
1290            // Vectors are almost parallel in the same direction, or dot was NaN
1291            self.lerp(rhs, s)
1292        }
1293    }
1294
1295    /// Casts all elements of `self` to `f64`.
1296    #[inline]
1297    #[must_use]
1298    pub fn as_dvec3(self) -> crate::DVec3 {
1299        crate::DVec3::new(self.x as f64, self.y as f64, self.z as f64)
1300    }
1301
1302    /// Casts all elements of `self` to `i8`.
1303    #[inline]
1304    #[must_use]
1305    pub fn as_i8vec3(self) -> crate::I8Vec3 {
1306        crate::I8Vec3::new(self.x as i8, self.y as i8, self.z as i8)
1307    }
1308
1309    /// Casts all elements of `self` to `u8`.
1310    #[inline]
1311    #[must_use]
1312    pub fn as_u8vec3(self) -> crate::U8Vec3 {
1313        crate::U8Vec3::new(self.x as u8, self.y as u8, self.z as u8)
1314    }
1315
1316    /// Casts all elements of `self` to `i16`.
1317    #[inline]
1318    #[must_use]
1319    pub fn as_i16vec3(self) -> crate::I16Vec3 {
1320        crate::I16Vec3::new(self.x as i16, self.y as i16, self.z as i16)
1321    }
1322
1323    /// Casts all elements of `self` to `u16`.
1324    #[inline]
1325    #[must_use]
1326    pub fn as_u16vec3(self) -> crate::U16Vec3 {
1327        crate::U16Vec3::new(self.x as u16, self.y as u16, self.z as u16)
1328    }
1329
1330    /// Casts all elements of `self` to `i32`.
1331    #[inline]
1332    #[must_use]
1333    pub fn as_ivec3(self) -> crate::IVec3 {
1334        crate::IVec3::new(self.x as i32, self.y as i32, self.z as i32)
1335    }
1336
1337    /// Casts all elements of `self` to `u32`.
1338    #[inline]
1339    #[must_use]
1340    pub fn as_uvec3(self) -> crate::UVec3 {
1341        crate::UVec3::new(self.x as u32, self.y as u32, self.z as u32)
1342    }
1343
1344    /// Casts all elements of `self` to `i64`.
1345    #[inline]
1346    #[must_use]
1347    pub fn as_i64vec3(self) -> crate::I64Vec3 {
1348        crate::I64Vec3::new(self.x as i64, self.y as i64, self.z as i64)
1349    }
1350
1351    /// Casts all elements of `self` to `u64`.
1352    #[inline]
1353    #[must_use]
1354    pub fn as_u64vec3(self) -> crate::U64Vec3 {
1355        crate::U64Vec3::new(self.x as u64, self.y as u64, self.z as u64)
1356    }
1357
1358    /// Casts all elements of `self` to `isize`.
1359    #[inline]
1360    #[must_use]
1361    pub fn as_isizevec3(self) -> crate::ISizeVec3 {
1362        crate::ISizeVec3::new(self.x as isize, self.y as isize, self.z as isize)
1363    }
1364
1365    /// Casts all elements of `self` to `usize`.
1366    #[inline]
1367    #[must_use]
1368    pub fn as_usizevec3(self) -> crate::USizeVec3 {
1369        crate::USizeVec3::new(self.x as usize, self.y as usize, self.z as usize)
1370    }
1371}
1372
1373impl Default for Vec3A {
1374    #[inline(always)]
1375    fn default() -> Self {
1376        Self::ZERO
1377    }
1378}
1379
1380impl PartialEq for Vec3A {
1381    #[inline]
1382    fn eq(&self, rhs: &Self) -> bool {
1383        self.cmpeq(*rhs).all()
1384    }
1385}
1386
1387impl Div for Vec3A {
1388    type Output = Self;
1389    #[inline]
1390    fn div(self, rhs: Self) -> Self {
1391        Self(unsafe { _mm_div_ps(self.0, rhs.0) })
1392    }
1393}
1394
1395impl Div<&Self> for Vec3A {
1396    type Output = Self;
1397    #[inline]
1398    fn div(self, rhs: &Self) -> Self {
1399        self.div(*rhs)
1400    }
1401}
1402
1403impl Div<&Vec3A> for &Vec3A {
1404    type Output = Vec3A;
1405    #[inline]
1406    fn div(self, rhs: &Vec3A) -> Vec3A {
1407        (*self).div(*rhs)
1408    }
1409}
1410
1411impl Div<Vec3A> for &Vec3A {
1412    type Output = Vec3A;
1413    #[inline]
1414    fn div(self, rhs: Vec3A) -> Vec3A {
1415        (*self).div(rhs)
1416    }
1417}
1418
1419impl DivAssign for Vec3A {
1420    #[inline]
1421    fn div_assign(&mut self, rhs: Self) {
1422        self.0 = unsafe { _mm_div_ps(self.0, rhs.0) };
1423    }
1424}
1425
1426impl DivAssign<&Self> for Vec3A {
1427    #[inline]
1428    fn div_assign(&mut self, rhs: &Self) {
1429        self.div_assign(*rhs);
1430    }
1431}
1432
1433impl Div<f32> for Vec3A {
1434    type Output = Self;
1435    #[inline]
1436    fn div(self, rhs: f32) -> Self {
1437        Self(unsafe { _mm_div_ps(self.0, _mm_set1_ps(rhs)) })
1438    }
1439}
1440
1441impl Div<&f32> for Vec3A {
1442    type Output = Self;
1443    #[inline]
1444    fn div(self, rhs: &f32) -> Self {
1445        self.div(*rhs)
1446    }
1447}
1448
1449impl Div<&f32> for &Vec3A {
1450    type Output = Vec3A;
1451    #[inline]
1452    fn div(self, rhs: &f32) -> Vec3A {
1453        (*self).div(*rhs)
1454    }
1455}
1456
1457impl Div<f32> for &Vec3A {
1458    type Output = Vec3A;
1459    #[inline]
1460    fn div(self, rhs: f32) -> Vec3A {
1461        (*self).div(rhs)
1462    }
1463}
1464
1465impl DivAssign<f32> for Vec3A {
1466    #[inline]
1467    fn div_assign(&mut self, rhs: f32) {
1468        self.0 = unsafe { _mm_div_ps(self.0, _mm_set1_ps(rhs)) };
1469    }
1470}
1471
1472impl DivAssign<&f32> for Vec3A {
1473    #[inline]
1474    fn div_assign(&mut self, rhs: &f32) {
1475        self.div_assign(*rhs);
1476    }
1477}
1478
1479impl Div<Vec3A> for f32 {
1480    type Output = Vec3A;
1481    #[inline]
1482    fn div(self, rhs: Vec3A) -> Vec3A {
1483        Vec3A(unsafe { _mm_div_ps(_mm_set1_ps(self), rhs.0) })
1484    }
1485}
1486
1487impl Div<&Vec3A> for f32 {
1488    type Output = Vec3A;
1489    #[inline]
1490    fn div(self, rhs: &Vec3A) -> Vec3A {
1491        self.div(*rhs)
1492    }
1493}
1494
1495impl Div<&Vec3A> for &f32 {
1496    type Output = Vec3A;
1497    #[inline]
1498    fn div(self, rhs: &Vec3A) -> Vec3A {
1499        (*self).div(*rhs)
1500    }
1501}
1502
1503impl Div<Vec3A> for &f32 {
1504    type Output = Vec3A;
1505    #[inline]
1506    fn div(self, rhs: Vec3A) -> Vec3A {
1507        (*self).div(rhs)
1508    }
1509}
1510
1511impl Mul for Vec3A {
1512    type Output = Self;
1513    #[inline]
1514    fn mul(self, rhs: Self) -> Self {
1515        Self(unsafe { _mm_mul_ps(self.0, rhs.0) })
1516    }
1517}
1518
1519impl Mul<&Self> for Vec3A {
1520    type Output = Self;
1521    #[inline]
1522    fn mul(self, rhs: &Self) -> Self {
1523        self.mul(*rhs)
1524    }
1525}
1526
1527impl Mul<&Vec3A> for &Vec3A {
1528    type Output = Vec3A;
1529    #[inline]
1530    fn mul(self, rhs: &Vec3A) -> Vec3A {
1531        (*self).mul(*rhs)
1532    }
1533}
1534
1535impl Mul<Vec3A> for &Vec3A {
1536    type Output = Vec3A;
1537    #[inline]
1538    fn mul(self, rhs: Vec3A) -> Vec3A {
1539        (*self).mul(rhs)
1540    }
1541}
1542
1543impl MulAssign for Vec3A {
1544    #[inline]
1545    fn mul_assign(&mut self, rhs: Self) {
1546        self.0 = unsafe { _mm_mul_ps(self.0, rhs.0) };
1547    }
1548}
1549
1550impl MulAssign<&Self> for Vec3A {
1551    #[inline]
1552    fn mul_assign(&mut self, rhs: &Self) {
1553        self.mul_assign(*rhs);
1554    }
1555}
1556
1557impl Mul<f32> for Vec3A {
1558    type Output = Self;
1559    #[inline]
1560    fn mul(self, rhs: f32) -> Self {
1561        Self(unsafe { _mm_mul_ps(self.0, _mm_set1_ps(rhs)) })
1562    }
1563}
1564
1565impl Mul<&f32> for Vec3A {
1566    type Output = Self;
1567    #[inline]
1568    fn mul(self, rhs: &f32) -> Self {
1569        self.mul(*rhs)
1570    }
1571}
1572
1573impl Mul<&f32> for &Vec3A {
1574    type Output = Vec3A;
1575    #[inline]
1576    fn mul(self, rhs: &f32) -> Vec3A {
1577        (*self).mul(*rhs)
1578    }
1579}
1580
1581impl Mul<f32> for &Vec3A {
1582    type Output = Vec3A;
1583    #[inline]
1584    fn mul(self, rhs: f32) -> Vec3A {
1585        (*self).mul(rhs)
1586    }
1587}
1588
1589impl MulAssign<f32> for Vec3A {
1590    #[inline]
1591    fn mul_assign(&mut self, rhs: f32) {
1592        self.0 = unsafe { _mm_mul_ps(self.0, _mm_set1_ps(rhs)) };
1593    }
1594}
1595
1596impl MulAssign<&f32> for Vec3A {
1597    #[inline]
1598    fn mul_assign(&mut self, rhs: &f32) {
1599        self.mul_assign(*rhs);
1600    }
1601}
1602
1603impl Mul<Vec3A> for f32 {
1604    type Output = Vec3A;
1605    #[inline]
1606    fn mul(self, rhs: Vec3A) -> Vec3A {
1607        Vec3A(unsafe { _mm_mul_ps(_mm_set1_ps(self), rhs.0) })
1608    }
1609}
1610
1611impl Mul<&Vec3A> for f32 {
1612    type Output = Vec3A;
1613    #[inline]
1614    fn mul(self, rhs: &Vec3A) -> Vec3A {
1615        self.mul(*rhs)
1616    }
1617}
1618
1619impl Mul<&Vec3A> for &f32 {
1620    type Output = Vec3A;
1621    #[inline]
1622    fn mul(self, rhs: &Vec3A) -> Vec3A {
1623        (*self).mul(*rhs)
1624    }
1625}
1626
1627impl Mul<Vec3A> for &f32 {
1628    type Output = Vec3A;
1629    #[inline]
1630    fn mul(self, rhs: Vec3A) -> Vec3A {
1631        (*self).mul(rhs)
1632    }
1633}
1634
1635impl Add for Vec3A {
1636    type Output = Self;
1637    #[inline]
1638    fn add(self, rhs: Self) -> Self {
1639        Self(unsafe { _mm_add_ps(self.0, rhs.0) })
1640    }
1641}
1642
1643impl Add<&Self> for Vec3A {
1644    type Output = Self;
1645    #[inline]
1646    fn add(self, rhs: &Self) -> Self {
1647        self.add(*rhs)
1648    }
1649}
1650
1651impl Add<&Vec3A> for &Vec3A {
1652    type Output = Vec3A;
1653    #[inline]
1654    fn add(self, rhs: &Vec3A) -> Vec3A {
1655        (*self).add(*rhs)
1656    }
1657}
1658
1659impl Add<Vec3A> for &Vec3A {
1660    type Output = Vec3A;
1661    #[inline]
1662    fn add(self, rhs: Vec3A) -> Vec3A {
1663        (*self).add(rhs)
1664    }
1665}
1666
1667impl AddAssign for Vec3A {
1668    #[inline]
1669    fn add_assign(&mut self, rhs: Self) {
1670        self.0 = unsafe { _mm_add_ps(self.0, rhs.0) };
1671    }
1672}
1673
1674impl AddAssign<&Self> for Vec3A {
1675    #[inline]
1676    fn add_assign(&mut self, rhs: &Self) {
1677        self.add_assign(*rhs);
1678    }
1679}
1680
1681impl Add<f32> for Vec3A {
1682    type Output = Self;
1683    #[inline]
1684    fn add(self, rhs: f32) -> Self {
1685        Self(unsafe { _mm_add_ps(self.0, _mm_set1_ps(rhs)) })
1686    }
1687}
1688
1689impl Add<&f32> for Vec3A {
1690    type Output = Self;
1691    #[inline]
1692    fn add(self, rhs: &f32) -> Self {
1693        self.add(*rhs)
1694    }
1695}
1696
1697impl Add<&f32> for &Vec3A {
1698    type Output = Vec3A;
1699    #[inline]
1700    fn add(self, rhs: &f32) -> Vec3A {
1701        (*self).add(*rhs)
1702    }
1703}
1704
1705impl Add<f32> for &Vec3A {
1706    type Output = Vec3A;
1707    #[inline]
1708    fn add(self, rhs: f32) -> Vec3A {
1709        (*self).add(rhs)
1710    }
1711}
1712
1713impl AddAssign<f32> for Vec3A {
1714    #[inline]
1715    fn add_assign(&mut self, rhs: f32) {
1716        self.0 = unsafe { _mm_add_ps(self.0, _mm_set1_ps(rhs)) };
1717    }
1718}
1719
1720impl AddAssign<&f32> for Vec3A {
1721    #[inline]
1722    fn add_assign(&mut self, rhs: &f32) {
1723        self.add_assign(*rhs);
1724    }
1725}
1726
1727impl Add<Vec3A> for f32 {
1728    type Output = Vec3A;
1729    #[inline]
1730    fn add(self, rhs: Vec3A) -> Vec3A {
1731        Vec3A(unsafe { _mm_add_ps(_mm_set1_ps(self), rhs.0) })
1732    }
1733}
1734
1735impl Add<&Vec3A> for f32 {
1736    type Output = Vec3A;
1737    #[inline]
1738    fn add(self, rhs: &Vec3A) -> Vec3A {
1739        self.add(*rhs)
1740    }
1741}
1742
1743impl Add<&Vec3A> for &f32 {
1744    type Output = Vec3A;
1745    #[inline]
1746    fn add(self, rhs: &Vec3A) -> Vec3A {
1747        (*self).add(*rhs)
1748    }
1749}
1750
1751impl Add<Vec3A> for &f32 {
1752    type Output = Vec3A;
1753    #[inline]
1754    fn add(self, rhs: Vec3A) -> Vec3A {
1755        (*self).add(rhs)
1756    }
1757}
1758
1759impl Sub for Vec3A {
1760    type Output = Self;
1761    #[inline]
1762    fn sub(self, rhs: Self) -> Self {
1763        Self(unsafe { _mm_sub_ps(self.0, rhs.0) })
1764    }
1765}
1766
1767impl Sub<&Self> for Vec3A {
1768    type Output = Self;
1769    #[inline]
1770    fn sub(self, rhs: &Self) -> Self {
1771        self.sub(*rhs)
1772    }
1773}
1774
1775impl Sub<&Vec3A> for &Vec3A {
1776    type Output = Vec3A;
1777    #[inline]
1778    fn sub(self, rhs: &Vec3A) -> Vec3A {
1779        (*self).sub(*rhs)
1780    }
1781}
1782
1783impl Sub<Vec3A> for &Vec3A {
1784    type Output = Vec3A;
1785    #[inline]
1786    fn sub(self, rhs: Vec3A) -> Vec3A {
1787        (*self).sub(rhs)
1788    }
1789}
1790
1791impl SubAssign for Vec3A {
1792    #[inline]
1793    fn sub_assign(&mut self, rhs: Self) {
1794        self.0 = unsafe { _mm_sub_ps(self.0, rhs.0) };
1795    }
1796}
1797
1798impl SubAssign<&Self> for Vec3A {
1799    #[inline]
1800    fn sub_assign(&mut self, rhs: &Self) {
1801        self.sub_assign(*rhs);
1802    }
1803}
1804
1805impl Sub<f32> for Vec3A {
1806    type Output = Self;
1807    #[inline]
1808    fn sub(self, rhs: f32) -> Self {
1809        Self(unsafe { _mm_sub_ps(self.0, _mm_set1_ps(rhs)) })
1810    }
1811}
1812
1813impl Sub<&f32> for Vec3A {
1814    type Output = Self;
1815    #[inline]
1816    fn sub(self, rhs: &f32) -> Self {
1817        self.sub(*rhs)
1818    }
1819}
1820
1821impl Sub<&f32> for &Vec3A {
1822    type Output = Vec3A;
1823    #[inline]
1824    fn sub(self, rhs: &f32) -> Vec3A {
1825        (*self).sub(*rhs)
1826    }
1827}
1828
1829impl Sub<f32> for &Vec3A {
1830    type Output = Vec3A;
1831    #[inline]
1832    fn sub(self, rhs: f32) -> Vec3A {
1833        (*self).sub(rhs)
1834    }
1835}
1836
1837impl SubAssign<f32> for Vec3A {
1838    #[inline]
1839    fn sub_assign(&mut self, rhs: f32) {
1840        self.0 = unsafe { _mm_sub_ps(self.0, _mm_set1_ps(rhs)) };
1841    }
1842}
1843
1844impl SubAssign<&f32> for Vec3A {
1845    #[inline]
1846    fn sub_assign(&mut self, rhs: &f32) {
1847        self.sub_assign(*rhs);
1848    }
1849}
1850
1851impl Sub<Vec3A> for f32 {
1852    type Output = Vec3A;
1853    #[inline]
1854    fn sub(self, rhs: Vec3A) -> Vec3A {
1855        Vec3A(unsafe { _mm_sub_ps(_mm_set1_ps(self), rhs.0) })
1856    }
1857}
1858
1859impl Sub<&Vec3A> for f32 {
1860    type Output = Vec3A;
1861    #[inline]
1862    fn sub(self, rhs: &Vec3A) -> Vec3A {
1863        self.sub(*rhs)
1864    }
1865}
1866
1867impl Sub<&Vec3A> for &f32 {
1868    type Output = Vec3A;
1869    #[inline]
1870    fn sub(self, rhs: &Vec3A) -> Vec3A {
1871        (*self).sub(*rhs)
1872    }
1873}
1874
1875impl Sub<Vec3A> for &f32 {
1876    type Output = Vec3A;
1877    #[inline]
1878    fn sub(self, rhs: Vec3A) -> Vec3A {
1879        (*self).sub(rhs)
1880    }
1881}
1882
1883impl Rem for Vec3A {
1884    type Output = Self;
1885    #[inline]
1886    fn rem(self, rhs: Self) -> Self {
1887        unsafe {
1888            let n = m128_floor(_mm_div_ps(self.0, rhs.0));
1889            Self(_mm_sub_ps(self.0, _mm_mul_ps(n, rhs.0)))
1890        }
1891    }
1892}
1893
1894impl Rem<&Self> for Vec3A {
1895    type Output = Self;
1896    #[inline]
1897    fn rem(self, rhs: &Self) -> Self {
1898        self.rem(*rhs)
1899    }
1900}
1901
1902impl Rem<&Vec3A> for &Vec3A {
1903    type Output = Vec3A;
1904    #[inline]
1905    fn rem(self, rhs: &Vec3A) -> Vec3A {
1906        (*self).rem(*rhs)
1907    }
1908}
1909
1910impl Rem<Vec3A> for &Vec3A {
1911    type Output = Vec3A;
1912    #[inline]
1913    fn rem(self, rhs: Vec3A) -> Vec3A {
1914        (*self).rem(rhs)
1915    }
1916}
1917
1918impl RemAssign for Vec3A {
1919    #[inline]
1920    fn rem_assign(&mut self, rhs: Self) {
1921        *self = self.rem(rhs);
1922    }
1923}
1924
1925impl RemAssign<&Self> for Vec3A {
1926    #[inline]
1927    fn rem_assign(&mut self, rhs: &Self) {
1928        self.rem_assign(*rhs);
1929    }
1930}
1931
1932impl Rem<f32> for Vec3A {
1933    type Output = Self;
1934    #[inline]
1935    fn rem(self, rhs: f32) -> Self {
1936        self.rem(Self::splat(rhs))
1937    }
1938}
1939
1940impl Rem<&f32> for Vec3A {
1941    type Output = Self;
1942    #[inline]
1943    fn rem(self, rhs: &f32) -> Self {
1944        self.rem(*rhs)
1945    }
1946}
1947
1948impl Rem<&f32> for &Vec3A {
1949    type Output = Vec3A;
1950    #[inline]
1951    fn rem(self, rhs: &f32) -> Vec3A {
1952        (*self).rem(*rhs)
1953    }
1954}
1955
1956impl Rem<f32> for &Vec3A {
1957    type Output = Vec3A;
1958    #[inline]
1959    fn rem(self, rhs: f32) -> Vec3A {
1960        (*self).rem(rhs)
1961    }
1962}
1963
1964impl RemAssign<f32> for Vec3A {
1965    #[inline]
1966    fn rem_assign(&mut self, rhs: f32) {
1967        *self = self.rem(Self::splat(rhs));
1968    }
1969}
1970
1971impl RemAssign<&f32> for Vec3A {
1972    #[inline]
1973    fn rem_assign(&mut self, rhs: &f32) {
1974        self.rem_assign(*rhs);
1975    }
1976}
1977
1978impl Rem<Vec3A> for f32 {
1979    type Output = Vec3A;
1980    #[inline]
1981    fn rem(self, rhs: Vec3A) -> Vec3A {
1982        Vec3A::splat(self).rem(rhs)
1983    }
1984}
1985
1986impl Rem<&Vec3A> for f32 {
1987    type Output = Vec3A;
1988    #[inline]
1989    fn rem(self, rhs: &Vec3A) -> Vec3A {
1990        self.rem(*rhs)
1991    }
1992}
1993
1994impl Rem<&Vec3A> for &f32 {
1995    type Output = Vec3A;
1996    #[inline]
1997    fn rem(self, rhs: &Vec3A) -> Vec3A {
1998        (*self).rem(*rhs)
1999    }
2000}
2001
2002impl Rem<Vec3A> for &f32 {
2003    type Output = Vec3A;
2004    #[inline]
2005    fn rem(self, rhs: Vec3A) -> Vec3A {
2006        (*self).rem(rhs)
2007    }
2008}
2009
2010impl AsRef<[f32; 3]> for Vec3A {
2011    #[inline]
2012    fn as_ref(&self) -> &[f32; 3] {
2013        unsafe { &*(self as *const Self as *const [f32; 3]) }
2014    }
2015}
2016
2017impl AsMut<[f32; 3]> for Vec3A {
2018    #[inline]
2019    fn as_mut(&mut self) -> &mut [f32; 3] {
2020        unsafe { &mut *(self as *mut Self as *mut [f32; 3]) }
2021    }
2022}
2023
2024impl Sum for Vec3A {
2025    #[inline]
2026    fn sum<I>(iter: I) -> Self
2027    where
2028        I: Iterator<Item = Self>,
2029    {
2030        iter.fold(Self::ZERO, Self::add)
2031    }
2032}
2033
2034impl<'a> Sum<&'a Self> for Vec3A {
2035    #[inline]
2036    fn sum<I>(iter: I) -> Self
2037    where
2038        I: Iterator<Item = &'a Self>,
2039    {
2040        iter.fold(Self::ZERO, |a, &b| Self::add(a, b))
2041    }
2042}
2043
2044impl Product for Vec3A {
2045    #[inline]
2046    fn product<I>(iter: I) -> Self
2047    where
2048        I: Iterator<Item = Self>,
2049    {
2050        iter.fold(Self::ONE, Self::mul)
2051    }
2052}
2053
2054impl<'a> Product<&'a Self> for Vec3A {
2055    #[inline]
2056    fn product<I>(iter: I) -> Self
2057    where
2058        I: Iterator<Item = &'a Self>,
2059    {
2060        iter.fold(Self::ONE, |a, &b| Self::mul(a, b))
2061    }
2062}
2063
2064impl Neg for Vec3A {
2065    type Output = Self;
2066    #[inline]
2067    fn neg(self) -> Self {
2068        Self(unsafe { _mm_xor_ps(_mm_set1_ps(-0.0), self.0) })
2069    }
2070}
2071
2072impl Neg for &Vec3A {
2073    type Output = Vec3A;
2074    #[inline]
2075    fn neg(self) -> Vec3A {
2076        (*self).neg()
2077    }
2078}
2079
2080impl Index<usize> for Vec3A {
2081    type Output = f32;
2082    #[inline]
2083    fn index(&self, index: usize) -> &Self::Output {
2084        match index {
2085            0 => &self.x,
2086            1 => &self.y,
2087            2 => &self.z,
2088            _ => panic!("index out of bounds"),
2089        }
2090    }
2091}
2092
2093impl IndexMut<usize> for Vec3A {
2094    #[inline]
2095    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
2096        match index {
2097            0 => &mut self.x,
2098            1 => &mut self.y,
2099            2 => &mut self.z,
2100            _ => panic!("index out of bounds"),
2101        }
2102    }
2103}
2104
2105impl fmt::Display for Vec3A {
2106    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2107        if let Some(p) = f.precision() {
2108            write!(f, "[{:.*}, {:.*}, {:.*}]", p, self.x, p, self.y, p, self.z)
2109        } else {
2110            write!(f, "[{}, {}, {}]", self.x, self.y, self.z)
2111        }
2112    }
2113}
2114
2115impl fmt::Debug for Vec3A {
2116    fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
2117        fmt.debug_tuple(stringify!(Vec3A))
2118            .field(&self.x)
2119            .field(&self.y)
2120            .field(&self.z)
2121            .finish()
2122    }
2123}
2124
2125impl From<Vec3A> for __m128 {
2126    #[inline(always)]
2127    fn from(t: Vec3A) -> Self {
2128        t.0
2129    }
2130}
2131
2132impl From<__m128> for Vec3A {
2133    #[inline(always)]
2134    fn from(t: __m128) -> Self {
2135        Self(t)
2136    }
2137}
2138
2139impl From<[f32; 3]> for Vec3A {
2140    #[inline]
2141    fn from(a: [f32; 3]) -> Self {
2142        Self::new(a[0], a[1], a[2])
2143    }
2144}
2145
2146impl From<Vec3A> for [f32; 3] {
2147    #[inline]
2148    fn from(v: Vec3A) -> Self {
2149        use crate::Align16;
2150        use core::mem::MaybeUninit;
2151        let mut out: MaybeUninit<Align16<Self>> = MaybeUninit::uninit();
2152        unsafe {
2153            _mm_store_ps(out.as_mut_ptr().cast(), v.0);
2154            out.assume_init().0
2155        }
2156    }
2157}
2158
2159impl From<(f32, f32, f32)> for Vec3A {
2160    #[inline]
2161    fn from(t: (f32, f32, f32)) -> Self {
2162        Self::new(t.0, t.1, t.2)
2163    }
2164}
2165
2166impl From<Vec3A> for (f32, f32, f32) {
2167    #[inline]
2168    fn from(v: Vec3A) -> Self {
2169        (v.x, v.y, v.z)
2170    }
2171}
2172
2173impl From<Vec3> for Vec3A {
2174    #[inline]
2175    fn from(v: Vec3) -> Self {
2176        Self::new(v.x, v.y, v.z)
2177    }
2178}
2179
2180impl From<Vec3A> for Vec3 {
2181    #[inline]
2182    fn from(v: Vec3A) -> Self {
2183        use crate::Align16;
2184        use core::mem::MaybeUninit;
2185        let mut out: MaybeUninit<Align16<Self>> = MaybeUninit::uninit();
2186        unsafe {
2187            _mm_store_ps(out.as_mut_ptr().cast(), v.0);
2188            out.assume_init().0
2189        }
2190    }
2191}
2192
2193impl From<(Vec2, f32)> for Vec3A {
2194    #[inline]
2195    fn from((v, z): (Vec2, f32)) -> Self {
2196        Self::new(v.x, v.y, z)
2197    }
2198}
2199
2200impl Deref for Vec3A {
2201    type Target = crate::deref::Vec3<f32>;
2202    #[inline]
2203    fn deref(&self) -> &Self::Target {
2204        unsafe { &*(self as *const Self).cast() }
2205    }
2206}
2207
2208impl DerefMut for Vec3A {
2209    #[inline]
2210    fn deref_mut(&mut self) -> &mut Self::Target {
2211        unsafe { &mut *(self as *mut Self).cast() }
2212    }
2213}
2214
2215impl From<BVec3> for Vec3A {
2216    #[inline]
2217    fn from(v: BVec3) -> Self {
2218        Self::new(f32::from(v.x), f32::from(v.y), f32::from(v.z))
2219    }
2220}
2221
2222impl From<BVec3A> for Vec3A {
2223    #[inline]
2224    fn from(v: BVec3A) -> Self {
2225        let bool_array: [bool; 3] = v.into();
2226        Self::new(
2227            f32::from(bool_array[0]),
2228            f32::from(bool_array[1]),
2229            f32::from(bool_array[2]),
2230        )
2231    }
2232}