diff --git a/glm/gtc/random.hpp b/glm/gtc/random.hpp index 099e1095..5d5ceeec 100644 --- a/glm/gtc/random.hpp +++ b/glm/gtc/random.hpp @@ -65,21 +65,46 @@ namespace glm genType const & Max); /// Generate random numbers in the interval [Min, Max], according a gaussian distribution - /// (From GLM_GTX_random extension) + /// + /// @param Mean + /// @param Deviation + /// @see gtc_random template genType gaussRand( genType const & Mean, genType const & Deviation); /// Generate a random 2D vector which coordinates are regulary distributed on a circle of a given radius - /// (From GLM_GTX_random extension) + /// + /// @param Radius + /// @see gtc_random template - detail::tvec2 circularRand(T const & Radius); + detail::tvec2 circularRand( + T const & Radius); /// Generate a random 3D vector which coordinates are regulary distributed on a sphere of a given radius - /// (From GLM_GTX_random extension) + /// + /// @param Radius + /// @see gtc_random template - detail::tvec3 sphericalRand(T const & Radius); + detail::tvec3 sphericalRand( + T const & Radius); + + /// Generate a random 2D vector which coordinates are regulary distributed within the area of a disk of a given radius + /// + /// @param Radius + /// @see gtc_random + template + detail::tvec2 diskRand( + T const & Radius); + + /// Generate a random 3D vector which coordinates are regulary distributed within the volume of a ball of a given radius + /// + /// @param Radius + /// @see gtc_random + template + GLM_FUNC_QUALIFIER detail::tvec3 ballRand( + T const & Radius); /// @} }//namespace glm diff --git a/glm/gtc/random.inl b/glm/gtc/random.inl index b2020f3e..6491a53c 100644 --- a/glm/gtc/random.inl +++ b/glm/gtc/random.inl @@ -81,16 +81,105 @@ GLM_FUNC_QUALIFIER detail::tvec4 linearRand linearRand(Min.w, Max.w)); } -template <> -half gaussRand +template +GLM_FUNC_QUALIFIER genType gaussRand ( - half const & Mean, - half const & Deviation + genType const & Mean, + genType const & Deviation ) { + genType w, x1, x2; + + do + { + x1 = compRand1(genType(-1), genType(1)); + x2 = compRand1(genType(-1), genType(1)); + + w = x1 * x1 + x2 * x2; + } while(w > genType(1)); + + return x2 * std_deviation * std_deviation * sqrt((genType(-2) * log(w)) / w) + mean; +} +template +GLM_FUNC_QUALIFIER detail::tvec2 gaussRand +( + detail::tvec2 const & Min, + detail::tvec2 const & Max +) +{ + return detail::tvec2( + gaussRand(Min.x, Max.x), + gaussRand(Min.y, Max.y)); +} + +template +GLM_FUNC_QUALIFIER detail::tvec3 gaussRand +( + detail::tvec3 const & Min, + detail::tvec3 const & Max +) +{ + return detail::tvec3( + gaussRand(Min.x, Max.x), + gaussRand(Min.y, Max.y), + gaussRand(Min.z, Max.z)); +} + +template +GLM_FUNC_QUALIFIER detail::tvec4 gaussRand +( + detail::tvec4 const & Min, + detail::tvec4 const & Max +) +{ + return detail::tvec4( + gaussRand(Min.x, Max.x), + gaussRand(Min.y, Max.y), + gaussRand(Min.z, Max.z), + gaussRand(Min.w, Max.w)); +} + +template +GLM_FUNC_QUALIFIER detail::tvec3 diskRand +( + T const & Radius +) +{ + detail::tvec2 Result(T(0)); + T LenRadius(T(0)); + + do + { + Result = compRand2(-Radius, Radius); + LenRadius = length(Result); + } + while(LenRadius > Radius); + + return Result; +} + +template +GLM_FUNC_QUALIFIER detail::tvec3 ballRand +( + T const & Radius +) +{ + detail::tvec3 Result(T(0)); + T LenRadius(T(0)); + + do + { + Result = compRand3(-Radius, Radius); + LenRadius = length(Result); + } + while(LenRadius > Radius); + + return Result; +} + template -detail::tvec2 circularRand +GLM_FUNC_QUALIFIER detail::tvec2 circularRand ( T const & Radius ) @@ -100,7 +189,7 @@ detail::tvec2 circularRand } template -detail::tvec3 sphericalRand +GLM_FUNC_QUALIFIER detail::tvec3 sphericalRand ( T const & Radius )