using System;
using D2D.Databases;
using UnityEngine;
namespace D2D.Utilities
{
///
/// Contains common math operations and better random.
///
public static class DMath
{
private static DataContainer _seed = new DataContainer(nameof(_seed), 0);
///
/// Sets the random seed.
///
[RuntimeInitializeOnLoadMethod]
private static void Init()
{
var seed = (int) (Time.deltaTime * 1000 * _seed.Value);
_seed.Value++;
UnityEngine.Random.InitState(seed);
}
///
/// Returns the random float in [min, max].
///
public static float Random(float min, float max)
{
return UnityEngine.Random.Range(min, max);
}
public static float RandomByAmplitude(float a)
{
return Random(-a, a);
}
///
/// Returns the random integer in [min, max].
///
public static int Random(int min, int max)
{
float randomValue = Random((float) min, (float) max);
return (int) Math.Round(randomValue, 0);
}
///
/// Returns 1 or -1.
///
public static int RandomSign()
{
return Random(0, 1f) > .5f ? 1 : -1;
}
///
/// Returns the random point in box [vector a: x/y/z, vector b: x/y/z].
///
public static Vector3 RandomPointInsideBox(Vector3 a, Vector3 b)
{
return new Vector3(Random(a.x, b.x), Random(a.y, b.y), Random(a.z, b.z));
}
public static Vector3 RandomPointInsideBoxCollider(this Transform transform, BoxCollider box)
{
return transform.position + -box.center + RandomPointInsideBox(-box.size / 2f, box.size / 2f);
}
public static Quaternion RandomRotation()
{
return Quaternion.Euler(RandomPointInsideBox(360));
}
///
/// Return the random point in box with width (x), height (y) and length (z). [0, x/y/z].
///
public static Vector3 RandomPointInsideBox(float x, float y, float z, bool includeNegative = true)
{
int k = includeNegative ? 1 : 0;
float randomX = Random(-x * k, x);
float randomY = Random(-y * k, y);
float randomZ = Random(-z * k, z);
return new Vector3(randomX, randomY, randomZ);
}
///
/// Returns the random point in box with width (a), height (a) and length (a).
///
public static Vector3 RandomPointInsideBox(float a, bool includeNegative = true)
{
return RandomPointInsideBox(a, a, a, includeNegative);
}
public static Vector3 RandomPointInsideBox2D(float a, bool includeNegative = true)
{
return RandomPointInsideBox(a, a, 0, includeNegative);
}
public static float RandomFloat(this Vector2 range)
{
return Random(range.x, range.y);
}
public static int RandomInt(this Vector2 range)
{
return Random((int) range.x, (int)range.y);
}
///
/// Round float to int
///
public static int Round(this float val)
{
return (int) Math.Round(val, 0);
}
///
/// Are numbers differ less by 0.01?
///
public static bool Almost(this float a, float b, float tolerance = .01f)
{
return Mathf.Abs(a - b) < tolerance;
}
///
/// Is number differ from zero less by 0.01?
///
public static bool AlmostZero(this float a, float tolerance = .01f)
{
return Almost(a, 0, tolerance);
}
///
/// Is distance between tow points (a and b) less than threshold.
///
public static bool Almost(this Vector3 a, Vector3 b, float threshold = .01f)
{
return (a - b).magnitude.AlmostZero(threshold);
}
public static Vector3 Multiply(this Vector3 a, Vector3 b)
{
a.x *= b.x;
a.y *= b.y;
a.z *= b.z;
return a;
}
}
}