SaveManager.cs 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269
  1. using UnityEngine;
  2. using System;
  3. using System.Linq;
  4. using System.Collections.Generic;
  5. using System.Text;
  6. using System.IO;
  7. using Util;
  8. namespace CM3D2.MultipleMaids.Plugin
  9. {
  10. public partial class MultipleMaids
  11. {
  12. private static readonly byte[] pngEnd = Encoding.ASCII.GetBytes("IEND");
  13. private static string sceneData;
  14. private const string baseDirectoryName = "< Base Directory >";
  15. private string saveScenePath = Path.Combine(Path.GetFullPath(".\\"), "Mod\\MultipleMaidsSave");
  16. private List<SavePng> saveScenes = new List<SavePng>(50);
  17. private string[] directoryList;
  18. private Texture2D frame;
  19. private Rect saveManagerRect;
  20. private Rect saveModalRect;
  21. private Rect resizeManagerRect;
  22. private Vector2 saveManagerScrollPos = Vector2.zero;
  23. private Vector2 dirListScrollPos = Vector2.zero;
  24. private bool saveManagerInitialize = false;
  25. private bool loadSaveFlag = false;
  26. private bool overwriteFlag = false;
  27. private bool createSaveFlag = false;
  28. private bool manageSaveFlag = false;
  29. private bool createDirectory = false;
  30. private bool resizeManager = false;
  31. private int selectedSave = 0;
  32. private int selectedDirectory = 0;
  33. private string currentDirectory = "";
  34. private string textFieldValue = "";
  35. public void InitializeSaveManager()
  36. {
  37. frame = MakeTex(2, 2, Color.white);
  38. if (!Directory.Exists(saveScenePath))
  39. {
  40. Directory.CreateDirectory(saveScenePath);
  41. }
  42. GetSaveDirectories();
  43. InitializeSaveList();
  44. saveManagerInitialize = true;
  45. }
  46. private void RefreshSaveManager()
  47. {
  48. SwitchDirectory(currentDirectory);
  49. GetSaveDirectories();
  50. InitializeSaveList();
  51. }
  52. private void InitializeSaveList()
  53. {
  54. saveScenes.Clear();
  55. string workingPath = Path.Combine(saveScenePath, currentDirectory);
  56. DirectoryInfo info = new DirectoryInfo(workingPath);
  57. foreach (var save in info.GetFiles("*.png"))
  58. {
  59. Texture2D screenshot = new Texture2D(1, 1, TextureFormat.ARGB32, false);
  60. screenshot.LoadImage(File.ReadAllBytes(save.FullName));
  61. saveScenes.Add(new SavePng(save, screenshot));
  62. }
  63. selectedSave = saveScenes.Count == 0 ? 0 : saveScenes.Count - 1;
  64. saveScenes.Sort((a, b) => a.info.LastWriteTime.CompareTo(b.info.LastWriteTime));
  65. saveManagerScrollPos.y = 0;
  66. }
  67. private void GetSaveDirectories()
  68. {
  69. DirectoryInfo[] directoryInfo = new DirectoryInfo(saveScenePath).GetDirectories();
  70. directoryList = new string[directoryInfo.Length + 1];
  71. directoryList[0] = baseDirectoryName;
  72. for (int i = 0; i < directoryInfo.Length; i++)
  73. {
  74. directoryList[i + 1] = directoryInfo[i].Name;
  75. }
  76. }
  77. private void SwitchDirectory(string target)
  78. {
  79. if (target.Equals(baseDirectoryName)) target = "";
  80. string targetDirectory = Path.Combine(saveScenePath, target);
  81. if (!Directory.Exists(targetDirectory))
  82. {
  83. currentDirectory = "";
  84. selectedDirectory = 0;
  85. GetSaveDirectories();
  86. }
  87. else
  88. {
  89. selectedDirectory = Array.FindIndex(directoryList, d => d.Equals(target, StringComparison.OrdinalIgnoreCase));
  90. selectedDirectory = selectedDirectory == -1 ? 0 : selectedDirectory;
  91. if (target == currentDirectory) return;
  92. currentDirectory = target;
  93. }
  94. InitializeSaveList();
  95. }
  96. private void LoadSave()
  97. {
  98. string filePath = saveScenes[selectedSave].info.FullName;
  99. if (!File.Exists(filePath))
  100. {
  101. InitializeSaveList();
  102. sceneData = null;
  103. return;
  104. }
  105. using (FileStream fileStream = File.OpenRead(filePath))
  106. {
  107. byte[] buffer = new byte[pngEnd.Length];
  108. long position = 0;
  109. while (true)
  110. {
  111. int bytesRead = fileStream.Read(buffer, 0, buffer.Length);
  112. if (bytesRead != pngEnd.Length)
  113. {
  114. sceneData = null;
  115. return;
  116. }
  117. if (BytesEqual(buffer, pngEnd))
  118. {
  119. fileStream.Position += 4;
  120. break;
  121. }
  122. fileStream.Position = ++position;
  123. }
  124. using (MemoryStream sceneStream = LZMA.Decompress(fileStream))
  125. {
  126. sceneData = Encoding.Unicode.GetString(sceneStream.ToArray());
  127. }
  128. }
  129. SavePng temp = saveScenes[selectedSave];
  130. saveScenes.RemoveAt(selectedSave);
  131. saveScenes.Add(temp);
  132. saveManagerScrollPos.y = 0;
  133. }
  134. private void Overwrite()
  135. {
  136. string filePath = saveScenes[selectedSave].info.FullName;
  137. if (!File.Exists(filePath))
  138. {
  139. RefreshSaveManager();
  140. }
  141. else
  142. {
  143. File.Delete(filePath);
  144. saveScenes.RemoveAt(selectedSave);
  145. saveManagerScrollPos.y = 0;
  146. }
  147. }
  148. private void MakeNewDirectory(string directoryName)
  149. {
  150. directoryName = string.Join("", directoryName.Split(Path.GetInvalidFileNameChars()));
  151. string newDirectory = Path.Combine(saveScenePath, directoryName);
  152. if (!Directory.Exists(newDirectory))
  153. {
  154. Directory.CreateDirectory(newDirectory);
  155. }
  156. GetSaveDirectories();
  157. SwitchDirectory(directoryName);
  158. }
  159. private void SaveScene()
  160. {
  161. string saveDirectory = Path.Combine(saveScenePath, currentDirectory);
  162. if (!Directory.Exists(saveDirectory))
  163. {
  164. thum_byte_to_base64_ = "";
  165. thum_file_path_ = "";
  166. RefreshSaveManager();
  167. return;
  168. }
  169. string sceneString = SerializeScene(true);
  170. #region MM GUI stuff
  171. Texture2D screenshot = new Texture2D(1, 1, TextureFormat.ARGB32, false);
  172. screenshot.LoadImage(File.ReadAllBytes(thum_file_path_));
  173. float num2 = screenshot.width / (float)screenshot.height;
  174. Vector2 vector2 = new Vector2(480f, 270f);
  175. int newWidth = screenshot.width;
  176. int newHeight = screenshot.height;
  177. if (vector2.x < (double)screenshot.width && vector2.y < (double)screenshot.height)
  178. {
  179. newWidth = (int)vector2.x;
  180. newHeight = Mathf.RoundToInt(newWidth / num2);
  181. if (vector2.y < (double)newHeight)
  182. {
  183. newHeight = (int)vector2.y;
  184. newWidth = Mathf.RoundToInt(newHeight * num2);
  185. }
  186. }
  187. else if (vector2.x < (double)screenshot.width)
  188. {
  189. newWidth = (int)vector2.x;
  190. newHeight = Mathf.RoundToInt(newWidth / num2);
  191. }
  192. else if (vector2.y < (double)screenshot.height)
  193. {
  194. newHeight = (int)vector2.y;
  195. newWidth = Mathf.RoundToInt(newHeight * num2);
  196. }
  197. TextureScale.Bilinear(screenshot, newWidth, newHeight);
  198. #endregion
  199. thum_byte_to_base64_ = "";
  200. thum_file_path_ = "";
  201. string filePath = Path.Combine(saveDirectory, $"mmsave{DateTime.Now:yyyyMMddHHmmss}.png");
  202. using (FileStream fileStream = File.Create(filePath))
  203. using (MemoryStream sceneStream = new MemoryStream(Encoding.Unicode.GetBytes(sceneString)))
  204. {
  205. byte[] screenshotBuffer = screenshot.EncodeToPNG();
  206. byte[] sceneBuffer = LZMA.Compress(sceneStream);
  207. fileStream.Write(screenshotBuffer, 0, screenshotBuffer.Length);
  208. fileStream.Write(sceneBuffer, 0, sceneBuffer.Length);
  209. }
  210. saveScenes.Add(new SavePng(new FileInfo(filePath), screenshot));
  211. selectedSave = saveScenes.Count - 1;
  212. }
  213. private static bool BytesEqual(byte[] a, byte[] b)
  214. {
  215. if (a.Length != b.Length) return false;
  216. for (int i = 0; i < a.Length; i++)
  217. {
  218. if (a[i] != b[i]) return false;
  219. }
  220. return true;
  221. }
  222. class SavePng
  223. {
  224. public FileInfo info { get; }
  225. public Texture2D screenshot { get; }
  226. public SavePng(FileInfo info, Texture2D screenshot)
  227. {
  228. this.info = info;
  229. this.screenshot = screenshot;
  230. }
  231. }
  232. }
  233. }