Skip to content

适用于Unity的日志增强模块

前言

最近在捣鼓Unity的各种小轮子,用来扩展自己的框架吧~
这次介绍一下用于Unity的日志增强系统

功能介绍

这个东西想加入现有的项目非常容易,单个cs文件复制即用,在游戏启动时初始化一次即可。
保存的日志文件位于Application.persistentDataPath路径的/GameLog目录中,以日志文件创建时间命名,方便后期查阅。
当然实现的功能暂时也很简单,基本上只有同步输出到文件, 之后会准备一个工具来实时监控这个日志文件

实现方法

首先创建工具类LoggingUtils,将其设计为单例模式,包含3个方法:

类型 名称 说明
方法 public void Init 游戏启动时初始化的工作
方法 private void OnLogMessage 捕获到系统Log时的回调函数
方法 public void Update 定期更新,暂定为FixedUpdate
字段 Queue<LogItem> m_vLogs 存储单条日志的队列
字段 FileInfo m_logFileInfo 要写入的外部文件

其中,LogItem是存储单条日志信息的数据结构,代码如下

初始化

先来看Init方法
签名:public void Init()
在游戏启动时调用,如果有多个场景可以用一个MonoBehavior在其Awake方法中调用,一次运行中仅第一次调用会生效,重复调用不会出问题。

核心在于“注册回调”这一步,Unity提供了一个方法用于用户自己扩展日志系统,注册完这个回调后,使用Debug.Log之类的方法输出日志时,Unity会同时调用用户自定义的其他方法。
这是Unity5.x的写法,在老版本中写法略有差异,想要兼容老版本Unity的话需要加判断Unity版本的宏,不过我们这个就不考虑老版本了。

回调方法

当Unity输出日志信息时,会调用OnLogMessage这个方法。
签名:private void OnLogMessage(string condition, string stackTrace, LogType type)
其中condition是日志信息本体的字符串。
stackTrace是调用Debug.Log之类方法代码位置的调用栈信息。
type顾名思义是这条日志的类型,分为Log,Warning,Error等

我们这里还加入了时间戳信息

输出到文件

本来是想把这个步骤直接写进上一个方法里的,不过有时候写入文件这个操作是会产生异常的,所以我就把这个步骤改成了类似异步的写法,OnLogMessage中只是把日志项加入队列,然后定时检查这个队列,把队列最前的一条信息写入文件,如果产生异常则这次Update不做任何操作,日志项也不会被移除,直到成功写入文件

可能产生的异常其实就是文件锁,当另外一个进程(比如说之后要做的一个实时日志查看器)已经在读写某个文件时,第二个进程就不能再次打开进行操作了。

使用方法

这里就不提供完整的文件了,自行把上面几个片段拼起来再改成单例模式就能用~
准备一个继承自MonoBehavior的脚本,挂载到每个场景的任意GameObject上(推荐用一个专用初始化的空GO吧)。
脚本的Awake方法中调用初始化方法:

然后在FixUpdate里加入更新用的代码:

然后运行游戏,就算什么也不做的话,已经可以在日志文件中至少看到两条日志啦

日志文件的位置可以在Unity Console的第一条Log里找到

可以做的更好。。

还有很多想法没有实现,比如我们还没有用到调用栈信息,可以考虑当收到了一条Error级别的日志时,同时把调用栈也追加输出到文件中

有用! (0)
Published in瞎折腾

Be First to Comment

发表评论

电子邮件地址不会被公开。 必填项已用*标注