using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.AI;

public class InputHandler : MonoBehaviour
{
    public NavMeshAgent playerAgent = null;
    PlayerInteractPoint currentInteractPoint = null;
    List<PlayerInteractPoint> interactionQueue = new List<PlayerInteractPoint>();
    const int maximumQueuedInteractions = 1;
    public ShakeParameters arrivalShake = null;

    // Start is called before the first frame update
    void Start()
    {
        PlayerInteractPoint[] interactables = FindObjectsOfType<PlayerInteractPoint>();

        foreach(PlayerInteractPoint pip in interactables)
        {
            pip.InteractInitiated.AddListener(delegate { QueueInteraction(pip); });
        }

        walkingToInteract = false;

    }

    // Update is called once per frame
    void Update()
    {
        if (!PlayerArrivedAtDestination)
        {
        }
        else if (walkingToInteract)
        {
            // Player was moving but just arrived at destination this Update call

            walkingToInteract = false;
            currentInteractPoint.PlayerArrival.Invoke(); // Let all the listeners on this interact point know that we've arrived

            if (currentInteractPoint != null && arrivalShake != null)
            {
                currentInteractPoint.gameObject.Shake(arrivalShake);
            }

            currentInteractPoint = null;
            CheckToRunNextIteraction();
        }
    }

    bool walkingToInteract = false;
    private bool PlayerArrivedAtDestination
    {
        get
        {
            float dist = playerAgent.remainingDistance;
            if (dist != Mathf.Infinity && playerAgent.pathStatus == NavMeshPathStatus.PathComplete && playerAgent.remainingDistance == 0 && Vector3.Distance(playerAgent.destination, playerAgent.transform.position) < 0.1f)
            {
                return true;
            }
            return false;
        }
    }

    private void QueueInteraction(PlayerInteractPoint interaction)
    {
        if (interactionQueue.Count < maximumQueuedInteractions)
        {
            // Only queue if the queue is empty and the last interaction is the same as the queueing one
            if (interactionQueue.Count == 0 ||
                interactionQueue[interactionQueue.Count - 1] != interaction)
            {
                interactionQueue.Add(interaction);
            }
        }

        CheckToRunNextIteraction();
    }

    private void CheckToRunNextIteraction()
    {
        if (currentInteractPoint == null)
        {
            if (interactionQueue.Count > 0)
            {
                PlayerInteractPoint interaction = interactionQueue[0];
                interactionQueue.RemoveAt(0);

                currentInteractPoint = interaction;

                playerAgent.SetDestination(interaction.OperationLocation.position);
                playerAgent.GetComponent<PlayerAgentFacingFixer>().FinalFacing = interaction.OperationLocation.rotation;
                walkingToInteract = true;
            }
        }
    }



    public void ClearQueueAndMove(FloorNavigation floorNav, Vector3 movementDestination)
    {
        currentInteractPoint = null;
        movementDestination.x = Mathf.Clamp(movementDestination.x, -3f, 2.5f);
        movementDestination.z = Mathf.Clamp(movementDestination.z, -3.2f, -0.5f);
        playerAgent.SetDestination(movementDestination);
        walkingToInteract = false;
    }
}
