using System.Collections; using UnityEngine; namespace RR.Game2D.Core.Managers { public class CameraFollow : MonoBehaviour { [Header("Follow")] [SerializeField, Min(0)] protected float damping = 1.5f; [SerializeField] protected Vector2 offset = new(2f, 1f); [SerializeField] protected bool faceLeft; [Header("Behaviour")] [SerializeField] protected bool snapOnFound = true; protected Transform _player; //private float lastX; protected Coroutine _bindRoutine; private void OnEnable() { offset = new Vector2(Mathf.Abs(offset.x), offset.y); _bindRoutine = StartCoroutine(BindLoop()); } private void OnDisable() { if (_bindRoutine != null) { StopCoroutine(_bindRoutine); _bindRoutine = null; } } private void FixedUpdate() { if (!_player) return; // ждём появления float currentX = _player.position.x; //if (currentX > lastX + 0.01f) faceLeft = false; //else if (currentX < lastX - 0.01f) faceLeft = true; faceLeft = Mathf.Abs(_player.localEulerAngles.y) >= 180 ? true : false; //lastX = currentX; Vector3 target = _player.position; target.x += faceLeft ? -offset.x : +offset.x; target.y += offset.y; target.z = transform.position.z; transform.position = Vector3.Lerp(transform.position, target, damping * Time.deltaTime); } /// /// Цикл привязки камеры к игроку. Ищет игрока на сцене. /// private IEnumerator BindLoop() { while (true) { if (!_player) { var t = ResolvePlayer(); if (t) { _player = t; //lastX = player.position.x; if (snapOnFound) SnapToPlayer(faceLeft); } } yield return null; // подождём кадр } } /// /// Метод для поиска объекта игрока. /// Сначала ищет экземпляр объекта игрока в GameManager, /// затем, ели не нашел, то ищет по тегу на сцене /// /// Transform playerPosition - позиция игрокка protected virtual Transform ResolvePlayer() { if (GameManager.Instance && GameManager.Instance.PlayerObj) return GameManager.Instance.PlayerObj.transform; var go = GameObject.FindWithTag("Player"); return go ? go.transform : null; } /// /// Метод для поиска игрока и привязки к нему камеры. /// /// Повернут ли игрок налево public virtual void FindPlayer(bool playerFaceLeft) { faceLeft = playerFaceLeft; _player = ResolvePlayer(); if (!_player) { Debug.Log("CameraFollow2D: player not found yet, will wait."); return; } //lastX = player.position.x; SnapToPlayer(faceLeft); } /// /// Метод для привязки камеры к игроку. /// /// Повернут ли игрок налево private void SnapToPlayer(bool playerFaceLeft) { if (!_player) return; Vector3 p = _player.position; p.x += (playerFaceLeft ? -offset.x : offset.x); p.y += offset.y; p.z = transform.position.z; transform.position = p; } } }