|
|
|
@ -8,22 +8,22 @@ namespace Fungus
|
|
|
|
|
{ |
|
|
|
|
public class ConversationManager |
|
|
|
|
{ |
|
|
|
|
protected Character[] characters; |
|
|
|
|
|
|
|
|
|
protected Character currentCharacter; |
|
|
|
|
protected Sprite currentPortrait; |
|
|
|
|
protected RectTransform currentPosition; |
|
|
|
|
protected struct ConversationItem |
|
|
|
|
{ |
|
|
|
|
public string Text { get; set; } |
|
|
|
|
public Character Character { get; set; } |
|
|
|
|
public Sprite Portrait { get; set; } |
|
|
|
|
public RectTransform Position { get; set; } |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
protected Character previousCharacter; |
|
|
|
|
protected Sprite previousPortrait; |
|
|
|
|
protected RectTransform previousPosition; |
|
|
|
|
protected Character[] characters; |
|
|
|
|
|
|
|
|
|
protected bool exitSayWait; |
|
|
|
|
|
|
|
|
|
public ConversationManager () |
|
|
|
|
{ |
|
|
|
|
// cache characters for faster lookup |
|
|
|
|
characters = GameObject.FindObjectsOfType<Fungus.Character>(); |
|
|
|
|
characters = UnityEngine.Object.FindObjectsOfType<Character>(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
protected Stage GetActiveStage() |
|
|
|
@ -41,7 +41,7 @@ namespace Fungus
|
|
|
|
|
/// Parse and execute a conversation string |
|
|
|
|
/// </summary> |
|
|
|
|
/// <param name="conv"></param> |
|
|
|
|
public IEnumerator Conversation(string conv) |
|
|
|
|
public IEnumerator DoConversation(string conv) |
|
|
|
|
{ |
|
|
|
|
if (string.IsNullOrEmpty(conv)) |
|
|
|
|
{ |
|
|
|
@ -55,53 +55,50 @@ namespace Fungus
|
|
|
|
|
yield break; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
//find SimpleScript say strings with portrait options |
|
|
|
|
//You can test regex matches here: http://regexstorm.net/tester |
|
|
|
|
Regex sayRegex = new Regex(@"((?<sayParams>[\w ,]*):)?(?<text>.*\r*\n)"); |
|
|
|
|
MatchCollection sayMatches = sayRegex.Matches(conv); |
|
|
|
|
var conversationItems = ParseConversation(conv); |
|
|
|
|
|
|
|
|
|
for (int i = 0; i < sayMatches.Count; i++) |
|
|
|
|
{ |
|
|
|
|
previousCharacter = currentCharacter; |
|
|
|
|
previousPortrait = currentPortrait; |
|
|
|
|
previousPosition = currentPosition; |
|
|
|
|
// Play the conversation |
|
|
|
|
|
|
|
|
|
string sayParams = sayMatches[i].Groups["sayParams"].Value; |
|
|
|
|
if (!string.IsNullOrEmpty(sayParams)) |
|
|
|
|
{ |
|
|
|
|
string[] separateParams; |
|
|
|
|
if (sayParams.Contains(",")) |
|
|
|
|
Character currentCharacter = null; |
|
|
|
|
Sprite currentPortrait = null; |
|
|
|
|
RectTransform currentPosition = null; |
|
|
|
|
|
|
|
|
|
Character previousCharacter = null; |
|
|
|
|
Sprite previousPortrait = null; |
|
|
|
|
RectTransform previousPosition = null; |
|
|
|
|
|
|
|
|
|
for (int i = 0; i < conversationItems.Count; ++i) |
|
|
|
|
{ |
|
|
|
|
separateParams = sayParams.Split(','); |
|
|
|
|
for (int j = 0; j < separateParams.Length; j++) |
|
|
|
|
ConversationItem item = conversationItems[i]; |
|
|
|
|
|
|
|
|
|
if (item.Character != null) |
|
|
|
|
{ |
|
|
|
|
separateParams[j] = separateParams[j].Trim(); |
|
|
|
|
currentCharacter = item.Character; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
|
|
|
|
|
if (item.Portrait != null) |
|
|
|
|
{ |
|
|
|
|
separateParams = sayParams.Split(' '); |
|
|
|
|
currentPortrait = item.Portrait; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
SetParams(separateParams); |
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
if (item.Position != null) |
|
|
|
|
{ |
|
|
|
|
//no params! Use previous settings? |
|
|
|
|
currentPosition = item.Position; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
string text = sayMatches[i].Groups["text"].Value; |
|
|
|
|
|
|
|
|
|
sayDialog.gameObject.SetActive(true); |
|
|
|
|
|
|
|
|
|
if (currentCharacter != null && currentCharacter != previousCharacter) |
|
|
|
|
if (currentCharacter != null && |
|
|
|
|
currentCharacter != previousCharacter) |
|
|
|
|
{ |
|
|
|
|
sayDialog.SetCharacter(currentCharacter); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
Stage stage = GetActiveStage(); |
|
|
|
|
|
|
|
|
|
if (stage != null && currentCharacter != null && (currentPortrait != previousPortrait || currentPosition != previousPosition)) |
|
|
|
|
if (stage != null && |
|
|
|
|
currentCharacter != null && |
|
|
|
|
(currentPortrait != previousPortrait || currentPosition != previousPosition)) |
|
|
|
|
{ |
|
|
|
|
PortraitOptions portraitOptions = new PortraitOptions(true); |
|
|
|
|
portraitOptions.character = currentCharacter; |
|
|
|
@ -112,14 +109,18 @@ namespace Fungus
|
|
|
|
|
stage.Show(portraitOptions); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
previousCharacter = currentCharacter; |
|
|
|
|
previousPortrait = currentPortrait; |
|
|
|
|
previousPosition = currentPosition; |
|
|
|
|
|
|
|
|
|
// Ignore Lua style comments and blank lines |
|
|
|
|
if (text.StartsWith("--") || text.Trim() == "") |
|
|
|
|
if (item.Text.StartsWith("--") || item.Text.Trim() == "") |
|
|
|
|
{ |
|
|
|
|
continue; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
exitSayWait = false; |
|
|
|
|
sayDialog.Say(text, true, true, true, false, null, () => { |
|
|
|
|
sayDialog.Say(item.Text, true, true, true, false, null, () => { |
|
|
|
|
exitSayWait = true; |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
@ -129,7 +130,49 @@ namespace Fungus
|
|
|
|
|
} |
|
|
|
|
exitSayWait = false; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
protected virtual List<ConversationItem> ParseConversation(string conv) |
|
|
|
|
{ |
|
|
|
|
//find SimpleScript say strings with portrait options |
|
|
|
|
//You can test regex matches here: http://regexstorm.net/tester |
|
|
|
|
Regex sayRegex = new Regex(@"((?<sayParams>[\w ,]*):)?(?<text>.*\r*\n)"); |
|
|
|
|
MatchCollection sayMatches = sayRegex.Matches(conv); |
|
|
|
|
|
|
|
|
|
var items = new List<ConversationItem>(sayMatches.Count); |
|
|
|
|
|
|
|
|
|
Character currentCharacter = null; |
|
|
|
|
for (int i = 0; i < sayMatches.Count; i++) |
|
|
|
|
{ |
|
|
|
|
string text = sayMatches[i].Groups["text"].Value; |
|
|
|
|
string sayParams = sayMatches[i].Groups["sayParams"].Value; |
|
|
|
|
string[] separateParams = null; |
|
|
|
|
|
|
|
|
|
if (!string.IsNullOrEmpty(sayParams)) |
|
|
|
|
{ |
|
|
|
|
if (sayParams.Contains(",")) |
|
|
|
|
{ |
|
|
|
|
separateParams = sayParams.Split(','); |
|
|
|
|
for (int j = 0; j < separateParams.Length; j++) |
|
|
|
|
{ |
|
|
|
|
separateParams[j] = separateParams[j].Trim(); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
{ |
|
|
|
|
separateParams = sayParams.Split(' '); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
var item = CreateConversationItem(separateParams, text, currentCharacter); |
|
|
|
|
|
|
|
|
|
// Previous speaking character is the default for next conversation item |
|
|
|
|
currentCharacter = item.Character; |
|
|
|
|
|
|
|
|
|
items.Add(item); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
return items; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/// <summary> |
|
|
|
@ -137,48 +180,55 @@ namespace Fungus
|
|
|
|
|
/// set the current character, position and portrait if provided. |
|
|
|
|
/// </summary> |
|
|
|
|
/// <param name="sayParams">The list of say parameters</param> |
|
|
|
|
private void SetParams(string[] sayParams) |
|
|
|
|
protected virtual ConversationItem CreateConversationItem(string[] sayParams, string text, Character currentCharacter) |
|
|
|
|
{ |
|
|
|
|
var item = new ConversationItem(); |
|
|
|
|
|
|
|
|
|
// Populate the story text to be written |
|
|
|
|
item.Text = text; |
|
|
|
|
|
|
|
|
|
if (sayParams == null || sayParams.Length == 0) |
|
|
|
|
{ |
|
|
|
|
Character character = null; |
|
|
|
|
Sprite portrait = null; |
|
|
|
|
RectTransform position = null; |
|
|
|
|
// Text only, no params - early out. |
|
|
|
|
return item; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// try to find the character first, since we need to get its portrait |
|
|
|
|
// try to find the character param first, since we need to get its portrait |
|
|
|
|
int characterIndex = -1; |
|
|
|
|
for (int i = 0; character == null && i < sayParams.Length; i++) |
|
|
|
|
for (int i = 0; item.Character == null && i < sayParams.Length; i++) |
|
|
|
|
{ |
|
|
|
|
for (int j = 0; j < characters.Length; j++) |
|
|
|
|
{ |
|
|
|
|
if (characters[j].NameStartsWith(sayParams[i])) |
|
|
|
|
{ |
|
|
|
|
characterIndex = i; |
|
|
|
|
character = characters[j]; |
|
|
|
|
item.Character = characters[j]; |
|
|
|
|
break; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// Assume last used character if none is specified now |
|
|
|
|
if (character == null) |
|
|
|
|
if (item.Character == null) |
|
|
|
|
{ |
|
|
|
|
character = currentCharacter; |
|
|
|
|
item.Character = currentCharacter; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// Next see if we can find a portrait for this character |
|
|
|
|
int portraitIndex = -1; |
|
|
|
|
if (character != null) |
|
|
|
|
if (item.Character != null) |
|
|
|
|
{ |
|
|
|
|
for (int i = 0; i < sayParams.Length; i++) |
|
|
|
|
{ |
|
|
|
|
if (portrait == null && |
|
|
|
|
character != null && |
|
|
|
|
if (item.Portrait == null && |
|
|
|
|
item.Character != null && |
|
|
|
|
i != characterIndex) |
|
|
|
|
{ |
|
|
|
|
Sprite s = character.GetPortrait(sayParams[i]); |
|
|
|
|
Sprite s = item.Character.GetPortrait(sayParams[i]); |
|
|
|
|
if (s != null) |
|
|
|
|
{ |
|
|
|
|
portraitIndex = i; |
|
|
|
|
portrait = s; |
|
|
|
|
item.Portrait = s; |
|
|
|
|
break; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
@ -194,26 +244,13 @@ namespace Fungus
|
|
|
|
|
if (i != characterIndex && |
|
|
|
|
i != portraitIndex) |
|
|
|
|
{ |
|
|
|
|
position = stage.GetPosition(sayParams[i]); |
|
|
|
|
item.Position = stage.GetPosition(sayParams[i]); |
|
|
|
|
break; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (character != null) |
|
|
|
|
{ |
|
|
|
|
currentCharacter = character; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (portrait != null) |
|
|
|
|
{ |
|
|
|
|
currentPortrait = portrait; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (position != null) |
|
|
|
|
{ |
|
|
|
|
currentPosition = position; |
|
|
|
|
} |
|
|
|
|
return item; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |