해당 글은 유튜버 골드메탈님의 강의를 바탕으로 작성되었습니다.
이번 강의는 코딩보다는 유니티 볼트를 주로 사용하여 게임을 만드는 강의입니다.
하지만 저의 경우에는 이를 볼트가 아닌 코딩으로 작성해보고자 하였습니다.
우선 1일차에는 기본적인 도트 이미지를 이용하여 게임의 전체적인 배경을 구현해주었고, 자동으로 이동하는 기초적인 AI를 구현하였습니다.
해당 강의 영상은 볼트를 사용하기 때문에 코드에 관한 설명이 전혀 나오지 않으므로 제가 직접 구현한 코드를 바탕으로 설명드려보려 합니다.
우선 에셋에 공유되어 있는 도트 이미지를 활용하여 배경을 구현해 줍니다.
배경을 배치할 때 각 배경들의 레이어 순서(Order in Layer)를 알맞게 조절하여 어색한 부분이 없도록 해줍니다.
다음으로 Prefab으로 저장되어 있는 Particle Object를 화면에 배치한 뒤, 다음과 같이 Shin과 겹치도록 위치를 조절해 줍니다.
이후 Jelly와 그림자를 배치하고, 적절하게 위치를 조절해줍니다. 그림자의 경우 Jelly의 자식 오브젝트로 설정해줍니다.
또한 이미 구현되어 있는 Animation을 Jelly에 적용시켜줍니다.
다음으로 카메라가 배경 바깥을 비추는 현상과 Jelly의 Pixel 이미지가 흐릿하게 보이는 현상을 해결하기 위해 'Pixel Perfect Camera'라는 패키지를 다운로드하여 Import 합니다.
이후 Main Camera에 'Pixel Perfect Camera' 컴포넌트를 추가한 뒤, 다음과 같이 설정하고 'Run In Edit Mode'를 클릭하여 설정을 적용시켜줍니다.
설정을 완료한 뒤 Game Scene을 통해 확인해보면 Particle System과 함께 배경이 잘 구현된것을 확인할 수 있습니다.
이제 Jelly를 자동으로 움직이게 하기 위한 코드를 작성해야 합니다.
우선 해당 강의에서는 Jelly의 움직임을 일정시간 움직이고, 일정시간 멈추고를 반복하는 식으로 구현하였기 때문에 저 또한 해당 움직임으로 구현하고자 하였습니다.
먼저 Scripts 폴더를 따로 생성하여 Jelly라는 이름으로 Script를 만들어 준 뒤 Jelly 오브젝트의 컴포넌트로 추가해주었습니다.
이후 Script를 열어 Awake() 함수 내에서 SpriteRenderer와 Animator 컴포넌트를 가져왔습니다.
public class Jelly : MonoBehaviour
{
SpriteRenderer sprite;
Animator anim;
void Awake()
{
sprite = GetComponent<SpriteRenderer>();
anim = GetComponent<Animator>();
}
}
다음으로 Jelly의 움직임을 구현하기 위한 각종 변수와 Move() 함수, 코루틴 함수를 추가해주었습니다.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Jelly : MonoBehaviour
{
public int move_delay; // 다음 이동까지의 딜레이 시간
public int move_time; // 이동 시간
float speed_x; // x축 방향 이동 속도
float speed_y; // y축 방향 이동 속도
bool isWandering;
bool isWalking;
SpriteRenderer sprite;
Animator anim;
void Awake()
{
sprite = GetComponent<SpriteRenderer>();
anim = GetComponent<Animator>();
isWandering = false;
isWalking = false;
}
void FixedUpdate()
{
if (!isWandering)
StartCoroutine(Wander()); // 코루틴 실행
if (isWalking)
Move();
}
void Move()
{
if (speed_x != 0)
sprite.flipX = speed_x < 0; // x축 속도에 따라 Spite 이미지를 뒤집음
transform.Translate(speed_x, speed_y, speed_y); // 젤리 이동
}
IEnumerator Wander()
{
move_delay = 6;
move_time = 3;
// Translate로 이동할 시 Object가 텔레포트 하는 것을 방지하기 위해 Time.deltaTime을 곱해줌
speed_x = Random.Range(-0.8f, 0.8f) * Time.deltaTime;
speed_y = Random.Range(-0.8f, 0.8f) * Time.deltaTime;
isWandering = true;
yield return new WaitForSeconds(move_delay);
isWalking = true;
anim.SetBool("isWalk", true); // 이동 애니메이션 실행
yield return new WaitForSeconds(move_time);
isWalking = false;
anim.SetBool("isWalk", false); // 이동 애니메이션 종료
isWandering = false;
}
}
코루틴 함수는 저 또한 많이 사용해본적이 없어서 구글링을 통해 최대한 아는만큼 구현해보았습니다.
다음으로는 맵에 경계를 두어 Jelly가 맵 바깥으로 나가는 것을 방지하기 위해 Object를 추가해주었습니다. 각각의 이름을 'Bottom', 'Top', 'Left', 'Right'로 지정해주었으며, 크기와 위치를 적절하게 조절해주었습니다.
다음으로 Jelly와 경계 사이의 접촉을 감지하기 위해 Collider를 추가하고 'Is Trigger' 속성을 체크해주었습니다.
Jelly 오브젝트 또한 Collider를 추가해주었으며 역시 'Is Trigger' 속성을 체크해주었습니다.
추가적으로 RigidBody2D 컴포넌트를 추가한 뒤, 다음과 같이 설정해주었습니다.
이후 Scene을 살펴보면 다음과 같이 맵 상하좌우에 경계가 배치된 것을 확인할 수 있습니다.
이제 실질적으로 Border 오브젝트와 Jelly 간의 충돌을 감지하고 이동을 제한하기 위해 Jelly 스크립트에 다음 코드를 추가해줍니다.
void OnTriggerEnter2D(Collider2D collision)
{
if (collision.gameObject.name.Contains("Bottom") || collision.gameObject.name.Contains("Top"))
speed_y = -speed_y;
else if (collision.gameObject.name.Contains("Left") || collision.gameObject.name.Contains("Right"))
speed_x = -speed_x;
}
즉, 충돌한 Object의 이름을 확인하여 'Bottom'이거나 'Top'일 경우 y축을 반대로, 'Left'이거나 'Right'일 경우 x축을 반대로 하여 이동 방향을 바꾸어주는 식으로 구현하였습니다.
이후 실행해보니 별다른 오류는 없었으며 잘 실행되는 것을 확인할 수 있었습니다.
'📌 etc > Unity 2D Raising Jelly Game' 카테고리의 다른 글
[Unity / C#] 2D 젤리 키우기 게임 - 6. 해금 시스템 만들기 (0) | 2022.03.26 |
---|---|
[Unity / C#] 2D 젤리 키우기 게임 - 5. UI 창 구축하기 (0) | 2022.03.23 |
[Unity / C#] 2D 젤리 키우기 게임 - 4. 젤리 판매 기능 구현 (0) | 2022.03.22 |
[Unity / C#] 2D 젤리 키우기 게임 - 3. 클리커 기능 구현 (0) | 2022.03.21 |
[Unity / C#] 2D 젤리 키우기 게임 - 2. 인터페이스 제작 및 기능 구현 (3) | 2022.03.20 |