我创建了一个足球比分计算器。我有一个可以更改场景的按钮,但是当我更改场景并重新打开它时,得分值将重置为0。这是代码:
public class Main : MonoBehaviour {
public Text plusUp;
public int value = 0;
public void button(int sc)
{
SceneManager.LoadScene(sc);
}
public void plus()
{
value++;
plusUp.text = value.ToString();
}
}
答案 0 :(得分:4)
1。。您可以在包含要保存的变量的对象上使用方法Object.DontDestroyOnLoad
。加载另一个场景时,它将使GameObject
这个脚本的附加内容仍然有效:
void Awake()
{
DontDestroyOnLoad(this.gameObject);
}
有关更多信息,请参见documentation
您也可以制作一个Singleton,但是这种设计模式稍微复杂一点,因为在加载另一个场景时Unity会破坏它。您仍然必须使用DontDestroyOnLoad
来了解如何在他们的GitHub page上实现此模式
2。。或者,您可以在加载另一个场景之前将值保存在磁盘上,然后使用PlayerPrefs
帮助方法加载该值:
public int value = 0;
void Awake()
{
//Load the saved score (this value will be saved even if you restart the app)
value = PlayerPrefs.GetInt("Score");
}
public void button1(int sc)
{
//Save your value before you load the scene
PlayerPrefs.SetInt("Score", value);
SceneManager.LoadScene(sc);
}
有关类型的更多信息,请参见documentation。
答案 1 :(得分:4)
有一些核心概念对理解这个问题很有用。
作用域:每个场景都在其自己的作用域中运行。一个场景中发生的任何变量,对象或更改都不会自动转移到另一场景。启动场景时,场景中的所有对象都被实例化和初始化,并且如果它们是Monobehaviours,则调用它们的Awake()/ Start()方法。
初始化-实例化对象时,将使用构造函数或默认值对其进行初始化。 Monobehaviours没有构造函数,因此任何变量都将推迟回默认值。
数据持久性-更改场景时,先前场景中的所有游戏对象都将被销毁,而新场景中的所有对象都将被实例化和初始化。由于先前场景中的所有对象都被破坏,因此在这些对象上设置的所有值都将消失。您可以使用DoNotDestroyOnLoad()防止销毁GameObject,但这不会覆盖新场景中定义的对象。通常不建议将DoNotDestroyOnLoad()用作游戏逻辑的核心部分,因为它通常会导致场景相互依赖(场景1必须定义GameObject的值并将其传递给场景2,可用” =不良做法)。
您似乎想不考虑场景而将分数保留为一个值。由于所有GameObjects和Monobehaviours都位于场景中,因此您可以:
使用Singleton pattern强制将对象逼近场景。
每当得分数据变化时将分数数据存储到文件中,并通过Start()方法从该文件中读取。
我推荐的方法:使用ScriptableObject来保存分数,并在更改分数和更新游戏对象时刷新该对象。 ScriptableObjects在项目级别作用域,因此它们会在场景之间自动保留。