In che modo dispositivi come Game Boy Advance raggiungono il frame rate?


31

Ho progettato il mio dispositivo di gioco portatile basato su un microcontrollore AVR e un piccolo display OLED.

Ho iniziato con un display monocromatico 128x64 pixel e posso disegnare comodamente su di esso con oltre 60 fotogrammi al secondo.

Di recente l'ho rielaborato per utilizzare un OLED RGB, 128x128 pixel senza pensare davvero troppo solo per scoprire che avrei potuto ottenere solo circa 4 FPS. Dopo un po 'di riflessione e attento refactoring posso ottenere fino a ~ 12 fps se non mi interessa troppo fare qualsiasi altra cosa!

La mia domanda è: in che modo un dispositivo come GBA (Game Boy Advance) ha raggiunto un frame rate di quasi 60 fps? Ho pensato di avere un "processore grafico" separato, ma mi sono reso conto che sarei ancora colto da bottiglia trasferendo i dati di visualizzazione a quello.

Mi sono anche chiesto di usare l'interfaccia parallela a 8 bit vestigiale che la maggior parte di questi schermi tende ad avere, il che potrebbe farmi una velocità di 8x, tranne per il fatto che i moderni MCU non tendono ad avere interfacce hardware parallele come fanno per seriale e bit- il bang probabilmente consumerà molto il guadagno di velocità.

Quali altre opzioni esistono?

Attualmente sto usando un ATmega1284P collegato a un controller OLED SSD1306 tramite USART-SPI. Questa è la versione monocromatica.

Lo schermo a colori era un SSD1351, non originariamente collegato a SPI hardware. Non ero convinto che avrebbe fatto abbastanza differenza, nel complesso è troppo lento

So di poter ottenere MCU più veloci, ma voglio sapere quali altre opzioni potrei esplorare: il processore GBA è molto più lento del mio 1284!


6
"Sarei ancora colosso da collo di bottiglia trasferendo i dati di visualizzazione a quello." DSI ha quattro corsie ciascuna fino a 1,2 Gbit / sec. Vi lascio il resto dei calcoli.
Oldfart

1
Proprio come qualsiasi grafica in qualsiasi dispositivo di videogioco, c'è memoria che gestirà la grafica. Secondo questo sito Web, esiste un indirizzo per la grafica, l'audio, ecc. Le istruzioni sarebbero memorizzate lì. Supponendo che non ci siano molti dati che potrebbero creare conflitti con il tempo di esecuzione, si eseguiranno quelle istruzioni per caricare facilmente i dati grafici.
KingDuken,

5
acquista il display senza il controller e crea il tuo controller
old_timer

4
@immibis: Quasi sicuramente qualche terribile controller basato su I2C o SPI. Le cose per hobby sono piene di cose lente troppo costose come quella quando puoi ottenere uno schermo da 400+ dpi per iPhone da $ 20 a causa di economie di scala.
R ..

6
@R .. Voglio solo sottolineare che la ragione di questi controller hobbisti è che possono interfacciarsi con quasi tutti i processori, dato che lo fai sembrare inutile. Non saresti in grado di interfacciarsi facilmente con uno schermo iPhone, se non del tutto. Probabilmente si collega a un processore grafico dedicato e forse personalizzato.
user253751

Risposte:


64

Altre risposte coprono la tua domanda piuttosto bene a livello astratto (hardware), ma avendo in realtà una reale esperienza con il GBA in particolare ho pensato che una spiegazione più dettagliata potrebbe valere la pena.

Il GBA aveva molte modalità e impostazioni di disegno che potevano essere utilizzate per controllare il modo in cui il processore grafico interpretava la RAM video, ma una cosa era inevitabile: la frequenza dei fotogrammi. Il processore grafico stava disegnando sullo schermo in un ciclo quasi (più su questo sotto) costante. (Questo è probabilmente il bit più rilevante per la tua domanda.)

Disegnerebbe una linea alla volta facendo una breve pausa tra ciascuna. Dopo aver tracciato l'ultima linea per la cornice, ci vorrebbe una pausa approssimativamente uguale al tempo necessario per disegnare 30 linee. Quindi ricominciare. I tempi di ciascuna linea e i tempi di ciascun fotogramma erano tutti predeterminati e incastonati nella pietra. In un certo senso il processore grafico era davvero il padrone di quel sistema e dovevi scrivere i tuoi giochi in base al suo comportamento, perché avrebbe continuato a fare quello che faceva se tu fossi pronto o no.

Circa il 75-80% delle volte spingeva attivamente sullo schermo. Quali frame rate potresti ottenere se stessi facendo lo stesso?

Quell'80% delle volte era anche ciò che la CPU doveva elaborare l'input dell'utente, calcolare lo stato del gioco e caricare sprite / riquadri in aree di VRAM che erano attualmente fuori dallo schermo (o almeno non incluse nella linea corrente che veniva tracciata).

Il 20% tra i frame, era tutto ciò che la CPU doveva modificare le impostazioni video o la RAM che avrebbe avuto un impatto sull'intero frame successivo.

Alla fine di ogni riga, il processore grafico inviava un interrupt di sincronizzazione della linea alla CPU. Questo interrupt può essere utilizzato per modificare le impostazioni su alcuni sprite o su alcuni livelli di sfondo (è così che puoi ottenere un effetto come un riflettore conico, modificando le dimensioni e la posizione di una delle maschere rettangolari tra ciascuna linea disegnata. per quanto riguarda l'hardware tutte quelle regioni sono rettangolari.). Devi fare attenzione a mantenere piccoli questi aggiornamenti e finire prima che il processore grafico inizi a disegnare la riga successiva o puoi ottenere brutti risultati. Qualsiasi tempo impiegato per elaborare questi interrupt riduce anche l'80% del tempo di elaborazione della CPU ...

Per i giochi che hanno ottenuto il massimo da questo sistema, né la CPU né il processore grafico hanno mai fatto una vera pausa; ognuno stava inseguendo l'altro attorno al ciclo aggiornando ciò che l'altro non stava guardando.


5
Benvenuto e ben messo.
Mindwin,

2
Alcuni sistemi "più recenti" come Nintendo DS hanno aggirato la limitazione del framerate fisso aggiungendo il registro VCOUNT per ritardare il fotogramma successivo per un periodo di tempo configurabile (di solito per aiutare la sincronizzazione dei giochi multiplayer).
foresta

21

La caratteristica chiave di tutte le console di gioco che li distinguevano dai primi PC e praticamente da tutti i computer domestici (1) erano gli sprite hardware .

La guida alla programmazione GBA collegata mostra come funzionano dal punto di vista del processore principale. Le bitmap che rappresentano il giocatore, lo sfondo, i nemici ecc. Vengono caricate in un'area della memoria. Un'altra area di memoria specifica la posizione degli sprite. Quindi, invece di dover riscrivere tutta la RAM video ogni frame, il che richiede molte istruzioni, il processore deve solo aggiornare la posizione degli sprite.

L'elaboratore video può quindi lavorare pixel per pixel per determinare quale sprite disegnare in quel punto.

Tuttavia, questo richiede una RAM a doppia porta condivisa tra i due, e penso che nel GBA il processore video sia sullo stesso chip del processore ARM e Z80 secondario.

(1) Eccezione notevole: Amiga


Solo un pazzo: i giochi arcade veramente antichi avevano gli sprite in una ROM associati al processore grafico, non una RAM a doppia porta. Non ho idea se questo fosse anche il caso delle prime console, anche se sicuramente avrebbe potuto essere fatto in quel modo.
TimWescott il

@TimWescott il GBA aveva più modalità di disegno e non ho esperienza con la maggior parte, quindi questo potrebbe non essere universalmente vero ma, non penso che nessuna di queste modalità avesse accesso diretto alle ROM (sulla cartuccia): in genere tutte le i dati di tile / sprite / palette dovevano essere trasferiti dalla ROM alla memoria video e il processore grafico ci ha lavorato da lì.
Mr.Mindor,

@ Mr.Mindor Scusate se non ero chiaro - non sto fingendo di sapere come ha fatto il GB o il GBA. Stavo solo commentando i primissimi giochi arcade Nintendo tra la fine degli anni '70 e l'inizio degli anni '80, e tutti ci chiedevamo come facessero .
TimWescott il

@TimWescott: penso che lo stesso valesse per il NES, anche se la ROM in questione si trovava all'interno dei Game Pak.
supercat

19

"La mia domanda è: come ha fatto un dispositivo come il GBA a raggiungere un frame rate di quasi 60 fps?"

Per rispondere solo alla domanda, l'hanno fatto con un processore grafico. Sono abbastanza sicuro che Game Boy abbia usato la grafica sprite. A un livello superiore, ciò significa che il processore grafico viene caricato cose come un'immagine di uno sfondo, un'immagine di Mario e un'immagine di Princess Peach, ecc. Quindi il processore principale emette comandi come "mostra l'offset dello sfondo da questo molto in xey, sovrapponi l'immagine di Mario n. 3 in questa posizione x, y ", ecc. Quindi il processore principale non è assolutamente interessato a disegnare ogni pixel, e il processore grafico non è assolutamente interessato a calcolare lo stato del gioco. Ognuno è ottimizzato per ciò che deve fare e il risultato è un videogioco abbastanza buono senza usare molta potenza di calcolo.


7
Chiamarlo "processore grafico" esagera ciò che fa, suggerendo che è una sorta di CPU propria. È solo un controller video, che è fondamentalmente un tipo complicato di sequencer. Mentre conta i pixel orizzontali e verticali, recupera i dati di titolo e / o sprite, li inserisce nei registri di spostamento e combina l'output dei registri di spostamento in un pixel di output. Non è in grado di eseguire un programma come un vero processore grafico "GPU".
Ross Ridge,

14

Il GBA aveva un processore piuttosto lento. ARM7 è molto bello; hanno semplicemente funzionato lentamente e non gli hanno dato quasi risorse.

C'è un motivo per cui molti giochi Nintendo a quel punto e prima erano a scorrimento laterale. HARDWARE. È tutto fatto in hardware. Avevi più strati di tessere più uno o più sprite e l'hardware ha fatto tutto il lavoro per estrarre pixel da quelle tabelle e guidare il display.

Costruisci la tessera impostata davanti e poi hai avuto un piccolo ricordo che era una mappa di tessere. Vuoi che la tessera in basso a sinistra sia la tessera 7? Metti un 7 in quella posizione di memoria. Vuoi che la tessera successiva sia la tessera 19? Nel set di tessere, inserisci un 19 lì e così via per ogni livello che hai abilitato. Per lo sprite, devi semplicemente impostare l'indirizzo x / y. È inoltre possibile eseguire il ridimensionamento e la rotazione impostando alcuni registri e l'hardware si occupa di tutto il resto.

La modalità 7, se ricordo bene, era una modalità pixel, ma era come una scheda video tradizionale in cui si inseriscono byte che coprono il colore di un pixel e l'hardware si occupa dell'aggiornamento del video. Penso che potresti giocare a ping pong o almeno quando hai avuto un nuovo frame potresti capovolgerli, ma non ricordo bene. Ancora una volta, il processore era abbastanza sotto-bloccato per quel giorno ed età e non aveva troppe risorse veloci. Quindi, mentre alcuni giochi erano in modalità 7, molti erano scroller laterali basati su tessere ...

Se si desidera una soluzione con un frame rate elevato, è necessario progettare tale soluzione. Non puoi semplicemente prendere qualsiasi vecchio display che trovi e parlarci tramite SPI o I²C o qualcosa del genere. Metti almeno un framebuffer davanti, idealmente due, e, se possibile, controlla la riga e la colonna su quel display.

Un certo numero di schermi che sospetto che tu stia acquistando hanno un controller su cui stai effettivamente parlando. Se si desidera prestazioni di tipo GBA / console, creare / implementare il controller. Oppure acquisti / costruisci con una GPU / chip video / BLOB logico e usi HDMI o un'altra interfaccia comune in un monitor di serie.

Solo perché una bicicletta ha pneumatici, una catena e ingranaggi non significa che può andare veloce come una moto. Devi progettare il sistema per soddisfare le tue esigenze prestazionali, end to end. Puoi mettere quella ruota di bicicletta su quella moto, ma non funzionerà come desiderato; tutti i componenti devono far parte del progetto complessivo.

Anche gli asteroidi funzionavano in questo modo; ne serviva solo uno 6502. La grafica vettoriale veniva eseguita con una logica separata; il 6502 ha inviato una minuscola stringa di dati al controller di grafica vettoriale, che utilizzava una ROM e quei dati per eseguire la stampa xy del fascio e z, on / off ... Alcuni stand-up avevano processori separati per gestire audio e video separati da il processore che calcola il gioco. Ovviamente oggi il video è gestito da alcune centinaia, se non migliaia, di processori che sono separati dal processore principale ...


Giuro che ricordo che mode7 è stato calunniato dal marketing come risposta alla "hyper mode" di Sega o qualcosa del genere ... forse "Super FX?" en.wikipedia.org/wiki/Mode_7
Caleb Jay,

coranac.com/tonc/text/bitmaps.htm#sec-modes Potrei averlo ricordato male Sto pensando forse alla modalità 5, o ad una delle modalità bitmap, ci sono alcune modalità a riquadri con sprite e modalità o modalità bitmap / framebuffer . forse c'è un 7. non sapevo di quello che hai collegato ma è buono a sapersi.
old_timer

hmm leggendo di più sulla modalità 7 e non è solo una modalità. Ad ogni modo il GBA ha modalità di tile e modalità bitmap che sono più lente in quanto devi essere responsabile di ogni pixel in cui la modalità di tile di un byte nella mappa di tile produce molti pixel. Hanno anche sfruttato la dimensione dei bus (larghezza) e la velocità della memoria, e una cosa cache della pipeline rom per aiutare a ottenere cose (istruzioni) dalla rom un po 'più velocemente. Ma dal primo giorno stavi faticando a far funzionare il software a un ritmo decente e per fortuna la logica si è occupata della maggior parte del lavoro video.
old_timer

se guardi questi display che stai acquistando che hanno queste interfacce parallele a 8 bit o 4 bit o spi o i2c che sono sulla tua strada per le prestazioni, vuoi il display grezzo senza quei controller e quindi puoi controllare come viene gestito il display , costruisci un framebuffer o due in modo da poter eseguire il ping / pong e un'interfaccia veloce dalla tua CPU al framebuffer. supponendo che tu inizi con un display abbastanza veloce in primo luogo.
old_timer

7

in che modo un dispositivo come GBA ha raggiunto un frame rate di quasi 60 fps?

Hardware.

Ha una memoria grafica, che può o meno condividere lo stesso bus della memoria programma / dati ... ma il bit importante è che ha un processore grafico che legge la memoria 60 volte al secondo e invia i dati al display LCD usando un interfaccia ottimizzata progettata per farlo in modo efficiente.

Puoi fare lo stesso con qualsiasi moderno microcontrollore dotato di una periferica "interfaccia LCD", ad esempio LPC4330, anche se questo potrebbe essere eccessivo. Ovviamente avrai bisogno di un pannello LCD compatibile.

Con i moderni microcontrollori veloci (ovvero ARM non AVR) e uno schermo così piccolo, probabilmente non avrai bisogno di sprite o di un blitter per accelerare le operazioni grafiche. Con un AVR a 8 bit potrebbe essere lento.

Ma a prescindere dalla CPU, fare un botto con l'interfaccia al display farà schifo.

Credo che l'Atari 2600 abbia utilizzato il bit banging della CPU per inviare l'immagine alla TV. È un po 'obsoleto.


Anche i 2600 avevano sprite hardware, anche se un numero molto limitato (due giocatori e due proiettili credo)
pjc50

2
@ pjc50, l'Atari 2600 sorta di sprite hardware avuto. Come ogni altra parte del sottosistema grafico, erano oggetti unidimensionali. Se il programmatore voleva qualcosa di diverso da una serie di linee verticali, il programma doveva aggiornare gli sprite dopo che ogni riga veniva disegnata sullo schermo.
Segna il

1
@Mark: il 2600 aveva sicuramente sprite hardware. L'hardware controllava solo il posizionamento orizzontale, ma gli sprite sul 2600 consentivano ai giochi di produrre giochi che erano molto più colorati di tutti i suoi concorrenti.
supercat
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.