all repos — mgba @ 7c7e934dacb82150e1565ce9149c60ac6144ef31

mGBA Game Boy Advance Emulator

src/gba/gba-video.h (view raw)

  1#ifndef GBA_VIDEO_H
  2#define GBA_VIDEO_H
  3
  4#include "gba-memory.h"
  5
  6#include <stdint.h>
  7
  8enum {
  9	VIDEO_CYCLES_PER_PIXEL = 4,
 10
 11	VIDEO_HORIZONTAL_PIXELS = 240,
 12	VIDEO_HBLANK_PIXELS = 68,
 13	VIDEO_HDRAW_LENGTH = 1006,
 14	VIDEO_HBLANK_LENGTH = 226,
 15	VIDEO_HORIZONTAL_LENGTH = 1232,
 16
 17	VIDEO_VERTICAL_PIXELS = 160,
 18	VIDEO_VBLANK_PIXELS = 68,
 19	VIDEO_VERTICAL_TOTAL_PIXELS = 228,
 20
 21	VIDEO_TOTAL_LENGTH = 280896,
 22
 23	REG_DISPSTAT_MASK = 0xFF38
 24};
 25
 26enum ObjMode {
 27	OBJ_MODE_NORMAL = 0,
 28	OBJ_MODE_SEMITRANSPARENT = 1,
 29	OBJ_MODE_OBJWIN = 2
 30};
 31
 32enum ObjShape {
 33	OBJ_SHAPE_SQUARE = 0,
 34	OBJ_SHAPE_HORIZONTAL = 1,
 35	OBJ_SHAPE_VERTICAL = 2
 36};
 37
 38union GBAOAM {
 39	struct {
 40		int y : 8;
 41		unsigned transformed : 1;
 42		union {
 43			unsigned doublesize : 1;
 44			unsigned disable : 1;
 45		};
 46		enum ObjMode mode : 2;
 47		unsigned mosaic : 1;
 48		unsigned multipalette : 1;
 49		enum ObjShape shape : 2;
 50
 51		int x : 9;
 52		union {
 53			unsigned matIndex : 5;
 54			struct {
 55				int : 3;
 56				unsigned hflip : 1;
 57				unsigned vflip : 1;
 58			};
 59		};
 60		unsigned size : 2;
 61
 62		unsigned tile : 10;
 63		unsigned priority : 2;
 64		unsigned palette : 4;
 65
 66		int : 16;
 67	} obj[128];
 68
 69	struct {
 70		int : 16;
 71		int : 16;
 72		int : 16;
 73		int a : 16;
 74		int : 16;
 75		int : 16;
 76		int : 16;
 77		int b : 16;
 78		int : 16;
 79		int : 16;
 80		int : 16;
 81		int c : 16;
 82		int : 16;
 83		int : 16;
 84		int : 16;
 85		int d : 16;
 86	} mat[32];
 87
 88	uint16_t raw[512];
 89};
 90
 91union GBATextMapData {
 92	struct {
 93		unsigned tile : 10;
 94		unsigned hflip : 1;
 95		unsigned vflip : 1;
 96		unsigned palette : 4;
 97	};
 98	uint16_t packed;
 99};
100
101union GBARegisterDISPCNT {
102	struct {
103		unsigned mode : 3;
104		unsigned cgb : 1;
105		unsigned frameSelect : 1;
106		unsigned hblankIntervalFree : 1;
107		unsigned objCharacterMapping : 1;
108		unsigned forcedBlank : 1;
109		unsigned bg0Enable : 1;
110		unsigned bg1Enable : 1;
111		unsigned bg2Enable : 1;
112		unsigned bg3Enable : 1;
113		unsigned objEnable : 1;
114		unsigned win0Enable : 1;
115		unsigned win1Enable : 1;
116		unsigned objwinEnable : 1;
117	};
118	uint16_t packed;
119};
120
121union GBARegisterBGCNT {
122	struct {
123		unsigned priority : 2;
124		unsigned charBase : 2;
125		unsigned : 2;
126		unsigned mosaic : 1;
127		unsigned multipalette : 1;
128		unsigned screenBase : 5;
129		unsigned overflow : 1;
130		unsigned size : 2;
131	};
132	uint16_t packed;
133};
134
135struct GBAVideoRenderer {
136	void (*init)(struct GBAVideoRenderer* renderer);
137	void (*deinit)(struct GBAVideoRenderer* renderer);
138
139	uint16_t (*writeVideoRegister)(struct GBAVideoRenderer* renderer, uint32_t address, uint16_t value);
140	void (*drawScanline)(struct GBAVideoRenderer* renderer, int y);
141	void (*finishFrame)(struct GBAVideoRenderer* renderer);
142
143	uint16_t* palette;
144	uint16_t* vram;
145	union GBAOAM* oam;
146
147	int framesPending;
148	int turbo;
149};
150
151struct GBAVideo {
152	struct GBA* p;
153	struct GBAVideoRenderer* renderer;
154
155	// DISPSTAT
156	int inHblank;
157	int inVblank;
158	int vcounter;
159	int vblankIRQ;
160	int hblankIRQ;
161	int vcounterIRQ;
162	int vcountSetting;
163
164	// VCOUNT
165	int vcount;
166
167	int32_t lastHblank;
168	int32_t nextHblank;
169	int32_t nextEvent;
170	int32_t eventDiff;
171
172	int32_t nextHblankIRQ;
173	int32_t nextVblankIRQ;
174	int32_t nextVcounterIRQ;
175
176	uint16_t palette[SIZE_PALETTE_RAM >> 1];
177	uint16_t vram[SIZE_VRAM >> 1];
178	union GBAOAM oam;
179};
180
181void GBAVideoInit(struct GBAVideo* video);
182void GBAVideoAssociateRenderer(struct GBAVideo* video, struct GBAVideoRenderer* renderer);
183int32_t GBAVideoProcessEvents(struct GBAVideo* video, int32_t cycles);
184
185void GBAVideoWriteDISPSTAT(struct GBAVideo* video, uint16_t value);
186uint16_t GBAVideoReadDISPSTAT(struct GBAVideo* video);
187
188#endif