骨骼视觉实例、IDLE 绑定与独立播放状态

2026-09-20。将现有已导出的骨骼道具接入 native-backed Room 视觉后端,实际创建 Skeleton3D / Skin / AnimationPlayer,动画模型走独占生命周期,并由宿主显式推进时间。

完整全武器目标未完成,构造覆盖仍为 1099 / 1419,273 阻塞、47 缺定义 / 创建等级。此处的动画表现接线不等于完整原版动画调度、整图注册或攻击型 proc 已完成。

原版语义核对

本批读取原 5A2440、5A14D0、59B7C0、59B5B0:

  • 正常 Room 模型从实际骨骼的动画表建立条目;过滤名称以 * 开头的条目。源数据中的 BIND 可以使动画计数为正,不能把“没有可播放 idle”当作没有动画。
  • 5A14D0 的正常骨骼路径读取被引用 Skeleton 的动画名称;不能把所有分支都简化成 ANIMATION.NAME 或文件名。
  • NAME / DURATION 的特殊无骨骼模式与当前正常 Room 路径有区别。正常播放入口 59B5B0 读取 Ogre AnimationState 的 length;不把描述文件 DURATION 当作骨骼 clip 长度。
  • 622FB0 在有动画时查找 IDLE,以 loop=true、speed=1 的参数启动。找不到时不能任意播放列表第一项。

本批绑定明确记录原骨骼动画名、已导出 glTF clip 名、源时长、rig 骨骼和资源哈希。没有修改既有角色 / 道具脚本的所有通用动画命名规则。

数据预检

新增 tools/build_native_animated_visuals.py 与 F2NativeAnimatedVisuals:

  • 扫描前批的 73 个带骨骼候选。
  • 解析实际 rig / clip Skeleton XML,保留源 MESH、rig、manifest、clip 哈希。
  • 将原 IDLE 明确映射到已有导出片段;文件路径匹配保留 Windows 不区分大小写的语义,不混淆游戏的动画名称。
  • 校验 glTF 与外部 buffer 哈希、源动画计数的正下界、骨骼列表、表面数量和时长。
  • 检查当前切面没有未处理的 KEY、cloth/dangle、源缩放或非白顶点颜色遗漏;拒绝不能正确重采样的关键帧网格。
  • 当前 57 个可建立 IDLE 绑定,16 个保留待修:14 个稀疏关键帧网格、2 个缩放轨道。

这不是 57 个逐一 GPU 验收,也不是原版逐帧姿态等价证书。报告明确保留 native_pose_parity=false。现有导出几何、骨骼插值和完整动画表合并还需要更强验证;源文件哈希与名称对应只证明输入身份。

实际运行时

NativeGodotVisualView 统一静态 / 骨骼显示视图:

  • 骨骼实例载入真实 PackedScene,严格检查单 mesh、单 skeleton、指定 clip 和骨骼名称集合,不以别的片段兜底。
  • 复制每个实例的 AnimationLibrary 后才设置 loop / length;不修改导入资源或其他正在播放的实例。
  • 新实例恢复骨骼 pose,在接到真实 native-backed 节点后启动明确的 IDLE,并更新 t=0。
  • 动画使用手动时钟模式。NativeGodotModelInstance.AdvanceVisualAnimation 与资源库 AdvanceAnimations 由宿主给出 delta,不使用墙钟或随机起始相位。
  • 原 Room 材质、query flags 和 shadow 设置应用到 skinned mesh。
  • 原动态事件 / KEY 消费和原版完整动画 tick 尚未接入;这个时钟接口不等于已经接到正式整图更新或存档重放。

NativeGodotVisualModelLibrary 根据实际绑定数据报告有动画,新模型经已验证的共享缓存控制器返回独占句柄。两个同路径骨骼模型不共享播放状态。销毁实例会释放整棵 Skeleton / Player 子树和独占模型。

加载后的动画状态接入原烘焙事件:视觉烘焙关闭、碰撞烘焙保留;随后 BAKE=true setter 同样读取有动画状态。低层只返回 MeshInstance3D 的旧静态创建入口拒绝动画输入,不再可能静默退成静止模型。

验证

实际 GPU 探针使用源 CATTAIL_05.MESH 的两份实例,共 17 项检查通过:

  • 创建真实 Skeleton3D / Skin / AnimationPlayer;
  • 同路径仍为两个独占模型;
  • 烘焙位与 BAKE setter 使用实际动画状态;
  • IDLE 名称、起始位置、源时长与循环设置;
  • 每个实例的动画资源、骨骼 pose 和播放时钟独立;
  • 单实例推进不影响另一份;资源库 tick 分别推进两份;
  • 导入的原 Animation 资源没有被改成循环;
  • 原材质保持绑定;整棵动画节点及模型清理完成。

1799 条核心断言、389 项相关 Python 回归通过。原静态资源 44 项 GPU 生命周期检查重新通过。Godot C# 构建零警告 / 零错误,coresimlint 通过。

查看本轮 frame0.webp / frame1.webp(build/native_animated_visual/,短边 512 / quality 80),两份芦苇的弯曲姿态随推进改变,未出现重复骨架、明显拉伸或不透明背景块。最初暗背景让细茎难辨,因此只调整了探针的中性背景和照明,未修改正式地图设置。

局部评分:COMP-BALANCE=2、COMP-SAFE-EDGE=2、COMP-VALUE-GROUP=2、LIGHT-KEY-FILL=2、LIGHT-BLOOM-ABUSE=2、MOT-VOL=2;12/12,100%,A,无零分 / 硬门触发。这个评分只针对独立双实例预览的可读性与可见运动,不代表原版骨骼插值、混合、所有动画资源或游戏画面已经一致。

产物与下一项

代码:tools/build_native_animated_visuals.py、core_sim.io/F2NativeAnimatedVisuals.cs、NativeGodotVisualView.cs,以及视觉目录 / 资源库 / 实例的对应接线。

报告:build/f2/native_animated_visuals.json、build/native_animated_visual/result.json。日志:native_animated_visual_core.log、native_animated_visual_regression.log、native_animated_visual_build.log、native_animated_visual_lint.log、native_animated_visual_audit.log。

下一项先修复 14 个稀疏关键帧重采样和 2 个缩放轨道缺口,再继续验证完整动画状态、事件及整图初始化 / 注册。7 个 v1.41 网格也仍在独立未验证项中,未隐去。

按 godot-master 的资源隔离原则复制实例动画库,并用明确时钟推进,完成实际 GPU 帧核验。main 原地工作、未提交,没有 attach 原游戏。默认 warp_autosave.json SHA256 保持 9840fe858b6e311c73f8c2d4ed49912d59d71365f6278392811730e012d32a7f。