Author: mesyeti <mesyeti@mesyeti.uk>
refactor the way changed cells are detected
source/app.c | 2 +- source/backend.h | 2 -- source/backends/soft.c | 26 ++------------------------ source/backends/stub.c | 11 ----------- source/buffer.c | 24 +++--------------------- source/buffer.h | 1 - source/interpreter/vt100.c | 6 +++--- source/screen.c | 38 ++++++++++++++------------------------ source/screen.h | 1 +
diff --git a/source/app.c b/source/app.c index 61a9771ed4e29c3c33e456da4f4e80b0389e7843..ed4ce6eed5076ca7154a7c24cb3bd014cc3d918b 100644 --- a/source/app.c +++ b/source/app.c @@ -86,7 +86,7 @@ Rect within = {0, 1, screen.buffer.width, screen.buffer.height - 1}; Pane_Render(&app.tabs[app.tabSel], within); - Backend_Render(); + Screen_Render(); oldFrameTime = newFrameTime; } diff --git a/source/backend.h b/source/backend.h index cdb23f1a85e28156272be8bc6a92bb95a6bd419b..4dadee10dceace2eaaa7d001f520a7fc7cb60b33 100644 --- a/source/backend.h +++ b/source/backend.h @@ -38,8 +38,6 @@ Texture* Backend_LoadTexture(uint8_t* data, int w, int h, int aW, int aH, int ch); void Backend_FreeTexture(Texture* texture); Vec2 Backend_GetTextureSize(Texture* texture); void Backend_OnWindowResize(void); -void Backend_OnScreenUpdate(void); -void Backend_OnCellChange(int x, int y); void Backend_Render(void); #endif diff --git a/source/backends/soft.c b/source/backends/soft.c index 15d93abf719315ee6a9e80623cf70aa0aba6b225..33709c93f12e00e613b13a101abe2c91f93aa7c4 100644 --- a/source/backends/soft.c +++ b/source/backends/soft.c @@ -23,7 +23,6 @@ BTexture textures[32]; uint32_t* buffer; int bufferW; int bufferH; - bool* changes; bool redraw; // SDL stuff @@ -82,8 +81,7 @@ state.buffer = SafeMalloc(video.windows[0].width * video.windows[0].height * sizeof(uint32_t)); state.bufferW = video.windows[0].width; state.bufferH = video.windows[0].height; - - state.changes = NULL; + state.redraw = true; } static void Free(void) { @@ -137,18 +135,6 @@ static void OnWindowResize(void) { } -static void OnScreenUpdate(void) { - if (!state.changes) { - free(state.changes); - } - - size_t size = screen.buffer.width * screen.buffer.height * sizeof(bool); - state.changes = SafeMalloc(size); - memset(state.changes, 0, size); - - state.redraw = true; -} - static void FillRect(int x, int y, int w, int h, Colour colour) { for (int iy = 0; iy < h; ++ iy) { for (int ix = 0; ix < w; ++ ix) { @@ -180,10 +166,6 @@ DrawPixel(ix + x, iy + y, srcPix); } } -} - -static void OnCellChange(int x, int y) { - state.changes[(y * screen.buffer.width) + x] = true; } static void Render(void) { @@ -199,9 +181,7 @@ Font_CharSize(&screen.font, &cw, &ch); for (int y = 0; y < screen.buffer.height; ++ y) { for (int x = 0; x < screen.buffer.width; ++ x) { - if (!state.changes[(y * screen.buffer.width) + x] && !state.redraw) continue; - - state.changes[(y * screen.buffer.width) + x] = false; + if (!Screen_CellChanged(x, y) && !state.redraw) continue; int cx = x * cw; int cy = y * ch; @@ -244,8 +224,6 @@ .loadTexture = &LoadTexture, .freeTexture = &FreeTexture, .getTextureSize = &GetTextureSize, .onWindowResize = &OnWindowResize, - .onScreenUpdate = &OnScreenUpdate, - .onCellChange = &OnCellChange, .render = &Render }; } diff --git a/source/backends/stub.c b/source/backends/stub.c index edad0a2e87c592fdade2d35c224ce2e789f300ad..57288d847ddb4b49033187c7fa7e981dbb507db0 100644 --- a/source/backends/stub.c +++ b/source/backends/stub.c @@ -33,15 +33,6 @@ static void OnWindowResize(void) { } -static void OnScreenUpdate(void) { - -} - -static void OnCellChange(int x, int y) { - (void) x; - (void) y; -} - static void Render(void) { } @@ -55,8 +46,6 @@ .loadTexture = &LoadTexture, .freeTexture = &FreeTexture, .getTextureSize = &GetTextureSize, .onWindowResize = &OnWindowResize, - .onScreenUpdate = &OnScreenUpdate, - .onCellChange = &OnCellChange, .render = &Render }; } diff --git a/source/buffer.c b/source/buffer.c index ebf1c839d295a74f3a3bd20de5deb5f04398ea66..6a4ddbe6f52732a937927eb3c749ef0385eb6a26 100644 --- a/source/buffer.c +++ b/source/buffer.c @@ -1,6 +1,5 @@ #include "mem.h" #include "buffer.h" -#include "backend.h" BufAttr BufAttr_Default(void) { return (BufAttr) { @@ -25,9 +24,8 @@ for (int i = 0; i < width * height; ++ i) { ret.buf[i] = FromChar(0); } - ret.width = width; - ret.height = height; - ret.isScreenBuf = false; + ret.width = width; + ret.height = height; return ret; } @@ -77,13 +75,7 @@ BufCell* ptr = Buffer_Get(buf, x, y); if (!ptr) return; - bool change = !Buffer_CellEq(*ptr, cell); - *ptr = cell; - - if (buf->isScreenBuf && change) { - Backend_OnCellChange(x, y); - } } void Buffer_InvertCell(Buffer* buf, int x, int y) { @@ -92,10 +84,6 @@ if (!cell) return; cell->attr.invert = !cell->attr.invert; - - if (buf->isScreenBuf) { - Backend_OnCellChange(x, y); - } } void Buffer_Clear(Buffer* buf) { @@ -118,13 +106,7 @@ int sx = ix + clip.x; int sy = iy + clip.y; - BufCell* cell = Buffer_Get(src, sx, sy); - - if (!Buffer_CellEq(*Buffer_Get(dest, x + ix, y + iy), *cell) && dest->isScreenBuf) { - Backend_OnCellChange(x + ix, y + iy); - } - - *Buffer_Get(dest, x + ix, y + iy) = *cell; + *Buffer_Get(dest, x + ix, y + iy) = *Buffer_Get(src, sx, sy); } } } diff --git a/source/buffer.h b/source/buffer.h index bfa2934a736b262bc1b474e2d6356df951a81d16..d3938aa7002ba9202e0531c06e16122b4b2b0207 100644 --- a/source/buffer.h +++ b/source/buffer.h @@ -34,7 +34,6 @@ typedef struct { BufCell* buf; int width; int height; - bool isScreenBuf; } Buffer; BufAttr BufAttr_Default(void); diff --git a/source/interpreter/vt100.c b/source/interpreter/vt100.c index 61efd0007b01821f2166967890f5d5d73bba65bd..c892111233fb9638d0f72f65d1c562b883d992d4 100644 --- a/source/interpreter/vt100.c +++ b/source/interpreter/vt100.c @@ -229,7 +229,7 @@ case 1002: break; // TODO: use cell motion mouse tracking case 1003: break; // TODO: use all motion mouse tracking case 1048: break; // TODO: save cursor case 1049: break; // TODO: save cursor & use alternate screen buffer - default: printf("Unsupported: %sh\n", param); + default: printf("Unsupported: %dh\n", param); } break; } @@ -244,13 +244,13 @@ case 12: terminal->blinkCursor = false; break; case 25: terminal->showCursor = false; break; case 1047: case 47: break; // TODO: use normal screen buffer - case 1000: this->mouseMode = OFF; break; + case 1000: this->mouseMode = MOUSE_OFF; break; case 1001: break; // TODO: do not use hilite motion mouse tracking case 1002: break; // TODO: do not use cell motion mouse tracking case 1003: break; // TODO: do not use all motion mouse tracking case 1048: break; // TODO: restore cursor case 1049: break; // TODO: restore cursor & use normal screen buffer - default: printf("Unsupported: %sh\n", param); + default: printf("Unsupported: %dl\n", param); } break; } diff --git a/source/screen.c b/source/screen.c index 14d103107708a433917451be47d1ad8a99b3fea5..8155d07e2a0200f3bb47530e224741114784de5c 100644 --- a/source/screen.c +++ b/source/screen.c @@ -26,9 +26,6 @@ Font_CharSize(&screen.font, &cw, &ch); screen.old = Buffer_New(video.windows[0].width / cw, video.windows[0].height / ch); screen.buffer = Buffer_New(video.windows[0].width / cw, video.windows[0].height / ch); - screen.buffer.isScreenBuf = true; - - Backend_OnScreenUpdate(); } void Screen_Free(void) { @@ -47,26 +44,19 @@ assert(0); } +bool Screen_CellChanged(int x, int y) { + BufCell* a = Buffer_Get(&screen.old, x, y); + BufCell* b = Buffer_Get(&screen.buffer, x, y); + + if (!a || !b) return false; + + return !Buffer_CellEq(*a, *b); +} + void Screen_Render(void) { -// int cw; -// int ch; -// Font_CharSize(&screen.font, &cw, &ch); -// -// for (int y = 0; y < screen.buffer.height; ++ y) { -// for (int x = 0; x < screen.buffer.width; ++ x) { -// int cx = x * cw; -// int cy = y * ch; -// -// BufCell* cell = Buffer_Get(&screen.buffer, x, y); -// -// ColourRGB fg = GetColour(true, cell->fgMode, cell->fg); -// ColourRGB bg = GetColour(false, cell->bgMode, cell->bg); -// -// Rect rect = {cx, cy, cw, ch}; -// Colour c = (Colour) {bg.r, bg.g, bg.b, 255}; -// Backend_RenderRect(rect, c); -// -// Font_RenderChar(&screen.font, cell->ch, cx, cy, fg); -// } -// } + Backend_Render(); + + Rect clip = {0, 0, screen.buffer.width, screen.buffer.height}; + + Buffer_Blit(&screen.old, &screen.buffer, 0, 0, clip); } diff --git a/source/screen.h b/source/screen.h index 1a374cc7276b63743f654f4fcde10f14f5d4c500..acd3e07ce8a6eb3c06a9e7cc8cc2da351508d8f3 100644 --- a/source/screen.h +++ b/source/screen.h @@ -15,6 +15,7 @@ void Screen_Init(void); void Screen_Free(void); ColourRGB Screen_GetColour(bool fg, uint8_t mode, BufCol col); +bool Screen_CellChanged(int x, int y); void Screen_Render(void); #endif