comparison vdp.c @ 40:7368a7071908

Broken window support
author Mike Pavone <pavone@retrodev.com>
date Sun, 09 Dec 2012 17:05:13 -0800
parents 3c69319269ef
children e591004487bc
comparison
equal deleted inserted replaced
39:3c69319269ef 40:7368a7071908
13 #define BIT_PAL 0x8 13 #define BIT_PAL 0x8
14 #define BIT_H40 0x1 14 #define BIT_H40 0x1
15 15
16 #define SCROLL_BUFFER_SIZE 32 16 #define SCROLL_BUFFER_SIZE 32
17 #define SCROLL_BUFFER_DRAW 16 17 #define SCROLL_BUFFER_DRAW 16
18
19 #define FLAG_DOT_OFLOW 0x1
20 #define FLAG_CAN_MASK 0x2
21 #define FLAG_MASKED 0x4
22 #define FLAG_WINDOW 0x8
18 23
19 void init_vdp_context(vdp_context * context) 24 void init_vdp_context(vdp_context * context)
20 { 25 {
21 memset(context, 0, sizeof(context)); 26 memset(context, 0, sizeof(context));
22 context->vdpmem = malloc(VRAM_SIZE); 27 context->vdpmem = malloc(VRAM_SIZE);
98 context->sprite_index = context->vdpmem[address+3] & 0x7F; 103 context->sprite_index = context->vdpmem[address+3] & 0x7F;
99 } 104 }
100 } 105 }
101 } 106 }
102 107
103 #define FLAG_DOT_OFLOW 0x1
104 #define FLAG_CAN_MASK 0x2
105 #define FLAG_MASKED 0x4
106 void read_sprite_x(uint32_t line, vdp_context * context) 108 void read_sprite_x(uint32_t line, vdp_context * context)
107 { 109 {
108 if (context->cur_slot >= context->slot_counter) { 110 if (context->cur_slot >= context->slot_counter) {
109 if (context->sprite_draws) { 111 if (context->sprite_draws) {
110 line += 1; 112 line += 1;
169 void external_slot(vdp_context * context) 171 void external_slot(vdp_context * context)
170 { 172 {
171 //TODO: Implement me 173 //TODO: Implement me
172 } 174 }
173 175
176 #define WINDOW_RIGHT 0x80
177 #define WINDOW_DOWN 0x80
178 #define ALWAYS_WINDOW 0
179
174 void read_map_scroll(uint16_t column, uint16_t vsram_off, uint32_t line, uint16_t address, uint16_t hscroll_val, vdp_context * context) 180 void read_map_scroll(uint16_t column, uint16_t vsram_off, uint32_t line, uint16_t address, uint16_t hscroll_val, vdp_context * context)
175 { 181 {
182 if (!vsram_off) {
183 uint16_t left_col, right_col;
184 #if ALWAYS_WINDOW
185 left_col = 0; right_col = 42;
186 uint16_t top_line, bottom_line;
187 top_line = 0; bottom_line = 241;
188 #else
189 if (context->regs[REG_WINDOW_H] & WINDOW_RIGHT) {
190 left_col = 0;
191 right_col = (context->regs[REG_WINDOW_H] & 0x1F) * 2;
192 if (right_col) {
193 right_col += 2;
194 }
195 } else {
196 left_col = (context->regs[REG_WINDOW_H] & 0x1F) * 2;
197 right_col = 42;
198 }
199 if (column >= left_col && column < right_col) {
200 uint16_t top_line, bottom_line;
201 if (context->regs[REG_WINDOW_V] & WINDOW_DOWN) {
202 top_line = (context->regs[REG_WINDOW_V] & 0x1F) * 8;
203 bottom_line = 241;
204 } else {
205 top_line = 0;
206 bottom_line = (context->regs[REG_WINDOW_V] & 0x1F) * 8;
207 }
208 if (line >= top_line && line < bottom_line) {
209 #endif
210 uint16_t address = context->regs[REG_WINDOW] << 10;
211 uint16_t line_offset, offset, mask;
212 if (context->latched_mode & BIT_H40) {
213 address &= 0xF000;
214 line_offset = (((line/* - top_line */) / 8) * 64 * 2) & 0xFFF;
215 mask = 0x7F;
216
217 } else {
218 address &= 0xF800;
219 line_offset = (((line/* - top_line*/) / 8) * 32 * 2) & 0xFFF;
220 mask = 0x3F;
221 }
222 offset = address + line_offset + (((column - 2/* - left_col*/) * 2) & mask);
223 context->col_1 = (context->vdpmem[offset] << 8) | context->vdpmem[offset+1];
224 printf("Window | top: %d, bot: %d, left: %d, right: %d, base: %X, line: %X offset: %X, tile: %X, reg: %X\n", top_line, bottom_line, left_col, right_col, address, line_offset, offset, ((context->col_1 & 0x3FF) << 5), context->regs[REG_WINDOW]);
225 offset = address + line_offset + (((column - 1/* - left_col*/) * 2) & mask);
226 context->col_2 = (context->vdpmem[offset] << 8) | context->vdpmem[offset+1];
227 context->v_offset = (line/* - top_line*/) & 0x7;
228 context->flags |= FLAG_WINDOW;
229 return;
230 #if !ALWAYS_WINDOW
231 }
232 }
233 context->flags &= ~FLAG_WINDOW;
234 #endif
235
236 }
176 uint16_t vscroll; 237 uint16_t vscroll;
177 switch(context->regs[REG_SCROLL] & 0x30) 238 switch(context->regs[REG_SCROLL] & 0x30)
178 { 239 {
179 case 0: 240 case 0:
180 vscroll = 0xFF; 241 vscroll = 0xFF;
291 if (col) 352 if (col)
292 { 353 {
293 col-=2; 354 col-=2;
294 dst = context->framebuf + line * 320 + col * 8; 355 dst = context->framebuf + line * 320 + col * 8;
295 sprite_buf = context->linebuf + col * 8; 356 sprite_buf = context->linebuf + col * 8;
296 plane_a = context->tmp_buf_a + SCROLL_BUFFER_DRAW - (context->hscroll_a & 0xF); 357 if (context->flags & FLAG_WINDOW) {
358 plane_a = context->tmp_buf_a + SCROLL_BUFFER_DRAW;
359 } else {
360 plane_a = context->tmp_buf_a + SCROLL_BUFFER_DRAW - (context->hscroll_a & 0xF);
361 }
297 plane_b = context->tmp_buf_b + SCROLL_BUFFER_DRAW - (context->hscroll_b & 0xF); 362 plane_b = context->tmp_buf_b + SCROLL_BUFFER_DRAW - (context->hscroll_b & 0xF);
298 end = dst + 16; 363 end = dst + 16;
299 //printf("A | tmp_buf offset: %d\n", 8 - (context->hscroll_a & 0x7)); 364 //printf("A | tmp_buf offset: %d\n", 8 - (context->hscroll_a & 0x7));
300 for (; dst < end; ++plane_a, ++plane_b, ++sprite_buf, ++dst) { 365 for (; dst < end; ++plane_a, ++plane_b, ++sprite_buf, ++dst) {
301 uint8_t pixel; 366 uint8_t pixel;
322 //plane_a = context->tmp_buf_a + 16 - (context->hscroll_a & 0x7); 387 //plane_a = context->tmp_buf_a + 16 - (context->hscroll_a & 0x7);
323 //plane_b = context->tmp_buf_b + 16 - (context->hscroll_b & 0x7); 388 //plane_b = context->tmp_buf_b + 16 - (context->hscroll_b & 0x7);
324 //end = dst + 8; 389 //end = dst + 8;
325 } 390 }
326 391
327 uint16_t remaining = context->hscroll_a & 0xF; 392 uint16_t remaining;
328 memcpy(context->tmp_buf_a + SCROLL_BUFFER_DRAW - remaining, context->tmp_buf_a + SCROLL_BUFFER_SIZE - remaining, remaining); 393 if (!(context->flags & FLAG_WINDOW)) {
394 remaining = context->hscroll_a & 0xF;
395 memcpy(context->tmp_buf_a + SCROLL_BUFFER_DRAW - remaining, context->tmp_buf_a + SCROLL_BUFFER_SIZE - remaining, remaining);
396 }
329 remaining = context->hscroll_b & 0xF; 397 remaining = context->hscroll_b & 0xF;
330 memcpy(context->tmp_buf_b + SCROLL_BUFFER_DRAW - remaining, context->tmp_buf_b + SCROLL_BUFFER_SIZE - remaining, remaining); 398 memcpy(context->tmp_buf_b + SCROLL_BUFFER_DRAW - remaining, context->tmp_buf_b + SCROLL_BUFFER_SIZE - remaining, remaining);
331 } 399 }
332 400
333 #define COLUMN_RENDER_BLOCK(column, startcyc) \ 401 #define COLUMN_RENDER_BLOCK(column, startcyc) \