From cbf5148b0ffbd979a807f035b472c0e48e4adf97 Mon Sep 17 00:00:00 2001 From: true Date: Sun, 5 Nov 2023 16:35:52 -0800 Subject: [PATCH] Toaster render fix, faster toasters with preload --- src/main.cpp | 95 ++++++++++++++++++++++++++++++++++------------------ 1 file changed, 63 insertions(+), 32 deletions(-) diff --git a/src/main.cpp b/src/main.cpp index 45b680f..9c90d51 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -14,12 +14,13 @@ extern "C" { #include "bmp.h" static BmpClass bmp; +File fbmp; #include "btn.h" -const char name[] = "true"; +const char name[] = "Your Name"; uint8_t fgprog = 1; // default uint8_t bgprog = 7; // programs @@ -42,17 +43,47 @@ uint8_t bgprog = 7; // programs #define LETTER_SPACING 1942 // user-configurable +#define MAX_TOASTERS 9 +#define TOAST_RANDOM 9 + Arduino_DataBus *bus = new Arduino_RPiPicoSPI(DISP_DC, DISP_NSS, SPI0_SCK, SPI0_MOSI, SPI0_MISO, spi0); Arduino_GFX *disp = new Arduino_GC9A01(bus, DISP_RESET, 0 /* rotation */, true /* IPS */); Arduino_Canvas *dout = new Arduino_Canvas(240 /* width */, 240 /* height */, disp); -Arduino_Canvas *drot = new Arduino_Canvas(ROT_SIZE, ROT_SIZE, disp); +Arduino_Canvas *drot = new Arduino_Canvas(ROT_SIZE, ROT_SIZE, NULL); +Arduino_Canvas *d64 = new Arduino_Canvas(64, 64, NULL); +Arduino_Canvas *toastbmp[6] = { + new Arduino_Canvas(64, 64, NULL), + new Arduino_Canvas(64, 64, NULL), + new Arduino_Canvas(64, 64, NULL), + new Arduino_Canvas(64, 64, NULL), + new Arduino_Canvas(64, 64, NULL), + new Arduino_Canvas(64, 64, NULL) +}; color_hsv hsv = {0, 255, 255}; color_rgb rgb; +uint8_t toast_cb_idx = 0; +static void bmp_cb(int16_t x, int16_t y, uint16_t *bitmap, int16_t w, int16_t h) +{ + uint16_t *src, *dst; + + // Serial.printf("Draw pos = %d, %d. size = %d x %d\n", x, y, w, h); + d64->draw16bitRGBBitmap(x, y, bitmap, w, h); + + // was having problems printing directly to the toastbmp buffer + // so rendering to temporary one and then copying + src = d64->getFramebuffer(); + dst = toastbmp[toast_cb_idx]->getFramebuffer(); + + for (x = 0; x < (64 * 64); x++) { + *dst++ = *src++; // [(x % 64) + ((x / 64) * ROT_SIZE)]; + } +} + void setup() { Serial.begin(115200); @@ -63,10 +94,8 @@ void setup() bus->begin(90000000); - if (!disp->begin()) { - Serial.println("failed to start disp"); - } - + disp->begin(); + dout->begin(); dout->fillScreen(BLACK); dout->flush(); @@ -74,6 +103,9 @@ void setup() drot->begin(); drot->setFont(u8g2_font_cubic11_h_cjk); // u8g2_font_spleen16x32_mr + d64->begin(); + d64->fillScreen(BLACK); + // buttons pinMode(SR_CLK, OUTPUT); pinMode(SR_DAT, OUTPUT); @@ -84,6 +116,22 @@ void setup() // filesystem LittleFS.begin(); + + // preload toasters + char fn[20]; + for (uint8_t i = 0; i < 6; i++) { + // start toast + toastbmp[i] = new Arduino_Canvas(64, 64, NULL); + toastbmp[i]->begin(); + toastbmp[i]->fillScreen(BLUE); // should not be visible + + // select toast file + sprintf(fn, "toast%i.bmp", i); + fbmp = LittleFS.open(fn, "r"); + toast_cb_idx = i; + bmp.draw(&fbmp, bmp_cb, false /* useBigEndian */, 0 /* x */, 0 /* y */, 64, 64); + fbmp.close(); + } } int16_t render_drot_printchar(const char *str, uint8_t idx, uint8_t size, uint16_t color) @@ -390,10 +438,6 @@ void bg_radarsweep(int16_t rot, int16_t offset, uint8_t lines) } -#define MAX_TOASTERS 5 -#define TOAST_RANDOM 9 - - struct Toasters { int16_t x; int16_t y; @@ -408,13 +452,7 @@ uint8_t toaster_count; uint8_t toaster_frametimer; -static void bmp_cb(int16_t x, int16_t y, uint16_t *bitmap, int16_t w, int16_t h) -{ - // Serial.printf("Draw pos = %d, %d. size = %d x %d\n", x, y, w, h); - drot->draw16bitRGBBitmap(x, y, bitmap, w, h); -} - -void print_toast(char *fn, int16_t out_x, int16_t out_y) +void print_toast(uint8_t idx, int16_t out_x, int16_t out_y) { int16_t x, y; int16_t nx, ny; @@ -423,25 +461,22 @@ void print_toast(char *fn, int16_t out_x, int16_t out_y) uint16_t src_pxl; - // framebuffer pointers - src = drot->getFramebuffer(); - dst = dout->getFramebuffer(); + uint8_t frame = toast[idx].frame; - // load toast file - File fbmp = LittleFS.open(fn, "r"); - bmp.draw(&fbmp, bmp_cb, false /* useBigEndian */, 0 /* x */, 0 /* y */, 64, 64); - fbmp.close(); + // framebuffer pointers + src = toastbmp[frame]->getFramebuffer(); + dst = dout->getFramebuffer(); // copy to destination with transparency for (y = 0; y < 64; y++) { for (x = 0; x < 64; x++) { - src_pxl = src[x + (y * ROT_SIZE)]; + src_pxl = src[x + (y * 64)]; if (src_pxl != TRANSPARENT_BG) { nx = x + out_x; ny = y + out_y; - if ((nx < 0) || (ny < 0)) break; - if ((nx >= 240) || (ny >= 240)) break; + if ((nx < 0) || (ny < 0)) continue; + if ((nx >= 240) || (ny >= 240)) continue; dst[nx + (ny*240)] = src_pxl; } @@ -482,8 +517,6 @@ void bg_toasters() } for (i = 0; i < MAX_TOASTERS; i++) { - char fn[20]; - switch (toast[i].type) { case 0: continue; case 1: { // normal toast @@ -491,13 +524,11 @@ void bg_toasters() // toast is toasted toast[i].type = 0; } else { - // select toast file - sprintf(fn, "toast%i.bmp", toast[i].frame); // move toast toast[i].x -= 3; toast[i].y += 2; - print_toast(fn, toast[i].x, toast[i].y); + print_toast(i, toast[i].x, toast[i].y); } } }