using System; using System.Collections.Generic; using UnityEngine; using Random = UnityEngine.Random; namespace EscapeRoomEngine.Engine.Runtime.Utilities { public static class Utilities { #region Math /// /// Returns whether a position relative to some placement is inside its dimensions. /// /// The position to check, relative to the placement. /// The placement to check the position against. public static bool IsInsideRelative(this Vector3Int position, Placement placement) { return position.x >= 0 && position.z >= 0 && position.x < placement.size.x && position.z < placement.size.y; } #endregion #region Randomness /// /// Return a random value in a range, including the last value. /// public static int RandomInclusive(int from, int to) => Random.Range(from, to + 1); #endregion } public static class ListExtensions { /// /// remove a random element from a list and return it. /// public static T PopRandomElement(this List list) { var index = Random.Range(0, list.Count); var element = list[index]; list.RemoveAt(index); return element; } /// /// Return a random value from a list. /// public static T RandomElement(this List list) => list[Random.Range(0, list.Count)]; /// /// Perform a Fisher-Yates shuffle on a given list, leaving it in a random order. /// public static void Shuffle(this List list) { for (var n = list.Count - 1; n > 0; n--) { var i = Utilities.RandomInclusive(0, n); var j = Utilities.RandomInclusive(0, n); (list[i], list[j]) = (list[j], list[i]); } } } public static class Vector2IntExtensions { /// /// Project a 2D vector onto the floor in 3D space. /// public static Vector3Int ProjectAtFloor(this Vector2Int vector) => vector.ProjectAtHeight(0); /// /// Project a 2D vector onto a specific height in 3D space. /// public static Vector3Int ProjectAtHeight(this Vector2Int vector, int height) => new Vector3Int(vector.x, height, vector.y); } public static class FloatExtensions { public static TimeSpan ToTimeSpan(this float seconds) => new(0, 0, 0, Mathf.RoundToInt(seconds), 0); } }