using UnityEngine;
using UnityEngine.Rendering.Universal;
using static UnityEngine.GraphicsBuffer;

public class ThrowableHand : Tool
{
    [Header("Throwable Hand Parameters")]
    public float range;
    public float forceModifier;
    public float loft;
    public GameObject testBomb;
  
    // Mathematical plane used to catch the raycast from camera to get direction for
    // looking at the mouse
    private Plane handGroundPlane;
    private DecalProjector targetProjection;
    private float throwForce;

    private void Update()
    {
        if (GameManager.Instance.PlayerController != null)
        {
            DrawTargetProjection();
        }
    }

    private void SetGroundPlane()
    {
        if (handGroundPlane == null)
        {
            handGroundPlane = new Plane(Vector3.up, -GameManager.Instance.PlayerController.DougBody.transform.position.y);
        }

        handGroundPlane.distance = -GameManager.Instance.PlayerController.DougBody.transform.position.y;
        handGroundPlane.normal = Vector3.up;
    }

    private void DrawTargetProjection()
    {
        if (targetProjection == null)
        {
            targetProjection = GetComponentInChildren<DecalProjector>();
        }

        Transform player = GameManager.Instance.PlayerController.DougBody.transform;
        Transform camera = GameManager.Instance.PlayerController.cameraController.MainCamera.transform;

        Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);

        Vector3 targetPoint;

        // First try real world geometry
        if (Physics.Raycast(ray, out RaycastHit hit, 1000f))
        {
            targetPoint = hit.point;
        }
        else
        {
            // Fallback plane if nothing hit
            Plane plane = new Plane(Vector3.up, player.position);

            if (!plane.Raycast(ray, out float distance))
                return;

            targetPoint = ray.GetPoint(distance);
        }

        // Flatten relative to player
        Vector3 offset = targetPoint - player.position;
        offset.y = 0f;

        // Clamp range
        offset = Vector3.ClampMagnitude(offset, range);
        throwForce = offset.magnitude;

        // Final position
        Vector3 finalPosition = player.position + offset;

        // Snap back to ground
        if (Physics.Raycast(
            finalPosition + Vector3.up * 10f,
            Vector3.down,
            out RaycastHit groundHit,
            50f))
        {
            finalPosition = groundHit.point;
        }

        targetProjection.transform.position = finalPosition;
    }

    public override void Use()
    {
        GameObject newBomb = Instantiate(testBomb);
        newBomb.transform.position = transform.position;

        Vector3 direction = transform.forward * throwForce * forceModifier;
        direction += GameManager.Instance.PlayerController.GetVelocity();
        direction.y = loft;

        newBomb.GetComponent<Rigidbody>().AddForce(direction, ForceMode.Impulse);
    }

    public override void UseAlt()
    {
        throw new System.NotImplementedException();
    }
}
