1-23)TIL /./Animation , 이동

최보훈·2024년 1월 23일
0

TIL

목록 보기
15/28
post-thumbnail

Animation

TopDownAnimationController.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TopDownAnimationController : TopDownAnimations
{
    private static readonly int IsWalking = Animator.StringToHash("IsWalking");
    private static readonly int Attack = Animator.StringToHash("Attack");
    private static readonly int IsHit = Animator.StringToHash("IsHit");
    //string의 비교는 비용이 높아 Hash값으로 비교하도록 처리하한다.
    //같은 이름은 더이상 사용 불가능
    protected override void Awake()
    {
        base.Awake();
    }
    private void Start()
    {
        controller.OnMoveEvent += Move;
    }
    private void Move(Vector2 directionVector)
    {
        animator.SetBool(IsWalking, directionVector.magnitude > 0.5);
    }
}
TopDownAnimations.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TopDownAnimations : MonoBehaviour
{
    protected Animator animator;
    protected TopDownCharacterController controller;

    protected virtual void Awake()
    {
        animator = GetComponentInChildren<Animator>();
        controller = GetComponent<TopDownCharacterController>();
    }
}

TopDownAnimationController 은 TopDownAnimations를 상속받아 사용한다.
후자의 Cs에서 움직임을 관리하는 TopDownCharacterController을 할당받아 이를 이용해 움짐임이 있을때 Action을 통해 움직임 상태를 받아올 수 있다.

적 이동

TopDownCharacterController.cs
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TopDownCharacterController : MonoBehaviour
{
    public event Action<Vector2> OnMoveEvent;
    public event Action<Vector2> OnLookEvent;

    protected virtual void Awake()
    {

    }

    public void CallMoveEvent(Vector2 direction)
    {
        if (OnMoveEvent == null)
        {
            Debug.Log("Null");
        }
        OnMoveEvent?.Invoke(direction); 
    }
}
TopDownMovement.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TopDownMovement : MonoBehaviour
{
    private TopDownCharacterController _controller;
    private Rigidbody2D _rigidbody;
    Vector2 newDirection = Vector2.zero;    

    private void Awake()
    {
        _controller = GetComponent<TopDownCharacterController>();
        _rigidbody = GetComponent<Rigidbody2D>();
    }
    private void Start()
    {
        _controller.OnMoveEvent += Move;
    }

    private void FixedUpdate()
    {
        ApplyMovement(newDirection);
    }

    private void Move(Vector2 dir)
    {
        newDirection = dir; 
    }
    private void ApplyMovement(Vector2 dir)
    {
        dir = dir * 5; // 5= 속도
        _rigidbody.velocity = dir;
    }
}

위의 두 스크립트를 이용해 오브젝트의 이동을 관리한다. 어딘가의 스크립트에서 TopDownMovement.cs의 CallMoveEvent가 실행되면, TopDownMovement.cs의 Move함수가 실행되게 된다. Move는 이동하고자 하는 방향으로의 방향백터를 인자로 받아 이동을 하게 해준다. 이 경우 어떤 오브젝트던 간에 이동하고자 하는 방향백터, CallMoveEvent함수만 있다면 이동을 할 수 있다.

EnemyController.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class EnemyController : TopDownCharacterController
{
   protected Transform ClosestTarget { get; private set; }
    protected override void Awake()
    {
        base.Awake();   
    }

    protected virtual void Start()
    {
        ClosestTarget = GameManager.Instance.Player;
    }

    protected virtual void FixedUpdate()
    {

    }
    protected float DistancetoTarget()
    {
        Debug.Log(Vector3.Distance(transform.position, ClosestTarget.position));
        return Vector3.Distance(transform.position, ClosestTarget.position);
    }
    protected Vector2 DirectionTotarget()
    {
        return (ClosestTarget.position - transform.position).normalized;
    }
}
ContactEnemyController.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ContactEnemyController : EnemyController
{
    [SerializeField][Range(0, 100)] private float followRange;
    [SerializeField] private string targetTag = "Player";

    protected override void Start()
    {
        base.Start();
    }
    protected override void FixedUpdate()
    {
        base.FixedUpdate();
        Vector2 direction = Vector2.zero;
        if(DistancetoTarget() < followRange)
        {
            direction = DirectionTotarget();
        }
        CallMoveEvent(direction);
    }


}

EnemyController.cs 는 TopDownCharacterController을 상속받는다. ContactEnemyController.cs는 EnemyController을 상속 받으며, 무언가 물체의 이동의 방향백터의 인풋이 필요할때 TopDownCharacterController을 상속받아 사용한다.

0개의 댓글