描述禁用引用完整性修复是一个轻量级SKSE插件,用于修复因破碎引用和放置在天际世界空间地面以下的导航网格数据而导致的微卡顿。在重型加载顺序中,部分记录最终会落到引擎边界以下的Z值(低于z=-30000)。这可能会给引擎造成持续的后台工作,并导致卡顿峰值。该插件会在这些引用的网格和纹理加载之前拦截它们,并自动修正无效数据。
感谢大家的支持,我们成功登上了热门模组榜,伙计们!
需求
什么 修复它受Z-Floor Patcher启发,这款SKSE插件遵循明确而严格的规则运行,确保仅修复有问题的记录。规则如下:
- 若记录被标记为初始禁用,且非持久化/无父级/未关联任务,且Z坐标不等于-30000,则自动将其设为-30000。
- 若记录被设为-30000或以下但未初始禁用,则授予该标记
- 如果记录被标记为已删除且不是导航网格,则移除已删除标记,添加初始禁用标记,并放到-30K位置
- 根据z-floor修补器的说明,将初始禁用导航的所有顶点放置在-30000处。
针对dll修改的每个ref,同时添加到playerRef的父级,并设置标志“设置启用状态与父级相反”,以确保它们不会因为意外或其他原因被重新启用。这只是一个同步安全措施,许多带有禁用ref的插件已经这么做了。
天际能容忍许多数据问题,但糟糕的放置坐标尤其令人恼火,因为它们仍会被渲染,尤其是被删除的引用在某些情况下可能导致游戏崩溃。
基本上,这个插件修复了游戏中未正确禁用因而仍在渲染的对象。它还修复了被标记为“已删除”的对象(你不应该用这种方式移除对象,这可能会导致问题),并修复了顶点垂直位置设置过低的导航网格。
禁用引用完整性修复 并非旨在成为通用的“性能魔法”模组。它旨在解决模组作者犯下的小错误,确保只有我们想要看到的内容被渲染。
核心行为核心插件中处理记录标志和位置的功能是从
基础物品交换器 源代码。
插件可在两个阶段运行:
- 主阶段使用InitItemImpl和Load3D虚表钩子,在网格和纹理加载前拦截引用。实际的卡顿防止正是在这里发生的。位于-30000且未带初始禁用标志的引用在此被无条件捕获并拦截,意味着任何排除逻辑都无法导致它们被静默跳过。
- 第二阶段在细胞加载事件和存档加载时运行。它负责正确处理Disable()调用、启用父级附着、导航网格顶点修正,并作为钩子可能遗漏的任何情况的兜底机制。此阶段在网格加载完成后触发,因此无法避免初始加载开销,但能确保后续游戏状态正确。
这可确保修正自动化,同时避免大范围盲改。这是一个无脚本的轻量级SKSE插件,因为它不包含脚本、无MCM菜单、无界面(SKSE框架、Prisma UI等),不添加任何游戏系统,采用事件驱动行为而非持续轮询。
该插件仅在细胞处理期间启用。
配置一切都可以在`中进行配置。
已禁用引用完整性修复.ini.
基本配置:
enable_logging = true
verbose_logging = false
log_level = 3
fix_references = true ; 启用参考修正逻辑。
fix_navmeshes = true ; 启用导航网格顶点低于地面的修正(实验性)
auto_fix_on_cell_load = true ; 在世界中移动时保持保护生效。
patch_interior = true ; 仅扫描并修复室内单元格。
patch_exterior = true ; 仅扫描并修复外部单元格。
include_deleted_refs = false ; 默认关闭。恢复已删除记录属于高级行为,仅当你理解其利弊时才应启用。
fix_all_init_disabled = false ; 对“最初禁用”引用的更积极处理。除非你特别需要,否则请保持关闭。
max_refs_per_batch = 0 ; 使用此参数限制每单元格工作量,若希望在承载较重的配置上进行更温和的增量清理。
排除与控制默认情况下,只有标记类型的引用被排除在修正之外。任何其他位于-30000且未设置初始禁用标志的表单类型都会被处理。
您可以通过INI排除已知的敏感内容:
这使您可以保留已知的边缘案例内容不被修改,同时仍能受益于其他地方的自动清理。DynDOLOD.esp默认已被设置为忽略,因为目前我不确定它所修改的初始禁用记录是否会导致其位置发生变化。
日志与诊断日志功能已内置且可配置。
- 标准 模式提供有用的操作摘要。
- 详细 此模式可用于深度故障排查。
- 日志级别 允许你将输出从仅错误调整到完整跟踪详情。1=错误,2=警告,3=信息,4=调试,5=跟踪
如果你正在测试口吃修复,日志有助于确认扫描了什么以及修复了什么。日志会记录记录类型和表单ID,这样你就可以自行查看哪些内容存在问题。
如果你想在游戏中验证该模组是否已应用其修复,可以使用“Prid”控制台命令。Prid允许在控制台中选中该引用,无论其状态(禁用/启用)如何。然后使用
更具信息性的控制台 你可以在实时状态下看到状态和Z轴位置。以下是一个使用示例:
Prid 0xFECF0871
以下是调试时预期会看到的日志示例:
剧透警告:
显示
[18:08:58.740] [33016] [I] 已禁用引用完整性修复 v1-1-0-0
[18:08:58.740] [33016] [I] [禁用引用完整性修复] 早期引用钩子已安装(InitItemImpl + Load3D)
[18:08:58.740] [33016] [I] 插件:Z-Floor 修补程序 v1.0.0
[18:08:58.740] [33016] [I] 作者:Alaxouche
[18:08:58.740] [33016] [I] 描述:用于修复错误禁用记录的SKSE插件
[18:08:58.740] [33016] [I]
[18:08:58.740] [33016] [I] 正在尝试注册消息接口...
[18:08:58.740] [33016] [I] 成功 - 已获取消息界面
[18:08:58.740] [33016] [I] 成功 - 消息处理器注册成功
[18:08:58.740] [33016] [I] [已禁用引用完整性修复] 已加载
[18:10:36.302] [19676] [I] [hooks:live] initSeen:1 initFixedPreLive:0 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:10:36.474] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门限 引用=0x01000DBC 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元=0x00009659 单元类型=外部 单元坐标=(4, -5) 基底=0x8500FE2D 源引用=wip Skyrim Regional Forests Framework 1.0.esp 源基底=wip Skyrim Regional Forests Framework 1.0.esp
[18:10:36.917] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0xFE41D4E1 oldZ=-30000.000 newZ=-30000.000 cell=0x000099C4 cellType=ext cellXY=(-1, -1) base=0x04039F87 srcRef=Serpents_Covenant_Merged.esp srcBase=Dragonborn.esm
[18:10:40.599] [19676] [信息] [引用修复] 阶段=初始化 原因=低于地板门限 引用=0x000C0627 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元=0x00009712 单元类型=外部 单元坐标=(5, -11) 基础=0x0001819B 源引用=Ivy - 河木镇风车花园.esp 源基础=Skyrim.esm
[18:10:40.648] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0x000C0628 oldZ=-30000.000 newZ=-30000.000 cell=0x00009712 cellType=ext cellXY=(5, -11) base=0x0001B0A9 srcRef=Ivy - Riverwood Windmill Garden.esp srcBase=Skyrim.esm
[18:10:40.649] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门 引用=0x000C053C 旧Z=-30000.000 新Z=-30000.000 单元格=0x00009712 单元格类型=外部 单元格坐标=(5, -11) 基础=0x0001B0A9 源引用=Ivy - Riverwood Windmill Garden.esp 源基础=Skyrim.esm
[18:10:41.287] [19676] [I] [hooks:live] initSeen:19580 initFixedPreLive:5 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:10:46.287] [19676] [I] [hooks:live] 初始化已见数:38398 初始化固定预直播数:5 初始化跳过(3d:0 附加:0 引用加载:0) 加载3d门控:0 | 诊断(检查通过:0 低于距离:0 排除:0) | 回退单元格:0 回退引用修复:0 导航网格事件单元格:0 导航网格事件顶点:0
[18:10:48.038] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0x00077E93 oldZ=-30000.000 newZ=-30000.000 cell=0x000093BF cellType=ext cellXY=(-11, 15) base=0x000C5860 srcRef=Environs - Hroggars House.esp srcBase=Skyrim.esm
[18:10:48.038] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门槛 引用=0x01001709 旧Z=-30000.000 新Z=-30000.000 单元格=0x000093BF 单元格类型=外部 单元格坐标=(-11, 15) 基底=0x8500AA2E 来源引用=Environs - Hroggars House.esp 来源基底=wip Skyrim Regional Forests Framework 1.0.esp
[18:10:49.461] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门限 引用=0xFECF0818 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元=0x000096F3 单元类型=外部 单元坐标=(5, -10) 基础=0x1F10E2E6 源引用=Northern Roads - Lux Via - Riverwood Wooden Bridge - Covered Bridge patch.esp 源基础=Lux Via.esp
[18:10:51.287] [19676] [I] [hooks:live] initSeen:56343 initFixedPreLive:8 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:10:52.742] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门 引用=0x000C3C6E 旧Z=-30000.000 新Z=-30000.000 单元格=0x00009883 单元格类型=外部 单元格坐标=(8, -23) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:52.743] [19676] [I] [ref修复] 阶段=初始化 原因=低于地板界限 引用=0x000C3C69 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元格=0x00009883 单元格类型=外部 单元格坐标=(8, -23) 基础=0x00050D03 来源引用=MoveableChain.esp 来源基础=Skyrim.esm
[18:10:52.746] [19676] [信息] [引用修复] 阶段=初始化 原因=低于地板闸门 引用=0x000C3C65 旧Z=-30000.000 新Z=-30000.000 单元格=0x00009883 单元格类型=外部 单元格坐标=(8, -23) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:55.230] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门 引用=0x0001D70A 旧Z=-30000.000 新Z=-30000.000 单元=0x00009440 单元类型=外部 单元坐标=(-8, 11) 基础=0x00026FDD 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:55.250] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板边界 引用=0x00061415 旧Z=-30000.000 新Z=-30000.000 单元=0x0000943E 单元类型=外部 单元坐标=(-6, 11) 基底=0x00050D03 源引用=MoveableChain.esp 源基底=Skyrim.esm
[18:10:55.251] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板闸门 引用=0x00061417 旧Z=-30000.000 新Z=-30000.000 单元格=0x0000943E 单元格类型=外部 单元格坐标=(-6, 11) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:55.252] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地面门限 引用=0x00061413 旧Z=-30000.000 新Z=-30000.000 单元=0x0000943E 单元类型=外部 单元坐标=(-6, 11) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:55.253] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门限 引用=0x00061419 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元格=0x0000943E 单元格类型=外部 单元格坐标=(-6, 11) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:55.253] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地面门限 引用=0x00061410 旧Z=-30000.000 新Z=-30000.000 单元格=0x0000943E 单元格类型=室外 单元格坐标=(-6, 11) 基础=0x00050D03 来源引用=MoveableChain.esp 来源基础=Skyrim.esm
[18:10:55.256] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门 引用=0x00061418 旧Z=-30000.000 新Z=-30000.000 单元=0x0000943E 单元类型=外部 单元坐标=(-6, 11) 基础=0x00050D03 源引用=MoveableChain.esp 源基础=Skyrim.esm
[18:10:56.287] [19676] [I] [hooks:live] initSeen:73430 initFixedPreLive:18 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:11:01.287] [19676] [I] [挂钩:实时] 初始化已见:89584 初始化固定预直播:18 初始化跳过(3D:0 已附加:0 引用已加载:0) 加载3D门控:0 | 诊断(洞穴正常:0 低于距离:0 排除:0) | 备用单元:0 备用引用修复:0 导航网格事件单元:0 导航网格事件顶点:0
[18:11:06.287] [19676] [I] [hooks:live] initSeen:105715 initFixedPreLive:18 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:11:11.287] [19676] [I] [hooks:live] 初始化已见:121226 初始化固定预直播:18 初始化跳过(3d:0 附加:0 引用已加载:0) 加载3d门控:0 | 诊断(cairOk:0 belowDis:0 excl:0) | 备用单元格:0 备用引用修复:0 导航网格事件单元格:0 导航网格事件顶点:0
[18:11:16.287] [19676] [I] [hooks:live] initSeen:136622 initFixedPreLive:18 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:11:17.896] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0x5A000808 oldZ=-30000.000 newZ=-30000.000 cell=0x0000BCB0 cellType=ext cellXY=(41, -23) base=0x00049441 srcRef=Riften Docks Overhaul.esp srcBase=Skyrim.esm
[18:11:17.914] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0x5A000881 oldZ=-30000.000 newZ=-30000.000 cell=0x0000BCB0 cellType=ext cellXY=(41, -23) base=0x00097F68 srcRef=Riften Docks Overhaul.esp srcBase=Skyrim.esm
[18:11:17.946] [19676] [I] [ref-fix] stage=init reason=below_floor_gate ref=0x5A000884 oldZ=-30000.000 newZ=-30000.000 cell=0x0000BCB0 cellType=ext cellXY=(41, -23) base=0x00093D2C srcRef=Riften Docks Overhaul.esp srcBase=Skyrim.esm
[18:11:21.287] [19676] [I] [hooks:live] initSeen:152350 initFixedPreLive:21 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:11:26.287] [19676] [I] [钩子:实时] 初始化已见:166821 初始化固定预实时:21 初始化跳过(3d:0 附加:0 引用已加载:0) 加载3d门控:0 | 诊断(洞穴正常:0 下方显示:0 排除:0) | 回退单元:0 回退引用修复:0 导航网格事件单元:0 导航网格事件顶点:0
[18:11:31.287] [19676] [I] [hooks:live] initSeen:180878 initFixedPreLive:21 initSkip(3d:0 attached:0 refsLoaded:0) load3dGated:0 | diag(cairOk:0 belowDis:0 excl:0) | fallbackCells:0 fallbackRefFixes:0 navmeshEventCells:0 navmeshEventVerts:0
[18:11:36.287] [19676] [I] [挂钩:直播] 初始化已见:194101 初始化固定预直播:21 初始化跳过(3D:0 附加:0 引用已加载:0) 加载3D门控:0 | 诊断(CAIR正常:0 低于距离:0 排除:0) | 回退单元格:0 回退引用修复:0 导航网格事件单元格:0 导航网格事件顶点:0
[18:11:36.452] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门 引用=0x00015B2A 旧Z=-30000.000 新Z=-30000.000 单元格=0x00009292 单元格类型=外部 单元格坐标=(-7, 24) 基础=0x8500592E 源引用=改 天际区域森林框架 1.0.esp 源基础=改 天际区域森林框架 1.0.esp
[18:11:37.644] [19676] [I] [ref-fix] 阶段=初始化 原因=低于地板门槛 引用=0xFE18D999 旧Z坐标=-30000.000 新Z坐标=-30000.000 单元格=0x00009A07 单元格类型=外部 单元格坐标=(-2, -3) 基础=0xFE382824 源引用=Environs - Tundra Farmhouse.esp 源基础=Dynamic Things Alternative.esp
兼容性专为打造
天际 特别版/周年纪念版/VR版. 兼容1.5.97和1.6.1170。其他版本未经测试。
常规兼容性说明:
- 兼容任何创建或修改记录的模组。
- 补充加载顺序清理和冲突解决,但不替代它们。
- 其他SKSE插件: 无已知冲突。
一如既往,如果你启用了实验性设置,请先在自有环境中进行测试。
性能预期与限制此模组允许正确禁用并因此不渲染不需要的记录。这些记录大多由其他模组导致。
游戏内容概览:
这个效果会随着你拥有的模组数量而扩展。我的模组只修复非原版游戏内容。除非你使用的模组确实有问题,否则你几乎不会注意到性能和稳定性的显著提升。
不该期待的内容:
- 它不会修复无关的瓶颈问题(脚本、绘制调用、纹理、CPU限制等)。
- 它并非通常意义上的FPS提升工具,而只是一个记录修复器。
尽管有非常严格的规则系统,此模组仍有可能会改动到非预期的记录。某些记录被禁用但未被设为-30000,是因为它们被任务使用、具有关联的父级、或属于持续引用等。某些记录类型不应被改动,例如标记类。如果您发现任何问题,请向我报告,以便我更深入检查并将这些引用排除在该插件的修改范围之外。您也可以将特定记录或插件加入黑名单。
请考虑,如果你经验足够丰富,在XEdit中手动修复这些问题,总好过完全依赖本工具。本工具仅作为针对这些特定记录所引发问题的额外防护。
FAQ问:在存档中途安装这个安全吗?
A:是的。
问:我是否应该立即启用所有选项?
A:从默认设置开始,进行试玩测试,只有在有明确理由时才启用实验性选项。
问:我需要一直开启详细日志记录吗?
A: 不。正常游玩时请保持详细模式关闭。仅在调试时临时使用。
制作人员与源代码- SKSE团队制作SKSE
- Ryan McKenzie 制作,基于 CommonLibSSE
- CharmedBaryon 用于 CommonLibSSE-NG-VR
- 嘟嘟姆 用于指示核心故障
- 超级创 用于 ClibDT - CommonLib 开发工具包
- 三人之力 用于Base Object Swapper源代码,作为模板使用
- 帕秋莉开发, Quantumyilmaz, 沙兹德2, J3w3ls, 田野上闪耀着的微光 感谢他们的协助、故障排查与建议
- 模组公会及所有Beta测试者,感谢他们抽出时间进行测试并提供反馈
源代码可在以下位置找到
这里.