using System.Collections; using UnityEngine; public class DiceView : MonoBehaviour, IBase, IBootLoader { private Rigidbody rb; private bool rolling; [SerializeField] private DiceSide[] diceSides; [SerializeField] private float sideValueTime = 1.2f; [Header("Physics Randomness")] [SerializeField] private float baseSpinForce = 900f; [SerializeField] private float sideForce = 0.18f; [SerializeField] private float liftForce = 0.1f; void Awake() { rb = GetComponent(); rb.useGravity = false; } public void Initialize() { InterfaceManager.Instance?.RegisterInterface(this); transform.localPosition = new Vector3(0, 20, 0); } public void Roll() { if (!rolling) StartCoroutine(RollRoutine()); } IEnumerator RollRoutine() { rolling = true; // MICRO DELAY → breaks physics sync between dice yield return new WaitForSeconds(Random.Range(0.01f, 0.06f)); rb.useGravity = true; // PER-DICE FORCE MULTIPLIER float spinMultiplier = Random.Range(0.8f, 1.25f); // RANDOM TORQUE rb.AddTorque( Random.Range(-baseSpinForce, baseSpinForce) * spinMultiplier, Random.Range(-baseSpinForce, baseSpinForce) * spinMultiplier, Random.Range(-baseSpinForce, baseSpinForce) * spinMultiplier, ForceMode.Impulse ); // RANDOM SIDE FORCE Vector3 sideDir = new Vector3( Random.Range(-1f, 1f), 0f, Random.Range(-1f, 1f) ).normalized; rb.AddForce(sideDir * sideForce, ForceMode.Impulse); // SMALL UPWARD FORCE rb.AddForce(Vector3.up * liftForce, ForceMode.Impulse); yield return new WaitForSeconds(sideValueTime); int value = GetDiceValue(); //TODO: Use the dice value as needed Debug.Log($"Dice rolled: {value}"); ResetDice(); } int GetDiceValue() { foreach (DiceSide side in diceSides) { if (side.OnGround()) return side.sideValue; } return 1; } void ResetDice() { rb.useGravity = false; rb.velocity = Vector3.zero; rb.angularVelocity = Vector3.zero; transform.localPosition = new Vector3(0, 20, 0); rolling = false; } }