c# - 使用 UnityAction 传递参数

标签 c# unity3d

尝试发送一个 UnityAction 作为我的方法之一的参数,如下所示:

public void PopulateConversationList(string [] fullConversation, string onLastPagePrompt, string npcName, int stage, UnityAction action)
{
    conversations.Add(new Conversation(fullConversation, onLastPagePrompt, npcName, stage, action));
}

dialogHolder.PopulateConversationList(stage1, "Okay", _name, 1, QuestManager.Instance().ActivateQuest);

这工作正常,但现在我想将以下操作作为参数传递:

public void ActivateQuest(int questId)
{
    Debug.Log("This is the id: " + questId);
}

但是,当我使用具有参数的操作时,它将不起作用:

dialogHolder.PopulateConversationList(stage1, "Okay", _name, 1, QuestManager.Instance().ActivateQuest(2));

上面给出了错误:无法从 void 转换为 UnityAction。 如何传递带有参数的 UnityAction 作为参数?

我在对话中这样调用Action:

dialog.OnAccept(ConvList[i].onLastPagePrompt, () =>
{
    ConvList[i].action();
    dialog.Hide();
});

编辑:我最终采用的解决方案:

enter dialogHolder.PopulateConversationList(stage1, "Okay", _name, 1, () =>
    {
        QuestManager.Instance().ActivateQuest(0);
    });

这样我也可以调用几个方法。

最佳答案

问题是:

public void PopulateConversationList(string[] fullConversation, string onLastPagePrompt, string npcName, int stage, UnityAction action)

action argument 不接受任何参数,但您正在向它传递一个需要参数的函数:

public void ActivateQuest(int questId)
{
    Debug.Log("This is the id: " + questId);
}

与:

dialogHolder.PopulateConversationList(stage1, "Okay", _name, 1, QuestManager.Instance().ActivateQuest(2));

注意 2传递给了 ActivateQuest功能。


传递参数给UnityEvent并不像人们想象的那么简单。您必须派生自 UnityEvent并提供参数类型。在这种情况下,你想传递 int。您必须使用 int 创建一个从 UnityEvent 派生的类作为通用的。

public class IntUnityEvent : UnityEvent<int>{}

IntUnityEvent action然后可以在函数中将变量作为参数传递,而不是 UnityAction action .

下面提供了一个简化的通用解决方案,因此对其他人也有帮助。只需将您的其他参数添加到 PopulateConversationList功能,你应该很高兴去。评论很好。

[System.Serializable]
public class IntUnityEvent : UnityEvent<int>
{
    public int intParam;
}

public IntUnityEvent uIntEvent;

void Start()
{
    //Create the parameter to pass to the function
    if (uIntEvent == null)
        uIntEvent = new IntUnityEvent();

    //Add the function to call
    uIntEvent.AddListener(ActivateQuest);

    //Set the parameter value to use
    uIntEvent.intParam = 2;

    //Pass the IntUnityEvent/UnityAction to a function
    PopulateConversationList(uIntEvent);
}

public void PopulateConversationList(IntUnityEvent action)
{
    //Test/Call the function 
    action.Invoke(action.intParam);
}

//The function to call
public void ActivateQuest(int questId)
{
    Debug.Log("This is the id: " + questId);
}

注意:

如果可能,避免使用 UnityEvent在团结中。使用 C# Actiondelegate因为它们更易于使用。此外,它们比 Unity 的 UnityEvent 快得多。 .

关于c# - 使用 UnityAction 传递参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44615452/

相关文章:

c# - 如何将视频从网络摄像头流式传输到 IIS 媒体服务

c# - Webbrowser 控件在放置在 Outlook 加载项中时不接收 Tab/Delete/Back 键

c# - 发送 RPC 添加 playerName

c# - 如何统一输入字段的(删除/使不可见/更改颜色)边框?

java - Unity AndroidJavaObject 无法正常工作而不显示错误

c# - 围绕库包装 Web 服务

c# - UpdatePanel 中的 AddThis 控件 - 确保它们在异步回发后正确呈现

c# - 使用反射优化对象创建

c# - 有没有办法在 Unity 2D Light System 中隐藏处于阴影中的玩家?

android - 如何在 Android 设备上创建和读取日志?