WinterJamSnowman/Assets/Scripts/LemonGenericLib/DialogueSystem/DialogueSystem.cs

405 lines
12 KiB
C#

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using TMPro;
using System;
using Lemon.GenericLib.Generics;
//note
//dialouge cannot be started in the start() call because it needs to wait for events
namespace Lemon.GenericLib.Dialogue
{
public class DialogueSystem : MonoBehaviour
{
[Header("dialogue configs")]
[SerializeField] private string[] dialougeTexts;
[SerializeField] private TextMeshProUGUI dialogueTextFeild;
[SerializeField] private static float typingSpeed = 50f;
private static float defaultTypingSpeed;
[SerializeField] Optional<string> interuptInput;
[SerializeField] Optional<string> advancingInput;
[SerializeField] private bool canUseExternalControls = true;
[SerializeField] public Color defaulrColour;
[Space]
[Header("timing configs")]
[SerializeField] private bool startImmediantly;
[SerializeField] public float startDelay;
[SerializeField] public float endDelay;
[Space]
[Header("command parsing configs")]
[SerializeField] private char commandPrefix;
[SerializeField] private bool skipEmpty;
[SerializeField] private char[] ignorePrefix;
[Space]
[Header("extra config ")]
[SerializeField] Optional<GameObject> continueButton;
public int SceneIndex;
public Action<string> dialogueCommandEvents;
public Action dialogueLineEvent;
public Action endDialougeEvents;
public Action dialogueStartEvents;
public Action initDialogueEvents;
public Action requiredEndEvent;
private int currentDialougeIndex = 0;
private bool isInterupt = false;
private bool isTyping = false;
public float waitTime = 0f;
public static bool doneSkipping = false;
//public DialogueLogger dialogueLogger;
// Start is called before the first frame update
IEnumerator Start()
{
dialogueTextFeild.text = "";
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
//dialougeLineEvent += TestEvent;
if (startImmediantly)
{
yield return new WaitForSeconds(0.5f);
StartCoroutine(StartDialogueRoutine());
}
defaultTypingSpeed = typingSpeed;
}
// Update is called once per frame
void Update()
{
if (!canUseExternalControls) return;
HandleInputs();
}
bool isInputInterupt = false;
private void HandleInputs()
{
if (interuptInput.Enabled && isTyping)
{
if (Input.GetButtonDown(interuptInput.Value))
{
//AudioManager2D.audioManager2DInstance.Play("UIClick");
if (!isInterupt)
{
isInterupt = true;
}
return;
}
}
if (advancingInput.Enabled)
{
if (Input.GetButtonDown(advancingInput.Value))
{
//AudioManager2D.audioManager2DInstance.Play("UIClick");
if (!isTyping)
{
//Debug.Log(isTyping);
AdvanceDialogue();
}
//else if (!isInterupt){
// isInputInterupt = true;
// isInterupt = true;
// StartCoroutine(resetInterupt());
//}
return;
}
}
}
public void LoadDialouge(string[] dialoguesToLoad, bool startImmediantly = true)
{
dialougeTexts = dialoguesToLoad;
dialogueStartEvents = null;
//endDialougeEvents = null;
if (startImmediantly)
{
StartDialogue();
}
}
public void StartDialogue()
{
if (dialougeTexts == null) return;
//AudioManager2D.audioManager2DInstance.Play("PageFlipSound");
StartCoroutine(StartDialogueRoutine());
}
IEnumerator StartDialogueRoutine()
{
initDialogueEvents?.Invoke();
dialogueTextFeild.color = defaulrColour;
yield return new WaitForSeconds(startDelay);
dialogueStartEvents?.Invoke();
currentDialougeIndex = 0;
TypeDialouge();
}
public void AdvanceDialogue()
{
//AudioManager2D.audioManager2DInstance.Play("ButtonSound");
if (!canUseExternalControls) return;
StopCoroutine("TypeDialougeRoutine");
if (dialougeTexts == null) return;
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
currentDialougeIndex++;
Debug.LogWarning(currentDialougeIndex + ", " + dialougeTexts.Length);
if (currentDialougeIndex < dialougeTexts.Length)
{
TypeDialouge(dialougeTexts[currentDialougeIndex]);
}
else
{
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
StartCoroutine(EndDialogueRoutine());
}
}
public void SkipDialogue()
{
//isInterupt = true;
//currentDialougeIndex = dialougeTexts.Length;
//currentDialougeIndex++;
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
AdvanceDialogue();
}
IEnumerator EndDialogueRoutine()
{
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
requiredEndEvent?.Invoke();
dialogueTextFeild.text = "";
yield return new WaitForSeconds(endDelay);
//fire events
//endDialougeEvents?.Invoke();
//FindObjectOfType<SceneTransition>().GoToScene(SceneIndex);
}
public void SkipDialougeTyping()
{
StopCoroutine("TypeDialougeRoutine");
dialogueTextFeild.text = "";
AdvanceDialogue();
}
public void TypeDialouge()
{
StopCoroutine("typeDialougeRoutine");
StartCoroutine(TypeDialougeRoutine(dialougeTexts[currentDialougeIndex]));
}
public void TypeDialouge(string dialougeToType)
{
StopCoroutine("typeDialougeRoutine");
StartCoroutine(TypeDialougeRoutine(dialougeToType));
}
public void InteruptDialouge()
{
isInterupt = true;
}
public void SetStartEvents(Action[] events)
{
dialogueStartEvents = null;
foreach (var item in events)
{
dialogueStartEvents += item;
}
}
public void SetEndEvents(Action[] events)
{
endDialougeEvents = null;
foreach (var item in events)
{
endDialougeEvents += item;
}
}
//create a wait time vaiable that is public
IEnumerator TypeDialougeRoutine(string dialougeToType)
{
float t = 0;
int charIndex = 0;
isInterupt = false;
isTyping = true;
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
Debug.Log(dialougeToType);
if (skipEmpty && (string.IsNullOrWhiteSpace(dialougeToType)))
{
SkipDialougeTyping();
}
else
{
dialogueCommandEvents?.Invoke(dialougeToType);
//make sure you can change wait time here woth the command fucntion
bool isSkipPrefix = false;
for (int i = 0; i < ignorePrefix.Length; i++)
{
if (dialougeToType[0].Equals(ignorePrefix[i]))
{
isSkipPrefix = true;
}
}
//Honestly have no idea where to put the wait so
if (waitTime > 0)
{
yield return new WaitForSeconds(waitTime);
}
waitTime = 0;
Debug.Log($"shoud skip?: { dialougeToType[0] } {isSkipPrefix} ");
doneSkipping = false;
if (dialougeToType[0].Equals(commandPrefix) || isSkipPrefix)
{
//wait even if wait time is 0
//reset wait time after wait
SkipDialougeTyping();
}
else
{
//dialougeToType = dialougeTextEffects.UpdateText(dialougeToType);
dialogueTextFeild.text = dialougeToType;
//dialougeTextEffects.UpdateText(dialougeToType);
//typing effect
while (charIndex < dialougeToType.Length)
{
isTyping = true;
//for whatever reason this needs to be in the loop to not show
if (continueButton.Enabled)
{
continueButton.Value.SetActive(false);
}
if (isInterupt)
{
charIndex = dialougeToType.Length;
}
else
{
t += Time.deltaTime * typingSpeed;
charIndex = Mathf.FloorToInt(t);
charIndex = Mathf.Clamp(charIndex, 0, dialougeToType.Length);
}
//process here
dialogueTextFeild.maxVisibleCharacters = charIndex;
//dialogueTextFeild.text = dialougeToType.Substring(0, charIndex);
yield return null;
}
doneSkipping = true;
//dialogueLogger.AddToLog(dialougeToType, false, false);
//dialogueTextFeild.text = dialougeToType;
}
}
isTyping = false;
//Fixes for continue button appearing when holding down skip
if (continueButton.Enabled)
{
if (doneSkipping == false)
{
continueButton.Value.SetActive(false);
}
else
{
continueButton.Value.SetActive(true);
}
}
}
IEnumerator resetInterupt()
{
yield return null;
isInputInterupt = false;
}
public void TestEvent(string testString)
{
Debug.Log(testString);
Debug.Log("Event is working as intended");
}
public static void setTypingSpeed(int newValue)
{
typingSpeed = newValue;
}
public static void setDefaultTypingSpeed()
{
typingSpeed = defaultTypingSpeed;
}
}
}