내일배움캠프 7주차 5일차 TIL - 3차원의 시점과 이동

백흰범·2024년 5월 31일
0
post-thumbnail

오늘 한 일

  • 배운 내용 정리하기
  • 밍글데이
  • 팀원 간 개인 프로젝트 서로 피드백하기


3차원의 시점

2차원과 다른점

  • 2차원은 아무런 설정 없이 캐릭터가 움직일 때 카메라를 따라가게 만들면 되지만,
    3차원은 마우스에 따라서 시야를 바꿔줘야할 필요가 있다. (3차원의 각도가 요구된다)
  • 3차원은 2차원과 달리 카메라를 상하좌우로 틀어줘야할 필요가 있다.


3차원 시야 구현 방법

카메라의 3차원 회전

  • x-는 카메라가 위를 보고, x+는 카메라가 아래를 본다.
  • y-는 카메라가 좌를 보고, y-는 카메라가 우를 본다.
  • 물론 추후에 이동 때문에 y rotation을 돌 때에는 캐릭터 오브젝트를 회전시킬 예정이다.

Delta

  • 마우스 포인터의 이동값을 받아낸다. (포인터가 한 프레임에서 다음 프레임으로 이동할 때의 변화량) 즉 델타를 나타냅니다. (DeltaTime이랑 비슷한 느낌)
    (게임 화면 좌표 기준으로 포인터 위치 변화량을 뽑아낸다.)
  • 상하가 -x, +x의 값이고
  • 좌우가 -y, +y의 값이다.

위를 보면 알겠지만
Delta.y의 값은 카메라 각도의 상하 움직임에 사용되어야하고 (-로 반영)
Delta.x의 값은 캐릭터 좌우의 움직임을 구현해야한다. (캐릭터의 yRot을 구현)



구현하기

Hierarchy 설정

코드

   void Start()
   {
       ...
       CharacterManager.Instance.Player.OnLook += Look;
       Cursor.lockState = CursorLockMode.Locked; // 이걸 해두지 않으면 마우스가 화면에서 벗어난다.
   }

    private void Look(Vector2 direction)
    {
        camCurXRot += direction.y * lookSensitive; // 민감도 배수
        camCurXRot = Mathf.Clamp(camCurXRot, minXLook, maxXLook);
        cameraContainer.localEulerAngles = new Vector3(-camCurXRot, 0, 0); // 카메라의 x축 회전

        transform.eulerAngles += new Vector3(0, direction.x * lookSensitive, 0); // 캐릭터의 y축 회전
    }

구현된 모습

  • 의도된대로 잘 움직여진다.



3차원의 이동



2차원과 다른점

2차원

  • 2차원은 x축과 y축이 존재하고, 3차원은 x축, y축, z축이 존재한다.
  • 2차원은 Vector2, 3차원은 Vector3를 사용해서 움직인다.
  • x - 좌우 | y - 상하

  • x - 좌우 | y - 높이 | z - 앞뒤

이러한 특징을 가졌기 때문에 상하좌우를 움직일 때는 3차원에서는 y부분이 사용되지 않게 조심하자



3차원 걷기 구현 방법

  • 2차원과 달리 3차원은 x, z를 활용해서 이동해야한다.
    (Vector2를 그대로 적용해버리면 높이가 올라가는 현상이 발생한다;)
  • 바라보는 시점에 따라서도 줘야하는 값이 달라진다.
    그럴 때 사용하는 코드는 transform.forward(오브젝트 앞뒤), transform.right(오브젝트 우좌)
    // 안하면 그냥 말 그대로 x와 z의 방향대로 움직이게 된다. (인형뽑기의 팔이나 다름 없다)
  • 해당 사진을 보면
    transform.forward는 저 파란색 화살표 방향의 단위 벡터를 반환해주고
    transform.right는 빨간색 화살표의 단위 벡터를 반환해준다는 의미가 된다.


구현하기

코드

  • 이동 부여 방식은 취향껏 AddForce의 Acceleration과 ClampMagnitude를 걸어주었다.
    • Vector3.ClampMagnitude(대상값, 최대값) 대상 벡터의 스칼라값이 최대값을 넘지 못하게 막는다.
    void FixedUpdate()
    {
        Move();
    }

    private void Move()
    {
        if (currentMove == Vector3.zero) { return; } // 움직임이 없을 시 즉시 반환

        Vector3 dir = transform.forward * currentMove.y + transform.right * currentMove.x; // 이게 3차원의 포인트이다.
        dir = dir.normalized;

        _rigidbody.AddForce(dir * moveSpeed, ForceMode.Acceleration);
        _rigidbody.velocity = Vector3.ClampMagnitude(_rigidbody.velocity, maxVelocity); // 스칼라 Clamp
    }

    private void MoveInput(Vector2 direction)
    {
        currentMove = direction;
    }
   

구현된 모습

  • 보이는 걸로는 잘 모르겠지만, 의도된대로 잘 움직인다.


3차원 이동에서 알게된 코드

transform.forward - 파란색 화살표의 단위 벡터
transform.right - 빨간색 화살표의 단위 벡터
Vector3.ClampMagnitude(대상값, 최대값) - 대상 벡터의 스칼라값이 최대값을 넘지 못하게 제한




쓰면서 느낀점

확실히 복습을 해보면서 부족한 부분을 채우니 해당 코드나 값들에 대한 이해도가 높아졌다.

profile
게임 개발 꿈나무

0개의 댓글