178 lines
5.2 KiB
C#
178 lines
5.2 KiB
C#
using System;
|
|
using UnityEngine;
|
|
|
|
public class Player : MonoBehaviour, IKitchenObjectParent
|
|
{
|
|
public static Player Instance { get; private set; }
|
|
public Transform KitchenObjectHoldPoint { get; set; }
|
|
|
|
private const float playerRadius = .7f;
|
|
private const float playerHeight = 2f;
|
|
|
|
public event EventHandler OnPickedSomething;
|
|
|
|
[SerializeField] private GameInput gameInput;
|
|
[SerializeField] private float moveSpeed = 7f;
|
|
[SerializeField] private float rotateSpeed = 10f;
|
|
[SerializeField] private float interactDistance = 2f;
|
|
|
|
[SerializeField] private LayerMask countersLayerMask;
|
|
|
|
private Vector2 inputVector;
|
|
|
|
private bool isWalking;
|
|
private KitchenObject kitchenObject;
|
|
public KitchenObject KitchenObject
|
|
{
|
|
get => kitchenObject;
|
|
set
|
|
{
|
|
kitchenObject = value;
|
|
if (value != null)
|
|
{
|
|
OnPickedSomething?.Invoke(this, EventArgs.Empty);
|
|
}
|
|
}
|
|
}
|
|
|
|
private Vector3 lastInteractDir;
|
|
private Vector3 moveDir;
|
|
private BaseCounter selectedCounter;
|
|
|
|
private void Awake()
|
|
{
|
|
if (Instance != null)
|
|
{
|
|
Debug.LogError("There is more than one Player instance!");
|
|
}
|
|
|
|
Instance = this;
|
|
KitchenObjectHoldPoint = transform.Find("KitchenObjectHoldPoint");
|
|
}
|
|
|
|
private void Start()
|
|
{
|
|
gameInput.OnInteractAction += GameInput_OnInteractAction;
|
|
gameInput.OnInteractAlternateAction += GameInput_OnInteractAlternateAction;
|
|
}
|
|
|
|
private void Update()
|
|
{
|
|
HandleMovement();
|
|
HandleInteractions();
|
|
}
|
|
|
|
public event EventHandler<SelectedCounterChangedEventArgs> OnSelectedCounterChanged;
|
|
|
|
private void GameInput_OnInteractAlternateAction(object sender, System.EventArgs e)
|
|
{
|
|
if (!KitchenGameManager.Instance.IsGamePlaying())
|
|
{
|
|
return;
|
|
}
|
|
|
|
selectedCounter?.InteractAlternate(this);
|
|
}
|
|
|
|
private void GameInput_OnInteractAction(object sender, System.EventArgs e)
|
|
{
|
|
if (!KitchenGameManager.Instance.IsGamePlaying())
|
|
{
|
|
return;
|
|
}
|
|
|
|
selectedCounter?.Interact(this);
|
|
}
|
|
|
|
private void HandleInteractions()
|
|
{
|
|
if (moveDir != Vector3.zero)
|
|
{
|
|
lastInteractDir = moveDir;
|
|
}
|
|
|
|
if (Physics.Raycast(transform.position, lastInteractDir, out RaycastHit raycastHit, interactDistance, countersLayerMask))
|
|
{
|
|
if (raycastHit.transform.TryGetComponent(out BaseCounter baseCounter))
|
|
{
|
|
// Debug.Log("Player stands in front of a BaseCounter");
|
|
if (baseCounter != selectedCounter)
|
|
{
|
|
SetSelectedCounter(baseCounter);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
SetSelectedCounter(null);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
SetSelectedCounter(null);
|
|
}
|
|
}
|
|
|
|
private void SetSelectedCounter(BaseCounter sC)
|
|
{
|
|
selectedCounter = sC;
|
|
// Debug.Log(selectedCounter != null ? "SelectedCounter changed to BaseCounter" : "SelectedCounter changed to null");
|
|
OnSelectedCounterChanged?.Invoke(this, new() { SelectedCounter = sC });
|
|
}
|
|
|
|
public bool IsWalking()
|
|
{
|
|
return isWalking;
|
|
}
|
|
|
|
private void HandleMovement()
|
|
{
|
|
inputVector = GameInput.GetMovementVectorNormalized();
|
|
moveDir = new(inputVector.x, 0, inputVector.y);
|
|
float moveDistance = moveSpeed * Time.deltaTime;
|
|
|
|
bool canMove = !Physics.CapsuleCast(transform.position, transform.position + (Vector3.up * playerHeight), playerRadius, moveDir, moveDistance);
|
|
if (!canMove)
|
|
{
|
|
// Cannot move towars moveDir
|
|
//Attempt only x movement
|
|
|
|
Vector3 moveDirX = new Vector3(moveDir.x, 0, 0).normalized;
|
|
canMove = (moveDir.x < -.5f || moveDir.x > +.5f) && !Physics.CapsuleCast(transform.position, transform.position + (Vector3.up * playerHeight), playerRadius, moveDir, moveDistance);
|
|
if (canMove)
|
|
{
|
|
//Can move only on the X
|
|
MovePlayer(moveDirX, moveDistance);
|
|
}
|
|
else
|
|
{
|
|
//Cannot move only on the X
|
|
|
|
//Attempt only Z movement
|
|
Vector3 moveDirZ = new Vector3(0, 0, moveDir.z).normalized;
|
|
canMove = (moveDir.z < -.5f || moveDir.z > +.5f) && !Physics.CapsuleCast(transform.position, transform.position + (Vector3.up * playerHeight), playerRadius, moveDir, moveDistance);
|
|
|
|
if (canMove)
|
|
{
|
|
//Can move only on the Z
|
|
MovePlayer(moveDirZ, moveDistance);
|
|
}
|
|
else
|
|
{
|
|
//Cannot move in any direction
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
MovePlayer(moveDir, moveDistance);
|
|
}
|
|
|
|
isWalking = moveDir != Vector3.zero;
|
|
transform.forward = Vector3.Slerp(transform.forward, moveDir, Time.deltaTime * rotateSpeed);
|
|
}
|
|
|
|
private void MovePlayer(Vector3 moveDirection, float moveDistance)
|
|
{
|
|
transform.position += moveDirection * moveDistance;
|
|
}
|
|
} |