Files
Stair_Horror/Assets/Scripts/PlayerController.cs

135 lines
4.6 KiB
C#

using UnityEngine;
using UnityEngine.InputSystem;
public class PlayerController : MonoBehaviour
{
[Header("Movement")]
public float moveSpeed = 5f;
public float gravity = -9.81f; // Standard Earth gravity
public float jumpHeight = 1.0f; // Optional, set to 0 if no jumping allowed
[Header("Look Settings")]
public float mouseSensitivity = 10f;
public float maxLookAngle = 70f;
[Header("Interaction")]
public float interactionDistance = 3f;
public LayerMask interactionLayer;
// Components
private CharacterController controller;
private Transform cameraTransform;
// State
private float verticalRotation = 0f;
private Vector3 velocity; // Stores our falling speed
private bool isGrounded; // Are we touching the floor?
// Inputs
private InputSystem_Actions inputActions;
private Vector2 moveInput;
void Awake()
{
inputActions = new InputSystem_Actions();
controller = GetComponent<CharacterController>();
cameraTransform = Camera.main.transform;
Cursor.lockState = CursorLockMode.Locked;
Cursor.visible = false;
// Bind Inputs
inputActions.Player.Move.performed += ctx => moveInput = ctx.ReadValue<Vector2>();
inputActions.Player.Move.canceled += ctx => moveInput = Vector2.zero;
inputActions.Player.Interact.started += ctx => TryInteract();
}
void OnEnable() => inputActions.Enable();
void OnDisable() => inputActions.Disable();
void Update()
{
HandleGravity(); // <--- NEW GRAVITY FUNCTION
HandleMovement();
HandleLook();
UpdateInteractionUI();
}
void HandleGravity()
{
// Check if the controller thinks it's on the ground
isGrounded = controller.isGrounded;
if (isGrounded && velocity.y < 0)
{
// Reset falling speed when on ground (keep slightly negative to stick to floor)
velocity.y = -2f;
}
// Apply Gravity over time
velocity.y += gravity * Time.deltaTime;
// Apply the velocity to the controller
controller.Move(velocity * Time.deltaTime);
}
void HandleMovement()
{
Vector3 move = transform.right * moveInput.x + transform.forward * moveInput.y;
controller.Move(move * moveSpeed * Time.deltaTime);
}
// ... (Keep HandleLook, UpdateInteractionUI, and TryInteract exactly the same as before)
// For brevity, I am not pasting the repeated Look/Interact code here,
// but ensure you keep those functions in your file!
// If you need the full paste again, let me know.
// ------------------------------------------------------------------------
// PASTE YOUR HandleLook, UpdateInteractionUI, and TryInteract HERE
// ------------------------------------------------------------------------
void HandleLook()
{
Vector2 rawInput = inputActions.Player.Look.ReadValue<Vector2>();
float mouseX = rawInput.x * mouseSensitivity * Time.deltaTime;
float mouseY = rawInput.y * mouseSensitivity * Time.deltaTime;
verticalRotation -= mouseY;
verticalRotation = Mathf.Clamp(verticalRotation, -maxLookAngle, maxLookAngle);
cameraTransform.localRotation = Quaternion.Euler(verticalRotation, 0f, 0f);
transform.Rotate(Vector3.up * mouseX);
}
void UpdateInteractionUI()
{
Ray ray = new Ray(cameraTransform.position, cameraTransform.forward);
RaycastHit hit;
if (Physics.Raycast(ray, out hit, interactionDistance, interactionLayer))
{
IInteractable interactable = hit.collider.GetComponent<IInteractable>();
if (interactable != null && InteractionUI.Instance != null)
InteractionUI.Instance.UpdatePrompt(interactable.GetDescription());
else if (InteractionUI.Instance != null)
InteractionUI.Instance.ClearPrompt();
}
else if (InteractionUI.Instance != null) InteractionUI.Instance.ClearPrompt();
}
void TryInteract()
{
Ray ray = new Ray(cameraTransform.position, cameraTransform.forward);
RaycastHit hit;
if (Physics.Raycast(ray, out hit, interactionDistance, interactionLayer))
{
IInteractable interactable = hit.collider.GetComponent<IInteractable>();
if (interactable != null)
{
interactable.Interact();
if (InteractionUI.Instance != null)
InteractionUI.Instance.UpdatePrompt(interactable.GetDescription());
}
}
}
}