160 lines
4.7 KiB
C#
160 lines
4.7 KiB
C#
|
|
using UnityEngine;
|
||
|
|
using UnityEngine.InputSystem;
|
||
|
|
|
||
|
|
public class FirstPersonController : MonoBehaviour
|
||
|
|
{
|
||
|
|
[Header("Movement Settings")]
|
||
|
|
public float speed = 5.0f;
|
||
|
|
public float mouseSensitivity = 10.0f;
|
||
|
|
|
||
|
|
[Header("Camera Settings")]
|
||
|
|
public Transform cameraTarget;
|
||
|
|
public float minVerticalAngle = -90.0f;
|
||
|
|
public float maxVerticalAngle = 90.0f;
|
||
|
|
|
||
|
|
private CharacterController controller;
|
||
|
|
private Vector2 moveInput;
|
||
|
|
private Vector2 lookInput;
|
||
|
|
private float verticalRotation = 0f;
|
||
|
|
private Vector3 velocity = Vector3.zero;
|
||
|
|
private float gravity = 9.81f;
|
||
|
|
|
||
|
|
[Header("Input System")]
|
||
|
|
public InputActionAsset inputActionAsset;
|
||
|
|
private InputAction moveAction;
|
||
|
|
private InputAction lookAction;
|
||
|
|
private InputAction toggleMenuAction; // Single action for TAB
|
||
|
|
|
||
|
|
[Header("Shop Menu")]
|
||
|
|
[SerializeField] GameObject inventoryMenuUI; // Current inventory
|
||
|
|
[SerializeField] GameObject buyMenuUI; // Buy inventory
|
||
|
|
|
||
|
|
private bool isPaused = false; // Master state for Cursor + Camera
|
||
|
|
|
||
|
|
void Start()
|
||
|
|
{
|
||
|
|
controller = GetComponent<CharacterController>();
|
||
|
|
|
||
|
|
if (cameraTarget == null) Debug.LogError("Assign 'Camera Target'!");
|
||
|
|
|
||
|
|
// Initialize state: Locked cursor, Camera active
|
||
|
|
SetPauseState(false);
|
||
|
|
inventoryMenuUI.SetActive(false);
|
||
|
|
buyMenuUI.SetActive(false);
|
||
|
|
// Initialize shop menu UI
|
||
|
|
}
|
||
|
|
|
||
|
|
void OnEnable()
|
||
|
|
{
|
||
|
|
if (inputActionAsset != null)
|
||
|
|
{
|
||
|
|
// Find Actions
|
||
|
|
moveAction = inputActionAsset.FindAction("Move");
|
||
|
|
lookAction = inputActionAsset.FindAction("Look");
|
||
|
|
|
||
|
|
// Make sure this name matches your Input Action Asset exactly!
|
||
|
|
toggleMenuAction = inputActionAsset.FindAction("ToggleMenu");
|
||
|
|
|
||
|
|
// Enable Actions
|
||
|
|
moveAction?.Enable();
|
||
|
|
lookAction?.Enable();
|
||
|
|
toggleMenuAction?.Enable();
|
||
|
|
|
||
|
|
// Subscribe to Events
|
||
|
|
if (moveAction != null)
|
||
|
|
{
|
||
|
|
moveAction.performed += ctx => moveInput = ctx.ReadValue<Vector2>();
|
||
|
|
moveAction.canceled += ctx => moveInput = Vector2.zero;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (lookAction != null)
|
||
|
|
{
|
||
|
|
lookAction.performed += ctx => lookInput = ctx.ReadValue<Vector2>();
|
||
|
|
lookAction.canceled += ctx => lookInput = Vector2.zero;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (toggleMenuAction != null)
|
||
|
|
{
|
||
|
|
toggleMenuAction.performed += OnToggleMenuPerformed;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
void OnDisable()
|
||
|
|
{
|
||
|
|
moveAction?.Disable();
|
||
|
|
lookAction?.Disable();
|
||
|
|
toggleMenuAction?.Disable();
|
||
|
|
}
|
||
|
|
|
||
|
|
// Triggered when TAB is pressed
|
||
|
|
void OnToggleMenuPerformed(InputAction.CallbackContext context)
|
||
|
|
{
|
||
|
|
// Toggle the boolean state
|
||
|
|
isPaused = !isPaused;
|
||
|
|
|
||
|
|
// Apply the new state
|
||
|
|
SetPauseState(isPaused);
|
||
|
|
}
|
||
|
|
|
||
|
|
// Central function to handle what happens when paused/unpaused
|
||
|
|
void SetPauseState(bool paused)
|
||
|
|
{
|
||
|
|
if (paused)
|
||
|
|
{
|
||
|
|
// FREEZE: Show cursor, unlock mouse, stop camera
|
||
|
|
Cursor.lockState = CursorLockMode.None;
|
||
|
|
Cursor.visible = true;
|
||
|
|
inventoryMenuUI.SetActive(true);
|
||
|
|
buyMenuUI.SetActive(true);
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
// RESUME: Hide cursor, lock mouse, allow camera
|
||
|
|
Cursor.lockState = CursorLockMode.Locked;
|
||
|
|
Cursor.visible = false;
|
||
|
|
inventoryMenuUI.SetActive(false);
|
||
|
|
buyMenuUI.SetActive(false);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
void Update()
|
||
|
|
{
|
||
|
|
// Always allow movement? Or restrict movement when paused?
|
||
|
|
// If you want to stop walking when TAB is pressed, wrap this in "if (!isPaused)"
|
||
|
|
HandleMovement();
|
||
|
|
|
||
|
|
// Only rotate camera if NOT paused
|
||
|
|
if (!isPaused)
|
||
|
|
{
|
||
|
|
HandleRotation();
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
void HandleMovement()
|
||
|
|
{
|
||
|
|
Vector3 move = transform.right * moveInput.x + transform.forward * moveInput.y;
|
||
|
|
|
||
|
|
velocity.y -= gravity * Time.deltaTime;
|
||
|
|
move.y = velocity.y;
|
||
|
|
|
||
|
|
controller.Move(move * speed * Time.deltaTime);
|
||
|
|
}
|
||
|
|
|
||
|
|
void HandleRotation()
|
||
|
|
{
|
||
|
|
// Horizontal (Body)
|
||
|
|
float mouseX = lookInput.x * mouseSensitivity * Time.deltaTime;
|
||
|
|
transform.Rotate(Vector3.up * mouseX);
|
||
|
|
|
||
|
|
// Vertical (Camera Target)
|
||
|
|
if (cameraTarget != null)
|
||
|
|
{
|
||
|
|
float mouseY = lookInput.y * mouseSensitivity * Time.deltaTime;
|
||
|
|
verticalRotation -= mouseY;
|
||
|
|
verticalRotation = Mathf.Clamp(verticalRotation, minVerticalAngle, maxVerticalAngle);
|
||
|
|
cameraTarget.localRotation = Quaternion.Euler(verticalRotation, 0f, 0f);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|