개요
FSR이란 FidelityFX Super Resolution의 약어로, 프레임 속도를 향상시키는 데 도움이 되는 AMD가 개발한 업스케일링 기술을 말합니다.
AMD 측에서는 공간적(Spatial) 업스케일링 방식 이라고 소개하며 이 기술은 AMD 또는 NVIDIA 그래픽 카드를 사용하는지 여부에 관계없이 작동합니다.
2021년 6월에 출시된 첫번째 FSR 1.0버전의 원리는 원래 해상도 보다 작게 렌더링된 단일 소스 이미지를 안티앨리어싱을 거친 다음 란초스 리샘플링 알고리즘을 사용하여 업스케일링하고, 이를 다시 날카롭게 보간하는 샤프닝(Sharpening) 필터를 거치는 방식입니다.
한국 모바일 게임중에서 검은사막 모바일이 FSR 1.0을 적용하고 있습니다.
FSR 1.0의 한계
- FSR 1.0이 동작하려면 높은 품질의 안티 앨리어싱이 적용된 소스 이미지가 필요하다는 것이 가장 큰 약점입니다.
- 낮은 품질의 안티 앨리어싱이 적용된 소스 이미지로는 낮은 수준의 업스케일링 결과밖에 나오지 않습니다. 특히 안티 앨리어싱이 없는 게임에 FSR 1.0을 적용하는 경우 업스케일링에 걸리는 시간이 더욱 증가합니다.
- 또한 업스케일링 퀄리티가 소스 이미지 해상도에 좌우됩니다. 소스 이미지 해상도가 낮으면 그만큼 정보가 부족해서 FSR이 렌더링 해야 할 많은 디테일을 놓치게 됩니다.
FSR 2.0
그래서 2022년 AMD에서 차세대 FSR 2.0을 발표 했습니다.
다음의 내용은 AMD FSR 2.0 (GDC 2022) 영상을 번역 및 요약한 것이라 누락되거나 틀린 정보가 있을 수 있습니다.
FSR 1.0이 현재 프레임의 소스 이미지만 이용해서 지지고 볶는 방식이었다면,
FSR 2.0은 이전 프레임과 현재 프레임을 비교하여 추출한 씬 컬러와 씬 뎁스, 씬 모션 벡터를 이용합니다.
빌트인 안티앨리어싱
FSR 1.0의 방식처럼 먼저 씬 컬러를 안티 앨리어싱(TAA) 하는데서 출발하는데요, 안티 앨리어싱 품질을 올리기 위해서 같은 뷰에서 촬영한 여러 개의 씬 컬러 샘플을 사용합니다.
샘플들을 촬영 할 때 실시간으로 시간의 흐름에 따라 카메라를 아주 약간 이동하여 지터링한 상태에서 촬영하기 때문에 각각 비슷하지만 약간 다른 정보를 포함하는 샘플을 생성합니다.
이 과정을 지터링 시퀀스라고 부르며 샘플 숫자가 많을수록 안티앨리어싱 퀄리티가 올라갑니다. 위 이미지에서 회색 박스가 원본 씬 컬러이며 각 점들은 얼마나 지터링 되었는지를 나타냅니다.
따라서 이론상 지터링 시퀀스는 무한히 계속 될 수 있지만 FSR 2.0에서 시퀀스 길이를 어느정도로 할지 스스로 알아서 고려하여 결정합니다.
안티 앨리어싱 과정에서 지터링 시퀀스가 있기 때문에 최종 결과물 픽셀이 약간 떨리는 것을 실제로 확인할 수 있습니다.
각 샘플들은 최종 출력 이미지에 기여하는 정도가 다릅니다.
이를 판단하는 기준은 원본 씬 컬러에서 카메라 지터링에 의해 얼마나 오프셋 되었는지와 얼마나 최근에 생성된 샘플인지에 따라 다릅니다.
최근일수록, 가까울수록 최종 출력 이미지에 대한 기여도가 높습니다.
이렇게 지터링한 저해상도 샘플들을 모아서 업스케일링을 수행할 목표 해상도의 픽셀에 맞춰서 란초스 알고리즘을 이용하여 중간 픽셀을 생성합니다.
란초스 알고리즘은 목표 해상도 픽셀 P
를 생성 하기 위해서 저해상도 샘플 S
들이 P
의 위치와 가까울수록 높은 가중치를 가지게 되는 구조입니다.
따라서 해당 가중치 곡선이 좁아지도록 제어하면 최종 결과물도 더욱 날카롭게 표현됩니다.
이것이 FSR2에 내장되어 있는 샤프닝(Sharpening) 보간 필터입니다. 샤프닝 필터의 원리가 가중치 곡선의 범위를 조절하는 것이기 때문에 성능 측면에서 거의 ‘공짜’입니다.
뎁스와 모션 벡터를 이용한 애니메이션 대응
위에서 설명한 업스케일링 이야기는 샘플이 공간적, 시간적 관점에서 움직이지 않는 정적인 이미지를 업스케일링 할 때에 국한되는 이야기 였습니다. 따라서 애니메이션에 대응하기 위해서 모션 벡터를 사용합니다.
모션 벡터는 샘플이 이전 프레임에 비해서 현재 프레임이 얼마나 움직였는지 설명합니다.
올바른 가장자리 픽셀을 따르기 위해 목표 해상도 픽셀 P
을 중심으로 ${3*3}$ 범위 픽셀의 가장 가까운 모션 벡터와 씬 뎁스를 이용합니다.
모션 벡터는 이럴때 사용합니다. 현재 프레임(${n}$)을 씬 컬러와 뎁스 데이터가 이전 프레임(${n-1}$)과 비교했을 때 더이상 연관이 없는 경우에는 고스팅(Ghosting) 문제가 발생합니다.
예를 들어 오브젝트가 나타나서 씬의 일부가 가려지거나(Disocclusion) 오브젝트의 색상, 음영이 변하는 경우 나타납니다.
이전 프레임과 현재 프레임의 깊이 값의 차이를 이용해 오브젝트가 움직일 때 화면이 실제로 변하는 영역을 검은색으로 가리는 마스킹 처리를 합니다.
(알파 블렌드 이펙트를 잔뜩 넣은 예제)
유니티에서는 알파 블렌딩된 Transparent 오브젝트가 모션 벡터 패스에 추가되지 않는 경우가 많습니다.
이를 위해 FSR 2에는 인스펙터에서 기본적으로 활성화된 리액티브(Reactive) 마스크라는 기능이 있습니다.
이 설정을 활성화하면 모션 벡터 버퍼에 추가할 필요 없이 알파 블렌딩/투명 오브젝트를 대폭 개선할 수 있습니다.
비활성화하면 추가 메모리를 확보할 수 있지만 프로젝트에서 투명 또는 알파 블렌디드 오브젝트를 사용하지 않는 한, 이 옵션을 활성화하는 것이 좋습니다.
요약
여기까지가 FSR 2.0 의 핵심 동작 원리입니다. 이를 간단하게 요약하였으며 조절할 수 있는 옵션들을 정리해봤습니다.
- FSR 2.0 는 씬 컬러, 뎁스, 모션벡터를 여러 프레임 단위로 사용합니다.
- FSR 2.0 는 지터링과 란초스 알고리즘의 혼합으로 동작합니다.
- 샤프닝 필터의 원리는 란초스 알고리즘의 가중치 곡선의 범위를 조절하는 것이기 때문에 성능 측면에서 거의 ‘공짜’입니다.
- 유니티의 FSR 2.0 는 고스팅 현상을 방지하기 위해서 모션 벡터를 사용하여 리액티브 마스크를 생성합니다.
- 리액티브 마스크를 비활성화하면 추가 메모리를 확보할 수 있지만 고스팅 현상으로 생기는 아티팩트가 있어서 가급적 활성화 하는 것을 권장합니다.
따라서 FSR2 옵션중에서 연산 성능에 영향을 미치는 것은 없으며 얼마나 작은 크기의 소스 이미지를 얼마나 높은 배율으로 스케일링 하느냐로 결정됩니다.
굉장히 심플합니다. 그래서 렌더링 되는 씬이 너무 가벼울 경우 낮은 해상도로 렌더링 한 다음 업스케일링 하는 성능 이득이 FSR 2의 렌더링 비용을 상쇄할 만큼 충분하지 않을 수 있습니다.
안타깝게도 모바일 디바이스에서는 이러한 경우가 많습니다.
실제로 FSR 2.0의 퀄리티 옵션은 다음과 같이 조절 할 수 있습니다.
- Quality : 1.5x scaling
- Balanced : 1.7x scaling
- Performance : 2.0x scaling
- Ultra Performance : 3.0x scaling
FSR 2.0은 씬 컬러, 뎁스와 모션 벡터를 여러 프레임 단위로 사용하기 떄문에 모바일의 저사양 보급기종에서는 메모리 부족 문제가 발생할 수 있습니다.
레퍼런스(Reference)
- 유니티 에셋 스토어의 FSR 2.0 : https://assetstore.unity.com/packages/tools/utilities/fsr-2-upscaling-for-unity-252172
- GDC 2022 AMD FSR 2.0 발표 : https://youtu.be/97JIldpUGE4
- 검은사막 모바일 : https://forum.blackdesertm.com/Board/Detail?boardNo=12&contentNo=476715
- 란초스 리샘플링 : https://en.wikipedia.org/wiki/Lanczos_resampling