NetMsg.cs 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247
  1. using UnityEngine;
  2. using System.Collections;
  3. using System;
  4. using System.Reflection;
  5. namespace Engine.Net
  6. {
  7. /// <summary>消息对象</summary>
  8. public class NetMsg
  9. {
  10. /// <summary>创建一个NetMsg对象</summary>
  11. public static NetMsg OnCreateNetMsg(int msgCode = 0)
  12. {
  13. return new NetMsg(msgCode);
  14. }
  15. /// <summary>创建一个NetMsg对象</summary>
  16. public static NetMsg OnCreateNetMsg(byte[] bytes)
  17. {
  18. return new NetMsg(bytes);
  19. }
  20. /// <summary>接受消息的最大长度</summary>
  21. public const int MAX_MSG_LEN = 81920;
  22. /// <summary>消息的固定最小长度</summary>
  23. public const int MIN_MSG_LEN = 12;
  24. /// <summary>消息内容长度</summary>
  25. public int nBodyLeng = 0;
  26. /// <summary>消息编号</summary>
  27. public int nCode = 0;
  28. public int UserId = -1;
  29. /// <summary>消息时序</summary>
  30. public short nSequence = 0;
  31. /// <summary>消息内容</summary>
  32. public NetBytes arrData = null;
  33. /// <summary>读取位置</summary>
  34. protected int nPos;
  35. public NetMsg()
  36. {
  37. arrData = new NetBytes();
  38. }
  39. public NetMsg(int msgCode)
  40. {
  41. nCode = msgCode;
  42. arrData = new NetBytes();
  43. }
  44. public NetMsg(byte[] bytes)
  45. {
  46. arrData = new NetBytes(bytes);
  47. }
  48. // 解包参数
  49. public virtual void UnPackMsg<T>(ref T x)
  50. {
  51. Type t = x.GetType();
  52. FieldInfo[] fields = t.GetFields();
  53. foreach (FieldInfo f in fields)
  54. {
  55. if (f.FieldType == typeof(int))
  56. {
  57. f.SetValue(x, arrData.ReadInt());
  58. }
  59. else if (f.FieldType == typeof(short))
  60. {
  61. f.SetValue(x, arrData.ReadShort());
  62. }
  63. else if (f.FieldType == typeof(byte))
  64. {
  65. f.SetValue(x, arrData.ReadByte());
  66. }
  67. else if (f.FieldType == typeof(byte[]))
  68. {
  69. f.SetValue(x, arrData.ReadByteArray());
  70. }
  71. else if (f.FieldType == typeof(bool))
  72. {
  73. f.SetValue(x, arrData.ReadBool());
  74. }
  75. else if (f.FieldType == typeof(float))
  76. {
  77. f.SetValue(x, arrData.ReadFloat());
  78. }
  79. else if (f.FieldType == typeof(Vector3))
  80. {
  81. f.SetValue(x, arrData.ReadVector3());
  82. }
  83. else if (f.FieldType == typeof(string))
  84. {
  85. f.SetValue(x, arrData.ReadString().Replace("\0", ""));//标准化;
  86. }
  87. else if(f.FieldType == typeof(char[]))
  88. {
  89. f.SetValue(x, arrData.ReadChars());
  90. }
  91. }
  92. }
  93. // 封装参数
  94. public virtual void PackMsg<T>(T x)
  95. {
  96. Type t = x.GetType();
  97. FieldInfo[] fields = t.GetFields();
  98. foreach (FieldInfo f in fields)
  99. {
  100. if (f.FieldType == typeof(int))
  101. {
  102. arrData.WriteInt((int)f.GetValue(x));
  103. }
  104. else if (f.FieldType == typeof(short))
  105. {
  106. arrData.WriteShort((short)f.GetValue(x));
  107. }
  108. else if (f.FieldType == typeof(byte))
  109. {
  110. arrData.WriteByte((byte)f.GetValue(x));
  111. }
  112. else if (f.FieldType == typeof(byte[]))
  113. {
  114. arrData.WriteByteArray((byte[])f.GetValue(x));
  115. }
  116. else if (f.FieldType == typeof(bool))
  117. {
  118. arrData.WriteBool((bool)f.GetValue(x));
  119. }
  120. else if (f.FieldType == typeof(float))
  121. {
  122. arrData.WriteFloat((float)f.GetValue(x));
  123. }
  124. else if (f.FieldType == typeof(Vector3))
  125. {
  126. arrData.WriteVector3((Vector3)f.GetValue(x));
  127. }
  128. else if (f.FieldType == typeof(string))
  129. {
  130. arrData.WriteString((string)f.GetValue(x), 20);
  131. }
  132. else if (f.FieldType == typeof(char[]))
  133. {
  134. arrData.WriteChars((char[])f.GetValue(x));
  135. }
  136. else
  137. {
  138. //CDebug.Log("打包数组参数" + f.FieldType);
  139. if (f.FieldType.IsArray)
  140. {
  141. System.Object[] datas = (System.Object[])f.GetValue(x);
  142. for(int i=0; i< datas.Length; i++)
  143. {
  144. PackMsg(datas[i]);
  145. }
  146. }
  147. }
  148. }
  149. }
  150. /// <summary>读取消息</summary>
  151. public virtual bool ReadMessage(byte[] buff, int nMsgSize)
  152. {
  153. if (buff != null)
  154. {
  155. if(nMsgSize< MIN_MSG_LEN)
  156. {
  157. return false;
  158. }
  159. //读取连接ID
  160. nCode = arrData.ReadInt();
  161. //读取用户id
  162. UserId = arrData.ReadInt();
  163. //消息包内容长度
  164. nBodyLeng = nMsgSize - MIN_MSG_LEN;
  165. if (nBodyLeng > MAX_MSG_LEN)
  166. {
  167. return false;
  168. }
  169. else
  170. {
  171. if (nBodyLeng <= 0)
  172. {
  173. return true;
  174. }
  175. //拷贝消息数据
  176. arrData.Data = new byte[nBodyLeng];
  177. Array.Copy(buff, MIN_MSG_LEN, arrData.Data, 0, nBodyLeng);
  178. arrData.Position = 0;
  179. return true;
  180. }
  181. }
  182. else
  183. {
  184. return false;
  185. }
  186. }
  187. /// <summary>消息打包</summary>
  188. public virtual byte[] FastPackMsg()
  189. {
  190. int packageSize = arrData.Length + MIN_MSG_LEN;
  191. NetBytes netBytes = new NetBytes();
  192. // 写入总长度
  193. netBytes.WriteInt(packageSize);
  194. // 写入消息号
  195. netBytes.WriteInt(nCode);
  196. // 写入用户id
  197. netBytes.WriteInt(UserId);
  198. // 写入其他数据
  199. if (arrData.Length > 0)
  200. netBytes.WriteBytes(arrData.Data, false);
  201. return netBytes.Data;
  202. }
  203. /// <summary>确保消息长度不会溢出</summary>
  204. private bool EnsureCap(int nCap)
  205. {
  206. if (arrData != null && arrData.Length >= nCap)
  207. return true;
  208. if (nCap > MAX_MSG_LEN)
  209. return false;
  210. int nCurSize = arrData == null ? 0 : arrData.Length;
  211. int nNewSize = Mathf.Max(nCurSize * 2, nCap);
  212. nNewSize = Mathf.Min(nNewSize, MAX_MSG_LEN);
  213. if (arrData == null)
  214. {
  215. arrData = new NetBytes(new byte[nNewSize]);
  216. }
  217. else
  218. {
  219. byte[] arrBytes = null;
  220. Array.Resize<byte>(ref arrBytes, nNewSize);
  221. arrData.Data = arrBytes;
  222. arrData.Position = 0;
  223. }
  224. return true;
  225. }
  226. }
  227. }