5.5 KiB
5.5 KiB
Console模块错误修复说明
🐛 已修复的问题
1. Rebuild Loop 错误
问题描述:
Trying to remove/add Background (UnityEngine.UI.Image) from/to rebuild list
while we are already inside a rebuild loop. This is not supported.
原因:
- 在
OnLogMessageReceived回调中立即调用RefreshLogDisplay()刷新UI - 在Unity的Canvas rebuild循环中修改UI元素会触发此错误
Canvas.ForceUpdateCanvases()在初始化时也会导致rebuild loop
修复方案:
ConsoleModule.cs
- ✅ 延迟刷新机制: 添加
needRefresh标志,不在回调中立即刷新UI
private bool needRefresh = false;
// 在OnLogMessageReceived中
needRefresh = true; // 标记需要刷新
// 在Update中
if (needRefresh)
{
needRefresh = false;
RefreshLogDisplay(); // 延迟到下一帧刷新
}
- ✅ 滚动位置延迟设置: 使用帧计数延迟设置滚动位置
private int lastRefreshFrame = -1;
// 只在刷新后的第2帧设置滚动位置
if (lockScroll && Time.frameCount > lastRefreshFrame + 1)
{
logScrollRect.verticalNormalizedPosition = 0f;
}
- ✅ 过滤器事件优化: 过滤器改变时也使用延迟刷新
private void OnInfoFilterChanged(bool value)
{
infoFilter = value;
needRefresh = true; // 而不是立即RefreshLogDisplay()
}
SettingsModule.cs
- ✅ 移除ForceUpdateCanvases: Canvas会自动在下一帧更新
private void ApplyResolution(Vector2 resolution)
{
mainWindow.sizeDelta = resolution;
currentResolutionText.text = $"当前窗口尺寸: {resolution.x} x {resolution.y}";
// 移除了 Canvas.ForceUpdateCanvases();
// Canvas会自动更新,不需要强制刷新
}
2. 中文字体警告
问题描述:
The character with Unicode value \u5F84 was not found in the [LiberationSans SDF]
font asset or any potential fallbacks.
原因:
- RuntimeUIGenerator使用的默认字体
LiberationSans SDF不支持中文字符 - TextMeshPro需要专门的中文字体资源
解决方案 (选择其一):
方案1: 使用中文字体 (推荐)
// 在游戏初始化时设置中文字体
UniversalDebugTool.Init();
// 加载支持中文的TMP字体
TMP_FontAsset chineseFont = Resources.Load<TMP_FontAsset>("Fonts/ChineseFont SDF");
UniversalDebugTool.SetSDFFont(chineseFont);
方案2: 禁用字体警告
在RuntimeUIGenerator的GetDefaultFont方法中添加过滤:
private static TMP_FontAsset GetDefaultFont()
{
// 禁用TMP字体警告
TMPro.TMP_Settings.warningsDisabled = true;
// 查找默认字体...
}
方案3: 创建中文字体资源
- 在Unity中:Window > TextMeshPro > Font Asset Creator
- 选择支持中文的字体(如Arial Unicode MS、Microsoft YaHei等)
- 设置Character Set为Unicode或Custom Characters
- 添加常用中文字符
- 生成字体资源并在代码中加载
📋 修改总结
文件变更
ConsoleModule.cs
- ✅ 添加
needRefresh标志 - ✅ 添加
lastRefreshFrame帧计数 - ✅ 修改
OnLogMessageReceived使用延迟刷新 - ✅ 修改
Update方法处理延迟刷新和滚动 - ✅ 修改所有过滤器事件使用延迟刷新
SettingsModule.cs
- ✅ 移除
Canvas.ForceUpdateCanvases()调用
性能影响
✅ 更好: 延迟刷新减少了不必要的UI重建
✅ 更稳定: 避免了rebuild loop错误
✅ 无副作用: 延迟一帧刷新对用户体验无影响
🧪 测试建议
1. 测试Rebuild Loop修复
void Start()
{
UniversalDebugTool.Init();
// 快速生成大量日志
for (int i = 0; i < 100; i++)
{
Debug.Log($"测试日志 {i}");
Debug.LogWarning($"警告 {i}");
Debug.LogError($"错误 {i}");
}
// 不应该再有rebuild loop错误
}
2. 测试滚动功能
void Update()
{
if (Input.GetKeyDown(KeyCode.Space))
{
Debug.Log($"新日志 - 帧数: {Time.frameCount}");
// 应该自动滚动到底部(如果锁定滚动已启用)
}
}
3. 测试过滤器
- 生成多种类型的日志
- 点击Console标签页
- 切换Info/Warning/Error/Fatal过滤器
- 不应该有rebuild loop错误
4. 测试分辨率设置
- 进入Settings标签页
- 修改宽度和高度
- 点击"应用"按钮
- 不应该有rebuild loop错误
⚠️ 注意事项
关于中文字体
如果你的游戏需要显示中文,必须:
- 创建或导入支持中文的TMP字体资源
- 在初始化后调用
UniversalDebugTool.SetSDFFont(yourChineseFont) - 或者在RuntimeUIGenerator中修改GetDefaultFont方法返回中文字体
最佳实践
public class GameInit : MonoBehaviour
{
[SerializeField] private TMP_FontAsset chineseFont;
void Start()
{
// 1. 初始化调试工具
UniversalDebugTool.Init();
// 2. 设置中文字体(如果需要)
if (chineseFont != null)
{
UniversalDebugTool.SetSDFFont(chineseFont);
}
// 3. 其他初始化...
}
}
✅ 预期结果
修复后,你应该看到:
- ✅ 没有 "Trying to remove/add ... from/to rebuild list" 错误
- ✅ Console正常显示日志
- ✅ 过滤器正常工作
- ✅ 滚动功能正常
- ⚠️ 可能仍有字体警告(如果没有设置中文字体)
字体警告不影响功能,只是文本显示为方块。如果需要中文显示,请按照上述方案添加中文字体。