범프 매핑(Bump Mapping) 은 1978년 제임스 블린(James Bliin)이 고안한 그래픽 프로그래머들의 오래된 기법으로, 지오메트리를 추가하지 않고 셰이딩 계산 조절을 통해 범프 표면을 흉내냅니다. 셰이딩에 표면 노멀 대신 새 노멀을 사용합니다. 새 노멀은 펄린 노이즈, 회색조 텍스처 등의 1d 함수로 조절할 수 있습니다. 이 기법은 실루엣, 오클루전, 섀도 등 몇 가지 결점을 지닌 실제 디스플레이스먼트 매핑보다 훨씬 빠릅니다.
![]() |
![]() |
![]() |
---|---|---|
범프 매핑 없음 | 범프 매핑 있음 | 범프 & 노멀 매핑 있음 |
리얼타임 렌더링에서는 보통 노멀 매핑(Normal Mapping) 이라는 (푸르스름한 텍스처) 변형 범프 매핑을 사용합니다. 노멀 맵은 텍스처의 픽셀마다 색을 저장하는데, 이는 실제로 길이가 1인 3d 벡터입니다.
노멀 맵을 생성하는 방법은 두 가지입니다.
- 회색조 이미지에서 노멀 맵 생성 - 각 픽셀의 가로/세로 인접 픽셀과의 차이를 미리 계산합니다. 두 파생 결과 수치(도함수)를 단위에 맞게 노멀로 변환하여 색으로 저장합니다.
- 하이 폴리 3D 모델에서 노멀 굽기 - 텍스처의 각 픽셀을 하이 폴리 오브젝트의 3D 표면 위치와 연결하고, 컬러로 인코딩된 노멀을 저장합니다.
결과 텍스처를 회전된 방향에 상관없이 재사용하려면 노멀 벡터를 보통 노멀(Normal), 탄젠트(Tangent), 바이노멀(Binormal) 등 3개의 벡터로 이루어진 탄젠트 스페이스(Tangent Space) 에 저장해야 합니다. 이를 통해 표면이 향하는 방향을 정의합니다. 따라서 모든 노멀을 탄젠트 스페이스로 변환하여 노멀을 표면에 상대적으로 정의된 대로 재사용할 수 있습니다. 탄젠트 스페이스 매핑은 오브젝트의 UV 매핑에 따라 좌우됩니다. 텍스처의 x 방향과 y 방향이 탄젠트 스페이스가 가진 월드 스페이스상의 두 벡터, 즉 탄젠트와 바이노멀을 결정하기 때문입니다. 탄젠트 스페이스 부작용 없이 온전한 UV 매핑을 만드는 것은 어렵고 시간도 많이 걸립니다.
펄린 노이즈 같은 3d 회색조 함수를 사용하고자 한다면 어떨까요? 이 함수는 UV 매핑이 필요하지 않고, 근처 범프 표면의 디테일한 렌더링을 향상시킬 수 있습니다. 탄젠트 스페이스의 필요 없이 범프 매핑을 구현하면 이 방법을 사용할 수 있습니다.
ddx와 ddy
탄젠트 스페이스 없는 범프 매핑을 구현하기 위해서 머티리얼 에디터에 ddx 와 ddy 라는 두 개의 머티리얼 표현식을 머티리얼 에디터에 추가했습니다.
각 표현식은 입력한 내용의 도함수 근사치를 반환합니다.
그래픽 하드웨어에서는 두 픽셀을 셰이딩한 뒤, 그 결과를 뺄셈하여 도함수의 근사치를 계산합니다(ddx = 오른쪽 - 왼쪽
, ddy = 아래 - 위
).
이 함수들은 픽셀 셰이더에서만 사용할 수 있으며, 일반적으로는 머티리얼 함수에서 커다란 이펙트를 구현할 때만 유용합니다.
항목 | 설명 |
---|---|
입력 | |
값(Value) | 도함수를 계산할 값입니다. |
출력 | |
출력(Out) | 입력한 값의 도함수 근사치입니다. 타입은 입력한 값과 일치합니다. 예를 들어 스칼라 입력은 스칼라 출력으로, 2d 입력은 2d 출력으로 결과가 나옵니다. |
ddx와 ddy는 2x2 블록으로 계산되므로, 해상도가 높은 입력 사용 시 약간 각이 지는 부작용이 생길 수 있습니다.
범프 매핑 머티리얼 함수
탄젠트 스페이스 노멀 맵을 사용하지 않고 머티리얼에 범프 매핑을 구현할 수 있도록 여러 머티리얼 함수가 제공됩니다.
ComputeFilterWidth

ddx와 ddy 를 이용해 값이 화면에서 얼마나 빨리 변하는지 계산하는 함수입니다. 이를 통해 노이즈가 발생하기 시작하는 거리에서 프로시저럴 셰이더를 페이드 아웃할 수 있습니다. 페이드 아웃 덕분에 움직이는 동안 깜빡임 현상이 감소합니다. 굴곡진 표면에 반사할 때 심각한 에일리어싱 부작용이 나타날 수 있으므로
범프 매핑 시 잊지 말고 진행해야 합니다.
아래 예시 이미지는 절차적 생성 범프 매핑 함수가 먼 거리에서 페이드 아웃되는 모습을 보여줍니다.


항목 | 설명 |
---|---|
입력 | |
입력(In) | 필터 폭을 계산할 값입니다. |
출력 | |
결과(Result) | 픽셀에서 픽셀까지 입력이 변하는 속도입니다. |
PerturbNormalLQ
PerturbNormalLQ 는 회색조 범프 맵 입력을 월드 스페이스 노멀로 변환하는 함수입니다. 하지만 2x2 블록 부작용이 발생하는 ddx와 ddy 를 사용하기 때문에, 출력할 월드 스페이스 노멀의 퀄리티가 낮을 수 있습니다.


항목 | 설명 |
---|---|
입력 | |
범프(Bump) | 월드 스페이스 노멀을 계산할 스칼라 범프 값(회색조)입니다. |
출력 | |
월드 스페이스 노멀(WS Normal) | 계산된 월드 스페이스 노멀입니다. |
이 함수가 출력하는 월드 스페이스 노멀을 사용하려면 머티리얼 노드의 탄젠트 스페이스 노멀(Tangent Space Normal) 을 false 로 설정해야 합니다.
이 함수는 참고용일 뿐, 머티리얼 함수 라이브러리에 노출되어 있지 않습니다. PerturbNormalHQ 함수를 대신 사용하세요.
PerturbNormalHQ
PerturbNormalHQ 함수는 ddx, ddy보다 도함수를 더 정확히 계산하여 퀄리티가 높습니다. 3개의 샘플 위치를 사용해 스칼라 함수를 여러 번 계산하는 것이 비결입니다.
항목 | 설명 |
---|---|
입력 | |
한 픽셀 오른쪽 범프(Bump one pixel right) | 현재 위치에서 한 픽셀 오른쪽인 스칼라 범프 값(회색조)입니다. |
중앙 범프(Bump center) | 현재 위치에서의 스칼라 범프 값(회색조)입니다. |
한 픽셀 아래 범프(Bump one pixel down) | 현재 위치에서 한 픽셀 아래쪽인 스칼라 범프 값(회색조)입니다. |
월드 스페이스 노멀(WS Normal) | 선택사항입니다. 범프 맵과 합쳐지는 월드 스페이스 노멀입니다. Vector Transform 표현식을 사용하면 탄젠트 스페이스 노멀을 월드 스페이스 노멀로 변환할 수 있습니다. |
출력 | |
월드 스페이스 노멀(WS Normal) | 결합된 월드 스페이스 노멀입니다. |
이 함수 출력의 월드 스페이스 노멀을 사용하려면 머티리얼 노드의 탄젠트 스페이스 노멀(Tangent Space Normal) 을 false 로 설정해야 합니다.
PreparePerturbNormalHQ
PreparePerturbNormalHQ 함수는 PerturbNormalHQ 함수가 월드 스페이스 노멀을 계산할 때 필요한 3개의 샘플 위치를 계산합니다.
항목 | 설명 |
---|---|
입력 | |
값(Value) | 현재 위치에서의 스칼라 범프 값(회색조)입니다. |
출력 | |
한 픽셀 오른쪽 값(Value one pixel right) | 현재 위치에서 한 픽셀 오른쪽인 스칼라 범프 값(회색조)입니다. |
값(Value) | 현재 위치에서의 스칼라 범프 값(회색조)입니다. |
한 픽셀 아래 값(Value one pixel down) | 현재 위치에서 한 픽셀 아래쪽인 스칼라 범프 값(회색조)입니다. |
필터 너비(FilterWidth) | 원거리의 디테일을 페이드 아웃시키는 데 유용한 필터 폭도 계산합니다. |
함수 3개 대신 단일 함수 사용하기
범프 매핑 함수를 캡슐화하는 머티리얼 함수를 만들고, 다른 함수에서 값을 3번 계산할 수 있습니다. 해당 기능을 사용하면 복잡도가 어느 정도 감소합니다.
텍스처 사용하기
텍스처를 범프 매핑 머티리얼 함수와 함께 사용하면 퍼포먼스를 높일 수 있지만, 그래픽 카드의 텍스처 필터링 방식으로 인해 아티팩트가 발생할 수 있습니다. 정상적으로 필터링된 색은 선형 보간되며, 파생된 도함수는 상수입니다. 즉 회색조 텍스처를 사용하면 표면에 매끄럽게 보간 계산되지 않은 노멀이 발생할 수 있습니다.
참고
이 문서에서 설명한 방법은 모튼 S. 미켈슨(Morten S. Mikkelsen)의 작업에 기반한 것입니다(레퍼런스 참고).
퍼포먼스
프로시저럴 셰이더 사용 시 퍼포먼스 비용이 많이 발생할 수 있으며, (텍스처 매핑에 비해) 에일리어싱 없이 구현하기 힘듭니다. 에픽게임즈에서는 현재 펄린 노이즈를 제공합니다. 해당 머티리얼 표현식을 최적화할 수는 있지만 많은 연산 비용이 듭니다. n 개의 레벨에 레벨 기능을 사용하려면 대부분의 연산을 n 번 수행해야 합니다. 게다가 범프 매핑으로 함수의 값을 3번 평가할 경우 비용은 더욱 증가합니다. 픽셀 수에 따라 비용이 달라진다는 점에 유의하십시오. 이 모든 기능을 활용할 수는 있지만, 프로토타입이나 통제된 상황에서만 사용하시기 바랍니다.
문제점
- 아직 플립/미러링된 UV를 제대로 처리할 수 없습니다.
앞으로의 작업
이 방법으로 명시적 저장된 탄젠트 스페이스를 대체할 수 있습니다. 이 분야를 발전시키려면 더 많은 경험을 쌓아야 합니다. 아티스트들은 지금까지 마련된 구현을 범프 매핑에 이용할 뿐만 아니라 연구 수단으로 활용할 수도 있습니다.
레퍼런스
-
GPU 상에서 파라미터화되지 않은 표면 범프 매핑 (Morten S. Mikkelsen)
-
파생형 맵 (Mikkelsen and 3D Graphics blog)