355 lines
11 KiB
C#
355 lines
11 KiB
C#
using System;
|
||
using System.Collections;
|
||
using System.Collections.Generic;
|
||
using UnityEngine;
|
||
|
||
public class ClockController : MonoBehaviour
|
||
{
|
||
public Transform hourHandPivot;
|
||
public Transform minuteHandPivot;
|
||
|
||
public Animator timeTravelVfxAnimator;
|
||
|
||
AudioSource pocketWatchAudioSource;
|
||
[SerializeField] AudioSource pocketWatchTimeTravelAudioSource;
|
||
|
||
[SerializeField] float rotationSpeedHourHand = 20f; // Adjust this to control the rotation speed
|
||
[SerializeField] float rotationSpeedMinuteHand = 240f; // Adjust this to control the rotation speed
|
||
|
||
[SerializeField] float multiplyClockHandsSpeed = 2f;
|
||
private float multipliedClockHandsSpeedFinal = 1f;
|
||
|
||
[Header("Non changable from the inspector.")]
|
||
|
||
[SerializeField] int hours;
|
||
[SerializeField] float minutes;
|
||
|
||
[SerializeField] float roundedMinutesValue;
|
||
|
||
[SerializeField] int targetHour;
|
||
[SerializeField] float targetMinutes;
|
||
|
||
[SerializeField] List<Renderer> pocketWatchRenderers;
|
||
|
||
private bool inputIsEnabled = true;
|
||
/* [HideInInspector]*/ public bool canUsePocketWatch = true;
|
||
[HideInInspector] public bool isUsingPocketWatch;
|
||
private bool updatePlayerAnimation = true;
|
||
private bool canClosePocketWatch = true;
|
||
|
||
public bool isInPresent = true;
|
||
|
||
private static ClockController _instance;
|
||
public static ClockController GetInstance() { return _instance; }
|
||
|
||
private void Awake()
|
||
{
|
||
if (!_instance)
|
||
{
|
||
_instance = this;
|
||
}
|
||
}
|
||
|
||
private void Start()
|
||
{
|
||
pocketWatchAudioSource = GetComponent<AudioSource>();
|
||
DisablePocketWatchRenderers();
|
||
}
|
||
|
||
private void Update()
|
||
{
|
||
float DpadVertical = Input.GetAxis("DpadVertical");
|
||
|
||
if (Input.GetKeyDown(KeyCode.Space) && /*!InventoryManager.GetInstance().inventoryIsOpen) */ !UIManager.GetInstance().userInterfaceIsOnScreen || //Keyboard -> Space
|
||
DpadVertical < 0 && /*!InventoryManager.GetInstance().inventoryIsOpen*/ !UIManager.GetInstance().userInterfaceIsOnScreen) // Controller -> down Dpad
|
||
{
|
||
if (inputIsEnabled)
|
||
{
|
||
if (!isUsingPocketWatch && GameProgressManager.GetInstance().PocketWatchIsObtained && canUsePocketWatch)
|
||
{
|
||
if (PlayerManager.GetInstance()._PlayerMovement.isCrouching == false)
|
||
{
|
||
OpenPocketWatch();
|
||
}
|
||
}
|
||
else
|
||
{
|
||
if (canClosePocketWatch && canUsePocketWatch)
|
||
{
|
||
ClosePocketWatch();
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
if (!AlternateUniverseManager.GetInstance().CanTearFabricOfReality)
|
||
{
|
||
if (isUsingPocketWatch)
|
||
{
|
||
UpdateClock();
|
||
}
|
||
}
|
||
else
|
||
{
|
||
// Αν μπορεί να σχιστεί η πραγματικότητα, οι δείκτες κινούνται τρελά προς τα πίσω
|
||
RotateClockHands(-rotationSpeedHourHand * 5f, -rotationSpeedMinuteHand * 5f);
|
||
}
|
||
}
|
||
|
||
public void OpenPocketWatch()
|
||
{
|
||
if (updatePlayerAnimation)
|
||
{
|
||
RaycastManager.GetInstance().RaycastIsDisabled();
|
||
EnablePocketWatchRenders();
|
||
PlayerManager.GetInstance()._PlayerMovement._CharacterAnimator.SetBool("IsLookingAtPocketWatch", true);
|
||
PlayerManager.GetInstance()._PlayerMovement.canCrouch = false;
|
||
PlayerManager.GetInstance().DisablePlayerMovement();
|
||
UIManager.GetInstance().OpenPocketWatchIndicationsPanel();
|
||
StartCoroutine(InputTimer());
|
||
updatePlayerAnimation = false;
|
||
}
|
||
isUsingPocketWatch = true;
|
||
}
|
||
|
||
IEnumerator InputTimer()
|
||
{
|
||
inputIsEnabled = false;
|
||
yield return new WaitForSeconds(0.4f);
|
||
inputIsEnabled = true;
|
||
}
|
||
|
||
public void ClosePocketWatch()
|
||
{
|
||
if (pocketWatchAudioSource.isPlaying)
|
||
{
|
||
pocketWatchAudioSource.Stop();
|
||
}
|
||
canUsePocketWatch = false;
|
||
canClosePocketWatch = true;
|
||
isUsingPocketWatch = false;
|
||
PlayerManager.GetInstance()._PlayerMovement._CharacterAnimator.SetBool("IsLookingAtPocketWatch", false);
|
||
PlayerManager.GetInstance()._PlayerMovement.canCrouch = true;
|
||
updatePlayerAnimation = true;
|
||
PlayerManager.GetInstance().EnablePlayerMovement();
|
||
RaycastManager.GetInstance().RaycastIsActivated();
|
||
UIManager.GetInstance().ClosePocketWatchIndicationsPanel();
|
||
StartCoroutine(ClosePocketWatchAndWaitForAnimationToEnd());
|
||
}
|
||
|
||
IEnumerator ClosePocketWatchAndWaitForAnimationToEnd()
|
||
{
|
||
yield return new WaitForSeconds(0.22f); //Animation time.
|
||
DisablePocketWatchRenderers();
|
||
canUsePocketWatch = true;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Updates the logic for the clock.
|
||
/// </summary>
|
||
private void UpdateClock()
|
||
{
|
||
float moveHand = Input.GetAxisRaw(/*"HorizontalArrows"*/"Horizontal");
|
||
float moveHandControllerForward = Input.GetAxis("RightTrigger");
|
||
float moveHandControllerBackward = Input.GetAxis("LeftTrigger");
|
||
|
||
if (Input.GetKey(KeyCode.LeftShift) || Input.GetKey(KeyCode.JoystickButton5)) // Button: RB
|
||
{
|
||
multipliedClockHandsSpeedFinal = multiplyClockHandsSpeed;
|
||
}
|
||
else
|
||
{
|
||
multipliedClockHandsSpeedFinal = 1f;
|
||
}
|
||
|
||
if (moveHand > 0f || moveHandControllerForward < 0)
|
||
{
|
||
RotateClockHands(rotationSpeedHourHand * multipliedClockHandsSpeedFinal, rotationSpeedMinuteHand * multipliedClockHandsSpeedFinal);
|
||
}
|
||
else if (moveHand < 0f || moveHandControllerBackward < 0)
|
||
{
|
||
RotateClockHands(-rotationSpeedHourHand * multipliedClockHandsSpeedFinal, -rotationSpeedMinuteHand * multipliedClockHandsSpeedFinal);
|
||
}
|
||
|
||
if (moveHand != 0f || moveHandControllerBackward != 0f || moveHandControllerForward != 0f)
|
||
{
|
||
// There is input, do something with the input value.
|
||
}
|
||
else
|
||
{
|
||
if (pocketWatchAudioSource.isPlaying)
|
||
{
|
||
pocketWatchAudioSource.Stop();
|
||
}
|
||
}
|
||
|
||
if (Input.GetKeyDown(KeyCode.E) || Input.GetKeyDown(KeyCode.JoystickButton0)) //Keyboard-> Enter Controller-> A
|
||
{
|
||
CalculateTime();
|
||
IsCorrectTime();
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Applies the rounded minutes of the clock.
|
||
/// </summary>
|
||
private void ApplyRoundedMinutes()
|
||
{
|
||
roundedMinutesValue = RoundDecimal(minutes);
|
||
|
||
if (roundedMinutesValue >= 59)
|
||
{
|
||
roundedMinutesValue = 0f;
|
||
}
|
||
|
||
Debug.Log("Original Value: " + minutes);
|
||
Debug.Log("Rounded Value: " + roundedMinutesValue);
|
||
}
|
||
|
||
/// <summary>
|
||
/// Rounds the minutes of the clock.
|
||
/// </summary>
|
||
/// <param name="value"> The value that needs to be rounded. </param>
|
||
/// <returns></returns>
|
||
private float RoundDecimal(float value)
|
||
{
|
||
int secondDigit = (int)((value / 1) % 10);
|
||
int firstDigit = (int)((value / 10) % 10);
|
||
|
||
// Round the second decimal digit to either 0 or 5 based on your conditions
|
||
if (secondDigit >= 0 && secondDigit <= 2)
|
||
{
|
||
secondDigit = 0;
|
||
//print("secondDecimalDigit:" + secondDecimalDigit);
|
||
}
|
||
else if (secondDigit > 6)
|
||
{
|
||
secondDigit = 0;
|
||
firstDigit = (firstDigit + 1) % 10;
|
||
print("FirstDecimalDigit:" + firstDigit);
|
||
}
|
||
else
|
||
{
|
||
if (secondDigit > 2 && secondDigit <= 6)
|
||
{
|
||
secondDigit = 5;
|
||
}
|
||
//print("secondDecimalDigit:" + secondDecimalDigit);
|
||
}
|
||
|
||
|
||
print("secondDecimalDigit:" + secondDigit);
|
||
|
||
// Convert the values to strings and concatenate them
|
||
string combinedString = firstDigit.ToString() + secondDigit.ToString();
|
||
|
||
// Parse the combined string back into an integer
|
||
int combinedNumber = int.Parse(combinedString);
|
||
|
||
return combinedNumber;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Rotates the clock hands.
|
||
/// </summary>
|
||
/// <param name="rotationSpeedHourHand"></param>
|
||
/// <param name="rotationSpeedMinuteHand"></param>
|
||
private void RotateClockHands(float rotationSpeedHourHand, float rotationSpeedMinuteHand)
|
||
{
|
||
hourHandPivot.Rotate(0f, rotationSpeedHourHand * Time.deltaTime, 0f);
|
||
minuteHandPivot.Rotate(0f, rotationSpeedMinuteHand * Time.deltaTime, 0f);
|
||
|
||
//Play rotation sound if should be player
|
||
if(pocketWatchAudioSource.isPlaying == false)
|
||
{
|
||
pocketWatchAudioSource.loop = true;
|
||
pocketWatchAudioSource.Play();
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Checks to see if the time that the player has entered is correct.
|
||
/// </summary>
|
||
/// <returns></returns>
|
||
public bool IsCorrectTime()
|
||
{
|
||
if (hours == targetHour && roundedMinutesValue == targetMinutes)
|
||
{
|
||
CorrectTime();
|
||
return true;
|
||
}
|
||
else
|
||
{
|
||
print("Target hour is false!");
|
||
return false;
|
||
}
|
||
}
|
||
|
||
public void CorrectTime()
|
||
{
|
||
print("Target hour is correct!");
|
||
canClosePocketWatch = false;
|
||
pocketWatchTimeTravelAudioSource.Play();
|
||
StartCoroutine(closePocketWatchAfterSeconds());
|
||
}
|
||
|
||
IEnumerator closePocketWatchAfterSeconds()
|
||
{
|
||
yield return new WaitForSeconds(0.5f);
|
||
ClosePocketWatch();
|
||
}
|
||
|
||
/// <summary>
|
||
/// This gets called from the unityEvent/ Or another script (if needed) when the target hour needs to be changed in order for an action to occcur.
|
||
/// </summary>
|
||
/// <param name="targetHour"></param>
|
||
public void EnterTargetHour(int targetHour)
|
||
{
|
||
this.targetHour = targetHour;
|
||
print("Target Hour =" + targetHour);
|
||
}
|
||
|
||
/// <summary>
|
||
/// This gets called from the unityEvent/ Or another script (if needed) when the target minutes needs to be changed in order for an action to occcur.
|
||
/// </summary>
|
||
/// <param name="targetMinutes"></param>
|
||
public void EnterTargetMinutes(float targetMinutes)
|
||
{
|
||
this.targetMinutes = targetMinutes;
|
||
print("Target mintutes =" + targetMinutes);
|
||
}
|
||
|
||
void CalculateTime()
|
||
{
|
||
float totalRotation = hourHandPivot.localEulerAngles.y;
|
||
float rotationPerHour = 360f / 12;
|
||
|
||
// Calculate hours based on the rotation of the hour hand
|
||
hours = Mathf.FloorToInt(totalRotation / rotationPerHour);
|
||
hours = hours % 12; // Convert to 12-hour format
|
||
|
||
// Calculate minutes based on the rotation of the minute hand
|
||
float minutesPerRotation = 360f / 60f;
|
||
minutes = Mathf.FloorToInt(minuteHandPivot.localEulerAngles.y / minutesPerRotation);
|
||
|
||
print(hours + ":" + minutes);
|
||
ApplyRoundedMinutes();
|
||
}
|
||
|
||
public void DisablePocketWatchRenderers()
|
||
{
|
||
foreach (var _pocketWatchRenderers in pocketWatchRenderers)
|
||
{
|
||
_pocketWatchRenderers.enabled = false;
|
||
}
|
||
}
|
||
|
||
public void EnablePocketWatchRenders()
|
||
{
|
||
foreach (var _pocketWatchRenderers in pocketWatchRenderers)
|
||
{
|
||
_pocketWatchRenderers.enabled = true;
|
||
}
|
||
}
|
||
}
|