using RTG;
using System.Collections.Generic;
using UnityEngine;

public class RTGController : UnitySingleton<RTGController>
{
    public enum GizmoId
    {
        None = 0,
        Move,
        Rotate,
        Scale,
        Universal,
    }
    private ObjectTransformGizmo objectMoveGizmo;
    private ObjectTransformGizmo objectRotationGizmo;
    private ObjectTransformGizmo objectScaleGizmo;
    private ObjectTransformGizmo objectUniversalGizmo;

    private GizmoId workGizmoId;
    private ObjectTransformGizmo workGizmo;
    public List<GameObject> selectedObjects = new List<GameObject>();
    public System.Action onTransformBegin;
    public System.Action<List<GameObject>> onTransformChanged;
    // Start is called once before the first execution of Update after the MonoBehaviour is created
    public RTGController()
    {
        objectMoveGizmo = RTGizmosEngine.Get.CreateObjectMoveGizmo();
        objectRotationGizmo = RTGizmosEngine.Get.CreateObjectRotationGizmo();
        objectScaleGizmo = RTGizmosEngine.Get.CreateObjectScaleGizmo();
        objectUniversalGizmo = RTGizmosEngine.Get.CreateObjectUniversalGizmo();

        objectMoveGizmo.Gizmo.SetEnabled(false);
        objectMoveGizmo.Gizmo.MoveGizmo.SetSnapEnabled(false);
        objectMoveGizmo.Gizmo.MoveGizmo.SetVertexSnapEnabled(false);
        objectRotationGizmo.Gizmo.SetEnabled(false);
        objectScaleGizmo.Gizmo.SetEnabled(false);
        objectUniversalGizmo.Gizmo.SetEnabled(false);

        objectMoveGizmo.Gizmo.PreDragBegin += OnGizmoDragBegin;
        objectRotationGizmo.Gizmo.PreDragBegin += OnGizmoDragBegin;
        objectScaleGizmo.Gizmo.PreDragBegin += OnGizmoDragBegin;
        objectUniversalGizmo.Gizmo.PreDragBegin += OnGizmoDragBegin;

        objectMoveGizmo.Gizmo.PostDragUpdate += OnGizmoDragUpdate;
        objectRotationGizmo.Gizmo.PostDragUpdate += OnGizmoDragUpdate;
        objectScaleGizmo.Gizmo.PostDragUpdate += OnGizmoDragUpdate;
        objectUniversalGizmo.Gizmo.PostDragUpdate += OnGizmoDragUpdate;

        objectMoveGizmo.Gizmo.PostDragEnd += OnGizmoDragEnd;
        objectRotationGizmo.Gizmo.PostDragEnd += OnGizmoDragEnd;
        objectScaleGizmo.Gizmo.PostDragEnd += OnGizmoDragEnd;
        objectUniversalGizmo.Gizmo.PostDragEnd += OnGizmoDragEnd;

        workGizmo = objectMoveGizmo;
        workGizmoId = GizmoId.None;
    }
    public void SetWorkGizmoId(GizmoId gizmoId)
    {
        objectMoveGizmo.Gizmo.SetEnabled(false);
        objectRotationGizmo.Gizmo.SetEnabled(false);
        objectScaleGizmo.Gizmo.SetEnabled(false);
        objectUniversalGizmo.Gizmo.SetEnabled(false);

        workGizmoId = gizmoId;
        if (gizmoId == GizmoId.None)
            return;
        else if (gizmoId == GizmoId.Move)
            workGizmo = objectMoveGizmo;
        else if (gizmoId == GizmoId.Rotate)
            workGizmo = objectRotationGizmo;
        else if (gizmoId == GizmoId.Scale)
            workGizmo = objectScaleGizmo;
        else if (gizmoId == GizmoId.Universal)
            workGizmo = objectUniversalGizmo;

        if (selectedObjects.Count != 0)
        {
            workGizmo.Gizmo.SetEnabled(true);
            workGizmo.RefreshPositionAndRotation();
        }
    }
    private void OnSelectionChanged()
    {
        if (selectedObjects.Count != 0)
        {
            workGizmo.Gizmo.SetEnabled(true);
            workGizmo.RefreshPositionAndRotation();
        }
        else
        {
            objectMoveGizmo.Gizmo.SetEnabled(false);
            objectRotationGizmo.Gizmo.SetEnabled(false);
            objectScaleGizmo.Gizmo.SetEnabled(false);
            objectUniversalGizmo.Gizmo.SetEnabled(false);
        }
    }
    public void SetGizmoTargetObjects(List<GameObject> objects)
    {
        selectedObjects.Clear();
        selectedObjects.AddRange(objects);
        objectMoveGizmo.SetTargetObjects(selectedObjects);
        objectRotationGizmo.SetTargetObjects(selectedObjects);
        objectScaleGizmo.SetTargetObjects(selectedObjects);
        objectUniversalGizmo.SetTargetObjects(selectedObjects);
    }
    private void OnGizmoDragBegin(Gizmo gizmo, int t)
    {
        onTransformBegin?.Invoke();
    }
    private void OnGizmoDragUpdate(Gizmo gizmo, int t)
    {
        onTransformChanged?.Invoke(selectedObjects);
    }
    private void OnGizmoDragEnd(Gizmo gizmo, int t)
    {
        onTransformChanged?.Invoke(selectedObjects); 
    }
}
