1.效果圖

image

image
2.相應(yīng)代碼塊DebugerGUI
using System.Collections.Generic;
using System.Diagnostics;
using UnityEngine;
namespace Custom.Log
{
class DebugerGUI : MonoBehaviour
{
struct Log
{
public string message;
public string stackTrace;
public LogType type;
}
#region Inspector Settings
/// <summary>
/// 顯示和隱藏控制臺(tái)窗口的熱鍵。
/// </summary>
[Header("顯示和隱藏控制臺(tái)窗口的熱鍵")]
public KeyCode toggleKey = KeyCode.BackQuote;
/// <summary>
/// 在打印的時(shí)候是否開啟堆棧打印
/// </summary>
[Header("是否開啟堆棧打印")]
public bool StackLog = false;
/// <summary>
///是否保留一定數(shù)量的日志
/// </summary>
[Header("是否保留一定數(shù)量的日志")]
public bool restrictLogCount = true;
/// <summary>
/// 是否通過搖動(dòng)設(shè)備(僅移動(dòng)設(shè)備)來打開窗戶
/// </summary>
[Header("是否通過搖動(dòng)設(shè)備(僅移動(dòng)設(shè)備)來打開窗戶")]
public bool shakeToOpen = true;
/// <summary>
/// 顯示字體大小
/// </summary>
[Header("顯示字體大小")]
public float FontSize = 30;
/// <summary>
/// 顯示字體大小
/// </summary>
[Header("顯示拖動(dòng)條寬度")]
public float ScrollbarSize = 50;
/// <summary>
/// (平方)在上面的加速度,窗口應(yīng)該打開
/// </summary>
[Header("(平方)在上面的加速度,窗口應(yīng)該打開")]
public float shakeAcceleration = 100f;
/// <summary>
/// 在刪除舊的日志之前保持日志的數(shù)量。
/// </summary>
[Header("在刪除舊的日志之前保持日志的數(shù)量")]
public int maxLogs = 1000;
#endregion
readonly List<Log> logs = new List<Log>();
/// <summary>
/// 對(duì)應(yīng)橫向、縱向滑動(dòng)條對(duì)應(yīng)的X,Y數(shù)值
/// </summary>
public Vector2 scrollPosition;
/// <summary>
/// 可見
/// </summary>
private bool visible;
/// <summary>
/// 折疊
/// </summary>
private bool collapse;
// Visual elements:
private static readonly Dictionary<LogType, Color> logTypeColors = new Dictionary<LogType, Color>
{
{ LogType.Assert, Color.white },
{ LogType.Error, Color.red },
{ LogType.Exception, Color.magenta },
{ LogType.Log, Color.green },
{ LogType.Warning, Color.yellow },
};
#region OnGUI
private const string windowTitle = "Debug(打印日志)";
//邊緣
private const int margin = 20;
private static readonly GUIContent clearLabel = new GUIContent("Clear", "清空打印信息.");
private static readonly GUIContent colseLabel = new GUIContent("Close", "關(guān)閉打印面板.");
//折疊
private static readonly GUIContent collapseLabel = new GUIContent("Collapse", "隱藏重復(fù)信息.");
private readonly Rect titleBarRect = new Rect(0, 0, 10000, 20);
private Rect windowRect = new Rect(margin, margin, Screen.width - (margin * 2), Screen.height - (margin * 2));
#endregion
void OnEnable()
{
Application.logMessageReceived += HandleLog;
}
void OnDisable()
{
Application.logMessageReceived -= HandleLog;
}
void Update()
{
Running();
}
[Conditional("EnableLog")]
public void Running()
{
if (Input.GetKeyDown(toggleKey))
{
visible = !visible;
}
if (shakeToOpen && Input.acceleration.sqrMagnitude > shakeAcceleration || Input.touchCount >= 6)
{
visible = true;
}
if (Input.touchCount >= 3)
{
visible = true;
}
}
void OnGUI()
{
if (!visible)
{
return;
}
windowRect = GUILayout.Window(666, windowRect, DrawConsoleWindow, windowTitle);
}
/// <summary>
/// 顯示一個(gè)列出已記錄日志的窗口。
/// </summary>
/// <param name="windowID">Window ID.</param>
private void DrawConsoleWindow(int windowID)
{
DrawLogsList();
DrawToolbar();
//允許拖動(dòng)window的觸發(fā)范圍.
GUI.DragWindow(titleBarRect);
}
/// <summary>
/// 繪制log列表
/// </summary>
private void DrawLogsList()
{
GUIStyle gs_vertica = GUI.skin.verticalScrollbar;
GUIStyle gs1_vertica = GUI.skin.verticalScrollbarThumb;
gs_vertica.fixedWidth = ScrollbarSize;
gs1_vertica.fixedWidth = ScrollbarSize;
GUIStyle gs_horizontal = GUI.skin.horizontalScrollbar;
GUIStyle gs1_horizontal = GUI.skin.horizontalScrollbarThumb;
gs_horizontal.fixedHeight = ScrollbarSize;
gs1_horizontal.fixedHeight = ScrollbarSize;
scrollPosition = GUILayout.BeginScrollView(scrollPosition, false, true);
//scrollPosition = GUILayout.BeginScrollView(scrollPosition,true,true, customGuiStyle, customGuiStyle);
for (var i = 0; i < logs.Count; i++)
{
var log = logs[i];
//如果選擇折疊選項(xiàng),則組合相同的消息。
if (collapse && i > 0)
{
var previousMessage = logs[i - 1].message;
if (log.message == previousMessage)
{
continue;
}
}
GUI.contentColor = logTypeColors[log.type];
GUILayout.Label(log.message);
if (StackLog)
{
GUILayout.Label(log.stackTrace);
}
}
GUI.color = Color.magenta;
GUILayout.EndScrollView();
gs_vertica.fixedWidth = 0;
gs1_vertica.fixedWidth = 0;
gs_horizontal.fixedHeight = 0;
gs1_horizontal.fixedHeight = 0;
// 在繪制其他組件之前,確保GUI顏色被重置。
GUI.contentColor = Color.white;
}
/// <summary>
/// Log日志工具欄
/// </summary>
private void DrawToolbar()
{
GUILayout.BeginHorizontal();
if (GUILayout.Button(clearLabel, GUILayout.Height(40)))
{
logs.Clear();
}
if (GUILayout.Button("Stack開關(guān)", GUILayout.Height(40)))
{
StackLog = !StackLog;
}
if (GUILayout.Button(colseLabel, GUILayout.Height(40)))
{
visible = false;
}
collapse = GUILayout.Toggle(collapse, collapseLabel, GUILayout.ExpandWidth(true), GUILayout.Height(40));// GUILayout.ExpandWidth保持長寬一致
GUILayout.EndHorizontal();
}
/// <summary>
/// Debug 對(duì)應(yīng)的回調(diào)處理
/// </summary>
/// <param name="message">信息.</param>
/// <param name="stackTrace">信息的來源</param>
/// <param name="type">信息類型 (error, exception, warning, assert).</param>
private void HandleLog(string message, string stackTrace, LogType type)
{
logs.Add(new Log
{
message = "<size=" + FontSize + ">" + message + "</size>",
stackTrace = "<size=" + FontSize + ">" + stackTrace + "</size>",
type = type,
});
TrimExcessLogs();
}
/// <summary>
/// 刪除超過允許的最大數(shù)量的舊日志。
/// </summary>
private void TrimExcessLogs()
{
if (!restrictLogCount)
{
return;
}
var amountToRemove = Mathf.Max(logs.Count - maxLogs, 0);
if (amountToRemove == 0)
{
return;
}
logs.RemoveRange(0, amountToRemove);
}
}
}