Unity-передача данных между сценами
Как я могу передать значение из одной сцены в другую?
Я пробовал следующие:
сцена первая:
void Start () {
score = 0;
updateScoreView ();
StartCoroutine (DelayLoadlevel(20));
}
public void updateScoreView(){
score_text.text = "The Score: "+ score;
}
public void AddNewScore(int NewscoreValue){
score = score + NewscoreValue;
updateScoreView ();
}
IEnumerator DelayLoadlevel(float seconds){
yield return new WaitForSeconds(10);
secondsLeft = seconds;
loadingStart = true;
do {
yield return new WaitForSeconds(1);
} while(--secondsLeft >0);
// here I should store my last score before move to level two
PlayerPrefs.SetInt ("player_score", score);
Application.LoadLevel (2);
}
Сцена вторая:
public Text score_text;
private int old_score;
// Use this for initialization
void Start () {
old_score = PlayerPrefs.GetInt ("player_score");
score_text.text = "new score" + old_score.ToString ();
}
но ничего не отображается на экране, и нет никакой ошибки.
это правильный способ передачи данных ?
Я использую Unity 5 free edition, разрабатываю игру для Gear VR (то есть игра будет работать на устройствах android).
любой предложение?
2 ответов
кроме playerPrefs еще один грязный способ-сохранить объект во время загрузки уровня, вызвав DontDestroyOnLoad на нем.
DontDestroyOnLoad (transform.gameObject);
любой скрипт, прикрепленный к игровому объекту, выживет, а также переменные в скрипте. Функция DontDestroyOnLoad обычно используется для сохранения всего GameObject, включая компоненты, прикрепленные к нему, и любые дочерние объекты в иерархии.
вы можете создать пустой GameObject и разместить только скрипт, содержащий переменные, которые вы хотите сохранить на нем.
здесь 3 способы сделать это, но решение этого зависит от типа данных, которые вы хотите передать между сценами. Компоненты / скрипты и GameObjects уничтожаются при загрузке новой сцены и даже если они помечены как static
.
1. Используйте static
ключевое слово.
используйте этот метод, если переменная для перехода к следующей сцене не является компонентом, делает не наследовать от MonoBehaviour
и не GameObject затем сделайте переменную static
.
встроенные примитивные типы данных, такие как int
, bool
, string
, float
, double
. Все эти переменные можно сделать static
переменной.
пример встроенных примитивных типов данных, которые can отметить как static:
static int counter = 0;
static bool enableAudio = 0;
static float timer = 100;
они должны работать без проблем.
пример объектов, которые can будет помечен как static:
public class MyTestScriptNoMonoBehaviour
{
}
затем
static MyTestScriptNoMonoBehaviour testScriptNoMono;
void Start()
{
testScriptNoMono = new MyTestScriptNoMonoBehaviour();
}
обратите внимание, что класс не наследует от MonoBehaviour
. Это должно сработать.
пример объектов, которые не может отметить как static:
все, что наследуется от Object
, Component
или GameObject
будет не работа.
1A.Все, что наследуется от MonoBehaviour
public class MyTestScript : MonoBehaviour
{
}
затем
static MyTestScript testScript;
void Start()
{
testScript = gameObject.AddComponent<MyTestScript>();
}
это не работа, потому что она наследуется от MonoBehaviour
.
1B.Все!--102-->GameObject
:
static GameObject obj;
void Start()
{
obj = new GameObject("My Object");
}
это не работает, потому что это GameObject
и GameObject
наследовать от Object
.
единство всегда будет разрушать его Object
даже если они объявлены с static
ключевое слово.
посмотреть #2 для решения проблемы.
2.Используйте DontDestroyOnLoad
функции.
вам нужно использовать это только в том случае, если данные для сохранения или передачи в следующую сцену наследуются от Object
, Component
или GameObject
. Это решает проблему, описанную в 1A и 1B.
вы можете использовать его, чтобы сделать этот объект не уничтожать при выгрузке:
void Awake()
{
DontDestroyOnLoad(transform.gameObject);
}
вы даже можете использовать его с static
ключевое слово решить проблему из 1A и 1B:
public class MyTestScript : MonoBehaviour
{
}
затем
static MyTestScript testScript;
void Awake()
{
DontDestroyOnLoad(transform.gameObject);
}
void Start()
{
testScript = gameObject.AddComponent<MyTestScript>();
}
на testScript
переменной теперь будет сохраняется при загрузке новой сцены.
3.Сохранить в локальное хранилище, а затем загрузить во время следующей сцены.
этот метод следует использовать, когда это данные игры, которые должны быть сохранены при закрытии и повторном открытии игры. Примером этого является высокий балл игрока, настройки игры, такие как громкость музыки, местоположения объектов, данные профиля джойстика и так далее.
Thare два способа сохранить это:
3A.Используйте PlayerPrefs
API-интерфейс.
используйте, если у вас есть только несколько переменных для сохранения. Скажем, оценка игрока:
int playerScore = 80;
и мы хотим сохранить playerScore:
сохранить счет в OnDisable
функции
void OnDisable()
{
PlayerPrefs.SetInt("score", playerScore);
}
загрузите его в OnEnable
функции
void OnEnable()
{
playerScore = PlayerPrefs.GetInt("score");
}
3B.Сериализуйте данные в форму json, xml или binaray, а затем сохраните их с помощью одного из API файлов C#, например File.WriteAllBytes
и File.ReadAllBytes
для сохранения и загрузки файлов.
используйте этот метод, если есть много переменных, чтобы сохранить.
General, вам нужно создать класс, который не наследуется от MonoBehaviour
. Этот класс вы должны использовать для хранения игровых данных, чтобы их можно было легко сериализовать или де-сериализовать.
пример данных для сохранения:
[Serializable]
public class PlayerInfo
{
public List<int> ID = new List<int>();
public List<int> Amounts = new List<int>();
public int life = 0;
public float highScore = 0;
}
возьмите DataSaver
класс, который является оберткой над File.WriteAllBytes
и File.ReadAllBytes
это упрощает сохранение данных из этой пост.
создать новый экземпляр:
PlayerInfo saveData = new PlayerInfo();
saveData.life = 99;
saveData.highScore = 40;
сохранить данные из PlayerInfo в файл с именем "игроки":
DataSaver.saveData(saveData, "players");
загрузить данные из файла с именем "players":
PlayerInfo loadedData = DataSaver.loadData<PlayerInfo>("players");