드디어 Reverie 의 충돌 시스템이 완성되었다!
Reverie 퍼즐들의 핵심은 모두 이 충돌 시스템을 기반으로 한다.
물론 개발 과정에서 변할 여지가 없는 것은 아니지만, 여기에 간단하게 그 규칙들을 정리해 본다.
Reverie 시스템 의 기본 개요
Reverie 충돌 시스템의 가장 큰 특징은 빈 공간을 일반 물건처럼 다룰 수 있다는 점이다.


위 그림은 빈 공간 (=흰색 물체)를 밀어 원래는 막혀 있던 길을 열어 주는 모습이다.
그런데 간단해 보이는 컨셉과는 달리, 이 충돌 시스템 아래에서 어떤 식으로 동작해야 할 지 판단하기가 애매한 경우가 생각보다 많이 발생한다.
그래서 이러한 상황을 위한 규칙들이 필요하다고 생각했고, 상당히 고민한 끝에 고안해 낸 3가지 규칙을 여기에 정리해 보았다.
용어들의 정의
규칙을 설명하기 전, 규칙에서 사용되는 용어 3개에 대한 소개가 필요할 것 같아 여기서 설명한다.
몰라도 대략은 이해 가능하니 귀찮은 사람은 넘겨도 된다.
1. 물체의 높이
이 게임은 2차원 게임이어서 물체의 충돌을 설명하는 데에는 x, y로만 충분할 것 같지만, Reverie 에서는 물체의 z좌표 또한 충돌 판단에 중요하게 사용한다.
물체의 z좌표란 2차원상에서 한 위치에 겹쳐 있는 여러 개의 물체 중, 어떤 물체가 더 위에 보여야 하는지를 나타내는 값이다.

이제부터 A 물체가 B 물체보다 '높다' 라고 말하는 것은, A의 z좌표가 B의 z좌표보다 높다는 것을 의미한다.
2. 판단 가능한 높이 차이
z 값에 대한 정보 없이, 게임 화면만 보고도 A가 B보다 z가 높다는 것을 알 수 있다면, A 가 B 보다 '판단 가능하게 높다' 라고 표현하고, A << B 라고 줄여서 적기로 하자.
정의가 약간 애매할 수도 있는데, 예시 후 아래에서 더 자세히 설명한다.


왼쪽 예시의 경우 화면만 봐도 A << B 이고, B << C 임을 알 수 있다.
이로부터 A << C 라는 것도 추론할 수 있다. (A 와 C가 겹치지는 않더라도)
오른쪽 예시의 경우 A << B 이고 C << B 지만, A 와 C의 관계는 추론해낼 수 없다.
이런 식으로 판단 가능한 높이차가 없는 것은 A ? C 라고 줄여서 적기로 하자.
* 사실 화면만 보고도 A 가 B 보다 높은지 알 수 있으면 A << B 라는 것은 완전히 엄밀하지는 않다.
엄밀한 정의는 다음과 같다.
- A 와 B의 충돌박스가 겹치고 'A의 z' > 'B의 z' 라면 A >> B 이다.
- A 와 C의 충돌박스가 겹치지 않더라도, A << B 이고 B << C 라면 A << C 이다.
- 1과 2를 통해 A와 B의 관계를 추론할 수 없다면 A ? B 이다.
3. 직접적 높음
A가 B보다 '바로 위' 인지를 나타내는 단어이다.
A >> B 이고 A >> X >> B 를 만족하는 X 가 존재하지 않는다면 A 는 B 보다 직접적으로 높다.

규칙
그럼 이제 규칙을 설명할 수 있다.
규칙 1: 게임 내의 모든 곳은 검정 / 흰색이 번갈아 가며 쌓여 있어야 한다.
그리고 이러한 상태를 '유효한 상태' 라고 하자.

예를 들어 왼쪽은 검정과 흰색이 번갈아 가며 올바르게 쌓여 있다.
그러나 오른쪽은 A 지역이 '검정', '흰색', '흰색' 이렇게 쌓여 있으며, 흰색이 연속해 2번 나오므로 이 상태는 유효한 상태가 아니다.
매우 당연해 보이는 말이지만, 생각보다 헷갈리는 상황을 잘 잡아 준다. 아래는 그 예시이다.


위와 같이 검정색 물체가 2개 있다가 중간에 위에 흰 물체 하나를 놓은 상황을 생각해 보자.
이때 A를 오른쪽으로 밀어도 유효한 상태일까?
얼핏 보기에는 A 의 오른쪽이 흰색이기 때문에 밀어도 유효할 것 같다.
그러나 자세히 생각해 보면, A물체는 현재 흰색 물체의 아래에 있는 상황이다.
이 상황에서 A를 밀면 눈에는 안 보이겠지만 흰색 물체 뒤에서 검정 물체 2개가 겹치게 된다.
따라서 '검정', '검정', '흰색' 으로 쌓이게 되며, 이는 유효하지 않은 상태이다.
규칙 2: 어떤 물체 A는 다음 조건이 만족되는 경우에 밀 수 있다:
조건) A를 포함한 어떤 물체들의 집합 S가 있고, S 의 모든 물체들을 민 후의 상태는 유효한 상태이다.
위 조건을 만족하여 A를 밀면, S 의 모든 물체도 같이 밀린다.

위의 단순한 예시를 보자.
A와 B가 붙어 있을 때, { A } 만 밀면 A와 B가 겹쳐서 유효하지 않은 상태가 된다.
하지만 { A, B } 를 밀면 유효한 상태가 되며, 따라서 A는 밀 수 있다고 판단한다.
이 규칙은 아래와 같은 상황에서 밀 수 있는지 판단할 때 유용하게 사용할 수 있다.

A를 오른쪽으로 당기는 상황을 생각해 보자.
이때 A 만 오른쪽으로 이동시킨다면 C 가 배경에 닿으면서 유효하지 않은 상태가 된다.
그러나 { A, B } 를 이동시킨다면 유효하다. 따라서 A를 오른쪽으로 당기면, { A, B } 가 이동하게 된다.
* 그런데, 여기서 미는 과정을 통해 기존엔 안 만나던 두 물체가 만나게 된다면 어떻게 될까?
즉 A ? B 이던 물체가 미는 과정을 통해서 만나는 경우이다.

예를 들어 위 상황에서 A를 밀면 당연히 C 위로 올라갈 것이라고 생각할 것이다.
그러나 현실은 A ? C 이기 때문에 A는 어디로 갈 지 알 수 없다.
z를 조절해 주지 않는다면 B보다도 아래 위치할 것이고 (작은 숫자가 z 좌표값),
그럼 억울하게 유효하지 않다는 판정을 받게 된다.
따라서 아래 규칙을 추가한다.
규칙 2.1: 옮기는 과정에서 유효한 상태를 만들기 위해 물체들의 z 좌표를 조절할 수 있다.
단, 새로운 z 를 적용해도 기존의 '판단 가능한 높이 관계' 는 모두 유지되어야 한다.
(마지막 문장은 위 그림에서 엉뚱하게 갑자기 B << C 라는 관계가 끊어지거나 할 수 없다는 의미이다)
마지막으로 사소한 한 가지 규칙이 더 있는데, 가능하면 불필요하게 많은 물체를 밀지 않는다.
좀 더 엄밀한 설명:
유효한 S가 여러 가지일 때, 어떤 S를 선택해야 하는지가 문제가 될 수 있다.
이때, 다음과 같은 선택 기준이 있다:
유효한 S 인 S1, S2 에 대하여, S1 ⊂ S2 라면 S2 는 채택하지 않는다.
* 이때, S1, S2 는 규칙 3에 의해서도 제약을 받음에도 유의하여야 한다.
* 이 제약 하에도 유효한 S가 여럿 있을 수 있는데, 이러면 규칙상으로는 어떤 것이 채택되어도 괜찮다.
3번 규칙. (2번 규칙에의 제약)
이 규칙을 설명하기 전에 한 가지 단어를 추가해야 한다.
'덩어리'란:
모든 하얀 물체를, 자신과 직접적으로 위에 있는 물체들과 연결하자.
이때 서로 연결된 모든 물체를 '덩어리' 라 한다.

규칙 3: 2 번 규칙에서 '덩어리' 에 포함된 검정 물체를 밀려 한다면, 덩어리의 다른 모든 물체도 같이 밀어야 한다.
짧게 말하면, '검정 물체가 움직이면 그 물체에 직접 닿아 있는 하얀 물체는 상대 위치가 고정된다' 로 이해하면 된다.
이 규칙은 없다고 해서 모순이 발생하는 것은 아니지만, 없는 경우 미는 과정에서 물체들이 분리되어서 불편하고, 직관적으로 민 후의 모습이 잘 상상이 가지 않는 경우가 많아 추가하였다.
엄밀한 설명:
검정 물체 A 에 대해 다음과 같은 집합 2개를 정의하자.
H = { x | x 는 A 보다 직접적으로 높음 }
L = { y | 어떤 x ∈ H 에 대해, y 는 x 보다 직접적으로 낮음 }
규칙 3: 2번 규칙의 S에 검정 물체 A 가 포함된다면,
H 의 모든 원소와 L 의 모든 원소 또한 S 에 포함되어야 한다.
위 3가지 규칙만 있어도, 물체의 배치가 있을 때 왠만한 경우엔 밀면 어떤 물체들이 어떻게 밀려야 하는지 판단이 가능하다!
해당 규칙을 코드로 구현하기 위해 상당히 노력을 많이 했다.
규칙에서의 원리를 그대로 코드로 똑같이 구현하면 성능이 너무 떨어지기 때문에, 규칙에서 제시한 계산 방식은 원리에 불과하고 실제로는 약간 다른 접근 방식을 택했다.
현재까지는 코드가 규칙과 같은 결과를 내고 있는데, 충분히 복잡한 상황에서는 코드의 결과와 규칙의 결과가 달라질 가능성도 있을 것 같다.
- 생각보다 포스트가 길어 실제 게임플레이 영상은 다음 포스트에 추가하려고 한다.
'유니티 게임 개발 일지' 카테고리의 다른 글
| [일지 / 그래픽] 5. 레버리 3번째 컨셉 아트 (도시) (0) | 2022.01.29 |
|---|---|
| [일지 / 개발] 4. Reverie 에 Undo 시스템 추가 (0) | 2022.01.15 |
| [일지 / 그래픽] 3. 레버리 2번째 컨셉 아트 (정글) (0) | 2021.08.27 |
| [일지 / 공부] 1. 빠른 충돌체크를 찾아서 (0) | 2021.08.17 |
| [게임 개발 일지] 0. 과거 Reverie 의 모습 / 앞으로의 계획 (0) | 2021.08.17 |