24 KiB
手动测试 12 · 区域相机系统
测试类型:Unity Editor 手动测试(Play Mode)
覆盖模块:CameraArea、CameraTriggerZone、CameraStateController、CinemachineConfiner2D、CameraBlendProfileSO
前置文档:Phase1_Verification_Guide.md§1(验证前准备)
快速工具
| 工具 | 用途 | 菜单路径 |
|---|---|---|
| Camera Area Setup(窗口) | 扫描场景中所有 CameraArea/TriggerZone/Controller,显示绑定状态,提供一键修复 | BaseGames → Camera → Camera Area Setup |
| Place Camera Area | 生成 CameraArea 节点(含 PolygonCollider2D 限位边界) | BaseGames → Scene → Place → Camera Area |
| Place Camera Trigger Zone | 生成 CameraTriggerZone + BoxCollider2D Trigger | BaseGames → Scene → Place → Camera Trigger Zone |
典型工作流:
- 在 Persistent 场景中放置两台全局虚拟相机(
VCamA/VCamB),绑定到CameraStateController._vcamA/_vcamB。 - 在关卡场景中使用 Place Camera Area 为每个相机区域放置
CameraArea数据节点(一个房间可放多个)。 - 选中
CameraArea,在 Scene 视图中拖拽黄色可视区域的边 Handle 调整可见范围,然后点击 Inspector 底部 「从可视区域更新限位区域(透视)」 自动换算限位多边形。 - 使用 Place Camera Trigger Zone 在区域入口放置触发器,并将目标
CameraArea拖入_targetArea。 - 打开 Camera Area Setup 窗口,点击 为全局 VCam 赋值 Follow 目标(会自动在 Player 下创建或复用
CameraFollowTarget子节点并绑定)。 - 所有条目显示绿色 ● → 进入 Play Mode 验证。
目录
- 系统架构说明
- Persistent 场景配置(CameraStateController)
- 关卡场景配置(CameraArea + CameraTriggerZone)
- ScriptableObject 资产说明
- Camera Area Setup 工具详解
- 验收测试用例
- 常见问题排查
1. 系统架构说明
Persistent.unity
└── [Camera]
└── CameraStateController ExecutionOrder = -100
组件: CameraStateController
│ _vcamA → VCamA(全局虚拟相机 A)
│ _vcamB → VCamB(全局虚拟相机 B)
│ _lookSystem → CameraLookSystem 节点
组件: CinemachineBrain ← 实际渲染相机(随 Main Camera 放置)
组件: CinemachineImpulseSource ← 屏幕抖动信号源
├── CameraLookSystem ← 运行时由 SetFollowTarget() 赋值基准目标
│ 组件: CameraLookSystem 双轴窥视偏移 + 速度门控;输出 VirtualTarget
├── VCamA
│ 组件: CinemachineCamera Follow = CameraLookSystem.VirtualTarget(运行时自动赋值)
│ 组件: CinemachinePositionComposer Body 跟随组件;初始值与 CameraArea 默认值对齐
│ 组件: CinemachineConfiner2D ← 由 CameraStateController 动态更新 BoundingShape2D
│ 组件: CameraAxisLockExtension 锁定 X 或 Y 轴(竖井 / 走廊场景)
│ 组件: CameraAsymmetricDampingExtension 非对称 Y 阻尼(下落快恢复,起跳慢追赶)
│ 组件: CameraAdaptiveLookaheadExtension 速度自适应 Lookahead(移动快 → 预见更多)
└── VCamB
组件: CinemachineCamera Follow = CameraLookSystem.VirtualTarget(运行时自动赋值)
组件: CinemachinePositionComposer 同 VCamA
组件: CinemachineConfiner2D ← 由 CameraStateController 动态更新 BoundingShape2D
组件: CameraAxisLockExtension
组件: CameraAsymmetricDampingExtension
组件: CameraAdaptiveLookaheadExtension
Level_01.unity
├── [CameraAreas]
│ ├── CameraArea_A 区域 A(可在同一房间内放置多个)
│ │ 组件: CameraArea _confinerCollider → PolygonCollider2D
│ │ │ _visibleBounds(可视矩形)
│ │ │ _blendProfile → CameraBlendProfileSO(可选)
│ │ │ _dedicatedCamera(专有 VCam,可选,priority > 全局)
│ │ └── PolygonCollider2D 定义该区域的相机限位边界
│ │
│ └── CameraArea_B 区域 B
│ ...(同上)
│
└── [Triggers]
├── CameraTriggerZone_AB 区域 A→B 入口
│ 组件: CameraTriggerZone _targetArea = CameraArea_B
│ 组件: BoxCollider2D isTrigger = true
└── CameraTriggerZone_BA 区域 B→A 入口
组件: CameraTriggerZone _targetArea = CameraArea_A
组件: BoxCollider2D isTrigger = true
核心流程:
- 玩家进入
CameraTriggerZone→OnTriggerEnter2D调用ICameraService.SwitchArea(targetArea) CameraStateController.SwitchArea→ 应用BlendProfile到CinemachineBrain.DefaultBlend- 无专有 VCam:配置非活跃全局 VCam 的
CinemachineConfiner2D.BoundingShape2D→ 提升其优先级至 10 → 降低旧 VCam 优先级至 0(ping-pong),Cinemachine Brain 自动触发混合过渡 - 有专有 VCam:提升
_dedicatedCamera优先级至_dedicatedPriority(默认 20),高于全局 VCam,Cinemachine 自动切换
- 无专有 VCam:配置非活跃全局 VCam 的
2. Persistent 场景配置(CameraStateController)
2.1 组件放置
在 Persistent 场景的 [Camera] 下建立以下节点结构:
| GameObject | 挂载组件 | 说明 |
|---|---|---|
[CameraController] |
CameraStateController、CinemachineBrain、CinemachineImpulseSource |
ExecutionOrder = -100 |
CameraLookSystem |
CameraLookSystem |
双轴窥视偏移(垂直+水平)+ 速度门控;输出 VirtualTarget 供 VCam 跟随;拖入 CameraStateController._lookSystem |
VCamA |
CinemachineCamera、CinemachinePositionComposer、CinemachineConfiner2D、CameraAxisLockExtension、CameraAsymmetricDampingExtension、CameraAdaptiveLookaheadExtension |
全局虚拟相机 A;PositionComposer 是 Body 组件,必须存在;拖入 CameraStateController._vcamA |
VCamB |
CinemachineCamera、CinemachinePositionComposer、CinemachineConfiner2D、CameraAxisLockExtension、CameraAsymmetricDampingExtension、CameraAdaptiveLookaheadExtension |
全局虚拟相机 B;同 VCamA;拖入 CameraStateController._vcamB |
注意:
CinemachineBrain须挂在附有Camera组件(Main Camera)的 GameObject 上, 否则 Cinemachine 无法驱动视口渲染。两台全局 VCam 初始优先级均为 0,由CameraStateController在运行时动态管理。
2.2 字段绑定清单
打开 Camera Area Setup 窗口(BaseGames → Camera → Camera Area Setup),
在 CameraStateController 区域确认以下项目全为绿色 ●:
| 字段 | 期望状态 |
|---|---|
_vcamA (CinemachineCamera) |
● 已绑定 |
_vcamB (CinemachineCamera) |
● 已绑定 |
_brain (CinemachineBrain) |
● 已绑定 |
_lookSystem (CameraLookSystem) |
● 已绑定 |
_impulseSource (CinemachineImpulseSource) |
◌ 可选;用于屏幕抖动 |
_defaultBlendProfile (CameraBlendProfileSO) |
◌ 可选;未设置则无混合过渡 |
3. 关卡场景配置(CameraArea + CameraTriggerZone)
3.1 添加 CameraArea
方式 A:使用快速放置工具(推荐)
- 菜单
BaseGames → Scene → Place → Camera Area - 工具自动创建以下节点结构:
CameraArea ├── CameraArea(组件,_confinerCollider 已绑定) └── PolygonCollider2D(默认矩形 24×12,isTrigger = true,定义限位区域) - 打开 Camera Area Setup 窗口,点击 为全局 VCam 赋值 Follow 目标
(工具会自动在 Player 下查找或创建
CameraFollowTarget子节点,绑定到两台全局 VCam)。 - 手动调整子节点
PolygonCollider2D顶点定义限位范围。
方式 B:手动创建
- 新建空 GameObject,命名如
CameraArea_A - 挂载
CameraArea(BaseGames.Camera) - 在同一 GameObject 或子对象上创建
PolygonCollider2D - 将
PolygonCollider2D拖入CameraArea._confinerCollider - (可选)如需专有相机参数,新建独立 VCam GameObject,挂载
CinemachineCamera,拖入CameraArea._dedicatedCamera
一个房间可放置多个
CameraArea,如大厅区域与 Boss 区域分别使用不同的限位和混合配置。
3.2 调整限位区域(PolygonCollider2D)
CameraArea 上(或子节点)的 PolygonCollider2D 定义了相机在该区域内的移动边界。
- 编辑顶点:选中
CameraArea节点 → Inspector 中PolygonCollider2D→ 点击 Edit Collider 图标,在 Scene 视图拖动顶点 - 自动修复:打开 Camera Area Setup 窗口,对应条目点击 修复:绑定子节点 PolygonCollider2D
最佳实践:限位区域应比实际可见范围大一格以上(约 1 unit),避免相机卡在边缘。
3.3 添加 CameraTriggerZone
使用快速放置工具(推荐)
- 菜单
BaseGames → Scene → Place → Camera Trigger Zone - 工具生成:
CameraTriggerZone ├── CameraTriggerZone(组件,_playerTag = "Player") └── BoxCollider2D(isTrigger = true,默认 2×2) - 在 Inspector 中将目标
CameraArea拖入CameraTriggerZone._targetArea - 调整
BoxCollider2D大小至覆盖整个区域过渡走廊宽度(通常 2×3 或 2×4)
典型布局:
[区域 A] ‖ [走廊] ‖ [区域 B]
←← TriggerZone_A→B (_targetArea = CameraArea_B)
TriggerZone_B→A (_targetArea = CameraArea_A) →→
双向过渡需要两个 TriggerZone 分别放置在走廊两端,各自指向对应区域的
CameraArea。
3.4 全局 VCam Follow 绑定
Persistent 场景中两台全局 VCam 的 CinemachineCamera.Follow 不直接指向 Player,
而是指向 CameraLookSystem 组件在运行时生成的 [CameraLookTarget] 虚拟目标节点。
该节点由 CameraStateController.SetFollowTarget(Transform) 在玩家注册时自动创建并赋值,
其世界位置 = Player 基准目标位置 + 当前窥视偏移(CameraLookSystem 的双轴输出)。
不要在 Inspector 中手动把 VCam.Follow 拖到 Player 本身或 Player/CameraFollowTarget。
SetFollowTarget会在运行时覆盖,且直接指向 Player 会绕过窥视偏移计算。
工具支持:
Camera Area Setup 窗口 → 为全局 VCam 赋值 Follow 目标 按钮
→ 该按钮仅用于调试回退(绕过 LookSystem,直指 Player/CameraFollowTarget)。
正式流程请通过 ICameraService.SetFollowTarget(playerTransform) 注册,由系统自动处理。
3.5 编辑可视区域(透视相机)
CameraArea 支持在 Scene 视图中直接定义摄像机的最大可视范围,并自动换算为限位 PolygonCollider2D 的顶点坐标。
Inspector 字段:
| 字段 | 说明 |
|---|---|
_visibleBounds |
摄像机应显示的最大可视矩形(世界坐标);Scene 视图选中时显示为黄色矩形 |
_cameraDepth |
摄像机到场景平面(Z = 0)的垂直距离;留 0 则自动读取 |transform.position.z| |
Scene 视图拖拽编辑:
选中 CameraArea GameObject 后,Scene 视图出现:
- 黄色矩形:可视区域(玩家在此区域内的最大可见范围)
- 蓝色多边形:当前
PolygonCollider2D限位边界(参考用)
矩形四条边各有一个滑动 Handle,拖拽即可调整:
- 左 / 右边 Handle:沿 X 轴滑动
- 上 / 下边 Handle:沿 Y 轴滑动
同步到限位区域:
调整好可视区域后,在 Inspector 底部点击 「从可视区域更新限位区域(透视)」,工具根据以下公式换算限位多边形:
halfH = depth × tan(vFOV / 2)
halfW = halfH × aspectRatio
confiner = visibleBounds 向内收缩 (halfW, halfH)
含义:相机视口边缘恰好与可视区域边框对齐。若区域小于单屏(inset 后为负),限位收缩为中心点,相机固定居中。
Inspector 参数预览区实时显示 FOV(来源:专有 VCam → 全局 VCamA → Camera.main → 60°)、深度、视口半宽 / 半高的计算值。
3.6 专有 VCam(特殊区域)
需要独特相机参数(如 Boss 区域特写 FOV)的区域,可在 CameraArea._dedicatedCamera 中指定一台独立的 CinemachineCamera:
- 在关卡场景中新建空 GameObject,挂载
CinemachineCamera(设置好 Lens、Follow、Noise 等参数) - 将其拖入该
CameraArea._dedicatedCamera _dedicatedPriority(默认 20)须高于全局 VCam 的激活优先级(10)
进入该区域时,CameraStateController 自动提升专有 VCam 优先级,Cinemachine 混合切换;离开时优先级归零,全局 VCam 重新接管。
4. ScriptableObject 资产说明
4.1 CameraBlendProfileSO
创建路径:Assets → Create → BaseGames → Camera → BlendProfile
| 字段 | 说明 | 典型值 |
|---|---|---|
Style |
混合曲线类型(EaseInOut / Linear / Cut / Custom) | EaseInOut |
BlendTime |
混合持续时间(秒) | 0.5 |
CustomCurve |
仅 Style = Custom 时使用 |
— |
使用:
- 全局默认:拖入
CameraStateController._defaultBlendProfile - 单独区域:拖入对应
CameraArea._blendProfile(覆盖全局默认)
4.2 CameraConfigSO
⚠ Legacy / 已废弃:
CameraConfigSO是早期相机系统的配置资产,现已不再被CameraStateController读取或应用。
当前架构直接通过CameraArea字段(ScreenPosition、DeadZoneSize、LookaheadTime、DampingDown、DampingUp等)在ConfigureSlot时写入 Cinemachine 组件,无需此 SO。
若项目中仍存在CameraConfigSO资产,可安全忽略或删除。
创建路径:Assets → Create → BaseGames → Camera → CameraConfig
| 字段 | 说明 | 典型值 |
|---|---|---|
FollowDamping |
— | |
LookAheadTime |
— | |
DeadZoneSize |
— | |
SoftZoneSize |
— | |
LookDownOffset |
— | |
LookUpOffset |
— | |
DefaultImpulseStrength |
— |
CameraConfigSO的配置值须由运行时的CameraStateController或相机系统读取并写入 Cinemachine 组件,具体写入逻辑取决于CameraStateController.ApplyConfig()的实现(如有扩展)。
5. Camera Area Setup 工具详解
菜单:BaseGames → Camera → Camera Area Setup
5.1 界面区域说明
工具栏
↻ 刷新:手动重新扫描当前已加载场景Place Camera Area:快捷调用BaseGames → Scene → Place → Camera AreaPlace Trigger Zone:快捷调用BaseGames → Scene → Place → Camera Trigger Zone
CameraStateController 区域
显示控制器组件绑定状态。若显示"未找到"提示,说明 Persistent 场景未加载(属正常)。
| 图标 | 含义 |
|---|---|
●(绿) |
项目已正确配置 |
✗(红) |
缺失必填项 |
◌(黄) |
可选项未设置 |
检查项:_vcamA、_vcamB(必填)、_brain(必填)、_lookSystem(必填)、_impulseSource(可选)、_defaultBlendProfile(可选)
底部按钮:为全局 VCam 赋值 Follow 目标 → 查找 Player/CameraFollowTarget 并写入两台 VCam 的 Follow 字段。
Camera Areas 区域
为每个 CameraArea 显示一行,检查项:
| 字段 | 状态 |
|---|---|
_confinerCollider (PolygonCollider2D) |
必填 |
_dedicatedCamera(专有 VCam) |
可选 |
_blendProfile |
可选 |
每行可点击 修复:绑定子节点 PolygonCollider2D 自动修复 _confinerCollider 未绑定的情况。
Camera Trigger Zones 区域
列出所有 CameraTriggerZone,高亮显示 _targetArea 未绑定的项目(红色 ✗)。
5.2 典型使用流程
1. 打开窗口 BaseGames → Camera → Camera Area Setup
2. (仅首次)加载 Persistent 场景,确认 _vcamA/_vcamB/_brain 全绿
3. 在关卡场景中使用 Place Camera Area × N(一个房间可放多个)
4. 选中每个 CameraArea,在 Scene 视图拖拽黄色可视区域边 Handle,点击 [从可视区域更新限位区域(透视)]
5. 点击 [为全局 VCam 赋值 Follow 目标](自动创建 Player/CameraFollowTarget 并绑定)
6. 使用 Place Trigger Zone 添加 N 个触发器,手动绑定 _targetArea
7. 所有条目绿色 ● → 进入 Play Mode 验证
6. 验收测试用例
测试前检查清单
| # | 检查项 | 操作 |
|---|---|---|
| 1 | Console 无红色 Error | Window → General → Console |
| 2 | Camera Area Setup 窗口所有必填项为绿色 ● | BaseGames → Camera → Camera Area Setup |
| 3 | Player 已在场景中(tag = Player) | Hierarchy |
| 4 | Physics2D Layer 矩阵已配置 | BaseGames → Tools → Validate Physics2D Layer Matrix |
MT-CAM-01:全局 VCam 正常跟随
目的:验证全局 VCam 激活后 CinemachineCamera 跟随玩家移动。
步骤:
- Persistent 场景中放置 VCamA/VCamB,
Follow = Player/CameraFollowTarget - 关卡场景中放置一个
CameraArea,通过CameraTriggerZone或RoomController触发SwitchArea - 按 Play,在 Scene 视图和 Game 视图同时观察
- 用 WASD/方向键移动 Player
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
| Game 视图相机跟随 Player 移动 | 玩家靠近边缘时相机平滑跟进 | ☐ |
| 相机不会越出 CameraArea 的限位范围 | 玩家走到边角时相机贴边停止 | ☐ |
| 无跳变(平滑)跟随 | 无抖动、跳帧 | ☐ |
MT-CAM-02:区域相机切换(CameraTriggerZone)
目的:验证玩家穿越触发器后全局 VCam ping-pong 平滑过渡到目标区域。
步骤:
- 场景中放置两个
CameraArea(A、B),各有独立PolygonCollider2D限位 - 在两区域之间放置两个
CameraTriggerZone(各自_targetArea互指) - 按 Play,引导 Player 穿越触发区进入区域 B
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
| 穿越触发器后 Game 视图开始混合过渡 | 相机平滑从 A 过渡到 B(非切割) | ☐ |
过渡时长约等于 CameraBlendProfileSO.BlendTime |
与 SO 设置一致(默认 0.5s) | ☐ |
| 过渡后相机限位在 CameraArea_B 的边界内 | 玩家无法把相机带出 B 的限位范围 | ☐ |
| 反向穿越触发器后相机切回 A | 同上,反向过渡 | ☐ |
MT-CAM-03:CinemachineConfiner2D 边界限位
目的:验证 CinemachineConfiner2D 正确将相机限制在 CameraArea 限位范围内。
步骤:
- 打开关卡场景,确认
CameraArea._confinerCollider已绑定,且CameraStateController已调用SwitchArea - 按 Play,将 Player 移动到房间的各个角落和边缘
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
相机在所有方向均不超出 PolygonCollider2D 多边形范围 |
无越界 | ☐ |
| 小房间(相机视口 > 房间)时相机居中,不晃动 | 稳定居中 | ☐ |
常见失败原因:
CameraArea._confinerCollider未绑定 → 打开 Camera Area Setup 点击修复- PolygonCollider2D 顶点数量少于 3 → 确认
_confinerCollider路径顶点完整
MT-CAM-04:屏幕抖动(CinemachineImpulseSource)
目的:验证调用 ICameraService.TriggerImpulse 时 Game 视图画面抖动。
步骤:
- 确认
CameraStateController._impulseSource已绑定 - 按 Play
- 在 Console 执行(或通过游戏内事件触发):
或让玩家受到一次伤害(若伤害系统已接入抖动调用)
ServiceLocator.Get<ICameraService>().TriggerImpulse(0.5f);
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
| Game 视图画面发生轻微抖动后恢复稳定 | 抖动时长约 0.2–0.4s,幅度可见 | ☐ |
| 无 Console 错误 | 无 NullReferenceException | ☐ |
MT-CAM-05:初始场景无 CameraStateController 时安全降级
目的:验证场景中未加载 Persistent 场景时,CameraTriggerZone 不崩溃。
步骤:
- 单独打开关卡场景(不加载 Persistent.unity)
- 按 Play,移动 Player 穿越
CameraTriggerZone
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
| 无 NullReferenceException | ServiceLocator.GetOrDefault<ICameraService>() 返回 null 时跳过 |
☐ |
| Console 可能有黄色 Warning(服务未注册) | 无红色 Error | ☐ |
MT-CAM-06:多场景加载时相机状态正确恢复
目的:验证通过 SceneLoader 加载新场景时,CameraStateController 正确切换到新场景首个 CameraArea。
步骤:
- 以 Persistent + Level_01 双场景启动
- 按 Play,触发场景加载切换到 Level_02
- Level_02 加载完成后观察相机
预期结果:
| 检查点 | 期望 | ✓ |
|---|---|---|
Level_02 的 RoomController 调用 SwitchArea 后相机切换正确 |
无黑屏、无旧场景相机残影 | ☐ |
旧场景 CameraArea 随场景卸载,全局 VCam 状态不受干扰 |
无相机混合错误 | ☐ |
注意:全局 VCam 常驻 Persistent 场景,
CinemachineConfiner2D.BoundingShape2D在SwitchArea时动态更新, 旧场景卸载后引用会变为 null,须确保SwitchArea在新场景CameraArea可用后再调用。
7. 常见问题排查
| 现象 | 原因 | 解决 |
|---|---|---|
| Game 视图相机不动(黑屏或固定位置) | 全局 VCam Follow 未绑定 |
ICameraService.SetFollowTarget(player) 注册玩家;或 Camera Area Setup → 为全局 VCam 赋值 Follow 目标 |
| 相机追赶卡顿/震颤 | CinemachineConfiner2D.BoundingShape2D 未绑定或碰撞体顶点有误 |
确认 CameraArea._confinerCollider 已绑定,PolygonCollider2D 顶点数 ≥ 3 |
| 进入区域后限位未更新(仍在旧区域限位内) | CameraArea._confinerCollider 为空,ConfigureSlot 跳过了更新 |
打开 Camera Area Setup 修复 _confinerCollider 绑定 |
场景中有多个 CinemachineBrain |
Persistent 场景外又添加了含 Camera 组件的对象 | 仅 Main Camera 上保留一个 Brain |
| 过渡时画面闪切而非混合 | CameraBlendProfileSO.BlendTime = 0 或 Style = Cut |
检查 BlendProfile 并将 BlendTime 设置为 > 0 |
CameraStateController 未找到(Console 错误) |
Persistent 场景未加载 | 确认 Build Settings 中 Persistent.unity 第一位;开发测试用 SceneManager.LoadScene("Persistent", Additive) |
| 触发器无响应(玩家穿越后相机不切) | CameraTriggerZone._targetArea 未绑定,或 _playerTag 不匹配 |
检查 _targetArea 是否已拖入 CameraArea;确认 Player Tag = "Player" |
Camera Area Setup 窗口列表为空 |
场景未保存或 DomainReload 后未刷新 | 点击窗口内 ↻ 刷新 按钮 |
| 专有 VCam 不切换 | _dedicatedPriority ≤ 全局激活优先级(默认 10) |
将 _dedicatedPriority 设置为 > 10(默认 20 已满足) |
Camera Area Setup 中 _lookSystem 红色 ✗ |
CameraStateController._lookSystem 未绑定 |
将 Persistent 场景 [Camera]/CameraLookSystem 节点拖入该字段;或重新运行 SceneScaffoldTools |
| 按住方向键相机偏移不出现(窥视无效) | CameraLookSystem._baseTarget 未设置 |
确认 ICameraService.SetFollowTarget(player) 在玩家 Awake/Start 后调用 |
| 下落时相机跟随过慢(非对称阻尼异常) | CameraAsymmetricDampingExtension 未挂到 VCamA/VCamB,或 DampingDown 未被 ConfigureSlot 写入 |
确认两台 VCam 已挂载该扩展;检查 CameraArea._dampingDown > 0 |
| 高速移动时 Lookahead 不变化 | CameraAdaptiveLookaheadExtension 未挂到 VCamA/VCamB,或 SetConfiguredMax 未被调用 |
确认两台 VCam 已挂载该扩展;检查 ConfigureSlot 代码路径正常执行 |