이브 서비스 6년차의 MMORPG 프로젝트에서 대략 200개에 달하는 Data Table(근무 당시에는 테이블과 스크립트를 구분하지 않고 모두 스크립트로 부름)을 직접 관리하다보면, 보통은 새로운 데이터를 추가하는 작업이 주를 이루지만 시스템의 개편 또는 추가에 따라 기존 테이블의 컬럼을 추가/변경하거나 아예 새로운 테이블을 제작하는 경우도 적지않게 발생한다.

아예 새로운 테이블을 제작하면 오히려 큰 문제가 없겠지만, 라이브 서비스에서 대부분의 작업은 기존의 데이터를 가공해 재활용하는 방식을 채택하게 된다. 이 때 보다 효율적으로 테이블을 관리할 수 있는, 이미 알만한 사람들은 다 알고 있을 너무너무 기초적인 작은 팁 하나를 공유하려 한다.



예시를 들어보자!

샘플 테이블을 만들어 여러가지 상황들에 대한 처리 방법을 예시로 들어보자.

다른 기능의 아이템들은 배제하고, HP포션 타입의 기능만 존재하는 확장성 없는 아이템 테이블을 만든다고 가정해보면, 아마 아래와 같은 컬럼들로 구성될 수 있을 것이다. (아마 실무 경험이 조금이라도 있다면, 아래 예시가 얼마나 말도 안되는 구조인 지 알 수 있겠지만, 예시를 위한 극단적인 사례이니 넘어가도록 한다....)


[ 오직 물약만을 위한 아이템 테이블.xlsx ]


그리고 위 그림에 나타나는 컬럼들의 기능은 아래와 같이 설정할 수 있을 것이다.


- Index: 아이템의 고유 식별자. 다른 테이블에서 1번 아이템 코드를 입력하면, 위 문서 기준 4행의 데이터를 로드할 것이다. 보통 이 부분에 "//"를 입력해 주석처리하여 로드를 On/Off 할 수 있게 설계한다.

- Description(설명): 실제 데이터로 로드하지 않고 테이블 상에서만 존재하는 별도의 설명 컬럼. 없어도 무방하지만 없으면 나중에 원하는 데이터를 찾기 어려울 수 있으니 양이 많아질 것 같으면 사용하는 것도 좋다.

- Name(아이템명): 조직에 따라 별도의 스트링 테이블을 관리해 이 컬럼에 스트링  코드만 넣는 곳도 있고, 위 예시처럼 텍스트를 직접 추가하는 곳도 있다. 필자는 업무 시 별도의 스트링 테이블을 관리하는 방식을 사용한다.(해외버전 제작 시 번역이 용이)

- Tooptip(아이템설명): Name 컬럼과 같은 구조를 가지는 아이템 설명 툴팁에 출력할 텍스트 컬럼. 사실 이 부분도 %s, %n, {0}과 같은 각종 링크코드를 사용하는 편이 실제 작업에 유리하지만, 컬럼 활용 예제이므로 넘어가도록 한다.

- Icon(아이콘이미지): 인벤토리 등의 UI에 출력할 해당 아이템의 아이콘 이미지. 실제 리소스 명을 쓰거나, 별도로 관리하는 리스트에 치환된 코드를 사용하기도 한다.

- Recovery(HP회복량): 회복시킬 HP량을 입력하는 컬럼.

- MAXea(최대소지량): 해당 아이템을 인벤토리 한 칸에 최대 몇 개까지 소지할 수 있는지 설정하는 컬럼.


자, 샘플 테이블의 준비가 끝났다. 이 상태로 테이블 제작이 완료된 상태에서, 이제 다음과 같은 사례에 대처하는 방법을 알아보자.




요구사항 1. 우리 게임에는 HP 포션만 있는데, MP 포션도 추가해야 겠어요!

이 정도는 위 예제를 작성할 줄 아는 사람이라면, 누구나 손쉽게 처리할 수 있을 것이다. 바로, MP회복과 관련한 기능 컬럼을 한 줄 추가하는 것이다.


[ 이 정도야 우습지! 새 컬럼을 추가하면 돼! ]



요구사항 2. 이번엔 공격력 강화 물약을 만들어야 겠어요!

이번에는 조금 고민이 될 지도 모른다. 고민이 되지 않는다면, 아마 당신은 이 글을 읽는 시간이 아까운 우수한 경력질일 것이다. 자부심을 갖고 안심하고 이 페이지를 닫거나, 아니면 우월감에 사로잡혀 잠시 마음의 위안을 얻거나 당신이 좋을대로 해도 괜찮을 것이다.

일단 새로운 기능 타입이 추가됐으니, 새로운 컬럼을 추가하면 될 것 같다. MP회복량 뒤에 "ATKup(공격력증가)" 컬럼을 만들면... 안된다. 그것만으로는 부족하다. 그대로 설계하고 배포하게 된다면, 아마 당신의 설계한 공격력 증가 아이템은, 디아블로1의 "엘릭서"처럼 영구효과를 지닌 아이템이 될 것이다. 요구사항이 영구 증가 효과라면 상관 없지만, 아마 "공격력 강화 물약"이라고 말한 이면에는 "한시적 기간 동안 적용"이라는 조건이 생략되어 있을 것이다.

그럼 이번에는 공격력 증가량 컬럼과 함께, 지속시간을 설정하는 Period(지속시간) 컬럼을 추가해보자.


[ 조.. 조금 성가시지만 아직 괜찮아! ]



요구사항 3. 방어력 강화 물약도 필요하고, 이번엔 힘/민첩/체력/지능/정신력/운을 각각 증가시킬 수 있는 물약도 필요해졌어요!

대략 정신이 멍해지고 있지는 않은가. 자, 당신에게 시련이 찾아왔다. 앞서 말했다시피 타해법을 알고 있다면, 당신은 소중한 개발 시간을 무의미하게 허비하고 있는 연봉돚거의 반열에 오르고 있으니 어서 사장님에게 들키기 전에 조용히 페이지를 닫을 것을 권한다.

이번에도 위와 마찬가지로, 모든 요구사항들에 대한 개별적인 컬럼을 추가해보도록 한다.

물론 이 것으로도 가능은 하다. 안되는 것은 아니다. 다만 이 방법이 이후에 설명할 컬럼 활용 기법에 비해 얼마나 컬럼의 낭비가 심한 지 직접 눈으로 확인해보면 조금이나마 도움이 되지 않을까 싶어 삽질을 계속해보도록 한다.


[ 해.. 해냈어! 웬지 눈이 침침한 것 같지만 기분탓이겠지! ]



요구사항 4. 새로운 요구사항이 잔뜩 있어요! 이번에는 불/물/바람/대지/빛/암흑 속성별 공격력 증가 물약하고, 고정 수치 방식이었던 기존 방식 외에 모든 강화 효과들에 대해 비율 타입(10% 증가 등)을 추가해주세요!


"안해! 안해! 안한다고! 넣지마, 그런 패치!"


라고 외치고 싶어지겠지만 그럴 수 없는 당신은 두 눈을 부릅뜨고, 이를 악물고, 떨리는 손은 주먹을 꽉쥐고 진격하는 거인과 같은 힘찬 의지로 작업을 완수하게 되고, 아래와 같은 대략 정신이 아득해지는 결과물을 손에 넣게 될 것이다. (주먹을 쥐었는데 어떻게 작업이 가능한지는 묻지 않기로 한다.)


[ 이젠 한 눈에 볼 수 없는 지경에 이르른.xlsx ]




이제 해결 방안을 알아보자.

마지막 요구사항 4를 보다 간단하게 처리할 수 있는 해결 방안은 아래와 같이, "타입"이라는 설정을 활용하는 것이다.

먼저, HP회복량 컬럼 앞에 "OptionType(옵션타입)"이라는 컬럼을 넣고, 지속시간을 제외한 모든 추가 컬럼들을 삭제한다.


[ 짧다! 간결하다! 직관적이다(?)! 언빌리버블! ]


옵션 타입에서 기능별로 옵션을 정의해주도록 한다. 위 그림의 경우는 아래와 같은 옵션 넘버 정의를 갖도록 설계한 예시이다.

1:HP 회복 / 2: MP 회복

3: 공격력 증가 / 4: 방어력 증가

5: 힘 증가 / 6: 민첩 증가 / 7: 체력 증가 / 8: 지능 증가 / 9: 정신력 증가 / 10: 행운 증가

11: 불 속성 공격력 증가 / 12: 물 속성 공격력 증가 ... (후략)


그 다음 기존에는 HP의 회복만 담당하던 Recovery 컬럼을, 종합적인 능력치 컬럼으로 활용하면 된다.

바로 "OptionType"에 입력된 값에 따라 Recovery 컬럼의 내용이 의미하는 바를 서로 다르게 설정해주는 것이다.


OptionType이 1이면, Recovery는 HP 회복량으로 사용

OptionType이 2이면, Recovery는 MP 회복량으로 사용

... (후략)



다음에는 위와 같은 방법으로, 고정 수치 타입과 비율 타입 역시 별도의 타입 컬럼을 생성해 정의해주도록 한다.


[ 이 것으로 값 관련 컬럼이 절반으로 줄었다! ]


- ValueType이 0 이면, Recovery의 값은 고정 수치 타입으로 인식.

- ValueType이 1 이면, Recovery의 값은 비율 타입으로 인식.



정리.

간단한 데이터 테이블의 경우, 앞선 예시처럼 단순히 컬럼을 직접 추가하는 방법을 사용해도 아무런 문제가 되지 않는다.

하지만 위에서 가정한 사례와 같이 기하급수적으로 컬럼이 증식할 경우, 실제 테이블 작업자와 테이블을 로드할 프로그램 모두에게 부담이 되게 되니 가급적이면 타입 컬럼을 효과적으로 활용할 것을 적극 권장한다.



Data Table은 기획팀과 프로그램팀 간에 성립하는, 일종의 약속과도 같다.

정답은 없으니, 두 팀이 머리를 맞대고 효과적인 테이블 설계 방법을 논의해보면 분명 훨씬 멋지고 훌륭한 테이블을 유지할 수 있을 것이다.





VS



[ 당신의 선택은? ]




WRITTEN BY
zerasion
디자이너의 의도는 플레이어의 의미가 된다.

,

많은 개발팀에서 프로그램팀의 코딩 작업 없이 디자이너가 입력값들을 직접 제어할 수 있도록 스크립트Script나 데이터 테이블Data Table을 사용한다.

하지만 개발이 지속되다보면 너무 많은 양의 스크립트나 테이블들이 생산되게 되고 전체적인 작업 흐름을 쉽게 파악하기 위해 "구조도 또는 상관도"라고 불리는 간단한 도식을 만들어 사용하게 되는 경우가 있다.

최근에 작업한 Data Tabl은 새로 제작해야하는 테이블이 5개, 이미 만들어진 것과 연결해야하는 테이블이 5개, 도합 10개의 테이블이 서로 연결지어진 작업이었다. 따라서 작업에 앞서 팀원들에게 간단히 설명하기 위한 상관도를 그릴 필요성을 느끼게 되었다.

개인적인 작업 스타일이 실제 테이블 제작에 앞서 마인드맵(Ex. Freemind. 다운로드)으로 먼저 컬럼 리스트를 추려보는 편인데 마인드맵을 펼치다보니 왠지 서로 연결된 컬럼들을 선으로 이어 가시적으로 상관도를 표현하면 좋겠다는 생각이 떠올랐고, 직전 프로젝트에서 잠시 배웠던 언리얼 엔진Unreal Engine 3의 키즈멧Kismet 방식을 차용하면 어떨까 하는 생각이 머리를 스쳤다.


언리얼 엔진의 키즈멧은 디자이너가 직접 여러가지 소스들을 제어할 수 있도록 제공되는 인터페이스로 작업물은 아래 [그림 1.]과 같은 형식으로 나타난다.


[그림 1. 키즈멧의 간단한 예시]



[그림 2. 키즈멧의 다소 복잡한(?) 예시. 연습용으로 만들었던 AI Test 로직이라 흐름이 어렵지 않지만, 실제 개발된 게임들의 키즈멧은 몇백배는 더 복잡하게 만들어진 경우도 많이 볼 수 있다]


항목과 항목들을 드래그&드랍으로 간편하게 연결하면, 위 그림처럼 선으로 연결되어 각 항목간의 상관 관계를 직관적으로 알아볼 수 있다는 장점이 있다.

물론 키즈멧도 작업량이나 방식에 따라 알아보기 어려울 정도의 복잡한 그림과 선으로 표현되게 되는 경우가 많지만, 이번 상관도 작업은 10개의 테이블에 대한 흐름만 표현하면 됐기 때문에 큰 문제는 없을 것으로 판단되어 제작에 들어갔다.

아래는 완성된 상관도 그림이다.


[그림 3-1. Kismet Style로 작성한 Data Table 상관도]


[그림 3-2. 3-1에서 공통 부분인 String과 Graphic을 제거한 뒤 재배치한 모습]


공통적으로 거의 모든 테이블이 참조하게 되는 String(텍스트 테이블)과 Graphic Resource(이미지 테이블)는 주요한 흐름이 아니기 때문에 다른 색상의 가느다란 점선으로 표현해 시계를 가리지 않도록 구성하고, 메인이되는 녹색 박스들의 Monster부터 World까지의 흐름을 검은색 굵은 선으로 표현했다.

키즈멧의 특징인 입출력(Input/Output) 항목에 대한 표현을 활용해 박스의 왼쪽 면에 입력 컬럼을 표시해 어떤 칼럼이 어떤 테이블을 참조하는지 설명하는 것을 중점적으로 표현하려 노력했다.


[그림 4. 두달 전 작업물]


불과 두달 전에 만들었던 흐름도(위 [그림 4.])와 비교해 볼 때 확실히 어떤 부분이 서로 연관되는지 가시적으로 보인다는 점에서 그래도 절반은 성공했다는 생각이 들지만, 전체적인 배치마저 키즈멧의 아날로그적인 배치를 사용하다보니 시선의 흐름이 부자연스러워 진 점은 추후 개선이 필요한 것으로 보인다.



PS. 혹시라도 언리얼 키즈멧을 학습하고 싶은 분이 계시다면, 다음의 링크를 통해 학습하시기를 권장합니다.

키즈멧 관련 페이지: http://udn.epicgames.com/Three/KismetUserGuideKR.html



WRITTEN BY
zerasion
디자이너의 의도는 플레이어의 의미가 된다.

,