BundleBuilderZ.cs 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382
  1. using System.Collections;
  2. using System.Collections.Generic;
  3. using UnityEngine;
  4. using UnityEditor;
  5. using System.IO;
  6. using System.Security.Cryptography;
  7. using System.Text;
  8. using Pack;
  9. public class BundleBuilderZ : EditorWindow
  10. {
  11. class MD5
  12. {
  13. public string Md5;
  14. public long Length;
  15. public MD5(string m, long length)
  16. {
  17. Md5 = m;
  18. Length = length;
  19. }
  20. }
  21. protected static BuildTarget target = BuildTarget.Android;
  22. static string StreamingAssetsPath = "Assets/StreamingAssets";
  23. static Dictionary<string, MD5> DicFileMD5 = null;
  24. static string VersionInfo = null;
  25. [MenuItem("AssetBundle/MD5Creator")]
  26. public static void MD5Creator()
  27. {
  28. #if UNITY_IOS
  29. string versionFileName = "afivs";
  30. string assetsFileName = "afimft";
  31. #else
  32. string versionFileName = "Version";
  33. string assetsFileName = "mainfest";
  34. #endif
  35. DicFileMD5 = new Dictionary<string, MD5>();
  36. string[] files = Directory.GetFiles(FileSystem.PackagePath(), "*", SearchOption.AllDirectories);
  37. MD5CryptoServiceProvider md5Generator = new MD5CryptoServiceProvider();
  38. int i = 0;
  39. StringBuilder sb = new StringBuilder(1024);
  40. foreach (string filePath in files)
  41. {
  42. if (filePath.Contains(".svn") || filePath.Contains(".meta") || filePath.Contains("DS_Store"))
  43. continue;
  44. EditorUtility.DisplayProgressBar(string.Format("生成MD5码-{0}", Path.GetFileName(filePath)), Path.GetFileName(filePath), (float)(++i) / files.Length);
  45. FileStream file = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.Read);
  46. byte[] hash = md5Generator.ComputeHash(file);
  47. sb.Clear();
  48. for (int j = 0; j < hash.Length; ++j)
  49. {
  50. sb.Append(hash[j].ToString("X2"));
  51. }
  52. string strMD5 = sb.ToString().ToLower();
  53. string key = Path.GetFileName(filePath);
  54. if (!DicFileMD5.ContainsKey(key))
  55. DicFileMD5.Add(key, new MD5(strMD5, file.Length));
  56. else
  57. Debug.LogWarning("<Two File has the same name> name = " + filePath);
  58. file.Close();
  59. file.Dispose();
  60. }
  61. EditorUtility.ClearProgressBar();
  62. string savePath = string.Format("{0}{1}", FileSystem.PackagePath(), assetsFileName);
  63. // 删除前一版的old数据
  64. if (File.Exists(savePath))
  65. {
  66. System.IO.File.Delete(savePath);
  67. }
  68. //PackPlatforms cfg = PackRun.GetConfigs();
  69. int size = 0;
  70. sb.Clear();
  71. if (string.IsNullOrEmpty(VersionInfo))
  72. {
  73. VersionInfo = "0.1.0.0";
  74. }
  75. //sb.Append("FileName,MD5,Length\r\n");
  76. sb.Append("ID,FullName,MD5,Size\r\n");
  77. sb.Append("int,string,string,ulong\r\n");
  78. sb.Append($"{++size},Version,{VersionInfo},0\r\n");
  79. foreach (KeyValuePair<string, MD5> pair in DicFileMD5)
  80. {
  81. if (pair.Key == versionFileName || pair.Key == assetsFileName)
  82. {
  83. continue;
  84. }
  85. sb.Append(++size);
  86. sb.Append(",");
  87. sb.Append(pair.Key);
  88. sb.Append(",");
  89. sb.Append(pair.Value.Md5);
  90. sb.Append(",");
  91. sb.Append(pair.Value.Length);
  92. sb.Append("\r\n");
  93. }
  94. FileStream fs = new FileStream(savePath, FileMode.OpenOrCreate);
  95. if (fs == null)
  96. return;
  97. UTF8Encoding encoding = new UTF8Encoding(false, false);
  98. StreamWriter textWriter = new StreamWriter(fs, encoding);
  99. if (textWriter == null)
  100. return;
  101. textWriter.Write(sb.ToString());
  102. textWriter.Flush();
  103. textWriter.Close();
  104. DicFileMD5.Clear();
  105. VersionInfo = null;
  106. Debug.Log("<color=red>================ MD5Creator Complete ================</color>");
  107. }
  108. public static void CreateMD5File(string version)
  109. {
  110. VersionInfo = version;
  111. MD5Creator();
  112. #if UNITY_IOS
  113. string versionFileName = "afivs";
  114. string assetsFileName = "afimft";
  115. #else
  116. string versionFileName = "Version";
  117. string assetsFileName = "mainfest";
  118. #endif
  119. FileHelper.WirteStringToFile($"{FileSystem.PackagePath()}{versionFileName}",version);
  120. }
  121. #region BundleBuidlerDeleteAssetsData;
  122. static void BundleBuidlerDeleteAssetsData()
  123. {
  124. Caching.ClearCache();
  125. if (Directory.Exists(StreamingAssetsPath))
  126. {
  127. string srcPath = GetAssetbundlesPath();
  128. string path = Application.streamingAssetsPath + srcPath.Replace(Path.GetDirectoryName(Application.dataPath), "");
  129. if (Directory.Exists(path))
  130. {
  131. Directory.Delete(path, true);
  132. }
  133. //Log.E("DeleteAndCreateDir.Delete (path); {0}", StreamingAssetsPath);
  134. }
  135. AssetDatabase.Refresh();
  136. DebugHelper.Log("<color=red>================ DeleteStreamingAssets Complete ================</color>");
  137. }
  138. #endregion BundleBuidlerDeleteAssetsData
  139. #region BundleBuidlerCopyToStreamingAssets;
  140. public static void BundleBuidlerCopyToStreamingAssets()
  141. {
  142. Caching.ClearCache();
  143. BundleBuidlerDeleteAssetsData();
  144. string path = Application.dataPath;
  145. string srcPath = GetAssetbundlesPath();
  146. path = Application.streamingAssetsPath + srcPath.Replace(Path.GetDirectoryName(Application.dataPath), "");
  147. DeleteAndCreateDir(path);
  148. CopyFolder(srcPath, path);
  149. DebugHelper.Log("<color=red>================ CopyToStreamingAssets Complete ================</color>");
  150. AssetDatabase.Refresh();
  151. }
  152. #endregion BundleBuidlerCopyToStreamingAssets
  153. public static void BuildApp(bool debug = false)
  154. {
  155. target = EditorUserBuildSettings.activeBuildTarget;// BuildTarget.Android;
  156. BuildOptions buildOption = BuildOptions.None;
  157. System.DateTime time = System.DateTime.Now;
  158. string DateTime = time.Month.ToString("D2") + time.Day.ToString("D2") +
  159. "_" + time.Hour.ToString("D2") + time.Minute.ToString("D2");
  160. PlayerSettings.applicationIdentifier = AssetBundleConstant.PgName;
  161. if (EditorUserBuildSettings.development)
  162. {
  163. buildOption |= BuildOptions.Development;
  164. buildOption |= BuildOptions.AllowDebugging;
  165. buildOption |= BuildOptions.ConnectWithProfiler;
  166. }
  167. else
  168. {
  169. buildOption |= BuildOptions.None;
  170. }
  171. string locationPathName;
  172. if (BuildTarget.iOS == target)
  173. {
  174. locationPathName = Application.dataPath;
  175. locationPathName = locationPathName.Replace("Assets", "/Xcode");
  176. }
  177. else if (BuildTarget.Android == target)
  178. {
  179. string apkName = AssetBundleConstant.ApkName;
  180. if (!debug)
  181. {
  182. ChangeAndroidVersionCode();
  183. }
  184. else
  185. {
  186. apkName = apkName + "_debug";
  187. }
  188. locationPathName = Application.dataPath;
  189. locationPathName = locationPathName.Replace("Assets", "/BatunityApk/");
  190. EditorUserBuildSettings.androidBuildSubtarget = MobileTextureSubtarget.ETC;
  191. PlayerSettings.Android.keystoreName = Application.dataPath.Replace("Assets", "/Cert/wenting.keystore");
  192. PlayerSettings.Android.keystorePass = "n9P5j2b7blMm";
  193. PlayerSettings.Android.keyaliasName = "game";
  194. PlayerSettings.Android.keyaliasPass = "KlYX666Ro";
  195. locationPathName += apkName + ".apk";
  196. }
  197. else
  198. {
  199. target = BuildTarget.StandaloneWindows64;
  200. locationPathName = Application.dataPath;
  201. locationPathName = locationPathName.Replace("Assets", "/RO");
  202. locationPathName += DateTime + "/" + DateTime + ".exe";
  203. PlayerSettings.SetArchitecture(BuildTargetGroup.Standalone, 0);
  204. }
  205. var buildResult = BuildPipeline.BuildPlayer(ms_scenes, locationPathName, target, buildOption);
  206. }
  207. private static void ChangeAndroidVersionCode()
  208. {
  209. int oldVersionCode = PlayerSettings.Android.bundleVersionCode;
  210. oldVersionCode = oldVersionCode % 100;
  211. oldVersionCode += 1;
  212. int bigVersionCode = 0;
  213. var bigVersionStrs = AssetBundleConstant.GameVersion.Split('.');
  214. if (bigVersionStrs.Length >= 1)
  215. {
  216. bigVersionCode += (int.Parse(bigVersionStrs[0]) * 1000000);
  217. }
  218. if (bigVersionStrs.Length >= 2)
  219. {
  220. bigVersionCode += (int.Parse(bigVersionStrs[1]) * 10000);
  221. }
  222. if (bigVersionStrs.Length >= 3)
  223. {
  224. bigVersionCode += (int.Parse(bigVersionStrs[2]) * 100);
  225. }
  226. PlayerSettings.Android.bundleVersionCode = (bigVersionCode + oldVersionCode);
  227. PlayerSettings.bundleVersion = AssetBundleConstant.GameVersion + oldVersionCode;
  228. }
  229. private static string[] ms_scenes =
  230. {
  231. "Assets/game.unity",
  232. "Assets/relogin.unity",
  233. };
  234. #region CommonMethod;
  235. static void DeleteAndCreateDir(string targetPath)
  236. {
  237. if (Directory.Exists(targetPath))
  238. {
  239. Directory.Delete(targetPath, true);
  240. DebugHelper.LogWarning("DeleteAndCreateDir.Delete (path); {0}", targetPath);
  241. }
  242. if (!Directory.Exists(targetPath))
  243. Directory.CreateDirectory(targetPath);
  244. }
  245. static void DeleteFile(string targetPath)
  246. {
  247. if (File.Exists(targetPath))
  248. {
  249. File.Delete(targetPath);
  250. }
  251. }
  252. private static void CopyFolder(string from, string to)
  253. {
  254. string[] dirs = Directory.GetDirectories(from);
  255. FileSystem.CreateDirIfNotExist(to);
  256. foreach (string sub in dirs)
  257. {
  258. string path = to + Path.GetFileName(sub);
  259. if (!Directory.Exists(path))
  260. Directory.CreateDirectory(to + Path.GetFileName(sub));
  261. CopyFolder(sub + "\\", path + "\\");
  262. }
  263. string[] files = Directory.GetFiles(from);
  264. foreach (string file in files)
  265. File.Copy(file, to + Path.GetFileName(file), true);
  266. }
  267. public static string GetAssetbundlesPath()
  268. {
  269. string path = Application.dataPath;
  270. path = Path.GetDirectoryName(path);
  271. BuildTarget buildTarget = EditorUserBuildSettings.activeBuildTarget;
  272. if (buildTarget == BuildTarget.iOS)
  273. {
  274. path = path + "/unityRes/";
  275. }
  276. else if (buildTarget == BuildTarget.Android)
  277. {
  278. path = path + "/AssetsAndroid/";
  279. }
  280. else
  281. {
  282. path = path + "/AssetsPC/";
  283. }
  284. return path;
  285. }
  286. public static string GetWwisePath()
  287. {
  288. string path = Application.dataPath;
  289. path = Path.GetDirectoryName(path);
  290. BuildTarget buildTarget = EditorUserBuildSettings.activeBuildTarget;
  291. if (buildTarget == BuildTarget.iOS)
  292. {
  293. path = path + "/client_WwiseProject/GeneratedSoundBanks/Windows/";
  294. }
  295. else if (buildTarget == BuildTarget.Android)
  296. {
  297. path = path + "/client_WwiseProject/GeneratedSoundBanks/Windows/";
  298. }
  299. else
  300. {
  301. path = path + "/client_WwiseProject/GeneratedSoundBanks/Windows/";
  302. }
  303. return path;
  304. }
  305. #endregion CommonMethod;
  306. [MenuItem("RO_Tool/Scene/EnableScene All")]
  307. public static void EnableScene()
  308. {
  309. SetScenes(true);
  310. }
  311. [MenuItem("RO_Tool/Scene/DisableScene All")]
  312. public static void DisableScene()
  313. {
  314. SetScenes(false);
  315. }
  316. static void SetScenes(bool enable)
  317. {
  318. EditorBuildSettingsScene[] scenes = EditorBuildSettings.scenes;
  319. foreach (EditorBuildSettingsScene scene in scenes)
  320. {
  321. if (scene.path.Contains("game") || scene.path.Contains("Loading") || scene.path.Contains("relogin"))
  322. continue;
  323. scene.enabled = enable;
  324. }
  325. EditorBuildSettings.scenes = scenes;
  326. AssetDatabase.Refresh();
  327. }
  328. [MenuItem("[ 快捷启动 ]/[ Run Game ]", false, 1)]
  329. static void RunGame()
  330. {
  331. Time.timeScale = 1.0f;
  332. UnityEditor.SceneManagement.EditorSceneManager.OpenScene(@"Assets/game.unity");
  333. EditorApplication.isPlaying = true;
  334. }
  335. [MenuItem("RO_Tool/生成公私钥")]
  336. public static void GenKey()
  337. {
  338. string publicKey, privateKey, privateKeyPk8;
  339. RsaKeyHelper.GenKey(out publicKey, out privateKey, out privateKeyPk8);
  340. Debug.LogError(string.Format("{0}\n\n\n{1}", publicKey, privateKeyPk8));
  341. }
  342. }