与大多数应用程序框架一样,Unity 游戏在主 UI 线程上运行。因此,从异步任务更改 UI 元素不起作用,因为我们只需要从主线程调用 Unity 的 API,例如从方法和 IEnumerators 调用。方法和 IEnumerators 在主 UI 线程上运行。
Unity 也没有像 .Net 在 Xamarin.Forms (Device.BeginInvokeOnMainThread) 中那样提供调用主线程的方法。
为此,我们需要使用 MVVM 架构。 MVVM 代表模型-视图-视图模型。我们不需要导入任何东西,只需改变我们项目的工作方式。
默认情况下,Unity 使用单例方法,不提供任何应用程序构建
框架。因此,MVVM 更适合制作多功能游戏。使用 MVVM,我们可以通过拆分 UI 管理、我们的应用程序的逻辑和数据,通过拆分模型、视图和逻辑来标准化我们的代码。 MVVM 广泛用于跨平台应用程序开发。
在 MVVM 中,我们将控件(UI 组件)绑定到 ViewModel 中的属性,我们只更改 ViewModel 中的属性。然后 ViewModel 将这些属性更改通知给 View,因此这些更改反映在我们场景中的 UI 组件中。
创建一个 ViewModel 类
public class MainSceneViewModel : INotifyPropertyChanged
{
public string Title { get { return title; } set { title = value; OnPropertyChanged(nameof(Title)); } }
string title;
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged(string propertyName)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
在你的场景脚本中(附加到 Unity Inspector 中的游戏对象)。
public class MainSceneScript : MonoBehaviour
{
public Text SceneTitle; // Assign Text Component in Unity Inspector
MainSceneViewModel mainSceneViewModel = new MainSceneViewModel();
void Start()
{
mainSceneViewModel.PropertyChanged += ViewModelPropertyChanged;
DelayedTitleChange();
}
async void DelayedTitleChange()
{
await Task.Delay(2000);
mainSceneViewModel.Title = "This is the Main Scene";
}
// Will be called whenever a property of `MainSceneViewModel` is updated.
void ViewModelPropertyChanged(object sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == nameof(MainSceneViewModel.Title))
{
SceneTitle.text = mainSceneViewModel.Title;
}
}
// Clean up
void Dispose()
{
mainSceneViewModel.PropertyChanged -= ViewModelPropertyChanged;
}
}
我们还可以使用模型并通知该模型的属性更改。