使用嵌套类作为 Unity3D 组​​件

Rab*_*820 2 c# inner-classes unity-game-engine unity-components

我使用的是 Unity 5.4.2f2 Personal,并且我编写了一个类似于以下内容的 C# 脚本:

using UnityEngine;
using System;

public class Outer : MonoBehaviour {

    // Some public outer fields

    public class Inner : MonoBehaviour {
        // Some public inner fields
    }

}
Run Code Online (Sandbox Code Playgroud)

我希望能够将Outer和附加Inner到场景中的游戏对象。不幸的是,Inner即使我添加了它,它也不会在 Unity Inspector 中显示为可用脚本[Serializable]。我知道很多人可能会说,如果我试图使嵌套类对外界可见,我的设置有问题,但为了这个问题,我只想知道这是否可以做到。即,有什么方法可以使嵌套类用作 Unity 组件吗?

der*_*ugo 5

这个答案是错误的

至少这只是半正确的:

好吧,是的,如果您的目标是通过检查器Add Component按钮使用和添加此组件,那么它不需要位于具有匹配类名的单独脚本文件中!

但是,如果您仅通过脚本在运行时添加该组件,那么您实际上可以做到这一点

Unity本身就是在组件中这样做的Dropdown(摘自用Rider反编译的源代码)

public class Dropdown : Selectable, IPointerClickHandler, ISubmitHandler, ICancelHandler
{
    protected internal class DropdownItem : MonoBehaviour, IPointerEnterHandler, ICancelHandler
    {
        ...
    }
    
    ...
}
Run Code Online (Sandbox Code Playgroud)

Selectable继承自UIBehaviour继承自MonoBehaviour

由于这种嵌套,运行时在检查器中看起来像这样

在此输入图像描述

但绝对有可能!

为了证明这一点,你可以轻松地做同样的事情,例如

public class TEST : MonoBehaviour
{
    private class NESTED : MonoBehaviour
    {
        [SerializeField] private int someInt;
        [SerializeField] private Transform someReference;
    }

    [ContextMenu("Add NESTED component")]
    private void AddNested()
    {
        gameObject.AddComponent<NESTED>();
    }
}
Run Code Online (Sandbox Code Playgroud)

因此,正如您所见,即使在播放模式之外的编辑时间,我也可以通过上下文菜单简单地添加这个“隐藏”组件

在此输入图像描述

并且它仍然是序列化的,并且在关闭并重新加载场景后仍然存在:

在此输入图像描述