A trecut ceva vreme de când nu am mai scris ceva și ca să nu merg tot pe tonalitatea “negativă”, m-am gândit să încep o serie de articole în care să vă ofer informații legate de cum funcționeză jocurile la un nivel mai profund decât cel pe care îl vedem pe monitor sau televizor.
Sa începem mai întâi cu un mic sumar despre arhitectura pe care o avem în PC-urile noastre. Bineînțeles, ce este în imagine este o versiune simplicată pentru subiectul de astăzi.
Din câte vedeți atât CPU-ul cât și GPU-ul au o memorie dedicată, prin urmare CPU-ul trebuie să încarce prin comenzi specifice datele din memoria CPU-ului în cea a GPU-ului. Ce încarcă? Geometrie, texturi și diverse date folosite de stagiile din pipeline-ul grafic despre care o să vorbim puțin mai încolo.
De exemplu, în jocuri precum Witcher 3 sau GTA V, acest transfer e folosit în mod constant, de aceea dacă logica de transfer este una defectuoasă sau ceva nu este sincronizat cum trebuie, atunci pot apărea fel și fel de artefacte. Unul dintre artefacte sunt acele momente în care geometria este mai pixelată și dintr-o dată devine mai frumoasă, acesta este un pop-in. Dar de ce trebuie să încarce mereu și nu o singură dată? Jocurile menționate mai sus sunt de tipul open-world, să încarci totul o singură dată poate duce la următoarele efecte
- timp de loading lung, foarte lung, ai da ALT-F4 după 2 minute
- crash sau artefecte din cauza unui consum de VRAM foarte mare
- consum de memorie RAM foarte mare
Prin urmare dezvoltatorii au venit cu acestă tehnică denumită streaming, care încarcă versiuni mai bune ale geometriei sau a texturilor pe măsură ce se schimbă poziția jucătorului/camerei în lume.
În memoria VRAM avem o porțiune de memorie dedicată unui framebuffer. Acesta este folosită la stocarea pixelilor ce vor fi afisați pe ecran. De exemplu, dacă avem o rezoluție de 1920 x 1080 și un format ce ține 32 de bytes per pixel atunci framebufferul o să ocupe circa 66 MB in format decimal. Dacă tot suntem în acestă zonă să discutăm despre VSync și de ce uneori avem nevoie de acest mecanism.
Să presupunem că nu am avea acestă opțiune activă, cam așa arată procesul prin care se actualizează imaginea de pe ecran.
Nu prea arată bine, nu? Ei bine acest lucru se întâmplă când placa video desenează mai repede decât rata de refresh a monitorului. De exemplu dacă ai un monitor cu frecvența de 60 de Hz și ai un FPS de 80 atunci sunt 20 de frame-uri în plus ce nu se vor sincroniza perfect, de aceea avem nevoie de VSync, o opțiune prin care placa video desenează la aceiași rată cu care poate monitorul să redea imaginea.
Dar am 80 de FPS, cum ajunge la 60?
Una dintre tehnicile folosite este întârzierea threadului principal cu timpul necesar ca să atingi 60 de FPS. În cazul nostru concret, 80 de FPS înseamna 12,5 milisecunde pe care CPU-ul le petrece intr-un frame, ca să ajungem la 60 de FPS, ocupăm threadul principal cu 4,1 milisecunde astfel încât să ajungem la rezultatul dorit. Ca să nu spuneți că am scos cifrele din burtă, formula de calcul este una simplă FPS vine de la frames per second. O secundă are 1000 de milisecunde, o simplă operație de împărițire la numărul de frameuri îți arată cât a durat un frame.
După VSync a urmat Adaptive-Vsync, unde placa video oprește VSyncul la frameuri mici de joc și pornește VSyncul la frameuri mari de joc. De asemenea, mai nou avem monitoarele ce rezolvă această problemă prin tehnologia G-Sync (Nvidia) și Free-Sync (AMD), unde placa video nu este cea care se adaptează la puterea de lucru a monitorului, ci invers.
Cam atât pentru articolul acesta, o să vă dau timp să digerați informația primită, dacă aveți întrebări, nu ezitați să mi le adresați în secțiunea de comentarii.
Sursă imagini:
https://www.ntu.edu.sg/home/ehchua/programming/opengl/CG_BasicsTheory.html
Digital Foundry
Gamers Nexus