• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Generated from vec.rs.tera template. Edit the template, not the generated file.
2 
3 use crate::{BVec4, DVec2, DVec3};
4 
5 #[cfg(not(target_arch = "spirv"))]
6 use core::fmt;
7 use core::iter::{Product, Sum};
8 use core::{f32, ops::*};
9 
10 #[cfg(feature = "libm")]
11 #[allow(unused_imports)]
12 use num_traits::Float;
13 
14 /// Creates a 4-dimensional vector.
15 #[inline(always)]
dvec4(x: f64, y: f64, z: f64, w: f64) -> DVec416 pub const fn dvec4(x: f64, y: f64, z: f64, w: f64) -> DVec4 {
17     DVec4::new(x, y, z, w)
18 }
19 
20 /// A 4-dimensional vector.
21 #[derive(Clone, Copy, PartialEq)]
22 #[cfg_attr(feature = "cuda", repr(align(16)))]
23 #[cfg_attr(not(target_arch = "spirv"), repr(C))]
24 #[cfg_attr(target_arch = "spirv", repr(simd))]
25 pub struct DVec4 {
26     pub x: f64,
27     pub y: f64,
28     pub z: f64,
29     pub w: f64,
30 }
31 
32 impl DVec4 {
33     /// All zeroes.
34     pub const ZERO: Self = Self::splat(0.0);
35 
36     /// All ones.
37     pub const ONE: Self = Self::splat(1.0);
38 
39     /// All negative ones.
40     pub const NEG_ONE: Self = Self::splat(-1.0);
41 
42     /// All NAN.
43     pub const NAN: Self = Self::splat(f64::NAN);
44 
45     /// A unit-length vector pointing along the positive X axis.
46     pub const X: Self = Self::new(1.0, 0.0, 0.0, 0.0);
47 
48     /// A unit-length vector pointing along the positive Y axis.
49     pub const Y: Self = Self::new(0.0, 1.0, 0.0, 0.0);
50 
51     /// A unit-length vector pointing along the positive Z axis.
52     pub const Z: Self = Self::new(0.0, 0.0, 1.0, 0.0);
53 
54     /// A unit-length vector pointing along the positive W axis.
55     pub const W: Self = Self::new(0.0, 0.0, 0.0, 1.0);
56 
57     /// A unit-length vector pointing along the negative X axis.
58     pub const NEG_X: Self = Self::new(-1.0, 0.0, 0.0, 0.0);
59 
60     /// A unit-length vector pointing along the negative Y axis.
61     pub const NEG_Y: Self = Self::new(0.0, -1.0, 0.0, 0.0);
62 
63     /// A unit-length vector pointing along the negative Z axis.
64     pub const NEG_Z: Self = Self::new(0.0, 0.0, -1.0, 0.0);
65 
66     /// A unit-length vector pointing along the negative W axis.
67     pub const NEG_W: Self = Self::new(0.0, 0.0, 0.0, -1.0);
68 
69     /// The unit axes.
70     pub const AXES: [Self; 4] = [Self::X, Self::Y, Self::Z, Self::W];
71 
72     /// Creates a new vector.
73     #[inline(always)]
new(x: f64, y: f64, z: f64, w: f64) -> Self74     pub const fn new(x: f64, y: f64, z: f64, w: f64) -> Self {
75         Self { x, y, z, w }
76     }
77 
78     /// Creates a vector with all elements set to `v`.
79     #[inline]
splat(v: f64) -> Self80     pub const fn splat(v: f64) -> Self {
81         Self {
82             x: v,
83 
84             y: v,
85 
86             z: v,
87 
88             w: v,
89         }
90     }
91 
92     /// Creates a vector from the elements in `if_true` and `if_false`, selecting which to use
93     /// for each element of `self`.
94     ///
95     /// A true element in the mask uses the corresponding element from `if_true`, and false
96     /// uses the element from `if_false`.
97     #[inline]
select(mask: BVec4, if_true: Self, if_false: Self) -> Self98     pub fn select(mask: BVec4, if_true: Self, if_false: Self) -> Self {
99         Self {
100             x: if mask.x { if_true.x } else { if_false.x },
101             y: if mask.y { if_true.y } else { if_false.y },
102             z: if mask.z { if_true.z } else { if_false.z },
103             w: if mask.w { if_true.w } else { if_false.w },
104         }
105     }
106 
107     /// Creates a new vector from an array.
108     #[inline]
from_array(a: [f64; 4]) -> Self109     pub const fn from_array(a: [f64; 4]) -> Self {
110         Self::new(a[0], a[1], a[2], a[3])
111     }
112 
113     /// `[x, y, z, w]`
114     #[inline]
to_array(&self) -> [f64; 4]115     pub const fn to_array(&self) -> [f64; 4] {
116         [self.x, self.y, self.z, self.w]
117     }
118 
119     /// Creates a vector from the first 4 values in `slice`.
120     ///
121     /// # Panics
122     ///
123     /// Panics if `slice` is less than 4 elements long.
124     #[inline]
from_slice(slice: &[f64]) -> Self125     pub const fn from_slice(slice: &[f64]) -> Self {
126         Self::new(slice[0], slice[1], slice[2], slice[3])
127     }
128 
129     /// Writes the elements of `self` to the first 4 elements in `slice`.
130     ///
131     /// # Panics
132     ///
133     /// Panics if `slice` is less than 4 elements long.
134     #[inline]
write_to_slice(self, slice: &mut [f64])135     pub fn write_to_slice(self, slice: &mut [f64]) {
136         slice[0] = self.x;
137         slice[1] = self.y;
138         slice[2] = self.z;
139         slice[3] = self.w;
140     }
141 
142     /// Creates a 2D vector from the `x`, `y` and `z` elements of `self`, discarding `w`.
143     ///
144     /// Truncation to `DVec3` may also be performed by using `self.xyz()` or `DVec3::from()`.
145     #[inline]
truncate(self) -> DVec3146     pub fn truncate(self) -> DVec3 {
147         use crate::swizzles::Vec4Swizzles;
148         self.xyz()
149     }
150 
151     /// Computes the dot product of `self` and `rhs`.
152     #[inline]
dot(self, rhs: Self) -> f64153     pub fn dot(self, rhs: Self) -> f64 {
154         (self.x * rhs.x) + (self.y * rhs.y) + (self.z * rhs.z) + (self.w * rhs.w)
155     }
156 
157     /// Returns a vector where every component is the dot product of `self` and `rhs`.
158     #[inline]
dot_into_vec(self, rhs: Self) -> Self159     pub fn dot_into_vec(self, rhs: Self) -> Self {
160         Self::splat(self.dot(rhs))
161     }
162 
163     /// Returns a vector containing the minimum values for each element of `self` and `rhs`.
164     ///
165     /// In other words this computes `[self.x.min(rhs.x), self.y.min(rhs.y), ..]`.
166     #[inline]
min(self, rhs: Self) -> Self167     pub fn min(self, rhs: Self) -> Self {
168         Self {
169             x: self.x.min(rhs.x),
170             y: self.y.min(rhs.y),
171             z: self.z.min(rhs.z),
172             w: self.w.min(rhs.w),
173         }
174     }
175 
176     /// Returns a vector containing the maximum values for each element of `self` and `rhs`.
177     ///
178     /// In other words this computes `[self.x.max(rhs.x), self.y.max(rhs.y), ..]`.
179     #[inline]
max(self, rhs: Self) -> Self180     pub fn max(self, rhs: Self) -> Self {
181         Self {
182             x: self.x.max(rhs.x),
183             y: self.y.max(rhs.y),
184             z: self.z.max(rhs.z),
185             w: self.w.max(rhs.w),
186         }
187     }
188 
189     /// Component-wise clamping of values, similar to [`f64::clamp`].
190     ///
191     /// Each element in `min` must be less-or-equal to the corresponding element in `max`.
192     ///
193     /// # Panics
194     ///
195     /// Will panic if `min` is greater than `max` when `glam_assert` is enabled.
196     #[inline]
clamp(self, min: Self, max: Self) -> Self197     pub fn clamp(self, min: Self, max: Self) -> Self {
198         glam_assert!(min.cmple(max).all(), "clamp: expected min <= max");
199         self.max(min).min(max)
200     }
201 
202     /// Returns the horizontal minimum of `self`.
203     ///
204     /// In other words this computes `min(x, y, ..)`.
205     #[inline]
min_element(self) -> f64206     pub fn min_element(self) -> f64 {
207         self.x.min(self.y.min(self.z.min(self.w)))
208     }
209 
210     /// Returns the horizontal maximum of `self`.
211     ///
212     /// In other words this computes `max(x, y, ..)`.
213     #[inline]
max_element(self) -> f64214     pub fn max_element(self) -> f64 {
215         self.x.max(self.y.max(self.z.max(self.w)))
216     }
217 
218     /// Returns a vector mask containing the result of a `==` comparison for each element of
219     /// `self` and `rhs`.
220     ///
221     /// In other words, this computes `[self.x == rhs.x, self.y == rhs.y, ..]` for all
222     /// elements.
223     #[inline]
cmpeq(self, rhs: Self) -> BVec4224     pub fn cmpeq(self, rhs: Self) -> BVec4 {
225         BVec4::new(
226             self.x.eq(&rhs.x),
227             self.y.eq(&rhs.y),
228             self.z.eq(&rhs.z),
229             self.w.eq(&rhs.w),
230         )
231     }
232 
233     /// Returns a vector mask containing the result of a `!=` comparison for each element of
234     /// `self` and `rhs`.
235     ///
236     /// In other words this computes `[self.x != rhs.x, self.y != rhs.y, ..]` for all
237     /// elements.
238     #[inline]
cmpne(self, rhs: Self) -> BVec4239     pub fn cmpne(self, rhs: Self) -> BVec4 {
240         BVec4::new(
241             self.x.ne(&rhs.x),
242             self.y.ne(&rhs.y),
243             self.z.ne(&rhs.z),
244             self.w.ne(&rhs.w),
245         )
246     }
247 
248     /// Returns a vector mask containing the result of a `>=` comparison for each element of
249     /// `self` and `rhs`.
250     ///
251     /// In other words this computes `[self.x >= rhs.x, self.y >= rhs.y, ..]` for all
252     /// elements.
253     #[inline]
cmpge(self, rhs: Self) -> BVec4254     pub fn cmpge(self, rhs: Self) -> BVec4 {
255         BVec4::new(
256             self.x.ge(&rhs.x),
257             self.y.ge(&rhs.y),
258             self.z.ge(&rhs.z),
259             self.w.ge(&rhs.w),
260         )
261     }
262 
263     /// Returns a vector mask containing the result of a `>` comparison for each element of
264     /// `self` and `rhs`.
265     ///
266     /// In other words this computes `[self.x > rhs.x, self.y > rhs.y, ..]` for all
267     /// elements.
268     #[inline]
cmpgt(self, rhs: Self) -> BVec4269     pub fn cmpgt(self, rhs: Self) -> BVec4 {
270         BVec4::new(
271             self.x.gt(&rhs.x),
272             self.y.gt(&rhs.y),
273             self.z.gt(&rhs.z),
274             self.w.gt(&rhs.w),
275         )
276     }
277 
278     /// Returns a vector mask containing the result of a `<=` comparison for each element of
279     /// `self` and `rhs`.
280     ///
281     /// In other words this computes `[self.x <= rhs.x, self.y <= rhs.y, ..]` for all
282     /// elements.
283     #[inline]
cmple(self, rhs: Self) -> BVec4284     pub fn cmple(self, rhs: Self) -> BVec4 {
285         BVec4::new(
286             self.x.le(&rhs.x),
287             self.y.le(&rhs.y),
288             self.z.le(&rhs.z),
289             self.w.le(&rhs.w),
290         )
291     }
292 
293     /// Returns a vector mask containing the result of a `<` comparison for each element of
294     /// `self` and `rhs`.
295     ///
296     /// In other words this computes `[self.x < rhs.x, self.y < rhs.y, ..]` for all
297     /// elements.
298     #[inline]
cmplt(self, rhs: Self) -> BVec4299     pub fn cmplt(self, rhs: Self) -> BVec4 {
300         BVec4::new(
301             self.x.lt(&rhs.x),
302             self.y.lt(&rhs.y),
303             self.z.lt(&rhs.z),
304             self.w.lt(&rhs.w),
305         )
306     }
307 
308     /// Returns a vector containing the absolute value of each element of `self`.
309     #[inline]
abs(self) -> Self310     pub fn abs(self) -> Self {
311         Self {
312             x: self.x.abs(),
313             y: self.y.abs(),
314             z: self.z.abs(),
315             w: self.w.abs(),
316         }
317     }
318 
319     /// Returns a vector with elements representing the sign of `self`.
320     ///
321     /// - `1.0` if the number is positive, `+0.0` or `INFINITY`
322     /// - `-1.0` if the number is negative, `-0.0` or `NEG_INFINITY`
323     /// - `NAN` if the number is `NAN`
324     #[inline]
signum(self) -> Self325     pub fn signum(self) -> Self {
326         Self {
327             x: self.x.signum(),
328             y: self.y.signum(),
329             z: self.z.signum(),
330             w: self.w.signum(),
331         }
332     }
333 
334     /// Returns a vector with signs of `rhs` and the magnitudes of `self`.
335     #[inline]
copysign(self, rhs: Self) -> Self336     pub fn copysign(self, rhs: Self) -> Self {
337         Self {
338             x: self.x.copysign(rhs.x),
339             y: self.y.copysign(rhs.y),
340             z: self.z.copysign(rhs.z),
341             w: self.w.copysign(rhs.w),
342         }
343     }
344 
345     /// Returns a bitmask with the lowest 4 bits set to the sign bits from the elements of `self`.
346     ///
347     /// A negative element results in a `1` bit and a positive element in a `0` bit.  Element `x` goes
348     /// into the first lowest bit, element `y` into the second, etc.
349     #[inline]
is_negative_bitmask(self) -> u32350     pub fn is_negative_bitmask(self) -> u32 {
351         (self.x.is_sign_negative() as u32)
352             | (self.y.is_sign_negative() as u32) << 1
353             | (self.z.is_sign_negative() as u32) << 2
354             | (self.w.is_sign_negative() as u32) << 3
355     }
356 
357     /// Returns `true` if, and only if, all elements are finite.  If any element is either
358     /// `NaN`, positive or negative infinity, this will return `false`.
359     #[inline]
is_finite(self) -> bool360     pub fn is_finite(self) -> bool {
361         self.x.is_finite() && self.y.is_finite() && self.z.is_finite() && self.w.is_finite()
362     }
363 
364     /// Returns `true` if any elements are `NaN`.
365     #[inline]
is_nan(self) -> bool366     pub fn is_nan(self) -> bool {
367         self.x.is_nan() || self.y.is_nan() || self.z.is_nan() || self.w.is_nan()
368     }
369 
370     /// Performs `is_nan` on each element of self, returning a vector mask of the results.
371     ///
372     /// In other words, this computes `[x.is_nan(), y.is_nan(), z.is_nan(), w.is_nan()]`.
373     #[inline]
is_nan_mask(self) -> BVec4374     pub fn is_nan_mask(self) -> BVec4 {
375         BVec4::new(
376             self.x.is_nan(),
377             self.y.is_nan(),
378             self.z.is_nan(),
379             self.w.is_nan(),
380         )
381     }
382 
383     /// Computes the length of `self`.
384     #[doc(alias = "magnitude")]
385     #[inline]
length(self) -> f64386     pub fn length(self) -> f64 {
387         self.dot(self).sqrt()
388     }
389 
390     /// Computes the squared length of `self`.
391     ///
392     /// This is faster than `length()` as it avoids a square root operation.
393     #[doc(alias = "magnitude2")]
394     #[inline]
length_squared(self) -> f64395     pub fn length_squared(self) -> f64 {
396         self.dot(self)
397     }
398 
399     /// Computes `1.0 / length()`.
400     ///
401     /// For valid results, `self` must _not_ be of length zero.
402     #[inline]
length_recip(self) -> f64403     pub fn length_recip(self) -> f64 {
404         self.length().recip()
405     }
406 
407     /// Computes the Euclidean distance between two points in space.
408     #[inline]
distance(self, rhs: Self) -> f64409     pub fn distance(self, rhs: Self) -> f64 {
410         (self - rhs).length()
411     }
412 
413     /// Compute the squared euclidean distance between two points in space.
414     #[inline]
distance_squared(self, rhs: Self) -> f64415     pub fn distance_squared(self, rhs: Self) -> f64 {
416         (self - rhs).length_squared()
417     }
418 
419     /// Returns `self` normalized to length 1.0.
420     ///
421     /// For valid results, `self` must _not_ be of length zero, nor very close to zero.
422     ///
423     /// See also [`Self::try_normalize`] and [`Self::normalize_or_zero`].
424     ///
425     /// Panics
426     ///
427     /// Will panic if `self` is zero length when `glam_assert` is enabled.
428     #[must_use]
429     #[inline]
normalize(self) -> Self430     pub fn normalize(self) -> Self {
431         #[allow(clippy::let_and_return)]
432         let normalized = self.mul(self.length_recip());
433         glam_assert!(normalized.is_finite());
434         normalized
435     }
436 
437     /// Returns `self` normalized to length 1.0 if possible, else returns `None`.
438     ///
439     /// In particular, if the input is zero (or very close to zero), or non-finite,
440     /// the result of this operation will be `None`.
441     ///
442     /// See also [`Self::normalize_or_zero`].
443     #[must_use]
444     #[inline]
try_normalize(self) -> Option<Self>445     pub fn try_normalize(self) -> Option<Self> {
446         let rcp = self.length_recip();
447         if rcp.is_finite() && rcp > 0.0 {
448             Some(self * rcp)
449         } else {
450             None
451         }
452     }
453 
454     /// Returns `self` normalized to length 1.0 if possible, else returns zero.
455     ///
456     /// In particular, if the input is zero (or very close to zero), or non-finite,
457     /// the result of this operation will be zero.
458     ///
459     /// See also [`Self::try_normalize`].
460     #[must_use]
461     #[inline]
normalize_or_zero(self) -> Self462     pub fn normalize_or_zero(self) -> Self {
463         let rcp = self.length_recip();
464         if rcp.is_finite() && rcp > 0.0 {
465             self * rcp
466         } else {
467             Self::ZERO
468         }
469     }
470 
471     /// Returns whether `self` is length `1.0` or not.
472     ///
473     /// Uses a precision threshold of `1e-6`.
474     #[inline]
is_normalized(self) -> bool475     pub fn is_normalized(self) -> bool {
476         // TODO: do something with epsilon
477         (self.length_squared() - 1.0).abs() <= 1e-4
478     }
479 
480     /// Returns the vector projection of `self` onto `rhs`.
481     ///
482     /// `rhs` must be of non-zero length.
483     ///
484     /// # Panics
485     ///
486     /// Will panic if `rhs` is zero length when `glam_assert` is enabled.
487     #[must_use]
488     #[inline]
project_onto(self, rhs: Self) -> Self489     pub fn project_onto(self, rhs: Self) -> Self {
490         let other_len_sq_rcp = rhs.dot(rhs).recip();
491         glam_assert!(other_len_sq_rcp.is_finite());
492         rhs * self.dot(rhs) * other_len_sq_rcp
493     }
494 
495     /// Returns the vector rejection of `self` from `rhs`.
496     ///
497     /// The vector rejection is the vector perpendicular to the projection of `self` onto
498     /// `rhs`, in rhs words the result of `self - self.project_onto(rhs)`.
499     ///
500     /// `rhs` must be of non-zero length.
501     ///
502     /// # Panics
503     ///
504     /// Will panic if `rhs` has a length of zero when `glam_assert` is enabled.
505     #[must_use]
506     #[inline]
reject_from(self, rhs: Self) -> Self507     pub fn reject_from(self, rhs: Self) -> Self {
508         self - self.project_onto(rhs)
509     }
510 
511     /// Returns the vector projection of `self` onto `rhs`.
512     ///
513     /// `rhs` must be normalized.
514     ///
515     /// # Panics
516     ///
517     /// Will panic if `rhs` is not normalized when `glam_assert` is enabled.
518     #[must_use]
519     #[inline]
project_onto_normalized(self, rhs: Self) -> Self520     pub fn project_onto_normalized(self, rhs: Self) -> Self {
521         glam_assert!(rhs.is_normalized());
522         rhs * self.dot(rhs)
523     }
524 
525     /// Returns the vector rejection of `self` from `rhs`.
526     ///
527     /// The vector rejection is the vector perpendicular to the projection of `self` onto
528     /// `rhs`, in rhs words the result of `self - self.project_onto(rhs)`.
529     ///
530     /// `rhs` must be normalized.
531     ///
532     /// # Panics
533     ///
534     /// Will panic if `rhs` is not normalized when `glam_assert` is enabled.
535     #[must_use]
536     #[inline]
reject_from_normalized(self, rhs: Self) -> Self537     pub fn reject_from_normalized(self, rhs: Self) -> Self {
538         self - self.project_onto_normalized(rhs)
539     }
540 
541     /// Returns a vector containing the nearest integer to a number for each element of `self`.
542     /// Round half-way cases away from 0.0.
543     #[inline]
round(self) -> Self544     pub fn round(self) -> Self {
545         Self {
546             x: self.x.round(),
547             y: self.y.round(),
548             z: self.z.round(),
549             w: self.w.round(),
550         }
551     }
552 
553     /// Returns a vector containing the largest integer less than or equal to a number for each
554     /// element of `self`.
555     #[inline]
floor(self) -> Self556     pub fn floor(self) -> Self {
557         Self {
558             x: self.x.floor(),
559             y: self.y.floor(),
560             z: self.z.floor(),
561             w: self.w.floor(),
562         }
563     }
564 
565     /// Returns a vector containing the smallest integer greater than or equal to a number for
566     /// each element of `self`.
567     #[inline]
ceil(self) -> Self568     pub fn ceil(self) -> Self {
569         Self {
570             x: self.x.ceil(),
571             y: self.y.ceil(),
572             z: self.z.ceil(),
573             w: self.w.ceil(),
574         }
575     }
576 
577     /// Returns a vector containing the fractional part of the vector, e.g. `self -
578     /// self.floor()`.
579     ///
580     /// Note that this is fast but not precise for large numbers.
581     #[inline]
fract(self) -> Self582     pub fn fract(self) -> Self {
583         self - self.floor()
584     }
585 
586     /// Returns a vector containing `e^self` (the exponential function) for each element of
587     /// `self`.
588     #[inline]
exp(self) -> Self589     pub fn exp(self) -> Self {
590         Self::new(self.x.exp(), self.y.exp(), self.z.exp(), self.w.exp())
591     }
592 
593     /// Returns a vector containing each element of `self` raised to the power of `n`.
594     #[inline]
powf(self, n: f64) -> Self595     pub fn powf(self, n: f64) -> Self {
596         Self::new(
597             self.x.powf(n),
598             self.y.powf(n),
599             self.z.powf(n),
600             self.w.powf(n),
601         )
602     }
603 
604     /// Returns a vector containing the reciprocal `1.0/n` of each element of `self`.
605     #[inline]
recip(self) -> Self606     pub fn recip(self) -> Self {
607         Self {
608             x: self.x.recip(),
609             y: self.y.recip(),
610             z: self.z.recip(),
611             w: self.w.recip(),
612         }
613     }
614 
615     /// Performs a linear interpolation between `self` and `rhs` based on the value `s`.
616     ///
617     /// When `s` is `0.0`, the result will be equal to `self`.  When `s` is `1.0`, the result
618     /// will be equal to `rhs`. When `s` is outside of range `[0, 1]`, the result is linearly
619     /// extrapolated.
620     #[doc(alias = "mix")]
621     #[inline]
lerp(self, rhs: Self, s: f64) -> Self622     pub fn lerp(self, rhs: Self, s: f64) -> Self {
623         self + ((rhs - self) * s)
624     }
625 
626     /// Returns true if the absolute difference of all elements between `self` and `rhs` is
627     /// less than or equal to `max_abs_diff`.
628     ///
629     /// This can be used to compare if two vectors contain similar elements. It works best when
630     /// comparing with a known value. The `max_abs_diff` that should be used used depends on
631     /// the values being compared against.
632     ///
633     /// For more see
634     /// [comparing floating point numbers](https://randomascii.wordpress.com/2012/02/25/comparing-floating-point-numbers-2012-edition/).
635     #[inline]
abs_diff_eq(self, rhs: Self, max_abs_diff: f64) -> bool636     pub fn abs_diff_eq(self, rhs: Self, max_abs_diff: f64) -> bool {
637         self.sub(rhs).abs().cmple(Self::splat(max_abs_diff)).all()
638     }
639 
640     /// Returns a vector with a length no less than `min` and no more than `max`
641     ///
642     /// # Panics
643     ///
644     /// Will panic if `min` is greater than `max` when `glam_assert` is enabled.
645     #[inline]
clamp_length(self, min: f64, max: f64) -> Self646     pub fn clamp_length(self, min: f64, max: f64) -> Self {
647         glam_assert!(min <= max);
648         let length_sq = self.length_squared();
649         if length_sq < min * min {
650             self * (length_sq.sqrt().recip() * min)
651         } else if length_sq > max * max {
652             self * (length_sq.sqrt().recip() * max)
653         } else {
654             self
655         }
656     }
657 
658     /// Returns a vector with a length no more than `max`
clamp_length_max(self, max: f64) -> Self659     pub fn clamp_length_max(self, max: f64) -> Self {
660         let length_sq = self.length_squared();
661         if length_sq > max * max {
662             self * (length_sq.sqrt().recip() * max)
663         } else {
664             self
665         }
666     }
667 
668     /// Returns a vector with a length no less than `min`
clamp_length_min(self, min: f64) -> Self669     pub fn clamp_length_min(self, min: f64) -> Self {
670         let length_sq = self.length_squared();
671         if length_sq < min * min {
672             self * (length_sq.sqrt().recip() * min)
673         } else {
674             self
675         }
676     }
677 
678     /// Fused multiply-add. Computes `(self * a) + b` element-wise with only one rounding
679     /// error, yielding a more accurate result than an unfused multiply-add.
680     ///
681     /// Using `mul_add` *may* be more performant than an unfused multiply-add if the target
682     /// architecture has a dedicated fma CPU instruction. However, this is not always true,
683     /// and will be heavily dependant on designing algorithms with specific target hardware in
684     /// mind.
685     #[inline]
mul_add(self, a: Self, b: Self) -> Self686     pub fn mul_add(self, a: Self, b: Self) -> Self {
687         Self::new(
688             self.x.mul_add(a.x, b.x),
689             self.y.mul_add(a.y, b.y),
690             self.z.mul_add(a.z, b.z),
691             self.w.mul_add(a.w, b.w),
692         )
693     }
694 
695     /// Casts all elements of `self` to `f32`.
696     #[inline]
as_vec4(&self) -> crate::Vec4697     pub fn as_vec4(&self) -> crate::Vec4 {
698         crate::Vec4::new(self.x as f32, self.y as f32, self.z as f32, self.w as f32)
699     }
700 
701     /// Casts all elements of `self` to `i32`.
702     #[inline]
as_ivec4(&self) -> crate::IVec4703     pub fn as_ivec4(&self) -> crate::IVec4 {
704         crate::IVec4::new(self.x as i32, self.y as i32, self.z as i32, self.w as i32)
705     }
706 
707     /// Casts all elements of `self` to `u32`.
708     #[inline]
as_uvec4(&self) -> crate::UVec4709     pub fn as_uvec4(&self) -> crate::UVec4 {
710         crate::UVec4::new(self.x as u32, self.y as u32, self.z as u32, self.w as u32)
711     }
712 }
713 
714 impl Default for DVec4 {
715     #[inline(always)]
default() -> Self716     fn default() -> Self {
717         Self::ZERO
718     }
719 }
720 
721 impl Div<DVec4> for DVec4 {
722     type Output = Self;
723     #[inline]
div(self, rhs: Self) -> Self724     fn div(self, rhs: Self) -> Self {
725         Self {
726             x: self.x.div(rhs.x),
727             y: self.y.div(rhs.y),
728             z: self.z.div(rhs.z),
729             w: self.w.div(rhs.w),
730         }
731     }
732 }
733 
734 impl DivAssign<DVec4> for DVec4 {
735     #[inline]
div_assign(&mut self, rhs: Self)736     fn div_assign(&mut self, rhs: Self) {
737         self.x.div_assign(rhs.x);
738         self.y.div_assign(rhs.y);
739         self.z.div_assign(rhs.z);
740         self.w.div_assign(rhs.w);
741     }
742 }
743 
744 impl Div<f64> for DVec4 {
745     type Output = Self;
746     #[inline]
div(self, rhs: f64) -> Self747     fn div(self, rhs: f64) -> Self {
748         Self {
749             x: self.x.div(rhs),
750             y: self.y.div(rhs),
751             z: self.z.div(rhs),
752             w: self.w.div(rhs),
753         }
754     }
755 }
756 
757 impl DivAssign<f64> for DVec4 {
758     #[inline]
div_assign(&mut self, rhs: f64)759     fn div_assign(&mut self, rhs: f64) {
760         self.x.div_assign(rhs);
761         self.y.div_assign(rhs);
762         self.z.div_assign(rhs);
763         self.w.div_assign(rhs);
764     }
765 }
766 
767 impl Div<DVec4> for f64 {
768     type Output = DVec4;
769     #[inline]
div(self, rhs: DVec4) -> DVec4770     fn div(self, rhs: DVec4) -> DVec4 {
771         DVec4 {
772             x: self.div(rhs.x),
773             y: self.div(rhs.y),
774             z: self.div(rhs.z),
775             w: self.div(rhs.w),
776         }
777     }
778 }
779 
780 impl Mul<DVec4> for DVec4 {
781     type Output = Self;
782     #[inline]
mul(self, rhs: Self) -> Self783     fn mul(self, rhs: Self) -> Self {
784         Self {
785             x: self.x.mul(rhs.x),
786             y: self.y.mul(rhs.y),
787             z: self.z.mul(rhs.z),
788             w: self.w.mul(rhs.w),
789         }
790     }
791 }
792 
793 impl MulAssign<DVec4> for DVec4 {
794     #[inline]
mul_assign(&mut self, rhs: Self)795     fn mul_assign(&mut self, rhs: Self) {
796         self.x.mul_assign(rhs.x);
797         self.y.mul_assign(rhs.y);
798         self.z.mul_assign(rhs.z);
799         self.w.mul_assign(rhs.w);
800     }
801 }
802 
803 impl Mul<f64> for DVec4 {
804     type Output = Self;
805     #[inline]
mul(self, rhs: f64) -> Self806     fn mul(self, rhs: f64) -> Self {
807         Self {
808             x: self.x.mul(rhs),
809             y: self.y.mul(rhs),
810             z: self.z.mul(rhs),
811             w: self.w.mul(rhs),
812         }
813     }
814 }
815 
816 impl MulAssign<f64> for DVec4 {
817     #[inline]
mul_assign(&mut self, rhs: f64)818     fn mul_assign(&mut self, rhs: f64) {
819         self.x.mul_assign(rhs);
820         self.y.mul_assign(rhs);
821         self.z.mul_assign(rhs);
822         self.w.mul_assign(rhs);
823     }
824 }
825 
826 impl Mul<DVec4> for f64 {
827     type Output = DVec4;
828     #[inline]
mul(self, rhs: DVec4) -> DVec4829     fn mul(self, rhs: DVec4) -> DVec4 {
830         DVec4 {
831             x: self.mul(rhs.x),
832             y: self.mul(rhs.y),
833             z: self.mul(rhs.z),
834             w: self.mul(rhs.w),
835         }
836     }
837 }
838 
839 impl Add<DVec4> for DVec4 {
840     type Output = Self;
841     #[inline]
add(self, rhs: Self) -> Self842     fn add(self, rhs: Self) -> Self {
843         Self {
844             x: self.x.add(rhs.x),
845             y: self.y.add(rhs.y),
846             z: self.z.add(rhs.z),
847             w: self.w.add(rhs.w),
848         }
849     }
850 }
851 
852 impl AddAssign<DVec4> for DVec4 {
853     #[inline]
add_assign(&mut self, rhs: Self)854     fn add_assign(&mut self, rhs: Self) {
855         self.x.add_assign(rhs.x);
856         self.y.add_assign(rhs.y);
857         self.z.add_assign(rhs.z);
858         self.w.add_assign(rhs.w);
859     }
860 }
861 
862 impl Add<f64> for DVec4 {
863     type Output = Self;
864     #[inline]
add(self, rhs: f64) -> Self865     fn add(self, rhs: f64) -> Self {
866         Self {
867             x: self.x.add(rhs),
868             y: self.y.add(rhs),
869             z: self.z.add(rhs),
870             w: self.w.add(rhs),
871         }
872     }
873 }
874 
875 impl AddAssign<f64> for DVec4 {
876     #[inline]
add_assign(&mut self, rhs: f64)877     fn add_assign(&mut self, rhs: f64) {
878         self.x.add_assign(rhs);
879         self.y.add_assign(rhs);
880         self.z.add_assign(rhs);
881         self.w.add_assign(rhs);
882     }
883 }
884 
885 impl Add<DVec4> for f64 {
886     type Output = DVec4;
887     #[inline]
add(self, rhs: DVec4) -> DVec4888     fn add(self, rhs: DVec4) -> DVec4 {
889         DVec4 {
890             x: self.add(rhs.x),
891             y: self.add(rhs.y),
892             z: self.add(rhs.z),
893             w: self.add(rhs.w),
894         }
895     }
896 }
897 
898 impl Sub<DVec4> for DVec4 {
899     type Output = Self;
900     #[inline]
sub(self, rhs: Self) -> Self901     fn sub(self, rhs: Self) -> Self {
902         Self {
903             x: self.x.sub(rhs.x),
904             y: self.y.sub(rhs.y),
905             z: self.z.sub(rhs.z),
906             w: self.w.sub(rhs.w),
907         }
908     }
909 }
910 
911 impl SubAssign<DVec4> for DVec4 {
912     #[inline]
sub_assign(&mut self, rhs: DVec4)913     fn sub_assign(&mut self, rhs: DVec4) {
914         self.x.sub_assign(rhs.x);
915         self.y.sub_assign(rhs.y);
916         self.z.sub_assign(rhs.z);
917         self.w.sub_assign(rhs.w);
918     }
919 }
920 
921 impl Sub<f64> for DVec4 {
922     type Output = Self;
923     #[inline]
sub(self, rhs: f64) -> Self924     fn sub(self, rhs: f64) -> Self {
925         Self {
926             x: self.x.sub(rhs),
927             y: self.y.sub(rhs),
928             z: self.z.sub(rhs),
929             w: self.w.sub(rhs),
930         }
931     }
932 }
933 
934 impl SubAssign<f64> for DVec4 {
935     #[inline]
sub_assign(&mut self, rhs: f64)936     fn sub_assign(&mut self, rhs: f64) {
937         self.x.sub_assign(rhs);
938         self.y.sub_assign(rhs);
939         self.z.sub_assign(rhs);
940         self.w.sub_assign(rhs);
941     }
942 }
943 
944 impl Sub<DVec4> for f64 {
945     type Output = DVec4;
946     #[inline]
sub(self, rhs: DVec4) -> DVec4947     fn sub(self, rhs: DVec4) -> DVec4 {
948         DVec4 {
949             x: self.sub(rhs.x),
950             y: self.sub(rhs.y),
951             z: self.sub(rhs.z),
952             w: self.sub(rhs.w),
953         }
954     }
955 }
956 
957 impl Rem<DVec4> for DVec4 {
958     type Output = Self;
959     #[inline]
rem(self, rhs: Self) -> Self960     fn rem(self, rhs: Self) -> Self {
961         Self {
962             x: self.x.rem(rhs.x),
963             y: self.y.rem(rhs.y),
964             z: self.z.rem(rhs.z),
965             w: self.w.rem(rhs.w),
966         }
967     }
968 }
969 
970 impl RemAssign<DVec4> for DVec4 {
971     #[inline]
rem_assign(&mut self, rhs: Self)972     fn rem_assign(&mut self, rhs: Self) {
973         self.x.rem_assign(rhs.x);
974         self.y.rem_assign(rhs.y);
975         self.z.rem_assign(rhs.z);
976         self.w.rem_assign(rhs.w);
977     }
978 }
979 
980 impl Rem<f64> for DVec4 {
981     type Output = Self;
982     #[inline]
rem(self, rhs: f64) -> Self983     fn rem(self, rhs: f64) -> Self {
984         Self {
985             x: self.x.rem(rhs),
986             y: self.y.rem(rhs),
987             z: self.z.rem(rhs),
988             w: self.w.rem(rhs),
989         }
990     }
991 }
992 
993 impl RemAssign<f64> for DVec4 {
994     #[inline]
rem_assign(&mut self, rhs: f64)995     fn rem_assign(&mut self, rhs: f64) {
996         self.x.rem_assign(rhs);
997         self.y.rem_assign(rhs);
998         self.z.rem_assign(rhs);
999         self.w.rem_assign(rhs);
1000     }
1001 }
1002 
1003 impl Rem<DVec4> for f64 {
1004     type Output = DVec4;
1005     #[inline]
rem(self, rhs: DVec4) -> DVec41006     fn rem(self, rhs: DVec4) -> DVec4 {
1007         DVec4 {
1008             x: self.rem(rhs.x),
1009             y: self.rem(rhs.y),
1010             z: self.rem(rhs.z),
1011             w: self.rem(rhs.w),
1012         }
1013     }
1014 }
1015 
1016 #[cfg(not(target_arch = "spirv"))]
1017 impl AsRef<[f64; 4]> for DVec4 {
1018     #[inline]
as_ref(&self) -> &[f64; 4]1019     fn as_ref(&self) -> &[f64; 4] {
1020         unsafe { &*(self as *const DVec4 as *const [f64; 4]) }
1021     }
1022 }
1023 
1024 #[cfg(not(target_arch = "spirv"))]
1025 impl AsMut<[f64; 4]> for DVec4 {
1026     #[inline]
as_mut(&mut self) -> &mut [f64; 4]1027     fn as_mut(&mut self) -> &mut [f64; 4] {
1028         unsafe { &mut *(self as *mut DVec4 as *mut [f64; 4]) }
1029     }
1030 }
1031 
1032 impl Sum for DVec4 {
1033     #[inline]
sum<I>(iter: I) -> Self where I: Iterator<Item = Self>,1034     fn sum<I>(iter: I) -> Self
1035     where
1036         I: Iterator<Item = Self>,
1037     {
1038         iter.fold(Self::ZERO, Self::add)
1039     }
1040 }
1041 
1042 impl<'a> Sum<&'a Self> for DVec4 {
1043     #[inline]
sum<I>(iter: I) -> Self where I: Iterator<Item = &'a Self>,1044     fn sum<I>(iter: I) -> Self
1045     where
1046         I: Iterator<Item = &'a Self>,
1047     {
1048         iter.fold(Self::ZERO, |a, &b| Self::add(a, b))
1049     }
1050 }
1051 
1052 impl Product for DVec4 {
1053     #[inline]
product<I>(iter: I) -> Self where I: Iterator<Item = Self>,1054     fn product<I>(iter: I) -> Self
1055     where
1056         I: Iterator<Item = Self>,
1057     {
1058         iter.fold(Self::ONE, Self::mul)
1059     }
1060 }
1061 
1062 impl<'a> Product<&'a Self> for DVec4 {
1063     #[inline]
product<I>(iter: I) -> Self where I: Iterator<Item = &'a Self>,1064     fn product<I>(iter: I) -> Self
1065     where
1066         I: Iterator<Item = &'a Self>,
1067     {
1068         iter.fold(Self::ONE, |a, &b| Self::mul(a, b))
1069     }
1070 }
1071 
1072 impl Neg for DVec4 {
1073     type Output = Self;
1074     #[inline]
neg(self) -> Self1075     fn neg(self) -> Self {
1076         Self {
1077             x: self.x.neg(),
1078             y: self.y.neg(),
1079             z: self.z.neg(),
1080             w: self.w.neg(),
1081         }
1082     }
1083 }
1084 
1085 impl Index<usize> for DVec4 {
1086     type Output = f64;
1087     #[inline]
index(&self, index: usize) -> &Self::Output1088     fn index(&self, index: usize) -> &Self::Output {
1089         match index {
1090             0 => &self.x,
1091             1 => &self.y,
1092             2 => &self.z,
1093             3 => &self.w,
1094             _ => panic!("index out of bounds"),
1095         }
1096     }
1097 }
1098 
1099 impl IndexMut<usize> for DVec4 {
1100     #[inline]
index_mut(&mut self, index: usize) -> &mut Self::Output1101     fn index_mut(&mut self, index: usize) -> &mut Self::Output {
1102         match index {
1103             0 => &mut self.x,
1104             1 => &mut self.y,
1105             2 => &mut self.z,
1106             3 => &mut self.w,
1107             _ => panic!("index out of bounds"),
1108         }
1109     }
1110 }
1111 
1112 #[cfg(not(target_arch = "spirv"))]
1113 impl fmt::Display for DVec4 {
fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result1114     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1115         write!(f, "[{}, {}, {}, {}]", self.x, self.y, self.z, self.w)
1116     }
1117 }
1118 
1119 #[cfg(not(target_arch = "spirv"))]
1120 impl fmt::Debug for DVec4 {
fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result1121     fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
1122         fmt.debug_tuple(stringify!(DVec4))
1123             .field(&self.x)
1124             .field(&self.y)
1125             .field(&self.z)
1126             .field(&self.w)
1127             .finish()
1128     }
1129 }
1130 
1131 impl From<[f64; 4]> for DVec4 {
1132     #[inline]
from(a: [f64; 4]) -> Self1133     fn from(a: [f64; 4]) -> Self {
1134         Self::new(a[0], a[1], a[2], a[3])
1135     }
1136 }
1137 
1138 impl From<DVec4> for [f64; 4] {
1139     #[inline]
from(v: DVec4) -> Self1140     fn from(v: DVec4) -> Self {
1141         [v.x, v.y, v.z, v.w]
1142     }
1143 }
1144 
1145 impl From<(f64, f64, f64, f64)> for DVec4 {
1146     #[inline]
from(t: (f64, f64, f64, f64)) -> Self1147     fn from(t: (f64, f64, f64, f64)) -> Self {
1148         Self::new(t.0, t.1, t.2, t.3)
1149     }
1150 }
1151 
1152 impl From<DVec4> for (f64, f64, f64, f64) {
1153     #[inline]
from(v: DVec4) -> Self1154     fn from(v: DVec4) -> Self {
1155         (v.x, v.y, v.z, v.w)
1156     }
1157 }
1158 
1159 impl From<(DVec3, f64)> for DVec4 {
1160     #[inline]
from((v, w): (DVec3, f64)) -> Self1161     fn from((v, w): (DVec3, f64)) -> Self {
1162         Self::new(v.x, v.y, v.z, w)
1163     }
1164 }
1165 
1166 impl From<(f64, DVec3)> for DVec4 {
1167     #[inline]
from((x, v): (f64, DVec3)) -> Self1168     fn from((x, v): (f64, DVec3)) -> Self {
1169         Self::new(x, v.x, v.y, v.z)
1170     }
1171 }
1172 
1173 impl From<(DVec2, f64, f64)> for DVec4 {
1174     #[inline]
from((v, z, w): (DVec2, f64, f64)) -> Self1175     fn from((v, z, w): (DVec2, f64, f64)) -> Self {
1176         Self::new(v.x, v.y, z, w)
1177     }
1178 }
1179 
1180 impl From<(DVec2, DVec2)> for DVec4 {
1181     #[inline]
from((v, u): (DVec2, DVec2)) -> Self1182     fn from((v, u): (DVec2, DVec2)) -> Self {
1183         Self::new(v.x, v.y, u.x, u.y)
1184     }
1185 }
1186