2#ifndef LIBSBX_MATH_RANDOM_HPP_
3#define LIBSBX_MATH_RANDOM_HPP_
11#include <libsbx/math/vector2.hpp>
12#include <libsbx/math/vector3.hpp>
22 using generator_type = std::mt19937;
26 template<numeric Type>
27 static auto next(Type min = std::numeric_limits<Type>::min(), Type max = std::numeric_limits<Type>::max()) -> Type {
28 using distribution_type = std::conditional_t<std::floating_point<Type>, std::uniform_real_distribution<Type>, std::uniform_int_distribution<Type>>;
30 auto distribution = distribution_type{min, max};
32 return distribution(_generator());
35 template<
integral Seed>
36 static auto seed(
const Seed seed) ->
void {
37 _generator().seed(
static_cast<generator_type::result_type
>(seed));
42 static auto _generator() -> generator_type& {
43 static auto device = std::random_device{};
44 static auto generator = generator_type{device()};
51template<std::ranges::random_access_range Range>
52auto shuffle_range(Range& range) ->
void {
53 for (
auto i = std::ranges::size(range); i > 1u; --i) {
54 const auto j = sbx::math::random::next<std::size_t>(0u, i - 1u);
56 std::swap(range[i - 1u], range[j]);
60template<std::ranges::sized_range Range>
61auto random_element(
const Range& range) -> std::ranges::range_value_t<Range> {
62 const auto size =
static_cast<std::ranges::range_difference_t<Range>
>(std::ranges::size(range));
63 const auto index = random::next<std::ranges::range_difference_t<Range>>(0, size - 1);
65 return *std::next(std::begin(range), index);
69auto random_point_in_circle(
const basic_vector2<Type>& center,
const Type radius) -> basic_vector2<Type> {
70 const auto r = radius * std::sqrt(random::next<Type>(Type{0}, Type{1}));
71 const auto theta = random::next<Type>(Type{0}, Type{2} * std::numbers::pi_v<Type>);
73 return center + basic_vector2<Type>{r * std::cos(theta), r * std::sin(theta)};
77auto random_point_on_circle(
const basic_vector2<Type>& center,
const Type radius) -> basic_vector2<Type> {
78 const auto theta = random::next<Type>(Type{0}, Type{2} * std::numbers::pi_v<Type>);
80 return center + basic_vector2<Type>{radius * std::cos(theta), radius * std::sin(theta)};
84auto random_point_in_sphere(
const basic_vector3<Type>& center,
const Type radius) -> basic_vector3<Type> {
85 const auto r = radius * std::cbrt(random::next<Type>(Type{0}, Type{1}));
86 const auto theta = random::next<Type>(Type{0}, Type{2} * std::numbers::pi_v<Type>);
87 const auto phi = random::next<Type>(Type{0}, std::numbers::pi_v<Type>);
89 const auto x = r * std::sin(phi) * std::cos(theta);
90 const auto y = r * std::sin(phi) * std::sin(theta);
91 const auto z = r * std::cos(phi);
93 return center + basic_vector3<Type>{x, y, z};
96auto random_color(
const std::float_t alpha = 1.0f) -> color;
Definition: random.hpp:18
RGBA color representation and utilities.
Core numeric concepts and type traits.