using System; using System.Collections; using Cinemachine; using UnityEngine; namespace UFS2.Gameplay { public class GameCameraController : Singleton { [SerializeField] private CinemachineVirtualCamera _CurrentVirtualCamera; [SerializeField] private CinemachineVirtualCamera _PlayerCamera; private CinemachineBrain _CMBrain; [SerializeField] private float _ZoomFov = 10f; [SerializeField] private float _ZoomTweenTime = 0.15f; [SerializeField] private LayerMask underwaterLayersMask; [SerializeField] private LayerMask topwaterLayerMask; private Animator rolnetkaAnimator; private Camera cameraCmp; private bool _IsInWater; private bool _IsPhotoMode; private bool _IsZoomPlaying; private bool _IsCameraZoomIn; public bool IsInWater => _IsInWater; public bool IsZoomPlaying => _IsZoomPlaying; public bool IsCameraZoomIn => _IsCameraZoomIn; private float defaultFov => Singleton.Instance.SettingsData.FOVValue; public static event Action OnEnterInToWater; public static event Action OnExitFromWater; public static event Action OnPhotoModeEnable; public static event Action OnPhotoModeDisable; public static event Action OnZoomTweenEnd; private void Start() { _CMBrain = GetComponent(); _CurrentVirtualCamera = _PlayerCamera; _CMBrain.m_CameraActivatedEvent.AddListener(_Listener); InitializeSettings(); SetCameraPivot(); cameraCmp = GetComponent(); } private void OnEnable() { SettingsManager.OnSettingApply += InitializeSettings; PlayerManager.OnAfterSettingCharacter += SetCameraPivot; OnEnterInToWater += ZoomCameraDisableInstant; OnEnterInToWater += ChangeUnderwaterCullingMask; OnExitFromWater += ChangeTopWaterCullingMask; AnglerViewFish.OnAnglerViewStart += SetCameraPivotToAnglerView; AnglerViewFish.OnAnglerViewEnd += SetCameraPivot; } private void OnDisable() { SettingsManager.OnSettingApply -= InitializeSettings; PlayerManager.OnAfterSettingCharacter -= SetCameraPivot; OnEnterInToWater -= ZoomCameraDisableInstant; OnEnterInToWater -= ChangeUnderwaterCullingMask; OnExitFromWater -= ChangeTopWaterCullingMask; AnglerViewFish.OnAnglerViewStart -= SetCameraPivotToAnglerView; AnglerViewFish.OnAnglerViewEnd -= SetCameraPivot; } private void ChangeUnderwaterCullingMask() { cameraCmp = ((cameraCmp == null) ? GetComponent() : cameraCmp); cameraCmp.cullingMask = underwaterLayersMask; } private void ChangeTopWaterCullingMask() { cameraCmp = ((cameraCmp == null) ? GetComponent() : cameraCmp); cameraCmp.cullingMask = topwaterLayerMask; } private void FixedUpdate() { bool flag = GameWaterSystem.IsPositionUnderWater(base.transform.position); if (!_IsInWater && flag) { _IsInWater = true; GameCameraController.OnEnterInToWater?.Invoke(); } if (_IsInWater && !flag) { _IsInWater = false; GameCameraController.OnExitFromWater?.Invoke(); } } private void Update() { ZoomCameraHandler(); PhotoCameraHandler(); } private void PhotoCameraHandler() { } private void ZoomCameraDisableInstant() { StopAllCoroutines(); _IsZoomPlaying = false; if (rolnetkaAnimator != null) { rolnetkaAnimator.SetBool("Hide", value: true); } _PlayerCamera.m_Lens.FieldOfView = defaultFov; } private void ZoomCameraDisable() { StopAllCoroutines(); rolnetkaAnimator?.SetBool("Hide", value: true); StartCoroutine(FieldViewTween(defaultFov)); } private void ZoomCameraEnable() { if (rolnetkaAnimator == null) { rolnetkaAnimator = UnityEngine.Object.Instantiate(FScriptsHandler.Instance.lornetkaMaskPrefab, FScriptsHandler.Instance.m_Canvas.transform).GetComponent(); rolnetkaAnimator.transform.SetAsFirstSibling(); } rolnetkaAnimator.SetBool("Hide", value: false); StopAllCoroutines(); StartCoroutine(FieldViewTween(_ZoomFov)); } public static void SetCameraFov(float value) { Singleton.Instance._PlayerCamera.m_Lens.FieldOfView = value; } public static float GetCurrentFov() { return Singleton.Instance._PlayerCamera.m_Lens.FieldOfView; } private IEnumerator FieldViewTween(float fovTarget) { float tMax = _ZoomTweenTime; float t = 0f; float startFov = _PlayerCamera.m_Lens.FieldOfView; _IsZoomPlaying = true; while (t < tMax) { t += Time.deltaTime; float fieldOfView = Mathf.Lerp(startFov, fovTarget, Mathf.Clamp01(t / tMax)); _PlayerCamera.m_Lens.FieldOfView = fieldOfView; yield return null; } _IsZoomPlaying = false; GameCameraController.OnZoomTweenEnd?.Invoke(); } private void _Listener(ICinemachineCamera cinemachineCamera, ICinemachineCamera previousCamera) { _CurrentVirtualCamera = _CMBrain.ActiveVirtualCamera.VirtualCameraGameObject.GetComponent(); InitializeSettings(); } private void ZoomCameraHandler() { if ((!(Singleton.Instance != null) || !Singleton.Instance.IsChatOpen) && !InputManager.isEagleEye && (!FScriptsHandler.Instance || !(FScriptsHandler.Instance.m_PlayerMain?.underWaterCamera)) && !_IsZoomPlaying && !_IsInWater && InputManager.isUnderwaterCameraFloatZoom) { _IsCameraZoomIn = !_IsCameraZoomIn; if (_IsCameraZoomIn) { ZoomCameraEnable(); } else { ZoomCameraDisable(); } } } private void InitializeSettings() { _CurrentVirtualCamera.m_Lens.FieldOfView = defaultFov; } private void SetCameraPivot() { if ((bool)FScriptsHandler.Instance.m_PlayerMain) { _PlayerCamera.Follow = FScriptsHandler.Instance.m_PlayerMain.CameraPivot; } } private void SetCameraPivotToAnglerView() { if ((bool)Singleton.Instance) { _PlayerCamera.Follow = Singleton.Instance.cameraPoint; } } } }