如何使可编写脚本的对象在 Unity 中使用持久性数据



我的目标是创建 50 个对象,这些对象都拥有相同的结构并使用持久性数据。

我首先了解了持久性数据,并遵循了 Unity 的官方教程并使其发挥作用。由于本教程使用一个对象,我开始创建我的游戏,例如:

保存和加载持久性数据的方法。

public void saveBuy1()
{

Debug.Log("SavingBuy1");
BinaryFormatter bf = new BinaryFormatter();
FileStream file = File.Create(Application.persistentDataPath + "/buy1.dat");
PlayerData data = new PlayerData();



data.isBoxSold = 1;
bf.Serialize(file, data);
file.Close();
}
public void loadBuy1()
{
Debug.Log("loading");

if (File.Exists(Application.persistentDataPath + "/buy1.dat"))
{
BinaryFormatter bf = new BinaryFormatter();
FileStream file = File.Open(Application.persistentDataPath + "/buy1.dat", FileMode.Open);
PlayerData data = (PlayerData)bf.Deserialize(file);
file.Close();

GameObject.Find("buyBox1").GetComponentInChildren<Text>().text = "Item bought";
isBoxsold1 = data.isBoxSold1;
}
}

我的播放器数据类:

[Serializable]
class PlayerData {
public int coinsAmount;
public int isBoxsold;
}

创建框

//Regular box 1
int isBoxSold = 0;
int price1 = 6;
public Text boxPrice1;
public Image boxImage1;
public Button buyButton1;

但我很快意识到,必须有一种比这样做更有效的方法来创建我的盒子对象:

//Regular box 1
int isBoxSold1 = 0;
int price1 = 6;
public Text boxPrice1;
public Image boxImage1;
public Button buyButton1;
//Regular box 2
int isBoxSold2 = 0;
int price2 = 6;
public Text boxPrice2;
public Image boxImage2;
public Button buyButton2;

然后创建 loadBuy1 方法的副本并调用它 loadBuy2 等...

所以我发现了可编写脚本的对象,它似乎解决了必须为每个框创建新的属性和字段的问题,而是创建一个类一次。但是,我不明白如何使用可脚本化对象与持久性连接这些盒子类实例?有没有办法创建一个加载和保存方法来一次保存和加载所有盒子对象的所有持久性数据?还是我仍然需要为每个盒子创建一个保存和加载方法?

听起来你想要的是将每个盒子的数据存储在适当的ScriptableObject类中。

[CreateAssetMenu]
public class Box : ScriptableObject
{
// Inspector
[SerializeField] private int _isBoxSold = 0;
[SerializeField] private int _price = 6;
[SerializeField] private Text _boxPrice;
[SerializeField] private Image _boxImage;
[SerializeField] private Button _buyButton;
// Public readonly properties
public int IsBoxSold => _isBoxSold;
public int Price => _price;
public Text BoxPrice => _boxPrice;
}

然后将它们存储为列表

[Serializable]
public class PlayerData 
{
public int coinsAmount;
[SerializeField] private List<Box> _boxes;
// Example: run through all boxes and update their texts
public void UpdateBoxes()
{
foreach(var box in _boxes)
{
box.BoxPrice.text = box.Price.ToString();
}
}
}

一般说明:

切勿+ ""用于系统路径!而是使用根据目标平台自动使用正确路径分隔符的Path.Combine,例如

var filepath = Path.Combine(Application.persistentDataPath, "buy1.dat");

最新更新