Niedawno obejmuję Test-Driven Development (TDD) i miało to wspaniały wpływ na mój rozwój i odporność mojej bazy kodu. Chciałbym rozszerzyć to podejście na niektóre prace renderowania, które wykonuję w OpenGL, ale nie byłem w stanie znaleźć żadnego dobrego podejścia do tego.
Zacznę od konkretnego przykładu, abyśmy wiedzieli, jakie rzeczy chcę przetestować; powiedzmy, że chcę utworzyć sześcian jednostkowy, który obraca się wokół jakiejś osi i że chcę zapewnić, że dla pewnej liczby ramek każda ramka jest renderowana poprawnie.
Jak mogę utworzyć zautomatyzowaną skrzynkę testową? Najlepiej byłoby nawet napisać przypadek testowy przed napisaniem dowolnego kodu do renderowania kostki (zgodnie ze zwykłymi praktykami TDD). Między innymi chciałbym się upewnić, że rozmiar, lokalizacja i orientacja kostki są poprawny w każdej renderowanej ramce. Może nawet chcę się upewnić, że równania oświetlenia w moich modułach cieniujących są poprawne w każdej klatce.
Jedyne zdalnie użyteczne podejście do tego, na jakie się natknąłem, polega na porównaniu renderowanych danych wyjściowych z danymi wyjściowymi, co zasadniczo wyklucza praktykę TDD i jest bardzo uciążliwe.
Mógłbym mówić o innych pożądanych wymaganiach, ale obawiam się, że te, które już wymieniłem, są poza zasięgiem.
Odpowiedzi:
Wydaje się, że to dobre zastosowanie frameworku testów zatwierdzających lub coś podobnego.
Jak stwierdzono w komentarzach, nadal będziesz mieć problem z fałszywymi trafieniami, jeśli zdarzy ci się zatwierdzić złe wyjście, ale to co najmniej w LEAST powie ci, kiedy wynik znacząco się zmienił.
Ponieważ używasz OpenGL, zakładam, że zatwierdzenia nie będą działać bezpośrednio dla ciebie, ale pomysł jest solidny. Po prostu sprawdź skrót pliku, a jeśli jest inny, pokaż awarię w odpowiedniej przeglądarce różnic (jak program do różnicowania obrazów). Jeśli zatwierdzisz nową wersję, zaktualizuj plik „zatwierdzony”, aby pasował do nowego wyniku.
źródło
Nie interesuję się grami, więc proszę o wszelkie potencjalne głupie i naiwne postrzeganie
Dla mnie pisanie testów, które porównują w pełni renderowane obrazy, nie jest tak naprawdę testami jednostkowymi , ale pełnymi testami integracyjnymi , ponieważ wszystko musi działać dobrze, aby test przebiegał pomyślnie.
Co powiesz na warstwę pośrednią, w której możesz sprawdzić, czy wszystko jest w porządku? Przychodzą mi na myśl dwie rzeczy:
Nie rysuj bezpośrednio, ale wydaj strumień poleceń, który zamienia się w renderowanie wywołań. Strumień poleceń można sprawdzić pod kątem poprawności. Nie jest to test kompleksowy, ale potrzebne są testy jednostkowe , a nie pełne testy integracyjne.
To jest naprawdę odmiana 1. Zawiń OpenGL, przechwyć wszystkie wywołania, usuń to z tego, co naprawdę chcesz przetestować i sprawdź, czy dane wyjściowe nadal pasują. Opakowanie OpenGL może samo sprawdzić, jeśli jest odpowiednio skonfigurowane, i zamienia się w próbkę .
źródło
Problem polega na tym, że silniki 3D nie są wymagane do wyświetlania dokładnego obrazu bit po bicie. Pewna swoboda jest tolerowana, o ile artefakty spowodowane przez nią nie są widoczne dla widza. Fakt, że tekstura jest o 1% ciemniejsza niż oczekiwano, zwykle nie stanowi poważnego problemu ... zwykle. W niektórych warunkach może to być artefakt wizualny. I na tym polega problem: trudno zautomatyzować test, które artefakty zostałyby zauważone przez człowieka, a które nie. Mimo to zautomatyzowane testy mogą być używane do prostych kontroli poczytalności, gdy są stosowane w bardzo prostej geometrii.
Możesz zrobić kilka prostych scen, a następnie porównać wygenerowany obraz z renderingiem referencyjnym. Renderowanie referencyjne może pochodzić z innego silnika graficznego lub może być wcześniejszym zrzutem ekranu z tego samego silnika (testy regresji).
Gdy niektóre testy kończą się niepowodzeniem po zmianie silnika graficznego, ludzki tester powinien porównać dane wyjściowe z obrazem referencyjnym i sam ocenić, czy nowy wynik wygląda tak dobrze, jak wcześniej (lub nawet lepiej). W takim przypadku test należy zmienić, aby porównać z nowymi, ulepszonymi wyjściami.
Kolejną rzeczą, którą możesz sprawdzić automatycznie, są wymagania dotyczące wydajności. Jednym z takich wymagań może być to, że podczas samoczynnego pokazu (symulującego prawdziwą sekwencję z gry) liczba klatek na sekundę nie może spaść poniżej 40 Fps w systemie testowym. To jest coś, co możesz przetestować automatycznie. Nie można przetestować, czy rendering jest satysfakcjonujący. Możesz jednak użyć takich testów, aby uniemożliwić programistom opracowanie gry, która wygląda świetnie, ale nie działa poprawnie na żadnym niedrogim systemie aż do wielu lat po premierze (cześć Crytek).
źródło