【问题标题】:Undo removal of GameObject with AddComponent script in Unity Editor (Play mode)在 Unity 编辑器中使用 AddComponent 脚本撤消移除 GameObject(播放模式)
【发布时间】:2016-05-03 05:51:13
【问题描述】:

这是一个我一直在努力回答的非常具体的问题。我有一个简单的脚本,可以在运行时唤醒/销毁期间创建/销毁组件:

// Simple script that creates and destroys an AudioSource component in runtime.
public class SimpleScript : MonoBehaviour {
  // Runtime AudioSource component to be used.
  private AudioSource source = null;

  void Awake() {
    source = gameObject.AddComponent<AudioSource>();
    source.hideFlags = HideFlags.HideAndDontSave;
  }

  void OnDestroy() {
    Destroy(source);
  }

  void Update() {
    // Do stuff with |source| . . .
  }
}

它在构建导出和所有东西上都可以正常工作,但是,我最近注意到一个非常特殊的情况,Unity 的行为有点奇怪。在 Unity 编辑器(播放模式)中,如果我删除此脚本(或脚本附加到的游戏对象),然后撤消该操作,则会导致两个 AudioSources 附加到复活的游戏对象。进一步来说;一个由我的脚本先前使用删除操作销毁+ 一个使用新的Awake 调用创建。正如预期的那样,重复执行此操作会产生越来越多的泄露组件。

使用不同的HideFlags 来禁用(?)序列化似乎没有任何好处,也没有尝试使用DestroyImmediate 等来破坏组件。我在这里的理解是,Unity 将手动创建的组件视为GameObject 的组件之一,因此在撤消脚本删除的同时注册销毁并撤消它。

关于如何绕过/避免 Unity 这种奇怪行为的任何建议?

干杯!

【问题讨论】:

  • 如果您要重新创建游戏对象,为什么不禁用并重新启用它?
  • 这里的问题是你一开始没有这个组件,也就是说,你必须在脚本的某个地方创建它,以便你可以启用/禁用它。 :)

标签: c# unity3d editor undo-redo


【解决方案1】:

你自己回答了你的问题,@anokta! Awake() 方法创建一个 AudioSource——即每次创建拥有的游戏对象时都会创建它。 现在,当您手动从层次视图中删除对象(即单击 > 删除等),然后 撤消 它时,您正在调用一个纯粹的编辑器机制来重新创建最后一次删除。这实际上将重新创建存在的对象(添加了AudioSource 的游戏对象)。而且因为现在这是一个已创建的新对象,它会自动立即再次执行其Awake() 方法。

我确定您已经知道这一点,并且可能正在寻找解决方法。在运行时手动删除编辑器中的对象是一个棘手的领域,并且可以创建无穷无尽的奇怪行为。

如果您真的想限制它,如何在其他地方(也许在全局管理器中)设置一个标志,一旦调用AddComponent&lt;AudioSource&gt;(); 就会打开?即

void Awake() {
    if (globalManager.AsCreated != true)
    {
        source = gameObject.AddComponent<AudioSource>();
        source.hideFlags = HideFlags.HideAndDontSave;
        globalManager.AsCreated = true;
    }
}

globalManager 是……某种全球经理。这样,您可以在运行时删除该对象(我仍然断言这会导致无穷无尽的奇怪行为)并且仍然可以撤消您想要的结果。 希望对您有所帮助!

【讨论】:

  • 遗憾地同意了,也许让这种情况发生是好的。我猜当涉及多个实例等时,全局标志解决方法可能会变得混乱。除此之外,我现在能想到的另一种解决方法是在添加组件之前检查 GetComponent。当然,这将限制我们每个游戏对象只有一个组件 - IMO 更okay。 :)
猜你喜欢
  • 1970-01-01
  • 2023-03-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-08-24
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多