using System.Collections; using System.Collections.Generic; using NitroxClient.GameLogic.ChatUI; using NitroxModel.Core; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.UI; namespace NitroxClient.MonoBehaviours.Gui.Chat { public class PlayerChatInputField : MonoBehaviour, ISelectHandler, IDeselectHandler { private PlayerChatManager playerChatManager; private bool selected; private static float timeLeftUntilAutoClose; public static bool FreezeTime; public InputField InputField; // Chat history private const int historyLength = 32; // 2^5 messages availables :D private List sentMessages; private int _sentMessagesIndex; private int sentMessagesIndex { get { return _sentMessagesIndex; } set { if (sentMessages.Count == 0) { // -1 is the state when there's no message sent _sentMessagesIndex = -1; } else if (value < 1) { sentMessagesIndex = 1; } else if (value > sentMessages.Count) { _sentMessagesIndex = sentMessages.Count; } else { // normal functionning InputField.text = sentMessages[value - 1]; _sentMessagesIndex = value; } } } private void Awake() { playerChatManager = NitroxServiceLocator.LocateService(); sentMessages = new(); sentMessagesIndex = -1; } public void OnSelect(BaseEventData eventData) { playerChatManager.SelectChat(); selected = true; ResetTimer(); } public void OnDeselect(BaseEventData eventData) { selected = false; } public static void ResetTimer() { timeLeftUntilAutoClose = PlayerChat.CHAT_VISIBILITY_TIME_LENGTH; FreezeTime = false; } private void Update() { if (FreezeTime) { return; } if (selected) { if (!string.IsNullOrWhiteSpace(InputField.text)) { if (UnityEngine.Input.GetKey(KeyCode.Return)) { if (UnityEngine.Input.GetKey(KeyCode.LeftShift)) { if (!InputField.text.EndsWith("\n")) { InputField.ActivateInputField(); InputField.text += "\n"; StartCoroutine(MoveToEndOfText()); } } else { // Detect if there's a ghost message on top of the list (one that wasn't sent but still saved) if (sentMessagesIndex != sentMessages.Count && sentMessages.Count > 0) { sentMessages.RemoveAt(sentMessages.Count - 1); } // If the list is too long, we'll just remove the first message of the list if (sentMessages.Count > historyLength) { sentMessages.RemoveAt(0); } sentMessages.Add(InputField.text); _sentMessagesIndex = sentMessages.Count; playerChatManager.SendMessage(); playerChatManager.DeselectChat(); // return to game after message sent } } } else { if (UnityEngine.Input.GetKey(KeyCode.Return)) { ResetTimer(); playerChatManager.DeselectChat(); } } // Chat history stuff // GetKeyDown means it's only getting executed once per press if (UnityEngine.Input.GetKeyDown(KeyCode.UpArrow)) { // If we're currently on the newest message, we want to save it to be able to come back to it (a ghost message) if (sentMessagesIndex == sentMessages.Count && sentMessages.Count > 0) { sentMessages.Add(InputField.text); _sentMessagesIndex = sentMessages.Count; } sentMessagesIndex--; } else if(UnityEngine.Input.GetKeyDown(KeyCode.DownArrow)) { // We shouldn't execute this check if we're already on top of the list if (sentMessagesIndex < sentMessages.Count) { sentMessagesIndex++; // If we're back to the newest message, we can delete it from the list because it has not been sent yet if (sentMessagesIndex == sentMessages.Count && sentMessages.Count > 0) { sentMessages.RemoveAt(sentMessages.Count - 1); _sentMessagesIndex = sentMessages.Count; } } } } else { timeLeftUntilAutoClose -= Time.unscaledDeltaTime; if (timeLeftUntilAutoClose <= 0) { playerChatManager.HideChat(); FreezeTime = true; } } } private IEnumerator MoveToEndOfText() { yield return null; InputField.MoveTextEnd(false); } } }