Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Announcements, support questions, and discussion for the Dialogue System.
xyztankman
Posts: 54
Joined: Mon Jun 21, 2021 7:48 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by xyztankman »

Tony Li wrote: Wed Jan 10, 2024 12:56 pm The Dialogue System uses Unity to call OnConversationStart(Transform) through reflection, so to the code editor it may appear as if it won't be used. If you click on the error in the Console window, the bottom of the Console will show the stack trace, which is the order of method calls. In the error, is SetTypewriterSpeed being called from OnConversationStart?

To verify whether it's finding the currentUI, you could change it to:

Code: Select all

private void OnConversationStart(Transform actor)
{
    // When a conversation starts, record the dialogue UI it's using and set its typewriter speeds:
    currentUI = DialogueManager.instance.activeConversation.conversationView.dialogueUI as StandardDialogueUI;
    if (currentUI == null) Debug.Log("Could not find the dialogue UI to set currentUI.");
    SetTypewriterSpeed(typewriterSpeed);
}
Full stack trace below, no debug message when clicked. I separated minSubtitleSeconds and made it a separate function, oddly there is no error message and the changed seconds works:

I only get the error when SetTypewriterSpeed is listed

Code: Select all

public void DialogueSetFastSpeed()
{
    DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 120;
    SetTypewriterSpeed(120);
}

Code: Select all

public void DialogueSetMinSubSpeed1()
{
    DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 1;
}

Code: Select all

NullReferenceException: Object reference not set to an instance of an object
SettingManager.SetTypewriterSpeed (System.Single speed) (at Assets/Scripts/MenuScripts/SettingManager.cs:586)
SettingManager.DialogueSetSlowSpeed () (at Assets/Scripts/MenuScripts/SettingManager.cs:601)
UnityEngine.Events.InvokableCall.Invoke () (at <6c9b376c3fca40b787e8c1a2133bf243>:0)
UnityEngine.Events.UnityEvent.Invoke () (at <6c9b376c3fca40b787e8c1a2133bf243>:0)
UnityEngine.UI.Button.Press () (at ./Library/PackageCache/com.unity.ugui@1.0.0/Runtime/UI/Core/Button.cs:70)
UnityEngine.UI.Button.OnPointerClick (UnityEngine.EventSystems.PointerEventData eventData) (at ./Library/PackageCache/com.unity.ugui@1.0.0/Runtime/UI/Core/Button.cs:114)
UnityEngine.EventSystems.ExecuteEvents.Execute (UnityEngine.EventSystems.IPointerClickHandler handler, UnityEngine.EventSystems.BaseEventData eventData) (at ./Library/PackageCache/com.unity.ugui@1.0.0/Runtime/EventSystem/ExecuteEvents.cs:57)
UnityEngine.EventSystems.ExecuteEvents.Execute[T] (UnityEngine.GameObject target, UnityEngine.EventSystems.BaseEventData eventData, UnityEngine.EventSystems.ExecuteEvents+EventFunction`1[T1] functor) (at ./Library/PackageCache/com.unity.ugui@1.0.0/Runtime/EventSystem/ExecuteEvents.cs:272)
UnityEngine.EventSystems.EventSystem:Update() (at ./Library/PackageCache/com.unity.ugui@1.0.0/Runtime/EventSystem/EventSystem.cs:530)
User avatar
Tony Li
Posts: 22112
Joined: Thu Jul 18, 2013 1:27 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by Tony Li »

Are you calling DialogueSetSlowSpeed() while a conversation is active?

If it's possible that you might be calling DialogueSetSlowSpeed() when no conversation is active, change the method to:

Code: Select all

private void SetTypewriterSpeed(float speed)
{
    typewriterSpeed = speed;
    if (currentUI != null)
    {
        foreach (var subtitlePanel in currentUI.conversationUIElements.subtitlePanels)
        {
            subtitlePanel.SetTypewriterSpeed(speed);
        }
    }
}
xyztankman
Posts: 54
Joined: Mon Jun 21, 2021 7:48 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by xyztankman »

Tony Li wrote: Wed Jan 10, 2024 1:18 pm Are you calling DialogueSetSlowSpeed() while a conversation is active?

If it's possible that you might be calling DialogueSetSlowSpeed() when no conversation is active, change the method to:

Code: Select all

private void SetTypewriterSpeed(float speed)
{
    typewriterSpeed = speed;
    if (currentUI != null)
    {
        foreach (var subtitlePanel in currentUI.conversationUIElements.subtitlePanels)
        {
            subtitlePanel.SetTypewriterSpeed(speed);
        }
    }
}
Yes I was calling DialogueSetSlowSpeed() without a conversation active, I was using it as a button to start a conversation to show the new speed. Here's a screenshot of the button setup. DialogueTest is the override.
TextSpeed_Button.PNG
TextSpeed_Button.PNG (64.33 KiB) Viewed 123926 times
No longer an error message, but the speed of the text doesn't seem to be updating for the buttons. Gif linked below as well

https://media.giphy.com/media/v1.Y2lkPT ... /giphy.gif
User avatar
Tony Li
Posts: 22112
Joined: Thu Jul 18, 2013 1:27 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by Tony Li »

Add [SerializeField] to the front of typewriterSpeed:

Code: Select all

[SerializeField] private float typewriterSpeed = 90;
This way you can see its value in the inspector. Then play the scene and keep the GameObject with this script selected so you can watch the value. When you click the button, does typewriterSpeed change?

If so, then the OnConversationStart() method should update the typewriter speeds of all subtitle panels assigned to the current dialogue UI's Subtitle Panels list. (Remember from my earlier post that it doesn't touch other subtitle panels, such as if a Dialogue Actor points to a bubble subtitle panel. You'll need to extend the script further if you need to do that.)
xyztankman
Posts: 54
Joined: Mon Jun 21, 2021 7:48 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by xyztankman »

Tony Li wrote: Wed Jan 10, 2024 2:02 pm Add [SerializeField] to the front of typewriterSpeed:

Code: Select all

[SerializeField] private float typewriterSpeed = 90;
This way you can see its value in the inspector. Then play the scene and keep the GameObject with this script selected so you can watch the value. When you click the button, does typewriterSpeed change?

If so, then the OnConversationStart() method should update the typewriter speeds of all subtitle panels assigned to the current dialogue UI's Subtitle Panels list. (Remember from my earlier post that it doesn't touch other subtitle panels, such as if a Dialogue Actor points to a bubble subtitle panel. You'll need to extend the script further if you need to do that.)
Confirmed that the TypewriterSpeed is changing correctly when shown in [SerializeField], although still not seeing a change in the actual dialogue. Could this be a problem with my UI prefab? I removed the PC and response menus as there is only an NPC dialogue that plays.
DialogueTestPrefab.PNG
DialogueTestPrefab.PNG (89.81 KiB) Viewed 123908 times
User avatar
Tony Li
Posts: 22112
Joined: Thu Jul 18, 2013 1:27 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by Tony Li »

Hi,

Your script is on the Dialogue Manager GameObject, correct? (I believe I mentioned that, but just checking in case you missed it.) It will only run OnConversationStart if it's on the Dialogue Manager or one of the participants.

If you don't want the script to be on the Dialogue Manager, you can use the DialogueManager.instance.conversationStarted C# event instead. Here's an example scene:

DS_TypewriterSpeedExample_2024-01-10.unitypackage

And here's an example script:

Code: Select all

using UnityEngine;
using PixelCrushers.DialogueSystem;

public class TypewriterSpeedManager : MonoBehaviour
{
    [SerializeField] private float typewriterSpeed = 90;

    private StandardDialogueUI currentUI;

    private void Start()
    {
        DialogueManager.instance.conversationStarted += OnConversationStarted;
    }

    private void OnDestroy()
    {
        DialogueManager.instance.conversationStarted -= OnConversationStarted;
    }

    private void OnConversationStarted(Transform actor)
    {
        // When a conversation starts, record the dialogue UI it's using and set its typewriter speeds:
        currentUI = DialogueManager.instance.activeConversation.conversationView.dialogueUI as StandardDialogueUI;
        SetTypewriterSpeed(typewriterSpeed);
    }

    private void SetTypewriterSpeed(float speed)
    {
        typewriterSpeed = speed;
        if (currentUI != null)
        {
            foreach (var subtitlePanel in currentUI.conversationUIElements.subtitlePanels)
            {
                subtitlePanel.SetTypewriterSpeed(speed);
            }
        }
    }

    public void SetFastSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 120;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(120);
    }

    public void SetNormalSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 90;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(90);
    }

    public void SetSlowSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 20;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(20);
    }
}
xyztankman
Posts: 54
Joined: Mon Jun 21, 2021 7:48 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by xyztankman »

Tony Li wrote: Wed Jan 10, 2024 2:51 pm Hi,

Your script is on the Dialogue Manager GameObject, correct? (I believe I mentioned that, but just checking in case you missed it.) It will only run OnConversationStart if it's on the Dialogue Manager or one of the participants.

If you don't want the script to be on the Dialogue Manager, you can use the DialogueManager.instance.conversationStarted C# event instead. Here's an example scene:

DS_TypewriterSpeedExample_2024-01-10.unitypackage

And here's an example script:

Code: Select all

using UnityEngine;
using PixelCrushers.DialogueSystem;

public class TypewriterSpeedManager : MonoBehaviour
{
    [SerializeField] private float typewriterSpeed = 90;

    private StandardDialogueUI currentUI;

    private void Start()
    {
        DialogueManager.instance.conversationStarted += OnConversationStarted;
    }

    private void OnDestroy()
    {
        DialogueManager.instance.conversationStarted -= OnConversationStarted;
    }

    private void OnConversationStarted(Transform actor)
    {
        // When a conversation starts, record the dialogue UI it's using and set its typewriter speeds:
        currentUI = DialogueManager.instance.activeConversation.conversationView.dialogueUI as StandardDialogueUI;
        SetTypewriterSpeed(typewriterSpeed);
    }

    private void SetTypewriterSpeed(float speed)
    {
        typewriterSpeed = speed;
        if (currentUI != null)
        {
            foreach (var subtitlePanel in currentUI.conversationUIElements.subtitlePanels)
            {
                subtitlePanel.SetTypewriterSpeed(speed);
            }
        }
    }

    public void SetFastSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 120;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(120);
    }

    public void SetNormalSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 90;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(90);
    }

    public void SetSlowSpeed()
    {
        DialogueManager.displaySettings.subtitleSettings.subtitleCharsPerSecond = 20;
        DialogueManager.displaySettings.subtitleSettings.minSubtitleSeconds = 5;
        SetTypewriterSpeed(20);
    }
}
ok now we're in business! I did have it on my own SettingsManager script but after moving it to the DialogueSystemController script it is working! Confirmed after changing scenes.

Thanks a bunch for your help again Tony!
User avatar
Tony Li
Posts: 22112
Joined: Thu Jul 18, 2013 1:27 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by Tony Li »

Glad to help!
brucezubaa
Posts: 1
Joined: Tue Jan 16, 2024 9:17 am

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by brucezubaa »

I was thinking that the ResetDatabase() was also clearing the typewriter settings because there wasn't a change on my end but it may be something in one of my other scenes that is causing the issue.
xyztankman
Posts: 54
Joined: Mon Jun 21, 2021 7:48 pm

Re: Set Dialogue System text speed/typerwriter effect via functions for all dialogues

Post by xyztankman »

Yes I was thinking that too, I did switch to the ResetGameState() and that seems to be working so far along with having the script directly on the dialogue manager.
Post Reply