/Assets/Scripts/Tes/UnityBinaryReader.cs

https://bitbucket.org/rusoaica/judgement-day-map-editor · C# · 450 lines · 383 code · 58 blank · 9 comment · 35 complexity · 73059107d649361ac12abc9fff935c58 MD5 · raw file

  1. using System;
  2. using System.IO;
  3. using UnityEngine;
  4. #pragma warning disable 0168
  5. public class UnityBinaryReader : IDisposable
  6. {
  7. private BinaryReader _reader;
  8. private byte[] _readBuffer = new byte[16]; //buffer the size of a decimal, created to minimize allocations
  9. public Stream BaseStream
  10. {
  11. get { return _reader.BaseStream; }
  12. }
  13. public UnityBinaryReader(Stream _input)
  14. {
  15. _reader = new BinaryReader(_input);
  16. }
  17. public UnityBinaryReader(Stream _input, System.Text.Encoding _encoding)
  18. {
  19. _reader = new BinaryReader(_input);
  20. }
  21. void IDisposable.Dispose()
  22. {
  23. Close();
  24. }
  25. ~UnityBinaryReader()
  26. {
  27. Close();
  28. }
  29. public void Close()
  30. {
  31. if (_reader != null)
  32. {
  33. _reader.Close();
  34. _reader = null;
  35. }
  36. }
  37. public byte ReadByte()
  38. {
  39. return _reader.ReadByte();
  40. }
  41. public sbyte ReadSByte()
  42. {
  43. return _reader.ReadSByte();
  44. }
  45. public void Read(byte[] _buffer, int _index, int _count)
  46. {
  47. _reader.Read(_buffer, _index, _count);
  48. }
  49. public byte[] ReadBytes(int _count)
  50. {
  51. return _reader.ReadBytes(_count);
  52. }
  53. public byte[] ReadRestOfBytes()
  54. {
  55. var _remaining_byte_count = _reader.BaseStream.Length - _reader.BaseStream.Position;
  56. Debug.Assert(_remaining_byte_count <= int.MaxValue);
  57. return _reader.ReadBytes((int)_remaining_byte_count);
  58. }
  59. public void ReadRestOfBytes(byte[] _buffer, int _start_index)
  60. {
  61. var _remaining_byte_count = _reader.BaseStream.Length - _reader.BaseStream.Position;
  62. Debug.Assert((_start_index >= 0) && (_remaining_byte_count <= int.MaxValue) && ((_start_index + _remaining_byte_count) <= _buffer.Length));
  63. _reader.Read(_buffer, _start_index, (int)_remaining_byte_count);
  64. }
  65. public string ReadASCIIString(int _length)
  66. {
  67. Debug.Assert(_length >= 0);
  68. return System.Text.Encoding.ASCII.GetString(_reader.ReadBytes(_length));
  69. }
  70. public string ReadPossiblyNullTerminatedASCIIString(int _length_including_possible_null_terminator)
  71. {
  72. Debug.Assert(_length_including_possible_null_terminator > 0);
  73. var _bytes = _reader.ReadBytes(_length_including_possible_null_terminator);
  74. var _char_count = (Utils.Last(_bytes) != 0) ? _bytes.Length : (_bytes.Length - 1); // Ignore the null terminator.
  75. return System.Text.Encoding.Default.GetString(_bytes, 0, _char_count);
  76. }
  77. #region Little Endian
  78. public bool ReadLEBool32()
  79. {
  80. return ReadLEUInt32() != 0;
  81. }
  82. public ushort ReadLEUInt16()
  83. {
  84. _reader.Read(_readBuffer, 0, 2);
  85. return (ushort)((_readBuffer[1] << 8) | _readBuffer[0]);
  86. }
  87. public uint ReadLEUInt32()
  88. {
  89. _reader.Read(_readBuffer, 0, 4);
  90. return ((uint)_readBuffer[3] << 24) | ((uint)_readBuffer[2] << 16) | ((uint)_readBuffer[1] << 8) | _readBuffer[0];
  91. }
  92. public ulong ReadLEUInt64()
  93. {
  94. _reader.Read(_readBuffer, 0, 8);
  95. return ((ulong)_readBuffer[7] << 56) | ((ulong)_readBuffer[6] << 48) | ((ulong)_readBuffer[5] << 40) | ((ulong)_readBuffer[4] << 32) | ((ulong)_readBuffer[3] << 24) | ((ulong)_readBuffer[2] << 16) | ((ulong)_readBuffer[1] << 8) | _readBuffer[0];
  96. }
  97. public short ReadLEInt16()
  98. {
  99. var _short_as_ushort = ReadLEUInt16();
  100. unsafe
  101. {
  102. return *((short*)(&_short_as_ushort));
  103. }
  104. }
  105. public int ReadLEInt32()
  106. {
  107. var _int_as_uint = ReadLEUInt32();
  108. unsafe
  109. {
  110. return *((int*)(&_int_as_uint));
  111. }
  112. }
  113. public long ReadLEInt64()
  114. {
  115. var _long_as_ulong = ReadLEUInt64();
  116. unsafe
  117. {
  118. return *((long*)(&_long_as_ulong));
  119. }
  120. }
  121. public float ReadLESingle()
  122. {
  123. var _single_as_uint = ReadLEUInt32();
  124. unsafe
  125. {
  126. return *((float*)(&_single_as_uint));
  127. }
  128. }
  129. public double ReadLEDouble()
  130. {
  131. var _double_as_uint = ReadLEUInt64();
  132. unsafe
  133. {
  134. return *((double*)(&_double_as_uint));
  135. }
  136. }
  137. public byte[] ReadLELength32PrefixedBytes()
  138. {
  139. var _length = ReadLEUInt32();
  140. return _reader.ReadBytes((int)_length);
  141. }
  142. public string ReadLELength32PrefixedASCIIString()
  143. {
  144. return System.Text.Encoding.ASCII.GetString(ReadLELength32PrefixedBytes());
  145. }
  146. public Vector2 ReadLEVector2()
  147. {
  148. var _x = ReadLESingle();
  149. var _y = ReadLESingle();
  150. return new Vector2(_x, _y);
  151. }
  152. public Vector3 ReadLEVector3()
  153. {
  154. var _x = ReadLESingle();
  155. var _y = ReadLESingle();
  156. var _z = ReadLESingle();
  157. return new Vector3(_x, _y, _z);
  158. }
  159. public Vector4 ReadLEVector4()
  160. {
  161. var _x = ReadLESingle();
  162. var _y = ReadLESingle();
  163. var _z = ReadLESingle();
  164. var _w = ReadLESingle();
  165. return new Vector4(_x, _y, _z, _w);
  166. }
  167. /// <summary>
  168. /// Reads a column-major 3x3 matrix but returns a functionally equivalent 4x4 matrix.
  169. /// </summary>
  170. public Matrix4x4 ReadLEColumnMajorMatrix3x3()
  171. {
  172. var _matrix = new Matrix4x4();
  173. for (int _column_index = 0; _column_index < 4; _column_index++)
  174. {
  175. for (int _row_index = 0; _row_index < 4; _row_index++)
  176. {
  177. if ((_row_index <= 2) && (_column_index <= 2)) // If we're in the 3x3 part of the matrix, read values. Otherwise, use the identity matrix.
  178. _matrix[_row_index, _column_index] = ReadLESingle();
  179. else
  180. _matrix[_row_index, _column_index] = (_row_index == _column_index) ? 1 : 0;
  181. }
  182. }
  183. return _matrix;
  184. }
  185. /// <summary>
  186. /// Reads a row-major 3x3 matrix but returns a functionally equivalent 4x4 matrix.
  187. /// </summary>
  188. public Matrix4x4 ReadLERowMajorMatrix3x3()
  189. {
  190. var _matrix = new Matrix4x4();
  191. for (int _row_index = 0; _row_index < 4; _row_index++)
  192. {
  193. for (int _column_index = 0; _column_index < 4; _column_index++)
  194. {
  195. if ((_row_index <= 2) && (_column_index <= 2))
  196. _matrix[_row_index, _column_index] = ReadLESingle();
  197. else
  198. _matrix[_row_index, _column_index] = (_row_index == _column_index) ? 1 : 0;
  199. }
  200. }
  201. return _matrix;
  202. }
  203. public Matrix4x4 ReadLEColumnMajorMatrix4x4()
  204. {
  205. var _matrix = new Matrix4x4();
  206. for (int _column_index = 0; _column_index < 4; _column_index++)
  207. for (int _row_index = 0; _row_index < 4; _row_index++)
  208. _matrix[_row_index, _column_index] = ReadLESingle();
  209. return _matrix;
  210. }
  211. public Matrix4x4 ReadLERowMajorMatrix4x4()
  212. {
  213. var _matrix = new Matrix4x4();
  214. for (int _row_index = 0; _row_index < 4; _row_index++)
  215. for (int _column_index = 0; _column_index < 4; _column_index++)
  216. _matrix[_row_index, _column_index] = ReadLESingle();
  217. return _matrix;
  218. }
  219. public Quaternion ReadLEQuaternionWFirst()
  220. {
  221. float _w = ReadLESingle();
  222. float _x = ReadLESingle();
  223. float _y = ReadLESingle();
  224. float _z = ReadLESingle();
  225. return new Quaternion(_x, _y, _z, _w);
  226. }
  227. public Quaternion ReadLEQuaternionWLast()
  228. {
  229. float _x = ReadLESingle();
  230. float _y = ReadLESingle();
  231. float _z = ReadLESingle();
  232. float _w = ReadLESingle();
  233. return new Quaternion(_x, _y, _z, _w);
  234. }
  235. #endregion
  236. #region Big Endian
  237. public bool ReadBEBool32()
  238. {
  239. return ReadBEUInt32() != 0;
  240. }
  241. public ushort ReadBEUInt16()
  242. {
  243. _reader.Read(_readBuffer, 0, 2);
  244. return (ushort)((_readBuffer[0] << 8) | _readBuffer[1]);
  245. }
  246. public uint ReadBEUInt32()
  247. {
  248. _reader.Read(_readBuffer, 0, 4);
  249. return ((uint)_readBuffer[0] << 24) | ((uint)_readBuffer[1] << 16) | ((uint)_readBuffer[2] << 8) | _readBuffer[3];
  250. }
  251. public ulong ReadBEUInt64()
  252. {
  253. _reader.Read(_readBuffer, 0, 8);
  254. return ((ulong)_readBuffer[0] << 56) | ((ulong)_readBuffer[1] << 48) | ((ulong)_readBuffer[2] << 40) | ((ulong)_readBuffer[3] << 32) | ((ulong)_readBuffer[4] << 24) | ((ulong)_readBuffer[5] << 16) | ((ulong)_readBuffer[6] << 8) | _readBuffer[7];
  255. }
  256. public short ReadBEInt16()
  257. {
  258. var _short_as_ushort = ReadBEUInt16();
  259. unsafe
  260. {
  261. return *((short*)(&_short_as_ushort));
  262. }
  263. }
  264. public int ReadBEInt32()
  265. {
  266. var _int_as_uint = ReadBEUInt32();
  267. unsafe
  268. {
  269. return *((int*)(&_int_as_uint));
  270. }
  271. }
  272. public long ReadBEInt64()
  273. {
  274. var _long_as_ulong = ReadBEUInt64();
  275. unsafe
  276. {
  277. return *((long*)(&_long_as_ulong));
  278. }
  279. }
  280. public float ReadBESingle()
  281. {
  282. var _single_as_uint = ReadBEUInt32();
  283. unsafe
  284. {
  285. return *((float*)(&_single_as_uint));
  286. }
  287. }
  288. public double ReadBEDouble()
  289. {
  290. var _double_as_uint = ReadBEUInt64();
  291. unsafe
  292. {
  293. return *((double*)(&_double_as_uint));
  294. }
  295. }
  296. public byte[] ReadBELength32PrefixedBytes()
  297. {
  298. var _length = ReadBEUInt32();
  299. return _reader.ReadBytes((int)_length);
  300. }
  301. public string ReadBELength32PrefixedASCIIString()
  302. {
  303. return System.Text.Encoding.ASCII.GetString(ReadBELength32PrefixedBytes());
  304. }
  305. public Vector2 ReadBEVector2()
  306. {
  307. var _x = ReadBESingle();
  308. var _y = ReadBESingle();
  309. return new Vector2(_x, _y);
  310. }
  311. public Vector3 ReadBEVector3()
  312. {
  313. var _x = ReadBESingle();
  314. var _y = ReadBESingle();
  315. var _z = ReadBESingle();
  316. return new Vector3(_x, _y, _z);
  317. }
  318. public Vector4 ReadBEVector4()
  319. {
  320. var _x = ReadBESingle();
  321. var _y = ReadBESingle();
  322. var _z = ReadBESingle();
  323. var _w = ReadBESingle();
  324. return new Vector4(_x, _y, _z, _w);
  325. }
  326. /// <summary>
  327. /// Reads a column-major 3x3 matrix but returns a functionally equivalent 4x4 matrix.
  328. /// </summary>
  329. public Matrix4x4 ReadBEColumnMajorMatrix3x3()
  330. {
  331. var _matrix = new Matrix4x4();
  332. for (int _column_index = 0; _column_index < 4; _column_index++)
  333. {
  334. for (int _row_index = 0; _row_index < 4; _row_index++)
  335. {
  336. if ((_row_index <= 2) && (_column_index <= 2)) // If we're in the 3x3 part of the matrix, read values. Otherwise, use the identity matrix.
  337. _matrix[_row_index, _column_index] = ReadBESingle();
  338. else
  339. _matrix[_row_index, _column_index] = (_row_index == _column_index) ? 1 : 0;
  340. }
  341. }
  342. return _matrix;
  343. }
  344. public Matrix4x4 ReadBERowMajorMatrix3x3()
  345. {
  346. var _matrix = new Matrix4x4();
  347. for (int _row_index = 0; _row_index < 4; _row_index++)
  348. {
  349. for (int _column_index = 0; _column_index < 4; _column_index++)
  350. {
  351. if ((_row_index <= 2) && (_column_index <= 2))
  352. _matrix[_row_index, _column_index] = ReadBESingle();
  353. else
  354. _matrix[_row_index, _column_index] = (_row_index == _column_index) ? 1 : 0;
  355. }
  356. }
  357. return _matrix;
  358. }
  359. public Matrix4x4 ReadBEColumnMajorMatrix4x4()
  360. {
  361. var _matrix = new Matrix4x4();
  362. for (int _column_index = 0; _column_index < 4; _column_index++)
  363. for (int _row_index = 0; _row_index < 4; _row_index++)
  364. _matrix[_row_index, _column_index] = ReadBESingle();
  365. return _matrix;
  366. }
  367. public Matrix4x4 ReadBERowMajorMatrix4x4()
  368. {
  369. var _matrix = new Matrix4x4();
  370. for (int _row_index = 0; _row_index < 4; _row_index++)
  371. for (int _column_index = 0; _column_index < 4; _column_index++)
  372. _matrix[_row_index, _column_index] = ReadBESingle();
  373. return _matrix;
  374. }
  375. public Quaternion ReadBEQuaternionWFirst()
  376. {
  377. float _w = ReadBESingle();
  378. float _x = ReadBESingle();
  379. float _y = ReadBESingle();
  380. float _z = ReadBESingle();
  381. return new Quaternion(_x, _y, _z, _w);
  382. }
  383. public Quaternion ReadBEQuaternionWLast()
  384. {
  385. float _x = ReadBESingle();
  386. float _y = ReadBESingle();
  387. float _z = ReadBESingle();
  388. float _w = ReadBESingle();
  389. return new Quaternion(_x, _y, _z, _w);
  390. }
  391. #endregion
  392. }