Co to jest „Scanline Racing”

13

Słyszałem, że wiele osób pracujących nad VR mówi o wyścigach Scanline i że ma to pomóc w poprawie opóźnień w ruchu od fotonu. Jednak nie jest dla mnie jasne, jak można to zrobić za pomocą OpenGL. Czy ktoś mógłby wyjaśnić, jak działa wyścig Scanline i jak można go zaimplementować w nowoczesnych procesorach graficznych.

Mokosha
źródło

Odpowiedzi:

14

Gdy twój GPU wyświetla na ekranie nową ramkę, przesyła obraz kablem HDMI (lub jakikolwiek inny) w procesie zwanym „skanowaniem”. Piksele są wysyłane w kolejności liniowej, zwykle od lewej do prawej i od góry do dołu. Proces jest tak zaplanowany, że zajmuje to większość czasu interwału odświeżania. Na przykład przy 60 Hz jedna ramka wynosi ~ 17 ms. Każde skanowanie zajmie prawdopodobnie około 15-16 ms, z 1-2 ms vblank pomiędzy nimi (dokładne wartości różnią się w zależności od trybu wyświetlania i wideo).

Tradycyjnie renderowanie jest podwójnie buforowane, co oznacza, że ​​w pamięci GPU są przechowywane dwa bufory: jeden, który jest obecnie skanowany („bufor przedni”), i jeden, który jest renderowany („bufor buforowy”). Każda ramka jest zamieniana. GPU nigdy nie renderuje do tego samego bufora, który jest skanowany, co zapobiega artefaktom ze względu na potencjalnie widzenie części niekompletnej ramki. Jednak efektem ubocznym tego jest zwiększone opóźnienie, ponieważ każda ramka może siedzieć w buforze przez kilka ms, zanim zacznie być skanowana.

VR jest bardzo wrażliwe na opóźnienia, więc nie jest to pożądane. Alternatywnym podejściem jest renderowanie bezpośrednio do przedniego bufora, ale należy bardzo dokładnie określić czas, tak aby każda linia obrazu była renderowana na krótko przed dotarciem do skanu. To się nazywa „wyścigi skanowane” lub „wyścigi wiązką” („wiązka” nawiązująca do dawnych czasów CRT). To mniej więcej wymaga renderowania obrazu w kolejności skanowania, tj. W tej samej kolejności, w której skanowane są piksele. Nie musi być dosłownie renderowany pojedynczo - może być renderowany w cienkie paski o wysokości kilku pikseli, ale musi być wykonywany w kolejności, ponieważ nie można cofać się i edytować pikseli, które już miały został zeskanowany.

Podejście to ma wiele wad; ma bardzo rygorystyczne wymagania wydajnościowe, musi być bardzo dokładnie mierzone względem vsync i znacznie komplikuje proces renderowania. Ale w zasadzie może zmniejszyć milisekundy opóźnienia, dlatego ludzie VR są tym zainteresowani.

Nathan Reed
źródło
1
Więc moje pytanie brzmi: jak to robimy na nowoczesnych GPU? Nie sądzę, aby można było przesłać zapytanie o skanowanie, i wydaje mi się, że nie można tak naprawdę przesyłać wywołań rysowanych według linii. Nawet gdybyś mógł - jakie masz gwarancje, że twoje losowania dotrą tam przed skanowaniem?
Mokosha,
1
@Mokosha Prawidłowo, nie ma możliwości zapytania bezpośrednio o skan AFAIK. W najlepszym razie możesz dowiedzieć się, kiedy vsync jest (za pomocą jakiegoś sygnału systemu operacyjnego) i oszacować, gdzie jest skanowanie, mierząc czas względem tego (znając szczegóły trybu wideo). W przypadku renderowania możesz eksperymentować, aby dowiedzieć się, jak długo trwa zwykle między glFlush a momentem renderowania, i na tej podstawie możesz zgadywać. Ostatecznie w przypadku błędu musisz wprowadzić pewien luz w czasie (np. Pozostać 2-3 ms przed skanowaniem) i zaakceptować, że prawdopodobnie będą pojawiać się okazjonalne artefakty.
Nathan Reed,
Efekt zwiększonego opóźnienia wynika z vsync, co powoduje, że zamiana przedniego i tylnego bufora synchronizuje się z vblank monitora. Samo podwójne buforowanie samo w sobie nie powoduje tego problemu i warto zminimalizować migotanie, ponieważ piksel może zmienić się tylko raz w buforze przednim.
Maurice Laveaux,
Wymyśliłem dokładny sposób przewidywania rastrów bez zapytania o linię skanowania, patrz odpowiedź poniżej.
Mark Rejhon
0

Wspaniałą rzeczą jest to, że możemy w końcu przewidzieć dokładną dokładność rastra w linii skanowania bez dostępu do zapytania dla poszczególnych linii:

https://www.youtube.com/watch?v=OZ7Loh830Ec

Wymyśliłem dokładne mikrosekundowe formuły jako przesunięcie VSYNC, aby przewidzieć położenie linii łzy. Tereliny podczas VSYNC OFF są zawsze dokładne rastrowo, więc można je wyprowadzić z widoczności podczas „symulowanego renderowania bufora przedniego” na poziomie paska poprzez powtarzanie zamiany bufora VSYNC OFF.

Zwróć uwagę na wątek forum - ciągle jest dodawany kod open source - https://forums.blurbusters.com/viewtopic.php?f=10&p=32002

Mark Rejhon
źródło
0

Jeśli jest to interesujące, Dreamcast miał tryb renderowania „wyścigi wiązką”, w którym był w stanie poświęcić stosunkowo niewielką część pamięci pikselom bufora ramki (np. 64 linie skanowania) i renderowałby rzędy 32 z kolei zsynchronizowane z aktualizacja wyświetlacza. Służyło to jednak tylko do oszczędzania pamięci. Wątpię, czy ktokolwiek generował „zmodyfikowaną” geometrię dla późniejszych części wyświetlacza.

Simon F.
źródło