是否可以阻止 Unity 在用户按下按钮后更改播放模式?
假设我有一个自定义编辑器,它可能具有无法正确序列化的状态;如果用户此时更改 Unity 编辑器模式,他们的更改将丢失。
这是一个完全摆脱不可序列化状态的选项,但这是完全不同的复杂性的任务。想避免这种情况。
上级:
我已经用下面的脚本测试了derHugo的答案:
using UnityEditor;
using UnityEngine;
namespace Innoactive.Hub.Training.Editors
{
[InitializeOnLoad]
public class ProveThatDudeWrongWindow : EditorWindow
{
private static ProveThatDudeWrongWindow windowInstance;
private string notSerializedString = "default";
static ProveThatDudeWrongWindow()
{
EditorApplication.playModeStateChanged += OnPlayModeStateChanged;
}
[MenuItem("Test/I'm damn sure he's wrong")]
private static void MenuItem()
{
if (windowInstance == null)
{
windowInstance = GetWindow<ProveThatDudeWrongWindow>();
}
windowInstance.notSerializedString = "some value";
}
[MenuItem("Test/Display current value")]
private static void DisplayCurrentNonSerializedValue()
{
windowInstance = GetWindow<ProveThatDudeWrongWindow>();
Debug.Log("string: " + windowInstance.notSerializedString);
}
private static void OnPlayModeStateChanged(PlayModeStateChange state)
{
if (state == PlayModeStateChange.ExitingEditMode)
{
EditorApplication.isPlaying = false;
}
Debug.Log("state: " + state);
}
}
}
然后我做了以下操作:
- 按
Test/I'm damn sure he's wrong
选项将非序列化值从default
值设置为some value
- 按
Test/Display current value
确保值已更改 - 按播放按钮
- 按
Test/Display current value
查看当前值。如果是default
,德雨果的解就行不通,如果是some value
,就行得通。
结果:德雨果很酷。
是的,我认为有
您可以注册EditorApplication.playModeStateChanged
看看我修改的文档中的示例:
using UnityEngine;
using UnityEditor;
public static class PlayModeStateChangedExample
{
private static void LogPlayModeState(PlayModeStateChange state)
{
Debug.Log(state);
}
public static void SetPlayModeEnabled(bool enabled)
{
//This is possible since you allways can remove
//a listener even if there is none so far
//This allways removes the listener making sure it is only added once
EditorApplication.playModeStateChanged -= LogPlayModeState;
if(!enabled)
{
EditorApplication.playModeStateChanged += LogPlayModeState;
}
}
}
现在剩下的就是将EditorApplication.isPlaying
重置回false
例如通过替换
Debug.Log(state);
跟
// This mode occures right before entering PlayMode
// and is the moment in which we want to intervene
if(state == PlayModeStateChange.ExitingEditMode)
{
EditorApplication.isPlaying = false;
}
以杀死播放模式。
因此,您可以从任何地方拨打电话,例如
PlayModeStateChangedExample.SetPlayModeEnabled(false);
但是,我不确定这是否会完全阻止序列化部分,因为它也在文档中声明
设置
isPlaying
会将结果延迟到此帧的所有脚本代码完成之后。