유니티/플랫포머 기초

[Unity] 플랫포머 기초 - 1. 플레이어 이동

이름?없음 2024. 11. 26. 10:26
반응형
반응형

 

이번에는 유니티를 사용하여 간단한 2D플랫포머 게임을 만들어 보겠습니다.

우선 기본적인 플레이어 이동부터 구현해 보겠습니다

 

우선 플레이어 이동을 구현하는데 필요한 오브젝트들을 배치해 보겠습니다

 

사각형 오브젝트를 생성 후 길게 늘려 땅을 만들어 주세요

그 후 이 오브젝트의 이름을 Ground로 수정한 후 BoxCollider2D 컴포넌트를 넣어주세요

 

캡슐을 하나 생성한 후 Player라고 이름을 붙여주세요

플레이어 오브젝트에 콜라이더와 Rigidbody2D 컴포넌트를 넣어주세요

그 후 Rigidbody의 FreezeRotation을 활성화하여 마음대로 회전하지 못하도록 설정하세요

 

사전 설정을 전부 끝났습니다

지금부터는 스크립트를 작성하여 보겠습니다

 

우선 플레이어의 입력을 감지하는 스크립트를 작성하여 보겠습니다

InputController라는 이름의 스크립트를 하나 생성하여 주세요

using System;
using UnityEngine;

/// <summary>
/// 전반적인 Input을 관리하는 클래스
/// </summary>
public class InputController : MonoBehaviour
{

    /// <summary>
    /// 플레이어의 좌우 입력 이벤트
    /// </summary>
    public event Action<float> OnMoveEvent;

    /// <summary>
    /// 플레이어 점프 이벤트
    /// </summary>
    public event Action OnJumpEvent;

    private void Update()
    {
        MovePlayer();
        JumpPlayer();
    }

    /// <summary>
    /// 플레이어 점프 입력을 감지하는 함수
    /// </summary>
    private void JumpPlayer()
    {
        //만약 스페이스바를 눌렀다면?
        if (Input.GetKeyDown(KeyCode.Space))
        {
            //점프 이벤트를 발행
            OnJumpEvent?.Invoke();
        }
    }

    /// <summary>
    /// 플레이어 이동 입력을 감지하는 함수
    /// </summary>
    private void MovePlayer()
    {
        //Horizontal입력 받기(A,D,<-,->)
        float x = Input.GetAxisRaw("Horizontal");

        //이동 이벤트 발행
        OnMoveEvent?.Invoke(x);
    }
}

InputController의 경우 event를 사용하여 옵저버 패턴으로 사용할 수 있도록 디자인하였습니다

외부에서 사용할 경우 이벤트만 구독하여 입력정보를 받을 수 있습니다

 

이제 플레이어를 움직여주는 스크립트를 작성하여 보겠습니다

PlayerMove라는 이름의 스크립트를 하나 생성하여 주세요

using UnityEngine;

/// <summary>
/// 플레이어 이동을 관리하는 클래스
/// </summary>
public class PlayerMove : MonoBehaviour
{

    /// <summary>
    /// 이동 스피드
    /// </summary>
    [SerializeField] private float _moveSpd;

    /// <summary>
    /// 물리 사용을 위하여 Rigidbody를 받기
    /// </summary>
    private Rigidbody2D _rigid;

    /// <summary>
    /// Input사용을 위하여 InputController를 받기
    /// </summary>
    private InputController _input;

    private void Awake()
    {
        //GetComponent로 찾아오기
        _input = GetComponent<InputController>();
        _rigid = GetComponent<Rigidbody2D>();

        //Input에 이동 이벤트 구독
        _input.OnMoveEvent += HandleMove;
    }

    /// <summary>
    /// 이동 이벤트를 처리하는 함수
    /// </summary>
    /// <param name="x">입력정보</param>
    private void HandleMove(float x)
    {
        //Rigidbody.velocity에 넣을 값 설정
        //x는 입력정보를 받아 Speed를 곱하여 설정
        //y는 점프 처리를 위하여 현재의 velocity로 설정
        var vel = new Vector2(x * _moveSpd, _rigid.velocity.y);

        //velocity설정
        _rigid.velocity = vel;
    }

    private void OnDestroy()
    {
        //Input이 아직 존재한다면?
        if( _input != null)
        {
            //이벤트 구독을 해제
            _input.OnMoveEvent -= HandleMove;
        }
    }
}

PlayerMove의 경우 Input의 입력정보를 받아 Rigidbody를 사용하여 물리적으로 움직일 수 있도록 구현하였습니다

 

마지막으로 Jump기능을 구현하여 보겠습니다

PlayerJump라는 이름의 스크립트를 하나 생성하여 주세요

using UnityEngine;

public class PlayerJump : MonoBehaviour
{
    /// <summary>
    /// 점프파워
    /// </summary>
    [SerializeField] private float _jumpPower;

    /// <summary>
    /// 물리 사용을 위하여 Rigidbody를 받기
    /// </summary>
    private Rigidbody2D _rigid;

    /// <summary>
    /// Input사용을 위하여 InputController를 받기
    /// </summary>
    private InputController _input;

    private void Awake()
    {
        //GetComponent로 찾아오기
        _input = GetComponent<InputController>();
        _rigid = GetComponent<Rigidbody2D>();

        //Input에 점프 이벤트 구독
        _input.OnJumpEvent += HandleJump;
    }

    /// <summary>
    /// 점프 이벤트 처리를 위한 함수
    /// </summary>
    private void HandleJump()
    {
        _rigid.AddForce(Vector2.up * _jumpPower, ForceMode2D.Impulse);
    }

    private void OnDestroy()
    {
        //Input이 아직 존재한다면?
        if (_input != null)
        {
            //이벤트 구독을 해제
            _input.OnJumpEvent -= HandleJump;
        }
    }
}

PlayerJump의 경우 Input의 입력정보를 받아 Rigidbody를 사용하여 물리적으로 점프할 수 있도록 구현하였습니다

 

이제 스크립트 작성이 완료되었습니다

Player오브젝트에 작성한 모든 스크립트를 넣어주세요

 

그 후 이동속도와 점프파워를 원하는 값으로 설정해 주세요

 

끝났습니다 실행시켜 보면 플레이어가 잘 이동하고 점프하는 것을 확인할 수 있습니다

 

하지만 지금은 더블점프가 되는 등 약간의 문제가 있습니다

다음 글에서는 지면 감지를 추가하여 이를 해결해 보겠습니다

반응형