반응형

포토샵에서 작업한 적 캐릭터 이미지를 유니티에 끌어다 Textrue폴더에 넣습니다 

그리고 아래 그림과 같이 그림 Inspector를 바꿉니다 

그리고 Sprite Editor에 들어감니다 

 

Slice를 누르고 Automatic 으로 그림을 나눕니다

그리고 Pivot을 나중에 캐릭터가 움직임에 원활히 할수있도록 위치를 조종합니다  

 

 

 

 

 

빈오브젝트를 만들고 이름을 Enemy 하고 Enemy그림파일을 각각 관절에 맞게 Hierarchy 창에 끌어다 놓고 그림을 인간형에 맞게 맞춥니다 

 

Enemy의 각각의 관절에 Sorting Layer -> Enemy 를 만들고 그림이 위아래가 바뀌지 않도록 합니다 

 

 

 

 

 

Enemy 오브젝트의 Window -> animation -> animation 을 열고 Create new Clip을 Enemy_Run을 만들고 적 캐릭터가 움직이는 애니메이션을 만듭니다 

 

 

Enemy 스크립트를 생성하고 작성합니다 

 

 

 

 

Enemy 스크립트 작성 

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

public class Enemy : MonoBehaviour
{

    //적캐릭터의 생명카운트
    public int health;

    //Player 위치
    [HideInInspector]
    public Transform player;

    //스피드
    public float speed;

    //공격과 재공격의 시간 
    public float timeBetweenAttacks;
    // 데미지
    public int damage;
    private void Start()
    {
        //Player tag 오브젝트를 찾는다
        player = GameObject.FindGameObjectWithTag("Player").transform;
    }

    //공격을 받을때 생명이 줄어드는 함수
    public void TakeDamage(int damageAmount)
    {
        health -= damageAmount;
        if (health <= 0)
        {
            Destroy(gameObject);
        }
    }
}

 

 

 

 

 

 

Enemy 오브젝트를 선택하고 Enemy 스크립트를 붙히고 Tag에 Enemy를 생성하고  Box Collider2 D를 붙이고 isTrigger를 체크하고 Rigidbody2 D에서 Gravity scale을 0으로 하고 Freeze Rotation -> z를 체크합니다 

 

Prefabs에 있는 bullet 프리팹을 선택하여 BulletCtrl 스크립트를 수정합니다 

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

public class BulletCtrl : MonoBehaviour
{
    public float speed;
    public float lifeTime;
    public GameObject explosion;

    public int damage;
   
   
    void Start() 
    {
        // 총알을 시간에 맞게 지운다
        //Destroy(gameObject, lifeTime);
        Invoke("DestroyBullet", lifeTime);
    } 
      void Update() 
    { 
        // 시간프레임과 speed에 따라 y축방향으로 움직인다
        transform.Translate(Vector2.up * speed * Time.deltaTime); 
    }

    //총알을 삭제하고 이팩트를 생성한다 
    void DestroyBullet()
    {
        Destroy(gameObject); 
        Instantiate(explosion, transform.position, Quaternion.identity);
    }

    private void OnTriggerEnter2D(Collider2D collision)
    {
        //적캐릭터 오브젝트와 닿게 되면 이팩트를 생성하고 적캐릭터 함수에 전달하여 생명을 감소시킨다 
        if (collision.tag == "Enemy")
        {
            collision.GetComponent<Enemy>().TakeDamage(damage);
            Instantiate(explosion, transform.position, Quaternion.identity);
            DestroyBullet();
        }
    }


}

 

 

 

 

bulletCtrl 스크립트를 수정하고 Explosion  -> Particle System  speed 20 , LifeTime 3 , Damage1을 넣습니다  

 

 

 

Player 오브젝트를 선택하고 Tag  -> Player를 선택합니다  그리고 player 스크립트를 수정합니다

그리고 Game 을 실행시키면 Enemy 가 총알에 맞고 Enemy Health가 0 이 되면 Enemy가 삭제되는 것을 확인할 수 있습니다  

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Player : MonoBehaviour
{
    public float speed;
    private Rigidbody2D rigid;
    private Vector2 moveAmount;
    private Animator anim;

    public float health;

    private void Start() 
    { 
        rigid = GetComponent<Rigidbody2D>();
        anim = GetComponent<Animator>();
    }
    private void Update()
    { 
        //키보드(WSAD)의 좌우상하를 방향을 정의해 준다
        Vector2 moveInput = new Vector2(Input.GetAxisRaw("Horizontal"), 
            Input.GetAxisRaw("Vertical")); 
        //움직임방향에 속도를 곱한다
        moveAmount = moveInput.normalized * speed;

    //키보드를 누르면 Player 애니메이터 파라미터를 적용하고 캐릭터를 움직인다
      if (moveInput != Vector2.zero) 
        { 
            anim.SetBool("Run", true); 
        } else 
        { 
            anim.SetBool("Run", false); 
        }

    
    }
    
    private void FixedUpdate() 
    { //움직임 방향에 시간에 따라 리지드 바디 포지션값을 더한다
      rigid.MovePosition(rigid.position + moveAmount * Time.fixedDeltaTime); 
    }

    // Player의 체력을 감소 시킨다
    public void TakeDamage(int damageAmount)
    {
        health -= damageAmount;
        if (health <= 0)
        {
            Destroy(gameObject);
        }
    }
}

    

 

 

 

 

Enemy 오브젝트를 선택하고 Enemy 스크립트를 오브젝트에서 삭제 하고 MeleeEnemy 스크립트를 작성합니다 

 

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

public class MeleeEnemy : Enemy
{
    public float stopDistance;

    private float attackTime;

    public  float attackSpeed;
    private void Update()
    {
        if (player != null)
        {
            //Enemy가 Player의  stopDistance 거리 밖이라면 Player 방향으로 speed 속도로 돌진한다 
            if (Vector2.Distance(transform.position,player.position ) > stopDistance) 
            {
                transform.position =
                    Vector2.MoveTowards(transform.position, player.position, speed * Time.deltaTime);
            }
            else
            {
                //Enemy가 Player의  stopDistance 거리 안쪽에 있으면 attackTime의 딜레이를 주고 공격한다 
                if (Time.time >= attackTime)
                {
                    StartCoroutine(Attack());
                    attackTime = Time.time + timeBetweenAttacks;
                }

            }
        }
    }

    // 적캐릭터의 공격
    IEnumerator Attack()
    {
        player.GetComponent<Player>().TakeDamage(damage);

        Vector2 originalPosition = transform.position;
        Vector2 targetPosition = player.position;

        float percent = 0;

        // 한번 공격할때 공격 가속도와 치고 빠지기를 반복한다 
        while (percent <= 1)
        {
            percent += Time.deltaTime * attackSpeed;
            float formula = (-Mathf.Pow(percent, 2) + percent) * 4;
            transform.position = Vector2.Lerp(originalPosition, targetPosition, formula);
            yield return null;
        }
    }
}

 

 

 

 

 

Enemy 오브젝트의 MeleeEnemy 스크립트를 붙힘니다 

그리고 Health 2 , speed 5 , timeBetweenAttacks 2, damage 1, stopDistance 3, attackSpeed 8을 넣습니다  

 

Inspector 창에서 Player,Enemy 레이어를 추가합니다 

 

 

 

 

 

 

Edit -> ProjectSettings -> Phsics2D  에서 아래 그림과 같이

플레이어 레이어가있는 오브젝트와 적 레이어가 있는 오브젝트가 더 이상 서로 충돌하지 않기 때문에 체크 해제 합니다 

 

 

 

 

 

게임을 실행하면 적 캐릭터가 Player를 따라 다니면서 공격하는 것을 볼 수 있습니다 

Enemy_sheet.png
0.12MB

반응형

+ Recent posts