RedDotStackHelper.cs 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295
  1. using System.Collections.Generic;
  2. using System.Diagnostics;
  3. using Debug = UnityEngine.Debug;
  4. namespace YIUIFramework
  5. {
  6. public static class RedDotStackHelper
  7. {
  8. #region 操作
  9. static readonly string m_OsCountFormat = "自己改变数量 {0} >> {1}";
  10. static readonly string m_OsTipsFormat = "自己改变提示 {0} >> {1} >> {2}";
  11. static readonly string m_OsChildCountFormat = "有子类改变数量 {0} >> {1}";
  12. static readonly string m_OsChildTipsFormat = "有子类改变提示 {0} >> {1} >> {2}";
  13. /// <summary>
  14. /// 获取操作拼接
  15. /// </summary>
  16. public static string GetOS(this RedDotStack self, RedDotData currentData)
  17. {
  18. var sb = SbPool.Get();
  19. switch (self.RedDotOSType)
  20. {
  21. case ERedDotOSType.Count:
  22. sb.AppendFormat(self.FirstData.ChangeData.Key == currentData.Key ? m_OsCountFormat : m_OsChildCountFormat,
  23. self.OriginalCount, self.ChangeCount);
  24. break;
  25. case ERedDotOSType.Tips:
  26. sb.AppendFormat(self.FirstData.ChangeData.Key == currentData.Key ? m_OsTipsFormat : m_OsChildTipsFormat,
  27. self.ChangeTips, self.OriginalCount, self.ChangeCount);
  28. break;
  29. default:
  30. Debug.LogError("此枚举没有实现 " + self.RedDotOSType);
  31. break;
  32. }
  33. return SbPool.PutAndToStr(sb);
  34. }
  35. #endregion
  36. #region 时间
  37. static readonly string m_TimeFormat = "{0:D2}/{1:D2}/{2:D2} - {3:D2}:{4:D2}:{5:D2}";
  38. /// <summary>
  39. /// 获取操作时间
  40. /// </summary>
  41. public static string GetTime(this RedDotStack self)
  42. {
  43. var time = self.DataTime;
  44. var sb = SbPool.Get();
  45. sb.AppendFormat(m_TimeFormat, time.Year, time.Month, time.Day, time.Hour, time.Minute, time.Second);
  46. return SbPool.PutAndToStr(sb);
  47. }
  48. #endregion
  49. #region 来源
  50. static readonly string m_SourceFormat = "改变的红点ID: {0} 名称: {1}";
  51. static readonly string m_SourceCountFormat = " 当前提示: {0} >> {1} >> {2}";
  52. /// <summary>
  53. /// 来源
  54. /// </summary>
  55. public static string GetSource(this RedDotStack self)
  56. {
  57. var data = self.FirstData;
  58. var sb = SbPool.Get();
  59. sb.AppendFormat(m_SourceFormat, data.ChangeData.Config.Key,
  60. RedDotMgr.Inst.GetKeyDes(data.ChangeData.Config.Key));
  61. sb.AppendFormat(m_SourceCountFormat, data.ChangeTips, data.OriginalCount, data.ChangeCount);
  62. return SbPool.PutAndToStr(sb);
  63. }
  64. #endregion
  65. #region 详细堆栈 带缓存
  66. /// <summary>
  67. /// 缓存堆栈解析数据
  68. /// </summary>
  69. private static Dictionary<StackTrace, string> m_StackContentDic = new Dictionary<StackTrace, string>();
  70. private static void ClearStackContentDic()
  71. {
  72. m_StackContentDic.Clear();
  73. }
  74. #region 存储的值
  75. private static BoolPrefs g_StackHideUnityEngineBoolPrefs =
  76. new BoolPrefs("RedDot_StackHideUnityEngine", null, true);
  77. public static bool StackHideUnityEngine
  78. {
  79. get => g_StackHideUnityEngineBoolPrefs.Value;
  80. set
  81. {
  82. g_StackHideUnityEngineBoolPrefs.Value = value;
  83. ClearStackContentDic();
  84. }
  85. }
  86. private static BoolPrefs g_StackHideYIUIBindBoolPrefs =
  87. new BoolPrefs("RedDot_StackHideYIUIBind", null, true);
  88. public static bool StackHideYIUIBind
  89. {
  90. get => g_StackHideYIUIBindBoolPrefs.Value;
  91. set
  92. {
  93. g_StackHideYIUIBindBoolPrefs.Value = value;
  94. ClearStackContentDic();
  95. }
  96. }
  97. private static BoolPrefs g_StackHideYIUIFrameworkBoolPrefs =
  98. new BoolPrefs("RedDot_StackHideYIUIFramework", null, true);
  99. public static bool StackHideYIUIFramework
  100. {
  101. get => g_StackHideYIUIFrameworkBoolPrefs.Value;
  102. set
  103. {
  104. g_StackHideYIUIFrameworkBoolPrefs.Value = value;
  105. ClearStackContentDic();
  106. }
  107. }
  108. private static BoolPrefs g_ShowStackIndexBoolPrefs =
  109. new BoolPrefs("RedDot_ShowStackIndex", null, false);
  110. public static bool ShowStackIndex
  111. {
  112. get => g_ShowStackIndexBoolPrefs.Value;
  113. set
  114. {
  115. g_ShowStackIndexBoolPrefs.Value = value;
  116. ClearStackContentDic();
  117. }
  118. }
  119. private static BoolPrefs g_ShowFileNameStackBoolPrefs =
  120. new BoolPrefs("RedDot_ShowFileNameStack", null, true);
  121. public static bool ShowFileNameStack
  122. {
  123. get => g_ShowFileNameStackBoolPrefs.Value;
  124. set
  125. {
  126. g_ShowFileNameStackBoolPrefs.Value = value;
  127. ClearStackContentDic();
  128. }
  129. }
  130. private static BoolPrefs g_ShowFilePathBoolPrefs =
  131. new BoolPrefs("RedDot_ShowFilePath", null, false);
  132. public static bool ShowFilePath
  133. {
  134. get => g_ShowFilePathBoolPrefs.Value;
  135. set
  136. {
  137. g_ShowFilePathBoolPrefs.Value = value;
  138. ClearStackContentDic();
  139. }
  140. }
  141. #endregion
  142. /// <summary>
  143. /// 根据堆栈 获取到已经解析后的详细信息
  144. /// </summary>
  145. public static string GetStackContent(this RedDotStack self)
  146. {
  147. var stackTrace = self.StackTrace;
  148. m_StackContentDic.TryGetValue(stackTrace, out var content);
  149. if (content != null)
  150. {
  151. return content;
  152. }
  153. content = AnalysisStack(stackTrace);
  154. if (string.IsNullOrEmpty(content))
  155. {
  156. content = "无堆栈显示 可能都被屏蔽了";
  157. }
  158. m_StackContentDic.Add(stackTrace, content);
  159. return content;
  160. }
  161. static readonly string m_FrameFormat = "{0} {1}.{2} : {3} : {4}";
  162. static readonly string m_FileFormat = "\tFile: {0}";
  163. static readonly string m_StackContinueUnityEngine = "UnityEngine";
  164. static readonly string m_StackContinueUnityEngineTMP = "TMP";
  165. static readonly string m_StackContinueYIUIBind = "YIUIBind";
  166. static readonly string m_StackContinueYIUIFramework = "YIUIFramework";
  167. /// <summary>
  168. /// 解析堆栈
  169. /// 会隐藏 某些堆栈
  170. /// </summary>
  171. private static string AnalysisStack(StackTrace stackTrace)
  172. {
  173. var sb = SbPool.Get();
  174. var stackFrames = stackTrace.GetFrames();
  175. if (stackFrames != null)
  176. {
  177. for (int i = 0; i < stackFrames.Length; i++)
  178. {
  179. var stackFrame = stackFrames[i];
  180. var method = stackFrame.GetMethod();
  181. var declaring = method.DeclaringType;
  182. if (declaring == null)
  183. {
  184. continue;
  185. }
  186. var stackNamespace = declaring.Namespace ?? ""; //命名空间
  187. var className = declaring.Name; //类名
  188. if (StackHideUnityEngine)
  189. {
  190. if (stackNamespace.Contains(m_StackContinueUnityEngine))
  191. {
  192. continue;
  193. }
  194. if (stackNamespace.Contains(m_StackContinueUnityEngineTMP))
  195. {
  196. continue;
  197. }
  198. }
  199. if (StackHideYIUIBind)
  200. {
  201. if (stackNamespace.Contains(m_StackContinueYIUIBind))
  202. {
  203. continue;
  204. }
  205. }
  206. if (StackHideYIUIFramework)
  207. {
  208. if (stackNamespace.Contains(m_StackContinueYIUIFramework))
  209. {
  210. continue;
  211. }
  212. }
  213. sb.Append(string.Format(m_FrameFormat,
  214. ShowStackIndex ? i.ToString() : "", //堆栈索引
  215. stackNamespace, //命名空间
  216. className, //类名
  217. method.Name, //方法名
  218. stackFrame.GetFileLineNumber().ToString())); //所在行数
  219. //所在的文件路径
  220. if (ShowFileNameStack)
  221. {
  222. var fileName = stackFrame.GetFileName();
  223. if (string.IsNullOrEmpty(fileName))
  224. {
  225. continue;
  226. }
  227. sb.AppendLine();
  228. if (ShowFilePath)
  229. {
  230. sb.Append(string.Format(m_FileFormat, fileName));
  231. }
  232. else
  233. {
  234. var filePathArray = fileName.Split('\\');
  235. sb.Append(string.Format(m_FileFormat, filePathArray[filePathArray.Length - 1]));
  236. }
  237. }
  238. sb.AppendLine();
  239. sb.AppendLine();
  240. }
  241. }
  242. return SbPool.PutAndToStr(sb);
  243. }
  244. #endregion
  245. }
  246. }