쯔꾸르식 유니티 게임 공부

03.이동불가 에이리어 만들기(레이캐스트 히트)

ruripanda 2024. 12. 29. 20:43

본 강좌는 케이디님의 쯔꾸르풍 유니티 게임 만들기 강좌를 참고하여 만들었음을 알려드립니다

using System.Collections;
using UnityEngine;

public class MovingObjcet : MonoBehaviour
{
    private BoxCollider2D boxCollider;//박스콜라이더
    public LayerMask layerMask;//통과불가 에이리어 설정

    //케릭터 이동속도
    public float speed;
    //벡터(케릭터의 이동 방향)
    private Vector3 vector;

    //뛰기,평범하게 걷기
    public float runSpeed;
    private float applyRunSpeed;
    private bool applyRunFlag = false;

    //픽셀 단위로 움직이기 구현
    public int walkCount;
    private int currentWalkCount;

    //한칸한칸 이동할때 플레그 형식으로 구현
    private bool canMove = true;

    private Animator animator;
    // Start is called once before the first execution of Update after the MonoBehaviour is created
    void Start()
    {
        boxCollider = GetComponent<BoxCollider2D>();
        animator = GetComponent<Animator>();
    }

    //코루틴으로 이동제어 한칸 한칸 이동하게
    IEnumerator MoveCoroutine()
    {
        while(Input.GetAxisRaw("Vertical") !=0 || Input.GetAxisRaw("Horizontal") != 0)
        {
            //시프트 키 입력 여부에 따라 뛰기 걷기 구분
            if (Input.GetKey(KeyCode.LeftShift))
            {
                applyRunSpeed = runSpeed;
                applyRunFlag = true;
            }

            else
            {
                applyRunSpeed = 0;
                applyRunFlag = false;
            }

            //이동방향 벡터 움직임 구현
            vector.Set(Input.GetAxisRaw("Horizontal"), Input.GetAxisRaw("Vertical"), transform.position.z);

            //좌상,좌하 등 대각선 방향이동 장금
            if(vector.x !=0)
                vector.y = 0;

            //에니메이터 불러오기
            animator.SetFloat("DirX", vector.x);
            animator.SetFloat("DirY", vector.y);

            RaycastHit2D hit;//레이케스트

            Vector2 start = transform.position; //캐릭터의 현제 위치 값
            Vector2 end = start + new Vector2(vector.x * speed * walkCount, vector.y * speed * walkCount);
            //캐릭터가 이동하고자하는 위치 값 그리고 사이즈

            boxCollider.enabled = false;
            hit = Physics2D.Linecast(start, end, layerMask);
            boxCollider.enabled = true;

            if (hit.transform != null)
                break;

            animator.SetBool("Walking", true);

            //캐릭터 이동구현 코드
            while (currentWalkCount < walkCount)
            {
                if (vector.x != 0)
                {
                    //Translate는 현제 값에서 +를 해주는 코드
                    transform.Translate(vector.x * (speed + applyRunSpeed), 0, 0);
                }
                else if (vector.y != 0)
                {
                    transform.Translate(0, vector.y * (speed + applyRunSpeed), 0);
                }
                if (applyRunFlag)
                    currentWalkCount++;//위의 applyRunFlas가 되면 추가되는 카운트 만약 아니라면 더해지지 않음
                currentWalkCount++;//위의 카운트와는 별개의 카운트로 구분 됨
                yield return new WaitForSeconds(0.01f);//0.01초마다 대기
            }
            currentWalkCount = 0;//0을 넣어서 반복문 초기화

        }

        animator.SetBool("Walking", false);
        //한칸한칸 이동할때 bool값
        canMove = true;
    }

    //매 프레임마다 이동명령을 받음
    void Update()
    {
        if (canMove)
        {
            //이동 방향키 입력을 할때 쯔구르 처럼 상하좌우 구분하게 하는 코드
            if (Input.GetAxisRaw("Horizontal") != 0 || Input.GetAxisRaw("Vertical") != 0)
            {
                //한칸 한칸 이동할때 bool값으로 canMove를 이용함
                canMove = false;
                StartCoroutine(MoveCoroutine());
            }
        }
    }
}

 

1.플레이어 캐릭터에 BoxCollider2D를 넣는다

참고로 빨간 화살표의 Edit Collider를 누르면 씬에서 BoxCollider2D의  크기를 줄일 수 있다

 

2.BoxCollider2D와 LayerMAsk를  장착한다

레이어마스크의 경우 통과불가능한 에이리어와 접촉하므로 중요하다!

RaycastHit2D를 장착한다

레이케스트는 보이지 않는 선을 쏴서 접촉하는 물체의 속성을 파악한다

물체의 존재를 변수로 파악한다

start는 캐릭터 위치를 나타내고

 

end는 접촉하는 물체의 크기를 반환한다

start + new Vector2(vector.x * speed * walkCount, vector.y * speed * walkCount);

시작지점 + 새로운 백터( 가로 * 이동속도 * 걷는거리, 세로 * 이동속도 * 걷는거리)를 구하여

48*48을 나타낸다

위 speed와 WalkCount는 인스펙터의 값이다

 

3.레이캐스트를 설정한다

hit = Physics2D.Linecast(start, end, layerMask);

변수명 히트 = 피직스2D.레이케스트(시작점, 끝점, 레이어마스트)로 설정하여

레이케스트가 감지를 하게 한다

그런데 문제는 이렇게 작성을하면 캐릭터가 자기스스로의 값(BoxCollider2D)에 충돌하므로

이렇게 hit변수 위아래에 플레이어 자신의 BoxCollider콜라이더를 일시적으로 껐다켜서 충돌을 방지한다

그리고 레이케스트가 물체를 감지했을때 이동코루틴을 실행하지 않는다는 코드를 적어넣는다

 

4.레이어 설정

 

레이어를 추가해서 NOPASSING 이동불가 에이리어를 만들어 준다

 

그 다음 씬에 이동불가 에이리어로 빈오브텍트에 BoxCollider2D를 만들어 놓고 NOPASSING를 레이어로 설정해놓는다

다음 플레이어 캐릭터에도 이렇게 NOPASSING를 넣는다

 

 

그러면 이렇게 이동을 못하게 막아준다

'쯔꾸르식 유니티 게임 공부' 카테고리의 다른 글

06.맵과 맵을 이동하기  (0) 2024.12.31
05.2D맵제작하기  (0) 2024.12.31
04.카메라 플레이어 추적  (0) 2024.12.30
02.캐릭터 이동  (0) 2024.12.28
01.플레이어 케릭터 이동  (0) 2024.12.26