using Thousandto.Core.Base; using System.Collections.Generic; using System.IO; using UnityEngine; using System.Text; using PathUtils = UnityEngine.Gonbest.MagicCube.PathUtils; using UnityEngine.Gonbest.MagicCube; namespace Thousandto.Code.Logic { public class BetterLua { //key秘钥 private static string key = "BgIAAACkAABSU0ExAAQAAAEAAQBtKN"; //所有lua脚本 private static Dictionary<string, byte[]> allLuaFile = new Dictionary<string, byte[]>(); //bytes整体偏移 private static int offset = 1; private static int _loadCnt = 0; public static bool IsLoaded() { return _loadCnt >= 2; } //初始化 public static void Init(string lan = null) { Debug.LogError("开始初始化Lua代码...."); _loadCnt = 0; var BetterLuaPath = PathUtils.GetConfigFilePath("Lua.bytes"); var StringDefinesPath = PathUtils.GetConfigFilePath(string.Format("LuaData_{0}.bytes", (lan == null ? LanguageSystem.Lang : lan))); #if UNITY_WEBGL //if (Application.platform == RuntimePlatform.WebGLPlayer) { //WebUtils.ReadBytes(BetterLuaPath, x => FFileReader.ReadBytesAsync(BetterLuaPath, x => { if (x != null) { using (MemoryStream stream = new MemoryStream(x)) { ReadFile(stream); stream.Close(); } _loadCnt++; } else { Debug.LogError("Lua1文件加载失败!:"+ BetterLuaPath); } }); //WebUtils.ReadBytes(StringDefinesPath, x => FFileReader.ReadBytesAsync(StringDefinesPath, x => { if (x != null) { using (MemoryStream stream = new MemoryStream(x)) { ReadFile(stream); stream.Close(); } _loadCnt++; } else { Debug.LogError("Lua2文件加载失败!:" + StringDefinesPath); } }); } //else #else { if (File.Exists(BetterLuaPath)) { using (FileStream stream = new FileStream(BetterLuaPath, FileMode.Open, FileAccess.Read)) { ReadFile(stream); stream.Close(); } _loadCnt++; } if (File.Exists(StringDefinesPath)) { using (FileStream stream = new FileStream(StringDefinesPath, FileMode.Open, FileAccess.Read)) { ReadFile(stream); stream.Close(); } _loadCnt++; } } #endif } //1.内容长度:4个字节 2.key长度:4个字节 3.key:3+keyLength 4.lua内容 //lua内容: 1>title总长度:8个字节 2>所有lua文件总览,用分隔符分开,每3个一组【文件路径;文件开始位置;文件长度;】 3>所有lua文件内容 private static void ReadFile(Stream stream) { using (BinaryReader reader = new BinaryReader(stream)) { int contentLength = reader.ReadInt32(); int keyLength = reader.ReadInt32(); //key stream.Seek(11, SeekOrigin.Begin); var keyBytes = new byte[keyLength - 3]; stream.Read(keyBytes, 0, keyLength - 3); DecryptKey(ref keyBytes); //秘钥是否正确 if (Encoding.UTF8.GetString(keyBytes) == key) { offset = 8 + keyLength; var titleCountBytes = new byte[8]; stream.Seek(offset, SeekOrigin.Begin); stream.Read(titleCountBytes, 0, 8); DecryptContent(ref titleCountBytes); int titleCount = int.Parse(Encoding.UTF8.GetString(titleCountBytes)); var titleBytes = new byte[titleCount]; stream.Seek(offset + 8, SeekOrigin.Begin); stream.Read(titleBytes, 0, titleCount); var titleStrArr = Encoding.UTF8.GetString(titleBytes).Split(';'); var titleStrArrLength = titleStrArr.Length; for (int i = 0; i < titleStrArrLength - 1; i += 3) { var startIndex = int.Parse(titleStrArr[i + 1]) + offset; var length = int.Parse(titleStrArr[i + 2]); var bytes = new byte[length]; stream.Seek(startIndex, SeekOrigin.Begin); stream.Read(bytes, 0, length); DecryptContent(ref bytes); allLuaFile.Add(titleStrArr[i], bytes); } } reader.Close(); } } //解密key public static void DecryptKey(ref byte[] bytes) { for (int i = 0; i < bytes.Length; i++) { bytes[i] = (byte)(bytes[i] ^ -82); bytes[i] += 106; } } //解密文本 public static void DecryptContent(ref byte[] bytes) { var bytesLength = bytes.Length; for (int i = 0; i < bytesLength; i++) { bytes[i] = (byte)(bytes[i] ^ -74); //bytes[i] += 95; } } //加载lua文件 public static byte[] BetterLuaLoader(ref string fileName) { if (allLuaFile.ContainsKey(fileName)) { var bytes = allLuaFile[fileName]; //配置表lua加载以后,这里可以把内存腾出来 if (fileName.StartsWith("config/data/")) { allLuaFile.Remove(fileName); } return bytes; } else { Debug.LogError("no file :" + fileName); return null; } } } }