융합 미디어아트 디렉터 & 에듀케이터
김 상 준 지음
현장의 노하우를 담은 실무 밀착형 가이드
FROM LOGIC TO ART
Sang Jun Kim
지난 10여 년간 국내 정상급 포스트 프로덕션과 미디어 그룹을 거치며, 한국 CG 및 VFX 업계의 최전선에서 밀도 높은 실무 경험을 축적해 왔습니다. 글로벌 표준으로 사용되는 하이엔드 소프트웨어들을 깊이 있게 다루며, 머릿속의 상상을 스크린 위의 현실로 완벽히 구현해 내는 기술적 기반을 다졌습니다.
그러나 고도화된 기술적 성취가 곧 작업의 완성을 보장하지는 않음을 현장에서 체감했습니다. 단순한 기술적 오퍼레이터를 넘어 기획력과 예술적 철학을 갖춘 크리에이티브 디렉터로 도약하고자, 시각 예술의 본질과 미디어 융합에 대한 학문적 연구를 거듭해 왔습니다.
이러한 탐구는 저의 CG 기술을 '미디어아트(Media Art)'라는 새로운 공간적 캔버스로 이끌었습니다. 후디니(Houdini)의 절차적 알고리즘과 거대한 데이터 통제력은 단순한 영화 효과를 넘어, 제너레이티브 비주얼을 구현하는 미디어아트의 핵심 동력이 됩니다. 세종문화회관 정면에 선보인 미디어 파사드 '천지창조'부터 재즈와 영상의 인터랙션을 시도한 'Cinema in Jazz'에 이르기까지, 장르를 넘나드는 융합 예술 시도를 통해 기술과 예술의 접점을 증명해 왔습니다.
현재는 경희대학교와 청강문화산업대학교에서 현장의 생생한 노하우를 후학들에게 전수하며, 문제 해결을 위한 논리적 사고와 융합적 시각을 지닌 차세대 미디어 크리에이터들을 양성하는 데 열정을 쏟고 있습니다.
3D 그래픽스, 특히 후디니(Houdini)를 배운다는 것은 단순히 툴의 버튼 위치를 외우는 과정이 아닙니다. 컴퓨터의 언어로 사물의 형태와 움직임을 수학적, 절차적으로 통제하는 '파이프라인 설계자(Technical Director)'가 되는 과정입니다.
방대한 후디니의 세계는 데이터의 뼈대를 논리적으로 설계하는 <3D FX Ⅰ : 프로시저럴 모델링>과, 그 위에 물리적 생명력을 불어넣는 <3D FX Ⅱ : 다이내믹스> 두 과정으로 나뉩니다.
본 교재(Vol. 2.1)는 다이내믹스 여정의 첫걸음으로서, 화려한 시각적 폭발 이전에 '왜 이 솔버를 써야 하는가?', '물리적 속성이 변했을 때 시스템이 어떻게 유기적으로 대응하는가?'와 같은 시뮬레이션의 본질적인 논리에 집중했습니다.
이 책을 통해 어떠한 클라이언트의 요구 상황에서도 능동적으로 시스템을 통제할 수 있는 진정한 전문가로 성장하기를 바랍니다.
Chapter 01. Rigid Body Dynamics (RBD) 기초와 Bullet Solver
건물이 폭발하며 수천, 수만 개의 파편이 쏟아지는 장면. 과거에는 이런 장면을 연출하기 위해 모든 면(Polygon)의 충돌을 하나하나 계산해야 했기에 슈퍼컴퓨터가 몇 날 며칠을 계산해야 했습니다. 감당할 수 없을 만큼 무거웠죠. 하지만 Bullet 물리 엔진이 도입되면서 상황이 완전히 달라졌습니다. 현대의 거대한 파괴 FX는 100% 이 Bullet Solver를 기반으로 작업합니다. 이번 챕터에서는 볼링 핀 쓰러뜨리기 실습을 통해 RBD의 기초부터 완벽히 다져보겠습니다.
에르빈 쿠만스
(Erwin Coumans)가 개발한 Bullet Physics Library는 GTA, 레드 데드 리뎀션 같은 AAA급 게임과 디즈니, 마블 영화 등에서 널리 쓰이는 세계 최고 수준의 오픈소스 물리 엔진입니다.
후디니가 과거에 자체 개발했던 기존 RBD Solver보다 압도적으로 가볍고 빠르기 때문에, 최신 버전의 후디니에서는 사실상 Rigid Body 연산의 100%를 이 Bullet 엔진이 담당하고 있습니다.
SOP (Surface Operator): 점, 선, 면을 다루고 모양을 만드는 밖의 공간입니다.
DOP
(Dynamics Operator): 만들어진 물체에 중력, 바람, 충돌 등 물리 법칙을 계산하는 가상의 시뮬레이션 공간입니다.
다이내믹스(DOP)로 넘어가기 전, 밖(SOP)에서 오브젝트들을 먼저 세팅해야 합니다. 일일이 볼링 핀을 모델링 하기는 번거로우니 기본 도형을 이용해 세팅해 봅시다.
Tube를 생성합니다. 파라미터에서 Height를 5로 수정하고 End Caps를 체크하여 닫아줍니다.Grid를 생성합니다. 파라미터에서 Rows와 Columns를 각각 5로 맞춥니다.Copy to Points 노드를 생성하여 왼쪽 입력에 Tube, 오른쪽 입력에 Grid를 연결합니다.
튜브와 그리드를 이용해 25개의 핀을 배열한 모습
볼링핀과 공을 SOP 단계에서 하나의 Merge로 합쳐버리면 DOP 안에서 각각 다른 속도나 무게를 주기가 매우 까다로워집니다.
가만히 서 있을 핀과 빠른 속도로 날아갈 공처럼 움직임이나 성질이 다른 그룹은 끝까지 트리를 분리해 두는 것이 정석입니다.
Sphere 노드를 새롭게 생성하고 Primitive Type을 Polygon Mesh로 변경합니다.
타격을 위해 대기 중인 볼링공(Sphere)의 X, Y 좌표 이동
Bullet 시뮬레이션을 가볍게 돌리기 위한 첫 번째 절대 규칙은 '모든 물체를 Point 단위로 패킹해야 한다'는 것입니다. 누락하면 수많은 면을 다 계산하느라 시스템이 다운될 수 있습니다.
1. 피봇 중심 맞추기: Copy to Points 아래에 Transform 노드를 답니다. 핀들이 바닥(Y=0)을 파고들어 있으므로 Translate Y 값을 2.5로 올려 바닥 위에 온전히 서 있게 만듭니다.
2. 핀 패킹하기: Transform 노드 아래에 Assemble 노드를 연결합니다.
다이내믹스 공간 안에서는 파편들이 수없이 충돌합니다. 이때 후디니의 솔버가 "방금 부딪힌 게 15번 핀인지, 23번 핀인지" 정확히 구별하려면 반드시 이름표(Name)를 달아주어야 합니다.
Assemble 노드의 Output Prefix를 설정하면 pin_0, pin_1 형태로 컴퓨터가 알아볼 수 있는 고유한 이름표를 달아줍니다.
1. 공 패킹하기: Sphere 노드 아래에도 동일하게 Assemble을 달고 옵션 체크 후, Output Prefix 칸에는 ball이라고 입력합니다.
2. Null 노드로 정리: 두 그룹 끝에 각각 Null 노드를 달아줍니다. 이름을 OUT_pins, OUT_ball로 변경하여 다이내믹스에서 불러오기 쉽게 정리합니다.
각각 Null 노드(OUT_pins, OUT_ball)로 마무리한 SOP 최종 트리
지오메트리 패킹이 끝났다면, 드디어 물리 연산을 수행할 가상 공간인 DOP(Dynamics Operator) 네트워크를 구축할 차례입니다.
DOP Network를 생성한 뒤 안으로 들어갑니다.Rigid Body Solver 노드를 생성합니다. (파라미터 창을 보면 Solver Engine이 기본적으로 'Bullet'으로 되어 있습니다.)Gravity Force 노드를 연결하여 중력을 적용합니다.데이터 변화를 주지 않지만, "이 지점이 작업이 완료된 출력 지점이다"라는 것을 알려주는 이정표 역할을 합니다. 다른 네트워크에서 경로를 찾을 때 오류를 방지해줍니다.
패킹된(Packed) 물체들을 DOP 안으로 가져올 때는 일반 Object 노드가 아니라 반드시 RBD Packed Object 노드를 사용해야 합니다.
RBD Packed Object 노드를 2개 생성하고 이름을 각각 pins와 ball로 변경합니다.OUT_pins Null 노드를 찾아 Accept를 누릅니다.OUT_ball 경로를 연결해 줍니다.Merge 노드를 만들어 pins와 ball을 하나로 묶어줍니다.Rigid Body Solver의 첫 번째 입력(Input 1: Objects)에 연결합니다.
Object -> Merge -> Solver -> Gravity로 이어지는 DOP 기본 트리
여러 개의 오브젝트를 DOP 공간에서 동시에 시뮬레이션하려면 반드시 Merge 노드로 하나로 묶어주어야 합니다.
그리고 이렇게 묶인 데이터 뭉치는 항상 Solver의 첫 번째 입력 단자(Input 1: Objects)로 들어가야 정상적으로 연산됩니다.
현재 타임라인 하단의 재생(Play) 버튼을 누르면 핀과 공이 허공에서 중력을 받아 끝없이 추락합니다. 물리 연산이 일어날 무한한 바닥을 만들어 주어야 합니다.
Ground Plane 노드를 생성합니다. (렌더링되지 않는 물리적 바닥)Merge 노드(merge2)를 생성합니다.Gravity Force 위쪽에 꽂아줍니다.
Ground Plane이 반드시 Merge 노드의 가장 왼쪽 핀에 연결되어야 합니다!
세팅을 바꾸었는데도 화면에서 물체들이 공중에 멈춰 있거나 변화가 없다면 시뮬레이션 캐시(임시 연산 결과)가 꼬인 것입니다.
DOP Network 노드 파라미터 창에서 [Reset Simulation] 버튼을 누른 뒤, 타임라인에서 Ctrl + ↑ 를 눌러 1프레임으로 되돌리고 다시 재생하세요. 하단의 파란색 바가 다시 계산되며 정상 작동합니다.
DOP의 Merge 노드는 '왼쪽 인풋이 오른쪽 인풋에 영향을 준다'는 원칙을 갖습니다.
바닥이 물체에 물리적 영향을 주어 떨어지지 않게 막아야 하므로, Merge 노드 입력 핀의 가장 왼쪽이 Ground Plane, 오른쪽이 Solver 연결선이 되도록 순서를 맞추어야 정상적으로 충돌합니다.
* 노드를 선택하고 Shift + R 을 누르면 좌우 선이 교차 정렬됩니다.
이제 공이 움직여서 핀을 타격해야 합니다. DOP 안의 ball 노드 파라미터에서 Initial State 탭을 열어 Velocity 수치를 직접 줘도 움직이긴 합니다. 하지만 실무에서는 대부분 이렇게 하지 않습니다.
Step A: 밖에서 속도(v) 코딩하기
Assemble 노드와 OUT_ball Null 노드 사이에 Point Wrangle을 생성해 달아줍니다.Step B: DOP에서 속도 상속받기 (Inherit)
ball 오브젝트 노드를 선택하고 Initial State 탭을 엽니다.
10의 속도로 날아가 핀을 타격하는 공 (재생 화면)
🤔 왜 밖(SOP)에서 속도를 세팅할까요?
DOP 안에서 Velocity를 주면 매 프레임마다 그 힘이 강제로 들어가는 비현실적인 결과가 나옵니다.
물리학적으로 '초기 투척 속도'를 정해주고 공기 저항에 의해 서서히 멈추는 리얼한 연산을 위해서는, 밖에서 1회성 속도 데이터를 만든 뒤 DOP으로 들고 들어오는 것이 정석입니다.
속력(Speed)은 방향 없이 크기만 가진 스칼라(Scalar) 값입니다. (예: 시속 5km)
반면 후디니에서 쓰는 속도(Velocity, @v)는 '어느 방향으로 얼마만큼 가는지' 방향과 크기를 모두 포함하는 벡터(Vector) 값입니다. 그래서 x, y, z 세 개의 축에 대해 수치를 입력할 수 있습니다.
만약 터진 파편들이 한 방향이 아니라 폭죽처럼 사방으로 튀게 하려면 어떻게 할까요? 각 핀들에게 랜덤한 Velocity를 주면 됩니다. 이럴 땐 코딩(Wrangle)보다 노드 기반인 VOP을 쓰는 것이 직관적입니다.
pins 그룹의 Assemble 노드 아래에 Point VOP을 생성하고 안으로 들어갑니다.Anti-Aliased Noise 노드와 Add 노드를 생성합니다.Add 노드에 연결하고, 최종 결과를 Global 노드의 v 핀으로 내보냅니다.
P(위치)를 기준으로 노이즈를 생성해 V(속도)에 더해주는 VOP 네트워크
노이즈 노드를 클릭하고 파라미터 창에서 Amplitude(진폭) 수치를 높이면 폭발하는 힘(속도)이 훨씬 강해져 파편들이 사방으로 멀리 튕겨 나가는 것을 확인할 수 있습니다.
공이 핀에 부딪혔는데 핀이 무거워 공이 튕겨 나간다면 어떻게 할까요? 실제 세계처럼 물체의 밀도(무게), 마찰력, 탄성을 조절해야 리얼한 시뮬레이션이 나옵니다. DOP 안의 RBD Packed Object 노드에서 Physical 탭을 열어 조절합니다.
| Physical 속성 | 역할 및 실습 적용 |
|---|---|
| Density | 밀도(무게). 공의 수치를 1000에서 10000으로 대폭 올리면 묵직하게 핀을 쓸고 지나갑니다. |
| Rotational Stiffness | 회전하려는 힘에 저항하는 정도. 수치가 낮을수록 물체가 공중에서 더 쉽게 팽이처럼 빙글빙글 돕니다. |
| Bounce | 탄성. 바닥(Ground)과 공, 핀의 Bounce 수치를 모두 1로 올리면 파편들이 통통 튀어 다닙니다. |
| Friction | 마찰력. 당구대 바닥이나 빙판처럼 미끄럽게 하려면 이 수치를 낮춥니다. |
복잡한 3D 모델(예: 뿔이 달린 드래곤)에 비닐 랩을 씌우고 팽팽하게 당겼을 때 나오는 단순화된 형태를 말합니다. 오목하게 파인 부분은 무시하고 볼록한 윤곽선만 연결하기 때문에 충돌 연산량이 기하급수적으로 줄어듭니다.
Bullet 엔진이 수만 개의 파편을 실시간에 가깝게 계산하는 비결은, 복잡한 모델링 모양 그대로 충돌 연산을 하지 않기 때문입니다. 물체를 단순화된 투명 비닐 랩으로 감싸서(Convex Hull) 계산을 극도로 가볍게 만듭니다.
파란색 가이드 라인(Convex Hull)이 실제 충돌을 담당하는 최적화된 영역입니다.
오늘 배운 RBD와 Bullet Solver의 모든 원리를 활용하여 당구(4구) 시뮬레이션을 만들어 봅니다. 이 과제를 통해 Density, Friction, Bounce 등 물리 속성을 능수능란하게 다루는 감각을 익혀보세요.
RBD Packed Object를 생성합니다. 이때 바닥은 움직이면 안 되므로 Initial Object Type을 Create Static Objects로 변경해야 합니다.
Point Wrangle을 이용해 '수구(흰 공)'에만 Velocity를 주어 3쿠션을 치도록 각도와 물리 수치(Bounce, Friction)를 세밀하게 조절해 보세요.