DefaultCompressionHelper.cs 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. //------------------------------------------------------------
  2. // Game Framework
  3. // Copyright © 2013-2021 loyalsoft. All rights reserved.
  4. // Homepage: http://www.game7000.com/
  5. // Feedback: http://www.game7000.com/
  6. //------------------------------------------------------------
  7. using GameFramework;
  8. using ICSharpCode.SharpZipLib.GZip;
  9. using System;
  10. using System.IO;
  11. namespace UnityGameFramework.Runtime
  12. {
  13. /// <summary>
  14. /// 默认压缩解压缩辅助器。
  15. /// </summary>
  16. public class DefaultCompressionHelper : Utility.Compression.ICompressionHelper
  17. {
  18. private const int CachedBytesLength = 0x1000;
  19. private readonly byte[] m_CachedBytes = new byte[CachedBytesLength];
  20. /// <summary>
  21. /// 压缩数据。
  22. /// </summary>
  23. /// <param name="bytes">要压缩的数据的二进制流。</param>
  24. /// <param name="offset">要压缩的数据的二进制流的偏移。</param>
  25. /// <param name="length">要压缩的数据的二进制流的长度。</param>
  26. /// <param name="compressedStream">压缩后的数据的二进制流。</param>
  27. /// <returns>是否压缩数据成功。</returns>
  28. public bool Compress(byte[] bytes, int offset, int length, Stream compressedStream)
  29. {
  30. if (bytes == null)
  31. {
  32. return false;
  33. }
  34. if (offset < 0 || length < 0 || offset + length > bytes.Length)
  35. {
  36. return false;
  37. }
  38. if (compressedStream == null)
  39. {
  40. return false;
  41. }
  42. try
  43. {
  44. GZipOutputStream gZipOutputStream = new GZipOutputStream(compressedStream);
  45. gZipOutputStream.Write(bytes, offset, length);
  46. gZipOutputStream.Finish();
  47. ProcessHeader(compressedStream);
  48. return true;
  49. }
  50. catch
  51. {
  52. return false;
  53. }
  54. }
  55. /// <summary>
  56. /// 压缩数据。
  57. /// </summary>
  58. /// <param name="stream">要压缩的数据的二进制流。</param>
  59. /// <param name="compressedStream">压缩后的数据的二进制流。</param>
  60. /// <returns>是否压缩数据成功。</returns>
  61. public bool Compress(Stream stream, Stream compressedStream)
  62. {
  63. if (stream == null)
  64. {
  65. return false;
  66. }
  67. if (compressedStream == null)
  68. {
  69. return false;
  70. }
  71. try
  72. {
  73. GZipOutputStream gZipOutputStream = new GZipOutputStream(compressedStream);
  74. int bytesRead = 0;
  75. while ((bytesRead = stream.Read(m_CachedBytes, 0, CachedBytesLength)) > 0)
  76. {
  77. gZipOutputStream.Write(m_CachedBytes, 0, bytesRead);
  78. }
  79. gZipOutputStream.Finish();
  80. ProcessHeader(compressedStream);
  81. return true;
  82. }
  83. catch
  84. {
  85. return false;
  86. }
  87. finally
  88. {
  89. Array.Clear(m_CachedBytes, 0, CachedBytesLength);
  90. }
  91. }
  92. /// <summary>
  93. /// 解压缩数据。
  94. /// </summary>
  95. /// <param name="bytes">要解压缩的数据的二进制流。</param>
  96. /// <param name="offset">要解压缩的数据的二进制流的偏移。</param>
  97. /// <param name="length">要解压缩的数据的二进制流的长度。</param>
  98. /// <param name="decompressedStream">解压缩后的数据的二进制流。</param>
  99. /// <returns>是否解压缩数据成功。</returns>
  100. public bool Decompress(byte[] bytes, int offset, int length, Stream decompressedStream)
  101. {
  102. if (bytes == null)
  103. {
  104. return false;
  105. }
  106. if (offset < 0 || length < 0 || offset + length > bytes.Length)
  107. {
  108. return false;
  109. }
  110. if (decompressedStream == null)
  111. {
  112. return false;
  113. }
  114. MemoryStream memoryStream = null;
  115. try
  116. {
  117. memoryStream = new MemoryStream(bytes, offset, length, false);
  118. using (GZipInputStream gZipInputStream = new GZipInputStream(memoryStream))
  119. {
  120. int bytesRead = 0;
  121. while ((bytesRead = gZipInputStream.Read(m_CachedBytes, 0, CachedBytesLength)) > 0)
  122. {
  123. decompressedStream.Write(m_CachedBytes, 0, bytesRead);
  124. }
  125. }
  126. return true;
  127. }
  128. catch
  129. {
  130. return false;
  131. }
  132. finally
  133. {
  134. if (memoryStream != null)
  135. {
  136. memoryStream.Dispose();
  137. memoryStream = null;
  138. }
  139. Array.Clear(m_CachedBytes, 0, CachedBytesLength);
  140. }
  141. }
  142. /// <summary>
  143. /// 解压缩数据。
  144. /// </summary>
  145. /// <param name="stream">要解压缩的数据的二进制流。</param>
  146. /// <param name="decompressedStream">解压缩后的数据的二进制流。</param>
  147. /// <returns>是否解压缩数据成功。</returns>
  148. public bool Decompress(Stream stream, Stream decompressedStream)
  149. {
  150. if (stream == null)
  151. {
  152. return false;
  153. }
  154. if (decompressedStream == null)
  155. {
  156. return false;
  157. }
  158. try
  159. {
  160. GZipInputStream gZipInputStream = new GZipInputStream(stream);
  161. int bytesRead = 0;
  162. while ((bytesRead = gZipInputStream.Read(m_CachedBytes, 0, CachedBytesLength)) > 0)
  163. {
  164. decompressedStream.Write(m_CachedBytes, 0, bytesRead);
  165. }
  166. return true;
  167. }
  168. catch
  169. {
  170. return false;
  171. }
  172. finally
  173. {
  174. Array.Clear(m_CachedBytes, 0, CachedBytesLength);
  175. }
  176. }
  177. private static void ProcessHeader(Stream compressedStream)
  178. {
  179. if (compressedStream.Length >= 8L)
  180. {
  181. long current = compressedStream.Position;
  182. compressedStream.Position = 4L;
  183. compressedStream.WriteByte(25);
  184. compressedStream.WriteByte(134);
  185. compressedStream.WriteByte(2);
  186. compressedStream.WriteByte(32);
  187. compressedStream.Position = current;
  188. }
  189. }
  190. }
  191. }