U3D教程宝典之两步实现超实用的XML存档

两步实现超实用的XML存档

本套存档的优点:易使用,跨平台,防作弊(内容加密 + 防拷贝)

脚本下载地址

使用方法非常简单:
把GameDataManager和XmlSaver两个脚本添加至工程后
(1)新建一个GameObject,起名GameDataManager并将GameDataManager脚本拖到上面。
(2)在GameDataManager里的GameData类中添加需要储存的数据
OK,跨平台防破解防拷贝的存档就搞定了!之后每次存档调用GameDataManager的Save函数,读档调用GameDataManager的Load函数。每次启动后GameDataManager会自动调用Load读档。如果玩家拿外来存档来覆盖本地存档,则游戏启动后数据清零,任何一次存档后作弊档被自动覆盖。注意:请勿放入二维以上数组,一般一维数据,枚举,自定义类等等数据类型可放心添加。

iOS,Android,PC,MAC都使用过的。密钥的设定根据平台而定。

GameDataManager.cs的内容

//========================================================================================================= 
//Note: Data Managing. 
//Date Created: 2012/04/17 by 风宇冲 
//Date Modified: 2012/12/14 by 风宇冲 
//========================================================================================================= 
using UnityEngine; 
using System.Collections; 
using System.IO; 
using System.Collections.Generic; 
using System; 
using System.Text; 
using System.Xml; 
using System.Security.Cryptography; 
//GameData,储存数据的类,把需要储存的数据定义在GameData之内就行// 
public class GameData 
{ 
    //密钥,用于防止拷贝存档// 
    public string key; 
    
    //下面是添加需要储存的内容// 
    public string PlayerName; 
    public float MusicVolume; 
    public GameData() 
    { 
        PlayerName = "Player"; 
        MusicVolume = 0.6f; 
    } 
} 
//管理数据储存的类// 
public class GameDataManager:MonoBehaviour 
{ 
    private string dataFileName ="tankyWarData.dat";//存档文件的名称,自己定// 
    private  XmlSaver xs = new XmlSaver(); 
    
    public  GameData gameData; 
    
    public void Awake() 
    { 
        gameData = new GameData(); 
        
        //设定密钥,根据具体平台设定// 
        gameData.key = SystemInfo.deviceUniqueIdentifier; 
        Load(); 
    } 
    
    //存档时调用的函数// 
    public  void Save() 
    { 
        string gameDataFile = GetDataPath() + "/"+dataFileName; 
        string dataString= xs.SerializeObject(gameData,typeof(GameData)); 
        xs.CreateXML(gameDataFile,dataString); 
    } 
    
    //读档时调用的函数// 
    public  void Load() 
    { 
        string gameDataFile = GetDataPath() + "/"+dataFileName; 
        if(xs.hasFile(gameDataFile)) 
        { 
           string dataString = xs.LoadXML(gameDataFile); 
           GameData gameDataFromXML = xs.DeserializeObject(dataString,typeof(GameData)) as GameData; 
            
            //是合法存档// 
             if(gameDataFromXML.key == gameData.key) 
            { 
                gameData = gameDataFromXML; 
            } 
            //是非法拷贝存档// 
            else 
            { 
                //留空:游戏启动后数据清零,存档后作弊档被自动覆盖// 
            } 
        } 
        else 
        { 
            if(gameData != null) 
            Save(); 
        } 
    } 
    
    //获取路径// 
    private static string GetDataPath() 
    { 
        // Your game has read+write access to /var/mobile/Applications/XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX/Documents 
        // Application.dataPath returns ar/mobile/Applications/XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX/myappname.app/Data              
        // Strip "/Data" from path 
        if(Application.platform == RuntimePlatform.IPhonePlayer) 
        { 
            string path = Application.dataPath.Substring (0, Application.dataPath.Length - 5); 
            // Strip application name 
            path = path.Substring(0, path.LastIndexOf('/'));  
            return path + "/Documents"; 
        } 
        else 
        //    return Application.dataPath + "/Resources"; 
            return Application.dataPath; 
    } 
} 

XmlSaver.cs

//========================================================================================================= 
//Note: XML processcing,  can not save multiple-array!!! 
//Date Created: 2012/04/17 by 风宇冲 
//Date Modified: 2012/04/19 by 风宇冲 
//========================================================================================================= 
using UnityEngine; 
using System.Collections; 
using System.Xml; 
using System.Xml.Serialization; 
using System.IO; 
using System.Text; 
using System.Security.Cryptography; 
using System; 
public class XmlSaver 
{    
    //内容加密 
    public string Encrypt(string toE) 
    { 
        //加密和解密采用相同的key,具体自己填,但是必须为32位// 
        byte[] keyArray = UTF8Encoding.UTF8.GetBytes("12348578902223367877723456789012"); 
        RijndaelManaged rDel = new RijndaelManaged(); 
        rDel.Key = keyArray; 
        rDel.Mode = CipherMode.ECB; 
        rDel.Padding = PaddingMode.PKCS7; 
        ICryptoTransform cTransform = rDel.CreateEncryptor(); 
        
        byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(toE); 
        byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray,0,toEncryptArray.Length); 
    
        return Convert.ToBase64String(resultArray,0,resultArray.Length); 
    } 
    
    //内容解密 
    public string Decrypt(string toD) 
    { 
        //加密和解密采用相同的key,具体值自己填,但是必须为32位// 
        byte[] keyArray = UTF8Encoding.UTF8.GetBytes("12348578902223367877723456789012"); 
        
        RijndaelManaged rDel = new RijndaelManaged(); 
        rDel.Key = keyArray; 
        rDel.Mode = CipherMode.ECB; 
        rDel.Padding = PaddingMode.PKCS7; 
        ICryptoTransform cTransform = rDel.CreateDecryptor(); 
        
        byte[] toEncryptArray = Convert.FromBase64String(toD); 
        byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray,0,toEncryptArray.Length); 
        
        return UTF8Encoding.UTF8.GetString(resultArray); 
    } 
    
    public string SerializeObject(object pObject,System.Type ty) 
    { 
       string XmlizedString   = null; 
       MemoryStream memoryStream  = new MemoryStream(); 
       XmlSerializer xs  = new XmlSerializer(ty); 
       XmlTextWriter xmlTextWriter  = new XmlTextWriter(memoryStream, Encoding.UTF8); 
       xs.Serialize(xmlTextWriter, pObject); 
       memoryStream = (MemoryStream)xmlTextWriter.BaseStream; 
       XmlizedString = UTF8ByteArrayToString(memoryStream.ToArray()); 
       return XmlizedString; 
    } 
    
    public object DeserializeObject(string pXmlizedString , System.Type ty) 
    { 
       XmlSerializer xs  = new XmlSerializer(ty); 
       MemoryStream memoryStream  = new MemoryStream(StringToUTF8ByteArray(pXmlizedString)); 
       XmlTextWriter xmlTextWriter   = new XmlTextWriter(memoryStream, Encoding.UTF8); 
       return xs.Deserialize(memoryStream); 
    } 
    
    //创建XML文件 
    public void CreateXML(string fileName,string thisData) 
    { 
       string xxx = Encrypt(thisData); 
       StreamWriter writer; 
       writer = File.CreateText(fileName); 
       writer.Write(xxx); 
       writer.Close(); 
    } 
    
    //读取XML文件 
    public string LoadXML(string fileName) 
    { 
       StreamReader sReader = File.OpenText(fileName); 
       string dataString = sReader.ReadToEnd(); 
       sReader.Close(); 
       string xxx = Decrypt(dataString); 
       return xxx; 
    } 
    
    //判断是否存在文件 
    public bool hasFile(String fileName) 
    { 
       return File.Exists(fileName); 
    } 
    public string UTF8ByteArrayToString(byte[] characters  ) 
    {     
       UTF8Encoding encoding  = new UTF8Encoding(); 
       string constructedString  = encoding.GetString(characters); 
       return (constructedString); 
    } 
    
    public byte[] StringToUTF8ByteArray(String pXmlString ) 
    { 
       UTF8Encoding encoding  = new UTF8Encoding(); 
       byte[] byteArray  = encoding.GetBytes(pXmlString); 
       return byteArray; 
    } 
} 

转载:http://blog.sina.com.cn/s/blog_471132920101d3kh.html

原文地址:https://www.cnblogs.com/softimagewht/p/3888757.html