본문 바로가기
Develop Story/Game Engine

Unreal 4 - Puzzle game 개발 - 02 기믹

by 늘상의 하루 2020. 10. 18.

neulsang-day.tistory.com/15

 

Unreal 4 - 블루프린트로 퍼즐 게임 만들기

이번에 이력서를 준비하면서 많은 회사들이 언리얼을 다루는 것을 알게 되었습니다. 문제는 제가 언리얼을 제대로 다뤄본 적이 없다는 사실입니다. 문제가 있으면 고쳐야죠. 바로 언리얼 공부��

neulsang-day.tistory.com

이전 글에서는 기본적인 캐릭터와 카메라 셋팅을 알아보았습니다.

이 글에서는 발판과 발판을 밟으면 움직이는 블럭을 만들 계획입니다.

보통 이러한 요소들을 기믹(Gimmick)이라고 부릅니다.

 

우선 좌측 모드창에서 트리거 박스를 하나 드래그 앤 드롭으로 배치해 줍시다.

배치를 하면 필드에 와이어 프레임만 있는 녹색 육면체가 하나 생성될 겁니다.

트리거(Trigger)는 접촉시 이벤트를 촉발시키는 방아쇠 개념입니다.

 

생성했다면 우측 디테일 창 상단에 있는 블루프린트 스크립트 추가 버튼을 클릭해 줍시다.

그러면 해당 오브젝트에 대한 블루프린트가 생성되며 콘텐츠 브라우저에 해당 블루프린트 클래스가 생성됩니다.

그 다음 출력되는 블루프린트 창은 조금 익숙해 지셨을 겁니다.

 

버튼을 만들어야 하니 좌측에서 컴포넌트 추가를 누르고 박스를 선택한 뒤 자유롭게 배치해 주시면 됩니다.

W, E, R 버튼으로 각각 방향, 회전 크기를 조절 가능하며 우측의 트랜스폼 항목에서 세부 조절이 가능합니다.

-필드에 배치될 때는 컬라이더를 기준으로 삼으니 초록색 육면체 밖으로 나가면 다른 오브젝트와 겹칠 수 있습니다.-

 

그런데 이것만 해서는 구분하기 어렵고 이 버튼이 어떤 버튼인지 알기 어렵습니다.

블루프린트를 작성하기에 앞서 컬러를 입히기 위해 머터리얼을 추가할 계획입니다.

박스를 선택하고 우측 디테일의 Materials 항목을 확인합시다.

드롭박스 메뉴를 선택하면 꽤 많은 머터리얼이 미리 준비되어 있을 것입니다.

기본적으로 제공되는 스타팅 리소스들도 있으니 선택은 자유입니다.

하지만 머터리얼을 만드는 과정 역시 알아야 하니 상단의 머터리얼을 누르고 이름과 저장 위치를 지정해 줍시다.

 

그 다음으로 완성된 머터리얼 구체를 더블 클릭하면 블루프린트 창과 같이 머터리얼 창이 생성됩니다.

 

 

머터리얼과 관련해서는 저보다 더 좋은 설명을 해 주시는 분들이 많이 있습니다.

사용할 것은 베이스 컬러이며 취향에 따라 메탈릭과 스페큘러 러프니스 이미션을 간단하게 설명하겠습니다.

-우클릭을 눌러 변수로 승격시키면 기본적인 값이 입력되니 한번씩 해 보시고 차이를 확인하시는 것도 좋은 방법입니다.-

 

베이스 컬러 : 물체의 표면에 출력되는 컬러 혹은 이미지입니다.

메탈릭 : 0과 1로 금속 성질을 부여합니다.

-오직 0과 1만 사용하세요.-

스페큘러 : 빛 반사 성질을 부여합니다.

-메탈릭과 비슷한 효과를 만들지만 반사광을 임의로 조정할 수 있습니다.-

러프니스 : 물체의 거칠기를 조절합니다.

-거칠면 반사가 적고 매끄러우면 반사가 잘 되겠죠.-

이미션 : 자체 발광하는 컬러를 설정합니다.

 

디테일이 좌측 하단에 있습니다.

지금 필요한 것은 베이스 컬러와 러프니스만 있으면 됩니다.

취향대로 셋팅해서 저장을 눌러 주시면 됩니다.

-스포이드 기능은 언리얼 엔진 바깥에 있는 것들도 뽑아 쓸 수 있습니다. 편리합니다.-

 

발판 위치를 조정해 주시면 됩니다. [End] 버튼을 누르면 오브젝트가 바닥에 붙습니다.

그런데 플레이를 해 보면 발판이 사라지는 것을 볼 수 있습니다.

 

트리거 오브젝트는 플레이시 숨겨 버리는 항목이 체크되어 있습니다.

Rendering에 체크되어 있는 Visible, Actor Hidden In Game을 해제해 주세요.

 

발판이 어떤 발판인지 인식할 수 있도록 Actor-Tags에서 태그를 달아 줍시다.

저는 Red Button이니 RB로 태그를 달아 주었습니다.

블루프린트의 뷰포트 창의 디테일에서 수정하면 일괄 적용됩니다.

-태그를 바꾸는 것으로 동작하는 박스를 바꿀 수 있습니다.-

 

이제 블루프린트를 작성할 건데 발판에는 태그만 사용하고 블루프린트를 작성하지 않을 계획입니다.

캐릭터에 넣어서 작동시켜 봅시다.

 

 

캐릭터 조작 블루프린트 아래쪽에 만들 발판 체크 블루프린트 완성본 입니다.

우선 밟았는지 아닌지 체크를 위해 Bool 타입의 변수를 만들어 줄 겁니다.

좌측 내 블루프린트의 변수 항목에서 추가하고 이름을 정해 줍시다.

- 적색, 녹색, 파란색 3가지 타입을 사용하니 미리 추가해 주시면 좋습니다. -

- 변수를 만들면 변수명 우측에 눈을 감고 있는 버튼이 있습니다. 외부에서도 볼 수 있게 클릭해서 눈을 뜬 상태로 바꿔 줍시다.-

 

먼저 트리거와 접촉한 상태와 접촉 해제한 상태에서 이벤트를 발생시키기 위해

ActorBeginOverlapActorEndOverlap을 만들어 줍시다.

그 다음 우클릭을 눌러 if를 검색하거나 branch를 검색하여 Branch노드를 생성해 줍시다.

- 브런치 노드는 조건이 참이면 true 거짓이면 false를 실행하는 조건문입니다. -

 

어떤 트리거와 충돌했는지를 판단하기 위해 조건을 만들어야 합니다.

방금 만들었던 Tag를 사용하기 위해 Actor Has Tag를 생성하고 발판의 tag명을 입력해 주신 다음

위 이미지와 같이 연결해 주시면 됩니다.

-Play Sound 노드는 없어도 무관합니다. 할당된 사운드 파일을 실행하는 노드입니다.-

 

브런치True 항목에서 방금 만든 변수명을 검색하면 Set RB Down을 생성할 수 있습니다.

생성 후에는 버튼이 눌렸다는 것을 확인시키기 위해 체크 박스를 눌러줍니다.

-Set은 보내기 Get은 가져오기 입니다.-

 

이런 방식으로 녹색 발판과 파란색 발판 판정을 함께 작업해 주시면 위 이미지와 같이 진행됩니다.

그런데 지금 당장 제대로 작동하는지 확인하기 어렵죠.

 

Print Text 노드를 사용하시면 플레이 화면에서 이벤트가 정상 작동하는지 체크할 수 있습니다.

해당 노드를 사용하고 이벤트 실행시 입력된 텍스트가 화면 좌측 상단에 출력됩니다.

완성된 노드는 이렇습니다.

이벤트 흐름은 이렇습니다.

 

트리거와 충돌하거나 충돌 해제됐을때 실행 ->

RB 트리거인가? (아니면 다음)->

GB 트리거인가? (아니면 다음)->

BB 트리거인가? (아니면 그냥 종료.)

 

컴파일 해 주시고 이제 판정은 끝났습니다. 박스가 움직여야 하니 박스를 작업하러 가 봅시다.

박스부터는 조금 복잡하게 진행됩니다.

 

 

우선 필드에 박스(큐브)를 하나 만들어 주고 움직일 것이기 때문에 디테일에서 무버블로 바꿔 줍시다.

다음으로는 버튼과 같은 색으로 맞춰서 직관성을 높여 줍시다.

만들어뒀던 머터리얼을 박스의 머터리얼에 드래그 앤 드롭을 하거나 드롭메뉴를 눌러 바꿔줍시다.

 

그 다음으로 블루프린트 추가 버튼을 눌러주세요.

블루프린트 완성본은 이렇습니다.

 

작업에 들어가기에 앞서 우리는 변수 2개를 미리 만들어 줄 겁니다.

첫 번째는 상자가 올라가있는지 내려가 있는지를 판단하는 Bool(Up) 변수입니다.

-Up 변수는 디테일 항목에서 인스턴스 편집 기능과 스폰시 노출 항목을 체크해 주세요.-

-이렇게 하면 메인 화면의 디테일 항목에 Up변수가 나타나고 개별적으로 편집이 가능합니다.-

두 번째는 상자의 초기 위치와 백터를 파악하고 저장하기 위한 Vector(Offset) 변수입니다.

-Pawn 변수는 조금 이따가 만들 계획입니다.-

-Transform 이 아니라 Vector를 쓰는 이유는 상자를 움직이기 위함입니다. 움직이는 모든 것들은 Vector입니다.-

 

먼저 상자를 움직이기 위해서는 상자가 어디에 있는지 부터 알아야 합니다.

 

게임이 시작하자마자 이벤트를 발동시키는 BeginPlay 이벤트와 GetActorLocation 노드를 만들어 줍시다.

그리고 GetActorLocation은 블루프린트가 들어간 오브젝트의 위치값을 가져오는 노드입니다.

GetActorLocation에서 진행선을 끌어다가 방금 만든 Offset 변수에 Set으로 저장해 줍시다.

-그러면 이제 박스의 초기 위치가 Offset에 저장되었습니다.-

 

다음으로는 Tick 이벤트를 생성해 줍시다.

가장 편한 방법은 상자를 지정한 위치로 순간이동 시키는 방법입니다.

하지만 여기서는 상자를 부드럽게 움직이기 위해 Lerp를 사용할 계획입니다.

 

Tick 이벤트는 매 프레임마다 이벤트를 반복 실행합니다.

그 다음으로는 플레이어가 발판을 제대로 밟았는지를 파악하기 위해 캐스팅(형변환) 작업을 해 줄겁니다.

캐릭터 블루프린트의 이름을 작성하고 형변환 노드를 생성해 줍시다.

Get Player Character를 생성해서 Object에 연결하고 As파츠를 변수로 승격시켜 준 다음 이름을 편한대로 바꿔 줍시다.

-보통 게임을 시작하자마자 캐스팅을 한번 해두면 매 프레임마다 할 필요가 없습니다.-

-하지만 이 게임에서는 캐릭터를 3개를 바꿔가며 조종하기에 어떤 캐릭터를 조종하고 있는지 매번 확인해 줄 필요가 있습니다.-

 

이제 Branch를 하나 만들어주고 방금 만들었던 Up을 연결시켜 줍니다.

Up이 체크되어 있으면 상자는 올라갈 것이고 체크 해제되어 있으면 내려가 있는 상태를 유지할 겁니다.

TrueFalseSetActorLocation 노드를 생성해 줍시다.

 

상자가 올라가는 노드 모음

간단히 Lerp는 선형 보간이리고 0에서 1까지 프레임별로 상승하는 함수입니다. 이걸 쓰면 매끄럽게 움직입니다.

이번에는 SetActorLocation에서 역순으로 작업을 진행해 볼 겁니다.

 

New Location 항목을 끌어다가 Lerp를 생성해 줍시다.

A 위치에는 지금 상자의 위치값 GetActorLocation을 넣고.

 

B 위치에는 Offset에 저장된 위치값에 +n 값을 더해줄 겁니다.

B를 드래그하여 +를 검색하고 Vector+Vector를 생성해 줍시다.

그리고 1번 위치를 다시 드래그하여 Offset을 생성해 줍시다.

2번 위치에 입력하는 값 만큼 상자는 자신의 위치를 기준으로 움직입니다.

 

Alpha는 Lerp를 움직일 시간값을 의미합니다.

쉽게 말해 상자가 움직이는 속도입니다. 0~1 사이로 맞춰주면 자연스럽습니다.

 

 

상자를 올렸으면 다시 내려야죠. 이건 더 간단합니다.

 

SetActorLocation을 생성하고 New Location에서 끌어다가 Lerp를 만듭니다.

그 다음 A에는 올라가 있는 상자의 위치값 GetActorLocation

B에는 돌아갈 초기 상자 위치값 Offset을 넣어줍니다.

Alpha값은 임의로 설정해 줍시다.

 

여기까지만 해도 플레이를 해 보면 상자가 움직이는 것을 확인할 수 있습니다.

메인 화면의 디테일에서 Up을 체크하여 상자가 이동하는지 확인해 보세요.

 

아직 발판을 밟으면 상자가 반응하는 노드는 만들지 않았습니다. 이제 만들어 봅시다.

 

이 작업은 상자가 올라가 있건 내려가 있건 동일하게 작업하기에 중복으로 만들어 줄 필요가 없습니다.

Branch를 만들고 SetActorLocation에서 연결해 주세요.

 

그리고 플레이어 캐릭터 블루프린트로부터 발판을 밟았는지 값을 얻어오기 위해

Pawn을 생성하고 드래그하여 Get RB Down(임의로 설정한 발판 변수 체크값)을 만들어 줍시다.

해당 값을 만들었으면 Branch에 연결해 줍시다.

-다른 컬러의 박스를 만들고 싶다면 새로 블루프린트를 작성하여 Get RB Down만 바꿔주면 됩니다.-

 

이렇게 하면 플레이어가 해당 컬러의 발판을 밟았을 때 값을 받아와서 TrueFalse로 판정을 할 수 있습니다.

True 일 때는 발판을 밟았다는 의미이니 이쪽만 연결해 주면 됩니다. 먼저 Delay 노드를 추가해 줍니다.

-Tick 이벤트는 매 프레임마다 실행되는데 Lerp를 사용했기에 상자가 이동하는 중에도 계속 이벤트를 호출합니다.-

-꼬이는 것을 방지하기 위해 Delay를 주겠습니다.-

 

RB Down이 계속 체크되어 있으면 이벤트가 계속 발생하기 때문에

Delay에 이어서 Set으로 Set RB Down을 해제해 줍시다.

-노드가 출력되지 않는다면 Pawn노드에서 이어서 해 보세요-

 

다시 Branch를 작성하고 이제 Up 변수를 연결해 줍시다.

올라간 것은 내려오고 내려온 것은 올라오는 등 번갈아가며 작동시키기 위해 Set으로 설정해 줍시다.

 

 

완성

 

다음은 클리어와 관련 UI를 작업해 봅시다.