using System.Collections.Generic;
using UnityEngine;
using Unity.Cinemachine;
using BaseGames.Core;
namespace BaseGames.Camera
{
///
/// 相机状态单例控制器。管理房间相机切换、限位器更新与屏幕抖动。
/// 须放置在持久化场景中。
///
[DefaultExecutionOrder(-100)]
public class CameraStateController : MonoBehaviour, ICameraService
{
[Header("引用")]
[SerializeField] private CinemachineBrain _brain;
[SerializeField] private CinemachineImpulseSource _impulseSource;
[Header("默认混合配置")]
[SerializeField] private CameraBlendProfileSO _defaultBlendProfile;
// ── 注册表 ────────────────────────────────────────────────────────────
private readonly HashSet _registeredCameras = new HashSet();
private RoomCamera _activeCamera;
// ── Unity Lifecycle ───────────────────────────────────────────────────
private void Awake()
{
if (ServiceLocator.GetOrDefault() != null) { Destroy(gameObject); return; }
ServiceLocator.Register(this);
}
private void OnDestroy()
{
ServiceLocator.Unregister(this);
}
// ── 公开 API ──────────────────────────────────────────────────────────
/// 向控制器注册一个房间相机(可选,也可由触发器直接调用 SwitchRoom)。
public void RegisterRoomCamera(RoomCamera camera)
{
if (camera != null) _registeredCameras.Add(camera);
}
/// 注销房间相机。
public void UnregisterRoomCamera(RoomCamera camera)
{
if (camera != null) _registeredCameras.Remove(camera);
}
/// 切换到目标房间相机,并应用对应的混合配置。
public void SwitchRoom(RoomCamera targetCamera)
{
if (targetCamera == null || targetCamera == _activeCamera) return;
// 应用混合配置到 Brain
if (_brain != null)
{
var profile = targetCamera.BlendProfile ?? _defaultBlendProfile;
if (profile != null)
_brain.DefaultBlend = profile.ToBlendDefinition();
}
// 禁用旧相机、启用新相机
_activeCamera?.Deactivate();
_activeCamera = targetCamera;
_activeCamera.Activate();
}
/// 触发屏幕抖动。
public void TriggerImpulse(Vector3 velocity)
{
if (_impulseSource != null)
_impulseSource.GenerateImpulse(velocity);
}
/// 以默认强度触发屏幕抖动。
public void TriggerImpulse(float strength = 0.3f)
=> TriggerImpulse(Vector3.down * strength);
}
}