Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
bevyengine
GitHub Repository: bevyengine/bevy
Path: blob/main/crates/bevy_math/src/sampling/standard.rs
6596 views
1
//! This module holds local implementations of the [`Distribution`] trait for [`StandardUniform`], which
2
//! allow certain Bevy math types (those whose values can be randomly generated without additional
3
//! input other than an [`Rng`]) to be produced using [`rand`]'s APIs. It also holds [`FromRng`],
4
//! an ergonomic extension to that functionality which permits the omission of type annotations.
5
//!
6
//! For instance:
7
//! ```
8
//! # use rand::{random, Rng, SeedableRng, rngs::StdRng, distr::StandardUniform};
9
//! # use bevy_math::{Dir3, sampling::FromRng};
10
//! let mut rng = StdRng::seed_from_u64(7313429298);
11
//! // Random direction using thread-local rng
12
//! let random_direction1: Dir3 = random();
13
//!
14
//! // Random direction using the rng constructed above
15
//! let random_direction2: Dir3 = rng.random();
16
//!
17
//! // The same as the previous but with different syntax
18
//! let random_direction3 = Dir3::from_rng(&mut rng);
19
//!
20
//! // Five random directions, using StandardUniform explicitly
21
//! let many_random_directions: Vec<Dir3> = rng.sample_iter(StandardUniform).take(5).collect();
22
//! ```
23
24
use core::f32::consts::TAU;
25
26
use crate::{
27
primitives::{Circle, Sphere},
28
Dir2, Dir3, Dir3A, Quat, Rot2, ShapeSample, Vec3A,
29
};
30
use rand::{
31
distr::{Distribution, StandardUniform},
32
Rng,
33
};
34
35
/// Ergonomics trait for a type with a [`StandardUniform`] distribution, allowing values to be generated
36
/// uniformly from an [`Rng`] by a method in its own namespace.
37
///
38
/// Example
39
/// ```
40
/// # use rand::{Rng, SeedableRng, rngs::StdRng};
41
/// # use bevy_math::{Dir3, sampling::FromRng};
42
/// let mut rng = StdRng::seed_from_u64(451);
43
/// let random_dir = Dir3::from_rng(&mut rng);
44
/// ```
45
pub trait FromRng
46
where
47
Self: Sized,
48
StandardUniform: Distribution<Self>,
49
{
50
/// Construct a value of this type uniformly at random using `rng` as the source of randomness.
51
fn from_rng<R: Rng + ?Sized>(rng: &mut R) -> Self {
52
rng.random()
53
}
54
}
55
56
impl Distribution<Dir2> for StandardUniform {
57
#[inline]
58
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Dir2 {
59
let circle = Circle::new(1.0);
60
let vector = circle.sample_boundary(rng);
61
Dir2::new_unchecked(vector)
62
}
63
}
64
65
impl FromRng for Dir2 {}
66
67
impl Distribution<Dir3> for StandardUniform {
68
#[inline]
69
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Dir3 {
70
let sphere = Sphere::new(1.0);
71
let vector = sphere.sample_boundary(rng);
72
Dir3::new_unchecked(vector)
73
}
74
}
75
76
impl FromRng for Dir3 {}
77
78
impl Distribution<Dir3A> for StandardUniform {
79
#[inline]
80
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Dir3A {
81
let sphere = Sphere::new(1.0);
82
let vector: Vec3A = sphere.sample_boundary(rng).into();
83
Dir3A::new_unchecked(vector)
84
}
85
}
86
87
impl FromRng for Dir3A {}
88
89
impl Distribution<Rot2> for StandardUniform {
90
#[inline]
91
fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Rot2 {
92
let angle = rng.random_range(0.0..TAU);
93
Rot2::radians(angle)
94
}
95
}
96
97
impl FromRng for Rot2 {}
98
99
impl FromRng for Quat {}
100
101