
루멘 & 라이트 블리딩 루멘은 언리얼 5에서 추가된 실시간 전역 조명 및 반사 엔진이다. 나온지 오래되지 않았기에 지원하지 않는 기능도 존재한다. 위 이미지의 옆면 벽 머티리얼을 보면 다른 부분과 달리 이질적인 모습을 볼 수 있다. 이는 해당 머티리얼을 구현하는 데 사용된 기능 중 루멘이 지원하지 않는 것이 존재하여 발생하는 문제이다. 따라서 해당 머티리얼의 속성을 변경해줄 필요가 있다. 해당 머티리얼을 눌러보면 머티리얼의 엘리먼트 이름에 Inst가 붙어있는 것을 볼 수 있다. 이는 진짜 머티리얼이 아니라는 것을 의미하며, 해당 머티리얼에 어떤 텍스처와 설정값을 써야 하는지 알려주는 블루프린트 같은 것이다. 해당 머티리얼을 우클릭해보면 해당 머티리얼에 대한 부모를 찾을 수 있다. 이후 해당 머티리얼에 대..

라이트의 종류 현재 작성한 레벨은 빛이 없어서 어두컴컴한 상태이다. 따라서 이번엔 빛을 추가해주며, 다양한 빛의 종류에 대해 알아보게 된다. 먼저 액터 배치 패널 라이트 부분에서 다음과 같은 라이트를 확인할 수 있다. 디렉셔널 라이트의 주요 용도는 햇빛이다. 빛의 방향만을 조절해주기 때문에, 어디에 배치하든 조명 위치는 중요하지 않다. 스카이 라이트는 반대로 모든 범위에서 나오는 빛이다. 그런데 처음에 배치하면 빛이 존재하지 않는다. 이는 스카이 라이트가 멀리 떨어진 빛을 캡처해 씬에 적용하는 것이기 때문이다. 따라서 레벨 전체를 감싸고 있는 구를 추가하고, 해당 구에서 빛을 가져오게 된다. 바로 적용되지 않고, 직접 리캡처 기능을 눌러 적용시켜주어야할 때가 있다. 이는 스카이라이트 디테일 탭에서 눌러주..

솔루션 : 모듈식 레벨 레이아웃 구현 저번에 마련한 기본적인 틀을 토대로 더욱 다양한 배치를 이어나가게 된다. 천장, 문, 기둥, 감옥, 지하동굴, 대영묘 등을 이번에 추가로 배치해준다. 먼저 천장이다. 4분할 화면을 통해 기존 배치된 에셋과 비교하여 정확한 배치를 할 수 있다. 하나를 배치한 이후에, Alt + 원하는 방향을 통해 복제하여 배치해준다. 안마당에 던전으로 들어가는 문도 설치해준다. 처음 문에 대한 에셋을 검색하면, 모듈식 에셋이기 때문에 문의 요소가 나눠져서 있다. 따라서 다 조립된 상태인 BP 클래스의 에셋을 사용할 수도 있다. 이후 열려있는 문을 만들어주기 위해 안쪽 나무문의 Z 각도를 조절하여 밖 또는 안쪽으로 열어 줄 수 있다. 천장이 연결되는 곳마다 기둥을 설치해주고, 천장 부분..

모듈식 레벨 레이아웃 아무것도 없는 빈 레벨을 생성했으므로, 저번에 다운받은 에셋을 이용하여 디자인했던 내용을 토대로 레벨을 만들어나가야 한다. 배치는 다방면에서 에셋의 배치를 체크하기 쉬운 4분할 화면으로 진행하게 된다. 배치를 할때는 그리드라는 기능을 이용할 수 있다. 그리드 기능은 현재 에셋을 움직이는 단위를 조정할 수 있는 기능이다. 만약 100으로 설정한다면, 에셋을 움직일때 100씩 움직이는 것을 확인할 수 있다. 먼저 던전의 입구를 시작할 간단한 안마당을 만들어주었다. 바닥 에셋으로 SM_Floor을 사용하였다. 그리고 해당 에셋을 아웃라이너에서 묶어 안마당이라는 폴더를 따로 작성하여 관리에 용이하도록 해준다. 해당 폴더 좌측 눈모양 표식을 누르면 해당 폴더의 에셋들이 전부 뷰포트에서 사라지..

모듈식 레벨 디자인 저번에 실행했던 레벨을 통해 좀 더 꼼꼼히 살펴보면서 어떤 빌딩 블록이 있는지 파악하고, 디자인을 시작하게 된다. 먼저 빌딩 블록들을 더 자세히 살펴보자. 현재 라이팅이 켜진 상태에서는 빌딩 블록을 자세히 파악하는데 어려움이 있어, 언릿 상태로 바꿔서 살펴보게 된다. 각각의 에셋들을 눌러보면, 모듈식으로 하나하나 조립하여 완성된 모습을 갖춘 것을 볼 수 있다. 그리고 이러한 에셋들의 메시가 어떤 것을 사용했는지 알고 싶다면, 해당 에셋을 누르고 디테일 탭의 스태틱 메시를 체크하여 확인이 가능하다. 또 해당 에셋의 화면을 4분할 하여 현재 화면 뿐만 아니라 해당 에셋에 대해 후면, 오른쪽, 상단의 시야로 확인이 가능하다. 현재 보고 있는 화면은 언릿 상태이지만, 나머지는 와이어프레임으로..

프로젝트 셋업하기 이번 섹션의 목표는 감옥같은 맵에서 숨겨진 지하 동굴을 지나 보물을 훔쳐내는 게임을 만드는 것이다. 숨겨진 지하동굴로 가는 길은 조각상을 특정 위치에 놓으면 열리게 된다. 보물의 경우 그냥 가져가면 보물 방의 문이 닫히게 되며, 대신 올려놓을 것이 필요하다. 이를 구현하기 위해 문을 움직일 Mover 컴포넌트, 조각상을 잡을 Grabber 컴포넌트, 위에 올라온 것을 확인해줄 Pressure plate 등이 필요하게 된며, 이번 섹션을 통해 하나씩 구현을 해나가게 된다. 먼저 이번 섹션을 위한 새로운 프로젝트를 셋업을 해주자. 이번 섹션을 위해 또 새로운 에셋을 다운받게 되며, 이번에 사용할 에셋은 Medieval Dungeon 에셋이다. 해당 에셋은 언리얼 5.3 버전을 지원하기 때문..
장애물 공격 - 마무리 이번 섹션을 통해 알아본 것은 다음과 같다. C++ 문법의 구조 (여러가지 문들과 표현식, 로켤 변수, if문과 같은 기본 항목) C++ 클래스 생성법 C++에서 블루프린트 자식 클래스 생성 멤버 변수와 멤버 함수 언리얼 내장 기능 (UPROPERTY, UE_LOG) 언리얼 타입 (FString, FVector, FRotator) 언리얼 클래스 (GameMOde, CHaracter Class) 이번 섹션을 통해 처음으로 언리얼과 C++을 연동하여 작성하는 법을 배웠다. C++의 경우 전체적으로 기본적인 기능과, 언리얼에 포함된 기능 및 타입 등을 이용해 보았다. 이를 통해 간단한 장애물 코스를 완성했으며, 우리가 이번 섹션을 통해 배운 것을 토대로 현재 섹션을 통해 만든 장애물 코..

레벨 디자인 및 다듬기 우리가 만든 각종 장애물 플랫폼을 이용하여 하나의 장애물 코스를 생각해보자. 처음에는 돌기둥을 이용해 위로 올라가고, 돌기둥을 통해 도착한 섬에서 푸셔를 피하고, 푸셔 다음에 위치한 회전 플랫폼을 통과하고, 추가적인 회전문 플랫폼을 피해 최종 목표 건물에 도착하는 것을 하나의 코스로 잡았다. 이러한 것을 레벨 디자인이라 하고, 자기만의 코스를 A4 용지 등에 정리하여 구상하고 난 이후에 언리얼에 직접 구현한다. 푸셔 코스를 통과하고 회전문 코스가 있는 섬으로 가기 위한 계단을 추가해주었는데, 계단이 너무 가파라서 올라가지 못할 수 있다. 해당 캐릭터의 디테일 패널을 보면 걸을 수 있는 바닥 각도를 조절하여 수정이 가능하다. 그리고 회전문을 추가해준다. 마찬가지로 우리가 만들었던 C..

FRotator 우리가 여태 만든 것은 상하좌우로 움직이는 플랫폼이다. 이번에는 회전하는 플랫폼을 추가해주기 위해 전에 틀만 만들었던 RotatePlatform 함수를 구현해준다. 구현 방법은 MovePlatform때와 매우 유사하다. 우선 GetActorRotation을 통해 현재 회전을 구해준다. 해당 함수를 보면 FRoataor 타입을 가지는 것을 알 수 있다. 따라서 헤더 파일에서 해당 타입으로 PlatformVelocity때와 같이 RotationVelocity을 선언해준다. 움직이는 경우와 회전하는 경우 이렇게 2가지가 생겼기에 기존 카테고리명 변경 및 추가를 해주었다. 이제 내부 구현도 거의 같다. 현재 회전에 화전값 * DeltaTime한 값을 더해주고 이를 세팅하게 된다. 현 상태로 컴파..

Const 멤버 함수 블루프린트에 순수함수가 있었던 것처럼, C++에도 유사한 기능으로 Const 함수가 존재한다. 순수함수는 실행핀의 필요성을 없애는 것이었지만, Const의 경우 해당 클래스의 상태를 수정할 수 없게 만든다. 우리가 전에 작성했던 ShouldPlatformReturn 함수의 경우를 살펴보자. 해당 함수안에 있는 MoveDistance 변수 같은 경우 수정할 필요도 없고, 해서도 안된다. 해당 함수는 MoveDistance의 값을 초기화하거나 변경하는 것이 아닌, 단순 체크용 함수이기 때문이다. 따라서 Const를 붙여주는 것이 좋다. Const의 경우 선언부와 구현부 위와 같이 붙여주어야 한다. 붙여주고 나면 GetDistanceMoved 함수에 오류가 발생한 것을 볼 수 있다. 이는..

반환문 저번 강의에 이어서 추가적으로 함수로 작성하면 좋아보이는 내용이 아직 남아있다. 이번에는 기존 if 문에서 DistanceMoved > MoveDistance 를 체크하는 부분과, DistanceMoved를 얻는 부분을 함수로 바꿔준다. 먼저 if 문의 경우 타입이 bool 이기 때문에 함수또한 bool 타입으로 선언해준다. 따라서 반환 타입이 없던 void 함수와 달리 해당 함수는 bool 타입을 반환하게 된다. 구현은 간단히 if 문에 있던 내용을 가져오면 된다. 대신 헤더 파일에 선언되어있는 MoveDistance와 달리 DistanceMove은 MovePlatform 함수에서 선언된 변수이기 때문에 다시 선언해줄 필요가 있다. 그러면 또 문제가 기존의 CurrentLocation또 추가적으..

멤버 함수 코드를 더욱 알아보기 쉽게 정리하기 위하여 우리가 직접 함수를 만들어 줄 수 있다. 이러한 함수는 헤더에서 선언하며, cpp에서 구현을 하게된다. 선언을 하기에 앞서서 헤더 파일을 보면 public:, protected: 이 적혀있는 것을 볼 수 있다. 이러한 것들을 접근지정자라고 하며, 해당 접근지정자 아래에 적힌 내용들이 접근할 수 있는 권한을 나타낸다. public은 어디서든 접근이 가능하고, protected는 현재 클래스에 대해 상속받는 클래스에 한해서 접근이 가능하다. 추가로 private: 또한 존재하며, 이 경우 현재 클래스에서만 접근이 가능하다. 우리가 만든 기능들은 현재 클래스에서만 필요한 기능이므로, private: 로 옮겨준다. 지금 추가로 만들 함수또한 마찬가지이다. 이..

FString 로그 메시지로 디버깅 하는 방법을 익혔지만, 이는 간단한 변수에 대해서만이다. 복잡한 문자열이나 벡터를 문자로 표현하는 법 등은 특별한 포맷 지정자가 존재하지 않아 어떻게 해야하는지 아직 알지 못한다. 이는 문자열로 표현이 가능하며, FString으로 선언한다. 문자열에 대한 포맷 지정자는 %s이다. 여기서 전과 다른 점이 하나 있는데, 바로 문자열 변수 앞에 *을 작성한 것이다. 이는 언리얼의 UE_LOG에서 인수를 인자로 받아들이지 못해서 생긴 문제이며, 이에 변환 연산자 *이 필요하다. *을 붙여주면 위와 같이 문자열이 출력되는 모습을 확인할 수 있다. 해당 문자열 변수에는 동적 타입도 할당이 가능하다. GetName() 함수를 통해 현재 액터에 대한 이름을 가져와 할당이 가능하다. ..

출력 로그에 기록하기 여태까지 강의를 진행하면서 오류가 발생하거나, 계산한 값들이 의도한바에 맞게 출력하는지 직접 체크하고 싶을 수 있다. 이런 게임 디버깅 체크용으로 출력 로그에 기록하는 방법을 사용할 수 있다. 만약 확장 프로그램인 Unreal Engine 4 Snippets를 설치했다면 Vscode에서 ulog만 쳐도 자동으로 아래와 같은 코드가 입력된다. 다음 코드를 보면 인수를 3개 받는데, 차례대로 로그 카테고리, 얼마나 시급한지를 나타내는 로그 수준, 출력 메시지이다. 이제 컴파일하고 언리얼로 돌아가 하단의 출력 로그를 살펴보자. 보면 우리가 작성한 로그가 5개가 출력된 것을 볼 수 있다. 이는 현재 MovingPlatform2.cpp에 대해 메시지를 표기하는 것인데, 해당 cpp에 대한 액..

GameMode 뷰포트에서 우클릭을 하면 여기에서 플레이라는 기능을 통하여 원하는 곳에서 플레이어를 스폰할 수 있다. 하지만 현 상태에서 게임 플레이를 누르면 캐릭터가 있는 위치에서만 플레이가 가능하다. 이는 언리얼에서는 우리가 어떤 캐릭터를 사용하고자 하는지 모르기 때문에 발생하는 문제이다. 이를 위해 게임모드 클래스를 사용하게 된다. 게임모드란 기본적으로 레벨에 들어가서 게임 규칙을 관리하는 액터이다. 누가 어디에 스폰해야 하는지, 플레이어에게 어떤 클래스를 아용하는지, 그 밖에 게임 작동 방식을 의미한다. 간단히 말해 특정 게임 또는 특정 경기의 규칙과 같다. 게임모드는 좌측 상단에서 설정할 수 있다. 프로젝트 세팅에 있는 GameMode 항목은 프로젝트 전체에 대한 설정으로 프로젝트에서 생성한 모..