Standardized screen device to the SDL version

This commit is contained in:
Devine Lu Linvega 2023-04-10 14:13:41 -07:00
parent adc0ccdad4
commit ed588f9190
3 changed files with 30 additions and 39 deletions

View File

@ -4,7 +4,7 @@
#include "screen.h" #include "screen.h"
/* /*
Copyright (c) 2021 Devine Lu Linvega, Andrew Alderwick Copyright (c) 2021-2023 Devine Lu Linvega, Andrew Alderwick
Permission to use, copy, modify, and distribute this software for any Permission to use, copy, modify, and distribute this software for any
purpose with or without fee is hereby granted, provided that the above purpose with or without fee is hereby granted, provided that the above
@ -16,12 +16,11 @@ WITH REGARD TO THIS SOFTWARE.
UxnScreen uxn_screen; UxnScreen uxn_screen;
static Uint8 blending[5][16] = { static Uint8 blending[4][16] = {
{0, 0, 0, 0, 1, 0, 1, 1, 2, 2, 0, 2, 3, 3, 3, 0}, {0, 0, 0, 0, 1, 0, 1, 1, 2, 2, 0, 2, 3, 3, 3, 0},
{0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3}, {0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3},
{1, 2, 3, 1, 1, 2, 3, 1, 1, 2, 3, 1, 1, 2, 3, 1}, {1, 2, 3, 1, 1, 2, 3, 1, 1, 2, 3, 1, 1, 2, 3, 1},
{2, 3, 1, 2, 2, 3, 1, 2, 2, 3, 1, 2, 2, 3, 1, 2}, {2, 3, 1, 2, 2, 3, 1, 2, 2, 3, 1, 2, 2, 3, 1, 2}};
{1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 0}};
static void static void
screen_write(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 color) screen_write(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 color)
@ -35,12 +34,21 @@ screen_write(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 color)
} }
} }
static void
screen_wipe(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y)
{
int v, h;
for(v = 0; v < 8; v++)
for(h = 0; h < 8; h++)
screen_write(p, layer, x + h, y + v, 0);
}
static void static void
screen_blit(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 color, Uint8 flipx, Uint8 flipy, Uint8 twobpp) screen_blit(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 *sprite, Uint8 color, Uint8 flipx, Uint8 flipy, Uint8 twobpp)
{ {
int v, h, opaque = blending[4][color]; int v, h, opaque = (color % 5) || !color;
for(v = 0; v < 8; v++) { for(v = 0; v < 8; v++) {
Uint16 c = sprite[v] | (twobpp ? sprite[v + 8] : 0) << 8; Uint16 c = sprite[v] | (twobpp ? (sprite[v + 8] << 8) : 0);
for(h = 7; h >= 0; --h, c >>= 1) { for(h = 7; h >= 0; --h, c >>= 1) {
Uint8 ch = (c & 1) | ((c >> 7) & 2); Uint8 ch = (c & 1) | ((c >> 7) & 2);
if(opaque || ch) if(opaque || ch)
@ -53,24 +61,6 @@ screen_blit(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y, Uint8 *sprite, Uint8
} }
} }
static void
screen_wipe(UxnScreen *p, Layer *layer, Uint16 x, Uint16 y)
{
int v, h;
for(v = 0; v < 8; v++)
for(h = 0; h < 8; h++)
screen_write(p, layer, x + h, y + v, 0);
}
static void
layer_clear(UxnScreen *p, Layer *layer)
{
Uint32 i, size = p->width * p->height;
for(i = 0; i < size; i++)
layer->pixels[i] = 0x00;
layer->changed = 1;
}
void void
screen_palette(UxnScreen *p, Uint8 *addr) screen_palette(UxnScreen *p, Uint8 *addr)
{ {
@ -100,15 +90,18 @@ screen_resize(UxnScreen *p, Uint16 width, Uint16 height)
if(bg && fg && pixels) { if(bg && fg && pixels) {
p->width = width; p->width = width;
p->height = height; p->height = height;
screen_clear(p); screen_clear(p, &p->bg);
screen_clear(p, &p->fg);
} }
} }
void void
screen_clear(UxnScreen *p) screen_clear(UxnScreen *p, Layer *layer)
{ {
layer_clear(p, &p->bg); Uint32 i, size = p->width * p->height;
layer_clear(p, &p->fg); for(i = 0; i < size; i++)
layer->pixels[i] = 0x00;
layer->changed = 1;
} }
void void

View File

@ -25,7 +25,7 @@ extern UxnScreen uxn_screen;
void screen_palette(UxnScreen *p, Uint8 *addr); void screen_palette(UxnScreen *p, Uint8 *addr);
void screen_resize(UxnScreen *p, Uint16 width, Uint16 height); void screen_resize(UxnScreen *p, Uint16 width, Uint16 height);
void screen_clear(UxnScreen *p); void screen_clear(UxnScreen *p, Layer *layer);
void screen_redraw(UxnScreen *p, Uint32 *pixels); void screen_redraw(UxnScreen *p, Uint32 *pixels);
Uint8 screen_dei(Uxn *u, Uint8 addr); Uint8 screen_dei(Uxn *u, Uint8 addr);

View File

@ -46,7 +46,7 @@ Uint16 dei_mask[] = {0x0000, 0x0000, 0x003c, 0x0014, 0x0014, 0x0014, 0x0014, 0x0
static int static int
emu_error(char *msg, const char *err) emu_error(char *msg, const char *err)
{ {
fprintf(stderr, "Error %s: %s\n", msg, err); fprintf(stderr, "%s: %s\n", msg, err);
return 0; return 0;
} }
@ -91,9 +91,8 @@ emu_start(Uxn *u, char *rom)
return 0; return 0;
if(!uxn_screen.width || !uxn_screen.height) if(!uxn_screen.width || !uxn_screen.height)
screen_resize(&uxn_screen, WIDTH, HEIGHT); screen_resize(&uxn_screen, WIDTH, HEIGHT);
screen_clear(&uxn_screen);
if(!uxn_eval(u, PAGE_PROGRAM)) if(!uxn_eval(u, PAGE_PROGRAM))
return emu_error("Boot", "Failed to start rom."); return emu_error("boot", "Failed to start rom.");
return 1; return 1;
} }
@ -189,7 +188,7 @@ display_start(char *title)
visual = DefaultVisual(display, 0); visual = DefaultVisual(display, 0);
window = XCreateSimpleWindow(display, RootWindow(display, 0), 0, 0, uxn_screen.width + PAD * 2, uxn_screen.height + PAD * 2, 1, 0, 0); window = XCreateSimpleWindow(display, RootWindow(display, 0), 0, 0, uxn_screen.width + PAD * 2, uxn_screen.height + PAD * 2, 1, 0, 0);
if(visual->class != TrueColor) if(visual->class != TrueColor)
return emu_error("Init", "True-color visual failed"); return emu_error("init", "True-color visual failed");
XSelectInput(display, window, ButtonPressMask | ButtonReleaseMask | PointerMotionMask | ExposureMask | KeyPressMask | KeyReleaseMask); XSelectInput(display, window, ButtonPressMask | ButtonReleaseMask | PointerMotionMask | ExposureMask | KeyPressMask | KeyReleaseMask);
wmDelete = XInternAtom(display, "WM_DELETE_WINDOW", True); wmDelete = XInternAtom(display, "WM_DELETE_WINDOW", True);
XSetWMProtocols(display, window, &wmDelete, 1); XSetWMProtocols(display, window, &wmDelete, 1);
@ -210,15 +209,15 @@ main(int argc, char **argv)
struct pollfd fds[3]; struct pollfd fds[3];
static const struct itimerspec screen_tspec = {{0, 16666666}, {0, 16666666}}; static const struct itimerspec screen_tspec = {{0, 16666666}, {0, 16666666}};
if(argc < 2) if(argc < 2)
return emu_error("Usage", "uxn11 game.rom args"); return emu_error("usage", "uxn11 game.rom args");
rom_path = argv[1]; rom_path = argv[1];
if(!uxn_boot(&u, (Uint8 *)calloc(0x10000 * RAM_PAGES, sizeof(Uint8)))) if(!uxn_boot(&u, (Uint8 *)calloc(0x10000 * RAM_PAGES, sizeof(Uint8))))
return emu_error("Boot", "Failed"); return emu_error("boot", "Failed");
/* start sequence */ /* start sequence */
if(!emu_start(&u, rom_path)) if(!emu_start(&u, rom_path))
return emu_error("Start", rom_path); return emu_error("start", rom_path);
if(!display_start(rom_path)) if(!display_start(rom_path))
return emu_error("Display", "Failed"); return emu_error("display", "Failed");
/* console vector */ /* console vector */
for(i = 2; i < argc; i++) { for(i = 2; i < argc; i++) {
char *p = argv[i]; char *p = argv[i];
@ -244,9 +243,8 @@ main(int argc, char **argv)
if((fds[2].revents & POLLIN) != 0) { if((fds[2].revents & POLLIN) != 0) {
n = read(fds[2].fd, coninp, CONINBUFSIZE - 1); n = read(fds[2].fd, coninp, CONINBUFSIZE - 1);
coninp[n] = 0; coninp[n] = 0;
for(i = 0; i < n; i++) { for(i = 0; i < n; i++)
console_input(&u, coninp[i]); console_input(&u, coninp[i]);
}
} }
if(uxn_screen.fg.changed || uxn_screen.bg.changed) if(uxn_screen.fg.changed || uxn_screen.bg.changed)
emu_draw(); emu_draw();