Unity 儲存和載入XML檔案
阿新 • • 發佈:2019-02-20
儲存工程的資訊:比如遊戲程序中的位置資訊,對抗雙方的個人資訊等:
方法1:使用xml檔案:
xml檔案要以UTF-8的格式儲存;
但是這樣做會使得programmer 可以從指令碼中控制xml檔案中的所有的字元,包括xml檔案中的語法命令字元,因此會帶來不安全隱患;
附上兩段程式碼:
A 這一段是我自己寫的,將一個xml檔案按照字串讀入;
雖然unity3d中的string型別說明中講到儲存的是unicode characters,但是實際上當xml檔案比較大的時候,如果儲存成unicode,就讀不出來,如果儲存成UTF-8就不存在這個問題;
C#版本:
using- using System.Collections;
- using System.Xml;
- using System.Xml.Serialization;
- using System.IO;
- using System.Text;
- publicclass ReadXML: MonoBehaviour {
- //store the read in file
- WWW statusFile;
- //decide wether the reading of xml has been finished
- bool isReadIn = false;
- // Use this for initialization
- IEnumerator Start () {//不能用void,否則沒有辦法使用yield
- isReadIn = false;
- yield return StartCoroutine(ReadIn());
- isReadIn = true;
- }
- IEnumerator ReadIn()
- {
- yield return statusFile = new WWW("file:///D:/unity/rotationAndcolor/Assets/information/testxml.xml");//注意路徑的寫法
- }
- // Update is called once per frame
- void Update () {
- if(isReadIn)
- {
- string statusData = statusFile.data;
- print(statusData.Length);
- }
- }
- //get the parameters in the xml file
- void getPatameters(string _xmlString)
- {
- //_xmlString.[0]
- }
- void postParameters()
- {
- }
- }
- publicclass _GameSaveLoad: MonoBehaviour {
- // An example where the encoding can be found is at
- // http://www.eggheadcafe.com/articles/system.xml.xmlserialization.asp
- // We will just use the KISS method and cheat a little and use
- // the examples from the web page since they are fully described
- // This is our local private members
- Rect _Save, _Load, _SaveMSG, _LoadMSG;
- bool _ShouldSave, _ShouldLoad,_SwitchSave,_SwitchLoad;
- string _FileLocation,_FileName;
- public GameObject _Player;
- UserData myData;
- string _PlayerName;
- string _data;
- Vector3 VPosition;
- // When the EGO is instansiated the Start will trigger
- // so we setup our initial values for our local members
- void Start () {
- // We setup our rectangles for our messages
- _Save=new Rect(10,80,100,20);
- _Load=new Rect(10,100,100,20);
- _SaveMSG=new Rect(10,120,400,40);
- _LoadMSG=new Rect(10,140,400,40);
- // Where we want to save and load to and from
- _FileLocation=Application.dataPath;
- _FileName="SaveData.xml";
- // for now, lets just set the name to Joe Schmoe
- _PlayerName = "Joe Schmoe";
- // we need soemthing to store the information into
- myData=new UserData();
- }
- void Update () {}
- void OnGUI()
- {
- //***************************************************
- // Loading The Player...
- // **************************************************
- if (GUI.Button(_Load,"Load")) {
- GUI.Label(_LoadMSG,"Loading from: "+_FileLocation);
- // Load our UserData into myData
- LoadXML();
- if(_data.ToString() != "")
- {
- // notice how I use a reference to type (UserData) here, you need this
- // so that the returned object is converted into the correct type
- myData = (UserData)DeserializeObject(_data);
- // set the players position to the data we loaded
- VPosition=new Vector3(myData._iUser.x,myData._iUser.y,myData._iUser.z);
- _Player.transform.position=VPosition;
- // just a way to show that we loaded in ok
- Debug.Log(myData._iUser.name);
- }
- }
- //***************************************************
- // Saving The Player...
- // **************************************************
- if (GUI.Button(_Save,"Save")) {
- GUI.Label(_SaveMSG,"Saving to: "+_FileLocation);
- myData._iUser.x=_Player.transform.position.x;
- myData._iUser.y=_Player.transform.position.y;
- myData._iUser.z=_Player.transform.position.z;
- myData._iUser.name=_PlayerName;
- // Time to creat our XML!
- _data = SerializeObject(myData);
- // This is the final resulting XML from the serialization process
- CreateXML();
- Debug.Log(_data);
- }
- }
- /* The following metods came from the referenced URL */
- string UTF8ByteArrayToString(byte[] characters)
- {
- UTF8Encoding encoding = new UTF8Encoding();
- string constructedString = encoding.GetString(characters);
- return (constructedString);
- }
- byte[] StringToUTF8ByteArray(string pXmlString)
- {
- UTF8Encoding encoding = new UTF8Encoding();
- byte[] byteArray = encoding.GetBytes(pXmlString);
- return byteArray;
- }
- // Here we serialize our UserData object of myData
- string SerializeObject(object pObject)
- {
- string XmlizedString = null;
- MemoryStream memoryStream = new MemoryStream();
- XmlSerializer xs = new XmlSerializer(typeof(UserData));
- XmlTextWriter xmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
- xs.Serialize(xmlTextWriter, pObject);
- memoryStream = (MemoryStream)xmlTextWriter.BaseStream;
- XmlizedString = UTF8ByteArrayToString(memoryStream.ToArray());
- return XmlizedString;
- }
- // Here we deserialize it back into its original form
- object DeserializeObject(string pXmlizedString)
- {
- XmlSerializer xs = new XmlSerializer(typeof(UserData));
- MemoryStream memoryStream = new MemoryStream(StringToUTF8ByteArray(pXmlizedString));
- XmlTextWriter xmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
- return xs.Deserialize(memoryStream);
- }
- // Finally our save and load methods for the file itself
- void CreateXML()
- {
- StreamWriter writer;
- FileInfo t = new FileInfo(_FileLocation+"//"+ _FileName);
- if(!t.Exists)
- {
- writer = t.CreateText();
- }
- else
- {
- t.Delete();
- writer = t.CreateText();
- }
- writer.Write(_data);
- writer.Close();
- Debug.Log("File written.");
- }
- void LoadXML()
- {
- StreamReader r = File.OpenText(_FileLocation+"//"+ _FileName);
- string _info = r.ReadToEnd();
- r.Close();
- _data=_info;
- Debug.Log("File Read");
- }
- }
- // UserData is our custom class that holds our defined objects we want to store in XML format
- publicclass UserData
- {
- // We have to define a default instance of the structure
- public DemoData _iUser;
- // Default constructor doesn't really do anything at the moment
- public UserData() { }
- // Anything we want to store in the XML file, we define it here
- publicstruct DemoData
- {
- publicfloat x;
- publicfloat y;
- publicfloat z;
- publicstring name;
- }
- }
js 版本:
import System;- import System.Collections;
- import System.Xml;
- import System.Xml.Serialization;
- import System.IO;
- import System.Text;
- // Anything we want to store in the XML file, we define it here
- class DemoData
- {
- var x : float;
- var y : float;
- var z : float;
- var name : String;
- }
- // UserData is our custom class that holds our defined objects we want to store in XML format
- class UserData
- {
- // We have to define a default instance of the structure
- publicvar _iUser : DemoData = new DemoData();
- // Default constructor doesn't really do anything at the moment
- function UserData() { }
- }
- //public class GameSaveLoad: MonoBehaviour {
- // An example where the encoding can be found is at
- // http://www.eggheadcafe.com/articles/system.xml.xmlserialization.asp
- // We will just use the KISS method and cheat a little and use
- // the examples from the web page since they are fully described
- // This is our local private members
- privatevar _Save : Rect;
- privatevar _Load : Rect;
- privatevar _SaveMSG : Rect;
- privatevar _LoadMSG : Rect;
- //var _ShouldSave : boolean;
- //var _ShouldLoad : boolean;
- //var _SwitchSave : boolean;
- //var _SwitchLoad : boolean;
- privatevar _FileLocation : String;
- privatevar _FileName : String = "SaveData.xml";
- //public GameObject _Player;
- var _Player : GameObject;
- var _PlayerName : String = "Joe Schmoe";
- privatevar myData : UserData;
- privatevar _data : String;
- privatevar VPosition : Vector3;
- // When the EGO is instansiated the Start will trigger
- // so we setup our initial values for our local members
- //function Start () {
- function Awake () {
- // We setup our rectangles for our messages
- _Save=new Rect(10,80,100,20);
- _Load=new Rect(10,100,100,20);
- _SaveMSG=new Rect(10,120,200,40);
- _LoadMSG=new Rect(10,140,200,40);
- // Where we want to save and load to and from
- _FileLocation=Application.dataPath;
- // we need soemthing to store the information into
- myData=new UserData();
- }
- function Update () {}
- function OnGUI()
- {
- // ***************************************************
- // Loading The Player...
- // **************************************************
- if (GUI.Button(_Load,"Load")) {
- GUI.Label(_LoadMSG,"Loading from: "+_FileLocation);
- // Load our UserData into myData
- LoadXML();
- if(_data.ToString() != "")
- {
- // notice how I use a reference to type (UserData) here, you need this
- // so that the returned object is converted into the correct type
- //myData = (UserData)DeserializeObject(_data);
- myData = DeserializeObject(_data);
- // set the players position to the data we loaded
- VPosition=new Vector3(myData._iUser.x,myData._iUser.y,myData._iUser.z);
- _Player.transform.position=VPosition;
- // just a way to show that we loaded in ok
- Debug.Log(myData._iUser.name);
- }
- }
- // ***************************************************
- // Saving The Player...
- // **************************************************
- if (GUI.Button(_Save,"Save")) {
- GUI.Label(_SaveMSG,"Saving to: "+_FileLocation);
- //Debug.Log("SaveLoadXML: sanity check:"+ _Player.transform.position.x);
- myData._iUser.x = _Player.transform.position.x;
- myData._iUser.y = _Player.transform.position.y;
- myData._iUser.z = _Player.transform.position.z;
- myData._iUser.name = _PlayerName;
- // Time to creat our XML!
- _data = SerializeObject(myData);
- // This is the final resulting XML from the serialization process
- CreateXML();
- Debug.Log(_data);
- }
- }
- /* The following metods came from the referenced URL */
- //string UTF8ByteArrayToString(byte[] characters)
- function UTF8ByteArrayToString(characters : byte[] )
- {
- var encoding : UTF8Encoding = new UTF8Encoding();
- var constructedString : String = encoding.GetString(characters);
- return (constructedString);
- }
- //byte[] StringToUTF8ByteArray(string pXmlString)
- function StringToUTF8ByteArray(pXmlString : String)
- {
- var encoding : UTF8Encoding = new UTF8Encoding();
- var byteArray : byte[] = encoding.GetBytes(pXmlString);
- return byteArray;
- }
- // Here we serialize our UserData object of myData
- //string SerializeObject(object pObject)
- function SerializeObject(pObject : Object)
- {
- var XmlizedString : String = null;
- var memoryStream : MemoryStream = new MemoryStream();
- var xs : XmlSerializer = new XmlSerializer(typeof(UserData));
- var xmlTextWriter : XmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
- xs.Serialize(xmlTextWriter, pObject);
- memoryStream = xmlTextWriter.BaseStream; // (MemoryStream)
- XmlizedString = UTF8ByteArrayToString(memoryStream.ToArray());
- return XmlizedString;
- }
- // Here we deserialize it back into its original form
- //object DeserializeObject(string pXmlizedString)
- function DeserializeObject(pXmlizedString : String)
- {
- var xs : XmlSerializer = new XmlSerializer(typeof(UserData));
- var memoryStream : MemoryStream = new MemoryStream(StringToUTF8ByteArray(pXmlizedString));
- var xmlTextWriter : XmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);
- return xs.Deserialize(memoryStream);
- }
- // Finally our save and load methods for the file itself
- function CreateXML()
- {
- var writer : StreamWriter;
- //FileInfo t = new FileInfo(_FileLocation+"//"+ _FileName);
- var t : FileInfo = new FileInfo(_FileLocation+"/"+ _FileName);
- if(!t.Exists)
- {
- writer = t.CreateText();
- }
- else
- {
- t.Delete();
- writer = t.CreateText();
- }
- writer.Write(_data);
- writer.Close();
- Debug.Log("File written.");
- }
- function LoadXML()
- {
- //StreamReader r = File.OpenText(_FileLocation+"//"+ _FileName);
- var r : StreamReader = File.OpenText(_FileLocation+"/"+ _FileName);
- var _info : String = r.ReadToEnd();
- r.Close();
- _data=_info;
- Debug.Log("File Read");
- }
- //}
方法2:使用unity 3d 的ISerializable類
它的好處是,可以將檔案存成自己定義的字尾形式,並且2進位制化儲存,在u3d的幫助文件中有相關介紹。