是否可以将变量类型返回到调用协程的脚本?

时间:2018-05-03 18:29:59

标签: c# unity3d

好吧,我的游戏中有一个对话系统。它的设计非常简单。每个对话包含一个节点列表,这些节点将是NPC会说的,并且对于每个节点,还有一个选项列表,玩家可以从中选择结束对话或继续。对话部分完美无缺。我想要做的是将它与任务系统结合起来。在我进入我的探索系统之前,我需要找到一种方法将我的对话系统连接到我的任务系统或NPC(最好是我的NPC)。我的对话系统的设置方式是使用Singleton模式,每个NPC只会在其上调用一个方法,根据其本地对话变量开始与玩家对话。

我一直坐在这里思考如何将对话管理器中的值传递给我的NPC,但考虑到我的run方法是一个Coroutine,我无法弄清楚如何返回该值如果需要,我退出协程。我觉得这应该是可能的,但我真的想不出办法做到这一点。任何帮助,将不胜感激。

理想的情况是让RunDialogue方法返回变量类型(bool?),但只能在EndDialogue方法中调用run之后。如果它返回true,则分配任务,否则什么都不做。

来自DialogueManager:

public void RunDialogue(Dialogue dia)
{
    StartCoroutine(run(dia));
}

IEnumerator run(Dialogue dia)
{
    DialoguePanel.SetActive(true);

    //start the convo
    int node_id = 0;

    //if the node is equal to -1 end the conversation
    while (node_id != -1)
    {
        //display the current node
        DisplayNode(dia.Nodes[node_id]);

        //reset the selected option
        selected_option = -2;

        //wait here until a selection is made by button click
        while (selected_option == -2)
        {
            yield return new WaitForSeconds(0.25f);
        }

        //get the new id since it has changed
        node_id = selected_option;

    }

    //the user exited the conversation
    EndDialogue();

}

来自NPC:

public override void Interact()
{
    DialogueManager.Instance.RunDialogue(dialogue);
}

1 个答案:

答案 0 :(得分:4)

有一种方法可以让coroutine返回一个值。需要一些嵌套,如果你想这样做,你可以看看这个视频:Unite 2013 - Extending Coroutines @ 20m38s on "adding return values"

否则,您可以将回调传递给协同程序。这可能会为你做。

在有意义的地方添加一些功能(例如NPC):

public void OnGiveQuest()
{
    // Add the quest
}

将其添加到对话中:

public override void Interact()
{
    DialogueManager.Instance.RunDialogue(dialogue, OnGiveQuest);
}

然后更改您的RunDialoguerun以进行回调:

public void RunDialogue(Dialogue dia, System.Action callback = null)
{
    StartCoroutine(run(dia, callback));
}

现在,对于协同程序,您可以将回调进一步传递给EndDialogue,也可以在结束调用后在此处理它。

IEnumerator run(Dialogue dia, System.Action callback = null)
{
    ...

    //the user exited the conversation
    EndDialogue();

    if(callback != null)
        callback();
}

现在,如果你想开始一个任务,我只会添加回调。否则你只需将其保留(默认值为null)。