fix: Question and answers working correctly
This commit is contained in:
parent
11243f1474
commit
a3415767cd
4 changed files with 497 additions and 100 deletions
|
@ -2,32 +2,66 @@ using System;
|
|||
using Messaging.Typer;
|
||||
using TMPro;
|
||||
using UnityEngine;
|
||||
using UnityEngine.Serialization;
|
||||
using Utilities;
|
||||
|
||||
namespace Messaging {
|
||||
public class Message : MonoBehaviour {
|
||||
public RectTransform RectTransform { private set; get; }
|
||||
public string Text => messageText.text;
|
||||
public string RealText => realMessageText.text;
|
||||
public string Text { private set; get; }
|
||||
public string RealText { private set; get; }
|
||||
public bool IsAnswer { private set; get; }
|
||||
public bool IsReal { private set; get; }
|
||||
|
||||
[SerializeField] private TMP_Text messageText;
|
||||
[SerializeField] private TMP_Text realMessageText;
|
||||
|
||||
private TextTyper _textTyper;
|
||||
private TextTyper _realTextTyper;
|
||||
private Coroutine _typingCoroutine;
|
||||
private Coroutine _realTypingCoroutine;
|
||||
[SerializeField] private MessageContainer questionContainer;
|
||||
[SerializeField] private MessageContainer answerContainer;
|
||||
|
||||
private void Awake() {
|
||||
RectTransform = GetComponent<RectTransform>();
|
||||
_textTyper = new TextTyper(messageText);
|
||||
_realTextTyper = new TextTyper(realMessageText);
|
||||
|
||||
questionContainer.InitializeTypers();
|
||||
answerContainer.InitializeTypers();
|
||||
}
|
||||
|
||||
public void SetMessageText(string text, bool animate) =>
|
||||
SetText(ref _typingCoroutine, messageText, _textTyper, text, animate);
|
||||
public void SetMessageRealText(string text, bool animate) =>
|
||||
SetText(ref _realTypingCoroutine, realMessageText, _realTextTyper, text, animate);
|
||||
public void SetMessageText(string text, bool animate, bool isAnswer) {
|
||||
Text = text;
|
||||
IsAnswer = isAnswer;
|
||||
IsReal = false;
|
||||
|
||||
if (isAnswer) {
|
||||
SetText(ref answerContainer.TypingCoroutine, answerContainer.messageText, answerContainer.TextTyper,
|
||||
text, animate);
|
||||
|
||||
answerContainer.container.SetActive(true);
|
||||
questionContainer.container.SetActive(false);
|
||||
} else {
|
||||
SetText(ref questionContainer.TypingCoroutine, questionContainer.messageText,
|
||||
questionContainer.TextTyper, text, animate);
|
||||
|
||||
questionContainer.container.SetActive(true);
|
||||
answerContainer.container.SetActive(false);
|
||||
}
|
||||
}
|
||||
|
||||
public void SetMessageRealText(string text, bool animate, bool isAnswer) {
|
||||
RealText = text;
|
||||
IsAnswer = isAnswer;
|
||||
IsReal = true;
|
||||
|
||||
if (isAnswer) {
|
||||
SetText(ref answerContainer.RealTypingCoroutine, answerContainer.realMessageText,
|
||||
answerContainer.RealTextTyper, text, animate);
|
||||
|
||||
answerContainer.container.SetActive(true);
|
||||
questionContainer.container.SetActive(false);
|
||||
} else {
|
||||
SetText(ref questionContainer.RealTypingCoroutine, questionContainer.realMessageText,
|
||||
questionContainer.RealTextTyper, text, animate);
|
||||
|
||||
questionContainer.container.SetActive(true);
|
||||
answerContainer.container.SetActive(false);
|
||||
}
|
||||
}
|
||||
|
||||
private void SetText(ref Coroutine routine, TMP_Text tmpText, TextTyper typer, string text, bool animate) {
|
||||
this.EnsureCoroutineStopped(ref routine);
|
||||
|
@ -37,5 +71,25 @@ namespace Messaging {
|
|||
else
|
||||
tmpText.text = text;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
private class MessageContainer {
|
||||
public GameObject container;
|
||||
public TMP_Text messageText;
|
||||
public TMP_Text realMessageText;
|
||||
|
||||
public Coroutine TypingCoroutine;
|
||||
public Coroutine RealTypingCoroutine;
|
||||
|
||||
public TextTyper TextTyper;
|
||||
public TextTyper RealTextTyper;
|
||||
|
||||
public void InitializeTypers() {
|
||||
TextTyper = new TextTyper(messageText);
|
||||
RealTextTyper = new TextTyper(realMessageText);
|
||||
|
||||
container.SetActive(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -19,43 +19,49 @@ namespace Messaging {
|
|||
string[] fLines = textAsset.text.Split(':');
|
||||
int i = 0;
|
||||
while (Application.isPlaying) {
|
||||
Debug.Log(textAsset.text);
|
||||
CreateMessage(MessageParser.SplitMessage(fLines[i % 2]).Key);
|
||||
++i;
|
||||
bool isAnswer = i % 2 != 0;
|
||||
|
||||
CreateMessage(MessageParser.SplitMessage(fLines[i % 2]).Key, isAnswer);
|
||||
await Task.Delay(2000);
|
||||
CreateRealMessage(MessageParser.SplitMessage(fLines[i % 2]).Value, isAnswer);
|
||||
await Task.Delay(2000);
|
||||
++i;
|
||||
}
|
||||
}
|
||||
|
||||
public void CreateMessage(string message) {
|
||||
ModifyMessageText(message, _messages.Length - 1);
|
||||
}
|
||||
public void CreateRealMessage(string message) {
|
||||
ModifyRealMessageText(message, _messages.Length - 1);
|
||||
public void CreateMessage(string message, bool isAnswer) {
|
||||
ModifyMessageText(message, _messages.Length - 1, isAnswer);
|
||||
}
|
||||
|
||||
private void ModifyMessageText(string message, int index) {
|
||||
ModifyPreviousMessageText(_messages[index].Text, index - 1);
|
||||
_messages[index].SetMessageText(message, true);
|
||||
}
|
||||
private void ModifyRealMessageText(string message, int index) {
|
||||
ModifyPreviousRealMessageText(_messages[index].Text, index - 1);
|
||||
_messages[index].SetMessageRealText(message, true);
|
||||
public void CreateRealMessage(string message, bool isAnswer) {
|
||||
ModifyRealMessageText(message, _messages.Length - 1, isAnswer);
|
||||
}
|
||||
|
||||
private void ModifyPreviousMessageText(string message, int index) {
|
||||
private void ModifyMessageText(string message, int index, bool isAnswer) {
|
||||
ModifyPreviousMessage(index);
|
||||
_messages[index].SetMessageText(message, true, isAnswer);
|
||||
}
|
||||
|
||||
private void ModifyRealMessageText(string message, int index, bool isAnswer) {
|
||||
_messages[index].SetMessageRealText(message, true, isAnswer);
|
||||
}
|
||||
|
||||
private void ModifyPreviousMessage(int index) {
|
||||
ModifyPreviousMessage(_messages[index].Text, _messages[index].RealText, index - 1,
|
||||
_messages[index].IsAnswer, _messages[index].IsReal);
|
||||
|
||||
_messages[index].SetMessageText("", false, _messages[index].IsAnswer);
|
||||
_messages[index].SetMessageRealText("", false, _messages[index].IsAnswer);
|
||||
}
|
||||
|
||||
private void ModifyPreviousMessage(string message, string realMessage, int index, bool isAnswer, bool isReal) {
|
||||
if (index < 0) return;
|
||||
|
||||
ModifyPreviousMessageText(_messages[index].Text, index - 1);
|
||||
ModifyPreviousMessage(_messages[index].Text, _messages[index].RealText, index - 1,
|
||||
_messages[index].IsAnswer, _messages[index].IsReal);
|
||||
|
||||
_messages[index].SetMessageText(message, false);
|
||||
}
|
||||
|
||||
private void ModifyPreviousRealMessageText(string message, int index) {
|
||||
if (index < 0) return;
|
||||
|
||||
ModifyPreviousRealMessageText(_messages[index].RealText, index - 1);
|
||||
|
||||
_messages[index].SetMessageRealText(message, false);
|
||||
_messages[index].SetMessageText(message, false, isAnswer);
|
||||
_messages[index].SetMessageRealText(realMessage, false, isAnswer);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -7,8 +7,7 @@ namespace Messaging.Typer {
|
|||
public class TextTyper {
|
||||
private readonly TMP_Text _textBox;
|
||||
|
||||
private static readonly Color32 Clear = new(0, 0, 0, 0);
|
||||
private const float SecondsPerCharacter = 1f / 60f;
|
||||
private const float SecondsPerCharacter = 0.07f;
|
||||
|
||||
public TextTyper(TMP_Text textBox) {
|
||||
_textBox = textBox;
|
||||
|
@ -18,63 +17,26 @@ namespace Messaging.Typer {
|
|||
float timeOfLastCharacter = 0;
|
||||
|
||||
TMP_TextInfo textInfo = _textBox.textInfo;
|
||||
foreach (TMP_MeshInfo meshInfer in textInfo.meshInfo) {
|
||||
if (meshInfer.vertices == null) continue;
|
||||
for (int j = 0; j < meshInfer.vertices.Length; j++) {
|
||||
meshInfer.vertices[j] = Vector3.zero;
|
||||
}
|
||||
}
|
||||
|
||||
_textBox.maxVisibleCharacters = 0;
|
||||
_textBox.text = processedMessage;
|
||||
_textBox.ForceMeshUpdate();
|
||||
|
||||
Color32[][] originalColors = new Color32[textInfo.meshInfo.Length][];
|
||||
for (int i = 0; i < originalColors.Length; i++) {
|
||||
Color32[] theColors = textInfo.meshInfo[i].colors32;
|
||||
originalColors[i] = new Color32[theColors.Length];
|
||||
Array.Copy(theColors, originalColors[i], theColors.Length);
|
||||
}
|
||||
int charCount = textInfo.characterCount;
|
||||
int visibleCharacterIndex = 0;
|
||||
while (true) {
|
||||
if (ShouldShowNextCharacter(SecondsPerCharacter, timeOfLastCharacter)) {
|
||||
if (visibleCharacterIndex <= charCount) {
|
||||
if (visibleCharacterIndex < charCount &&
|
||||
ShouldShowNextCharacter(SecondsPerCharacter, timeOfLastCharacter)) {
|
||||
visibleCharacterIndex++;
|
||||
timeOfLastCharacter = Time.unscaledTime;
|
||||
if (visibleCharacterIndex == charCount) {
|
||||
onFinish?.Invoke();
|
||||
}
|
||||
visibleCharacterIndex++;
|
||||
_textBox.maxVisibleCharacters = visibleCharacterIndex;
|
||||
timeOfLastCharacter = Time.unscaledTime;
|
||||
if (visibleCharacterIndex == charCount) {
|
||||
onFinish?.Invoke();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int j = 0; j < charCount; j++) {
|
||||
TMP_CharacterInfo charInfo = textInfo.characterInfo[j];
|
||||
if (!charInfo.isVisible) continue;
|
||||
|
||||
int vertexIndex = charInfo.vertexIndex;
|
||||
int materialIndex = charInfo.materialReferenceIndex;
|
||||
Color32[] destinationColors = textInfo.meshInfo[materialIndex].colors32;
|
||||
Color32 theColor = j < visibleCharacterIndex ? originalColors[materialIndex][vertexIndex] : Clear;
|
||||
destinationColors[vertexIndex + 0] = theColor;
|
||||
destinationColors[vertexIndex + 1] = theColor;
|
||||
destinationColors[vertexIndex + 2] = theColor;
|
||||
destinationColors[vertexIndex + 3] = theColor;
|
||||
}
|
||||
|
||||
_textBox.UpdateVertexData(TMP_VertexDataUpdateFlags.Colors32);
|
||||
for (int i = 0; i < textInfo.meshInfo.Length; i++) {
|
||||
TMP_MeshInfo theInfo = textInfo.meshInfo[i];
|
||||
theInfo.mesh.vertices = theInfo.vertices;
|
||||
_textBox.UpdateGeometry(theInfo.mesh, i);
|
||||
}
|
||||
|
||||
if (visibleCharacterIndex == charCount) {
|
||||
break;
|
||||
}
|
||||
|
||||
yield return null;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue