2 분 소요

Intro

저번 포스팅에서 공격 애니메이션을 만들었습니다. 이번 포스팅에서는 만들어진 공격 애니메이션에 실제로 공격이 되도록 만들어보려합니다.

 

코루틴

유니티에서 애니메이션에 이벤트를 발생시키는 많이 사용되는 방법중하나로, 코루틴을 사용하는 방법이 있습니다.
 

코루틴(Coroutine)은 여러가지 작업을 원하는타이밍에 비동기적으로, 쉽게말해 따로따로 실행할수있도록 해주는 기능입니다.

  image

  코루틴함수를 사용하기 위해서는 IEnumerator라는 반환타입으로, 리턴되는값은 yield로 선언해주어야합니다.

콜라이더 설정

우선 플레이어가 공격하고있음을 알수있도록 콜라이더를 설정해줍니다.

저는 왼손 -> 오른손 콤보공격으로 애니메이션을 만들어뒀기때문에 2개의 콜라이더를 만들었습니다.

image

이때 반드시 isTrigger 옵션을 체크해주어야합니다.

그리고 공격할때만 콜라이더가 활성화될수있도록 현재는 비활성화 해줍니다.

image

 

코드작성

이제 코드를 통해 공격을 구현해봅니다. 저는 코루틴을 사용해서 구현했습니다.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Attack : MonoBehaviour
{
    [SerializeField] private PlayerInput playerInput;

    [SerializeField] private BoxCollider leftHandCollider;               
    [SerializeField] private BoxCollider rightHandCollider;

    private Animator anim;

    readonly private int hashAttackType = Animator.StringToHash("AttackType");
    readonly private int hashComboCount = Animator.StringToHash("ComboCount");
    readonly private int hashAttackTrigger = Animator.StringToHash("Attack");

    private bool hasEquipedWeapon = false;      // 무기 장착여부(현재는 기본 false)
    private bool isAttack = false;              // 공격중인지 여부
    private bool isComboAllowed = false;        // 콤보공격 가능여부

    private int comboCount = 0;                 // 콤보공격 카운트

    // AttackType 설정
    public int AttackType
    {
        get => anim.GetInteger(hashAttackType);
        set => anim.SetInteger(hashAttackType, value);
    }

    private void Awake()
    {
        anim = GetComponent<Animator>();
    }

    private void Update()
    {
        BaseAttack();
    }

    // 기본공격
    private void BaseAttack()
    {
        // 무기가 없을 때(주먹공격)
        if(hasEquipedWeapon == false)
        {
            AttackType = 0;
        }
     
        if(playerInput.attackKeydown)
        {
            if(!isAttack)
            {
                comboCount = 1;
                StartCoroutine(BaseAttackPunch(comboCount));
            }
            else if(isComboAllowed)
            {
                comboCount = 2;
                StartCoroutine(BaseAttackPunch(comboCount));
            }
        }
    }

    // 기본 주먹공격
    IEnumerator BaseAttackPunch(int combo)
    {
        isAttack = true;
        isComboAllowed = true;

        anim.SetInteger(hashAttackType, AttackType);
        anim.SetInteger(hashComboCount, comboCount);
        anim.SetTrigger(hashAttackTrigger);

        // 애니메이션에 맞게 콜라이더 활성/비활성화
        yield return new WaitForSeconds(0.3f);
        if (combo == 1)
            leftHandCollider.enabled = true;
        else
            rightHandCollider.enabled = true;

        yield return new WaitForSeconds(0.5f);
        if (combo == 1)
            leftHandCollider.enabled = false;
        else
        {
            rightHandCollider.enabled = false;
            isComboAllowed = false;
        }

        isAttack = false;
    }

}
  • 멤버변수와 함수이름이 약간씩 바뀌었습니다.
  • 공격키 입력이 들어오면 BaseAttackPunch 코루틴이 실행됩니다.
    • 이때 첫번째 공격이면 comboCount = 1로, 두번째 콤보공격이면 2로주어 각 공격에맞는 애니메이션을 실행해주었습니다.
    • 각 애니메이션에 맞게 콜라이더를 활성화/비활성화 시켜주었습니다.

  지난 포스팅에서 설정했던 Animator를 약간 수정했습니다.

image

  • 파라미터의 이름을 변경했습니다. AttackCount -> AttackType
  • int형 파라미터 ComboCount를 두어 현재 ComboCount를 바탕으로 애니메이션이 실행됩니다.
  • PunchLeft -> PunchRight 트랜지션의 컨디션을 아래와같이 설정했습니다.

image

테스트

Cube를 하나 생성하여 씬에 올려줍니다.

간단하게 Monster 스크립트를 작성하여 콜라이더가 제대로 작동하는지 확인합니다.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Monster : MonoBehaviour
{
    BoxCollider boxCol;

    private void Awake()
    {
        boxCol = GetComponent<BoxCollider>();
    }

    private void OnTriggerEnter(Collider other)
    {
        if (other.CompareTag("Weapon"))
            Debug.Log("Hit!!");
    }
}

image

  • 공격 애니메이션에 맞춰서 콜라이더가 활성/비활성화되는것을 확인할수있습니다.
  • Cube를 공격했을때에도 공격이 작동하는것을 콘솔창에서 확인할수있습니다.

하지만 아직 문제점이있는데, 공격키를 계속연타하게되면 의도치않은 콜라이더의 활성화가 발생한다는것입니다. 이 문제는 추후에 찾아 고치려고합니다.

댓글남기기