RiftMayhem/Assets/Scripts/Interactables/GamepadInteractionController.cs
2025-02-21 18:35:51 +00:00

145 lines
3.9 KiB
C#

using System.Collections;
using System.Collections.Generic;
using TMPro;
using UnityEngine;
using UnityEngine.UI;
public class GamepadInteractionController : MonoBehaviour
{
[Header("Settings")]
[SerializeField] private float interactionRadius = 3f;
[SerializeField] private float highlightRadius = 5f;
[SerializeField] private LayerMask interactableMask;
[Header("UI References")]
[SerializeField] private GameObject interactionPrompt;
[SerializeField] private Image interactionIcon;
[SerializeField] private TMP_Text interactionText;
private List<Interactable> nearbyInteractables = new List<Interactable>();
private Interactable currentTarget;
private bool isShowingInteractables;
PlayerController playerController;
private void Awake()
{
playerController = GetComponent<PlayerController>();
}
float rightTrigger;
private void Update()
{
// Show interactables when holding Right Trigger
rightTrigger = Input.GetAxisRaw("RightTrigger");
isShowingInteractables = rightTrigger > 0.5f;
if (isShowingInteractables)
{
UpdateNearbyInteractables();
HighlightClosestInteractable();
}
else
{
ClearHighlights();
}
// Interact with Right Bumper
if (Input.GetButtonDown("RightBumper") && currentTarget != null)
{
InteractWithCurrent();
}
}
Collider[] colliders;
private void UpdateNearbyInteractables()
{
nearbyInteractables.Clear();
colliders = Physics.OverlapSphere(transform.position, highlightRadius, interactableMask);
foreach (var collider in colliders)
{
if (collider.TryGetComponent<Interactable>(out var interactable))
{
nearbyInteractables.Add(interactable);
}
}
}
float closestDistance;
Interactable closest;
float distance;
private void HighlightClosestInteractable()
{
closestDistance = float.MaxValue;
closest = null;
foreach (var interactable in nearbyInteractables)
{
distance = Vector3.Distance(transform.position, interactable.transform.position);
if (distance < closestDistance)
{
closestDistance = distance;
closest = interactable;
}
}
// Only highlight if within interaction range
if (closest != null && closestDistance <= interactionRadius)
{
SetCurrentTarget(closest);
}
else
{
ClearCurrentTarget();
}
}
private void SetCurrentTarget(Interactable target)
{
if (currentTarget != target)
{
ClearCurrentTarget();
currentTarget = target;
// Show interaction prompt
interactionPrompt.SetActive(true);
interactionText.text = $"Press RB to {target.GetInteractionText()}";
// Highlight the interactable
target.OnFocused(this.transform, playerController, true);
target.OnHighlight();
}
}
private void ClearCurrentTarget()
{
if (currentTarget != null)
{
currentTarget.OnUnhighlight();
currentTarget = null;
interactionPrompt.SetActive(false);
}
}
private void ClearHighlights()
{
foreach (var interactable in nearbyInteractables)
{
interactable.OnUnhighlight();
}
nearbyInteractables.Clear();
ClearCurrentTarget();
}
private void InteractWithCurrent()
{
if (currentTarget != null)
{
distance = Vector3.Distance(transform.position, currentTarget.transform.position);
if (distance <= interactionRadius)
{
currentTarget.Interact(true);
}
}
}
}