역자의 말.
일본 쪽에서도 거의 대부분 유니티를 사용해서 툰 렌더링을 주로 처리 했었는데요... 간만에 언리얼 엔진을 사용한 툰 렌더링 소개 기사가 올라왔네요. 같이 한번 살펴 보고자 간단히 기사를 번안해 봤습니다.
원문
안녕하세요.
주식회사 스파크크리에이티브의 클라이언트 엔지니어 나카지마입니다.
2회에서는 지난 내용을 바탕으로 셀 셰이딩에서 사용되는 다양한 표현을 UE에서 실제로 만들어 보도록 하겠습니다.
이번에 소개하는 3가지 표현
이번에는 이 세 가지 표현에 대해 정리해 보겠습니다.
개요
천사의 고리(헤어 링)
노멀 전이
익숙한 표현도 있고 생소한 표현도 있지만, 모두 셀 셰이딩을 더욱 멋지게 표현하는 데 중요한 표현이라고 생각합니다.
アウトライン
아웃라인 표현은 노멀 반전된 메쉬를 이용합니다. 따라서 동일한 모델의 메쉬를 복제하여 노멀 반전시킬 수 있는 메쉬를 준비해야 합니다.
이번에는 UE 내에서 메시 복제를 진행하지만, 모델 데이터에 아웃라인용 메시를 미리 준비해 두어도 무방합니다. 메시 복제는 레벨에 배치한 모델을 선택하고 디테일 탭에서 SkeletalMeshComponent를 우클릭하여 [복제]를 선택하면 됩니다.
이름은 알기 쉽게 SkeletalMeshComponent_Outline으로 정했습니다. 이것으로 사전 준비가 완료되었습니다.
메시 복제가 완료되면, 노멀 반전 처리를 할 아웃라인용 머티리얼을 생성합니다.
먼저 머티리얼의 디테일 패널을 아래 그림과 같이 변경합니다.
주요 변경 사항은 Blend Mode, Shading Model, Two Sided 세 가지입니다.
Two Sided는 양면 그리기 설정 항목입니다. 보통은 메시의 표면만 그려지지만, Two Sided를 ON으로 설정하면 뒷면도 그려집니다. 확인용 한쪽 면을 제거한 박스 메쉬에서 Two Sided 유무에 따른 차이를 확인하면 다음과 같습니다.
Two Sided를 ON으로 설정하여 뒷면이 그려지게 되었고, 상자 안쪽이 그려진 것을 확인할 수 있습니다.
뒷면이 그려진 것을 확인했다면, TwoSidedSign 노드를 이용하여 뒷면을 가져옵니다.
TwoSidedSign 값이 1이면 메시의 표면이면 1, 뒷면이면 -1을 반환하는 노드입니다. TwoSidedSign 값이 1이면 빨간색, -1이면 파란색이 되는 머티리얼을 확인용 박스 메시에 적용하고 그리기 결과를 확인합니다.
Two Sided를 ON으로 설정하여 그려진 뒷면은 파란색으로, 표면은 빨간색으로 바뀌었습니다.
노멀 반전에서는 뒷면만 그리는 상태로 만들어야 합니다. 이 박스 메시의 경우, 파란색 부분만 그려지는 상태가 되어야 한다는 뜻입니다.
여기서 Blend Mode를 Masked로 설정한 것이 활용되는데, Masked로 설정하면 오파시티 마스크의 핀이 활성화됩니다. 오파시티 마스크는 Opacity Mask Clip Value에 설정된 값보다 작은 값이 입력되면 드로잉을 하지 않습니다.
Opacity Mask Clip Value는 머티리얼의 디테일 패널에서 확인할 수 있으며, 기본값은 0.3333입니다.
여기에 TwoSidedSign 노드에 -1을 곱한 값을 입력하면 표면은 -1, 뒷면은 1이 되므로 뒷면만 그리게 됩니다.
오파시티 마스크에 입력하는 노드는 아래 그림과 같습니다.
이 처리를 확인용 박스 메시의 머티리얼에 적용해 보겠습니다.
상자 메시의 뒷면인 파란색 부분만 그려진 상태가 되어 메시를 노멀 반전시킬 수 있었습니다.
하지만 이 상태로는 아직 아웃라인으로서는 작동하지 않습니다.
이 확인용 박스 메쉬를 아웃라인용으로 복제된 메쉬라고 가정하고 일반 박스 메쉬와 중첩해 보겠습니다.
너무 겹쳐서 확인용 박스 메시가 전혀 보이지 않는 상태가 됩니다.
아웃라인으로 작동하도록 하기 위해 VertexNormalWS에서 노멀 방향을 얻어 월드 위치 오프셋에 입력합니다.
월드 위치 오프셋은 머티리얼을 적용하고 있는 메시의 버텍스를 입력한 벡터만큼 이동시키므로, 노멀 방향을 입력하면 메시가 부풀어 오르는 듯한 동작을 합니다.
이 처리를 확인용 박스 메시의 머티리얼에 적용한 상태에서 다시 일반 박스 메시와 겹쳐봅니다.
조금 잘 보이지는 않지만, 상자의 외곽선에 파란색 선이 그려져 있는 것이 보이시나요?
이것으로 아웃라인용 머티리얼의 기초 처리가 완료되었습니다.
현재 노드의 전체 모습은 아래 그림과 같습니다(확인용 머티리얼 처리는 포함되지 않음).
완성된 머티리얼을 모델을 복제된 메시에 설정합니다. 머티리얼을 세팅한 후 외형을 확인해 봅시다.
아웃라인이 상당히 두껍기 때문에 조정이 필요할 것 같습니다. 월드 위치 오프셋에 입력하는 VertexNormalWS에 적당한 수치를 곱하면 조정할 수 있습니다.
두께 조절을 위해 OutlineWidth라는 이름의 파라미터를 추가했습니다. 몸통의 OutlineWidth를 0.1, 얼굴은 0.0으로 설정하면 적당히 얇아집니다.
마지막으로 아웃라인용 머티리얼의 디테일 패널에서 ShadingModel을 Unlit으로 설정하는 것을 잊지 마세요.
아웃라인용 머티리얼 노드의 전체 구성은 다음과 같습니다.
아웃라인의 색상은 기본적으로 검은색으로 설정되어 있지만, 조정할 수 있도록 파라미터를 추가해 보았습니다. 이것으로 아웃라인용 머티리얼이 완성되었습니다.
UE5.1 이상에서는 오버레이 머티리얼(OverlayMaterial)을 사용하여 쉽게 아웃라인을 표현할 수 있습니다. 단, 머티리얼 슬롯이 하나이기 때문에 헤어와 의상으로 아웃라인을 구분하고 싶을 때 사용하기에는 조금 어려울 수 있습니다.
천사의 고리( 헤어 링 )
흔히 애니메이션적인 표현으로 캐릭터의 머리카락에 아래 그림의 빨간 동그라미 부분과 같은 하이라이트가 들어간 것을 볼 수 있습니다.
이것은 '천사의 고리'라고 불리며, 보다 애니메이션적인 표현을 위해 활용하고 싶은 요소입니다.
하프벡터와 종법선(binormal)의 내적분을 이용하여 천사의 고리를 재현할 수 있습니다.
하프 벡터는 카메라 벡터와 라이트 벡터를 더한 것을 정규화하여 구하고, 종속선은 접선 벡터(tangent)와 법선 벡터의 외積으로 얻은 벡터를 정규화하여 구합니다. 내적은 dot 노드, 외적은 cross 노드를 각각 이용하여 필요한 벡터를 구합니다.
하프벡터와 종속선의 내적분 값은 아래 그림과 같은 모양이 됩니다.
이 상태로는 알기 어렵지만, 검은색 부분에는 0~-1의 값이 들어있기 때문에 절대값을 구하면 아래 그림과 같이 됩니다.
절대값은 abs 노드를 사용하여 구할 수 있습니다.
OneMinus 노드에 의해 방금 구한 값을 1에서 빼고, 적당한 값으로 곱하면 천사의 고리에 활용할 기초 부분이 완성됩니다.
완성된 것을 음영을 만들 때와 마찬가지로 Lerp로 연결하면 모델에 잘 어울립니다.
노멀 트랜스퍼
모델의 얼굴에 그림자, 하이라이트 등을 그릴 때 얼굴의 모양과 자외선으로 인해 얼굴이 예상과 다르게 보일 수 있습니다. 이러한 경우 '노멀 트랜스퍼'를 사용하여 렌더링을 정리할 수 있습니다.
노멀 트랜스퍼는 가상 오브젝트(구와 같은 단순한 오브젝트)의 노멀을 준비하여 사용할 모델의 실제 노멀을 처리하는 계산으로 대체하는 기법입니다.
여기서는 법선 트랜스퍼를 사용하여 모델의 얼굴에 그림자를 그립니다. 먼저 가상 개체의 법선을 준비합니다. 법선이 구형이라고 가정합니다. 구형 법선은 아래와 같이 벡터 [정점 좌표 - 물체 좌표]를 정규화하여 얻을 수 있습니다.
노드로 만들면 아래 그림과 같이 됩니다.
다음으로 준비된 노멀을 모델의 노멀로 대체합니다. 모델의 노멀선을 계산에 이용하고 있는 부분을 준비된 노멀선으로 바꾸면 노멀선 전사가 완료됩니다.
완전히 교체해도 문제가 없지만, 모델의 노멀과 구형 노멀을 Lerp에 연결하여 계산에 활용할 노멀을 조정할 수 있도록 했습니다. 또한, 노멀 투렌스터의 위치를 조정할 수 있도록 위치 오프셋을 위한 파라미터를 준비했습니다.
노멀 트랜스퍼를 이용한 것과 그렇지 않은 것의 외형적 차이는 다음과 같습니다.
얼굴의 음영 외에도 천사의 고리가 잘 표현되지 않을 때에도 효과적인 수단이다.
마지막으로
이 세 가지 표현을 통합한 결과는 다음과 같다.
Unlit 셰이더를 사용해도 다양한 기법을 사용하여 더 예쁜 모습을 표현할 수 있었습니다. 하지만 Unlit 셰이더의 경우 '떨어지는 그림자'를 표현하기 위해서는 의사 그림자 맵을 준비해야 하기 때문에 난이도가 꽤 높은 편입니다.
다음 시간에는 1편에서 말씀드린 것처럼, 좀 더 심혈을 기울여 포스트 이펙트를 이용한 표현법을 소개하도록 하겠습니다.
'TECH.ART.FLOW.IO' 카테고리의 다른 글
[언리얼.페스트.서울.2023]NCSOFT의 차세대 프로젝트 중에 하나인 Project M 발표 자료 공개. 이옥연AD (1) | 2023.10.05 |
---|---|
[번역] UE5로 만드는 셀 셰이딩 1편: 셀 셰이딩 입문 (0) | 2023.10.05 |
[Fork][Pipeline] File and Folder Management, Create, Find, Delete (0) | 2023.10.05 |
[번역][올드스쿨]My little journey to next gen skin shading. (1) | 2023.10.04 |
[FORK] PyQt for Maya and Unreal (0) | 2023.10.02 |