프로젝트를 생성하고, 가장 먼저 sprite shape를 이용해 지형을 만들어준다. Sprite Shape Renderer 컴포넌트에 Edge Material과 Fill Material을 각각 추가하고, Sprite Shape Controller 컴포넌트의 Edit Spline을 통해 세부적인 지형을 설정한다.
이후 플레이어 캐릭터가 들어갈 빈 2D object를 생성해주고, 상반신과 하반신 에셋을 자식 오브젝트로 추가해준다.
상, 하반신 위치를 자연스럽게 조절한 후에 캐릭터 오브젝트에 캡슐 콜라이더를 추가한다. 캡슐 콜라이더의 Offset과 Size값을 조절하여 보드 크기에 맞게 콜라이더를 설정하고, 서클 콜라이더도 마찬가지로 Offset과 Radius값을 조절하여 머리 크기에 맞게 콜라이더를 설정해 준다.
캐릭터까지 생성해준 후에, 지형을 만들어줬던 sprite shape의 컴포넌트로 Surface Effector 2D를 추가해주고 Edge Collider 2D의 Used By Effector를 체크해준다.
(동시에 여러 콜라이더가 있을 경우 어떤 콜라이더에 이펙터를 적용할 것인지를 체크하는 용도이다)
이제 캐릭터의 회전을 구현할 차례인데, Transform 컴포넌트에 있는 Rotation의 Z값을 통해서도 캐릭터를 회전시킬 수 있으나 그럴 경우 물리 엔진과 조화롭지 않고 게임 오브젝트 자체만 회전하는 부자연스러운 움직임이 구현된다.
자연스러운 회전을 구현하기 위해서는 Torque를 AddForce 형태로 가해주면 된다. 'PlayerController'라는 이름으로 C# 스크립트를 생성해주고, 아래 코드를 통해 캐릭터 회전을 구현한다.
// 인스펙터 상에서 회전력을 조절하기 위해 변수를 직렬화 상태로 선언 및 초기화
[SerializeField] float torqueAmount = 1f;
// 물리 움직임을 구현하므로 RigidBody2D 네임스페이스로 변수 선언
RigidBody2D rb2d;
// 변수 초기화
void Start()
{
rb2d = GetComponent<RigidBody2D>();
}
void Update()
{
RotatePlayer();
}
// 플레이어 회전 메소드
void RotatePlayer()
{
if (Input.GetKey(KeyCode.LeftArrow))
{
rb2d.AddTorque(torqueAmount);
}
else if (Input.GetKey(KeyCode.RightArrow))
{
rb2d.AddTorque(-torqueAmount);
}
}
회전은 위와 같이 구현을 마쳤으며, 다음으로 플레이어 이동을 구현한다. 회전과 마찬가지로 RigidBody의 물리 작용(AddForce)을 이용하여 구현할 수도 있겠지만, 게임의 특성상 한 방향으로만 이동하기에 이에 적합한 'Surface Effector'를 사용하기로 한다.
조금 전에 만들어두었던 지형 오브젝트인 sprite shape에 Surface Effector 2D 컴포넌트를 추가해 주고, PlayerController 스크립트에 캐릭터 이동을 위한 코드를 아래와 같이 추가해준다.
// 기본 이동 속도와 특정 키 입력 시 반응하는 부스트 속도 변수 직렬화 상태로 선언 및 초기화
[SerializeField] float baseSpeed = 20f;
[SerializeField] float boostSpeed = 30f;
// surface effector 사용을 위해 변수 선언
SurfaceEffector2D surfaceEffector2D;
void Start()
{
// 선언한 변수 초기화
surfaceEffector2D = FindObjectOfType<SurfaceEffector2D>();
}
// 기본 속도를 baseSpeed로, 위 방향키 입력 시 스피드를 boostSpeed로 설정하는 메소드
void RespondToBoost()
{
if (Input.GetKey(KeyCode.UpArrow))
{
surfaceEffector2D.speed = boostSpeed;
}
else
{
surfaceEffector2D.speed = baseSpeed;
}
}
이렇게 게임 환경과 플레이어 움직임을 모두 구현했다. 이동 속도나 회전력은 모두 직렬화했기 때문에, 게임을 반복적으로 플레이하면서 가장 자연스러운 값을 찾아 인스펙터 상에서 손쉽게 설정해줄 수 있다.