#include "sim_display.h" #include "graphics.h" #include #define GET_BIT(x, bit) ((x & (1 << bit)) >> bit) uint32_t RGB565_to_RGB888(uint16_t rgb565, bool isBGR) { uint8_t r5 = (rgb565 >> 11) & 0x1F; uint8_t g6 = (rgb565 >> 5) & 0x3F; uint8_t b5 = rgb565 & 0x1F; uint8_t r8 = (r5 * 527 + 23) >> 6; uint8_t g8 = (g6 * 259 + 33) >> 6; uint8_t b8 = (b5 * 527 + 23) >> 6; if (isBGR) { return (b8 << 16) | (g8 << 8) | r8; } else { return (r8 << 16) | (g8 << 8) | b8; } } #ifndef USER_SDL3 static uint32_t pixelColor, backgroundColor; static int scaleFactor, w, h; uint8_t border; void SIM_Display_INIT(int width, int height, uint32_t pixcolor, uint32_t backcolor, int scale, uint8_t b) { w = width * scale; h = height * scale; pixelColor = pixcolor; backgroundColor = backcolor; scaleFactor = scale; border = b; } void SIM_Display_START() { initgraph(w, h); setbkcolor(backgroundColor); setfillcolor(pixelColor); cleardevice(); } void SIM_Display_STOP() { closegraph(); } void drawPixel(int oledX, int oledY) { int startX = oledX * scaleFactor; int startY = oledY * scaleFactor; if (border) fillrectangle(startX + 1, startY + 1, startX + scaleFactor - 1, startY + scaleFactor - 1); else solidrectangle(startX, startY, startX + scaleFactor, startY + scaleFactor); } void SIM_OneColor_DrawFromBuffer(uint8_t* buf, uint16_t width, uint16_t height) { BeginBatchDraw(); cleardevice(); for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { uint8_t byteData = buf[y * width + x]; for (int i = 0; i < 8; i++) { uint8_t bit = GET_BIT(byteData, i); if (bit)drawPixel(x, y * 8 + i); } } } EndBatchDraw(); } void SIM_Color_DrawPiexl(uint32_t buf, uint16_t x, uint16_t y) { BeginBatchDraw(); // cleardevice(); setfillcolor(buf); drawPixel(x, y); EndBatchDraw(); } void SIM_Color_DrawHLineBuffer(uint32_t *buf, uint16_t x, uint16_t y, uint16_t width) { BeginBatchDraw(); // cleardevice(); for (int x_ = 0; x_ < width; x_++) { setfillcolor(*buf); drawPixel(x + x_, y); buf++; } EndBatchDraw(); } void SIM_Color_DrawFromBuffer(uint32_t* buf, uint16_t width, uint16_t height) { BeginBatchDraw(); cleardevice(); for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { setfillcolor(*buf); drawPixel(x, y); buf++; } } EndBatchDraw(); } void SIM_Color_ImgFromBuffer(uint32_t* buf, uint16_t x, uint16_t y, uint16_t width, uint16_t height) { BeginBatchDraw(); // cleardevice(); for (int y_i = 0; y_i < height; y_i++) { for (int x_i = 0; x_i < width; x_i++) { setfillcolor(*buf); drawPixel(x + x_i, y + y_i); buf++; } } EndBatchDraw(); } void SIM_Color_FillFromBuffer(uint32_t* buf, uint16_t xs, uint16_t ys, uint16_t xe, uint16_t ye) { BeginBatchDraw(); // cleardevice(); for (int y_i = ys; y_i < ye; y_i++) { for (int x_i = xs; x_i < xe; x_i++) { setfillcolor(*buf); drawPixel(x_i, y_i); buf++; } } EndBatchDraw(); } #else bool SIM_Display_Init(char *name, int width, int height, uint32_t pixcolor, uint32_t backcolor, int scale, SIM_Display_t *display) { if (SDL_Init(SDL_INIT_VIDEO) < 0) { SDL_Log("SDL_Init failed: %s", SDL_GetError()); return false; } display->scale = scale; display->pixelcolor.full = pixcolor; display->backcolor.full = backcolor; display->window = SDL_CreateWindow(name, width * scale, height * scale, SDL_WINDOW_RESIZABLE); if (!display->window) { SDL_Log("Could not create a window: %s", SDL_GetError()); return false; } SDL_SetWindowPosition(display->window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED); display->renderer = SDL_CreateRenderer(display->window, nullptr); if (!display->renderer) { SDL_Log("Create renderer failed: %s", SDL_GetError()); return false; } SDL_SetRenderDrawColor(display->renderer, 0, 0, 0, 0); SDL_RenderClear(display->renderer); return true; } void SIM_Color_DrawPiexl(SIM_Display_t *display, SIM_Color_t color, uint16_t x, uint16_t y) { SDL_SetRenderDrawColor(display->renderer, color.ch.red, color.ch.green, color.ch.blue, color.ch.alpha); for (int y_ = y * display->scale; y_ < (y * display->scale) + display->scale; ++y_) { for (int x_ = x * display->scale; x_ < (x * display->scale) + display->scale; ++x_) { SDL_RenderPoint(display->renderer, x_, y_); } } } void SIM_OneColor_DrawFromBuffer(SIM_Display_t *display, uint8_t *buf, uint16_t width, uint16_t height) { SIM_Color_t color; for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { uint8_t byteData = buf[y * width + x]; for (int i = 0; i < 8; i++) { uint8_t bit = GET_BIT(byteData, i); if (bit)color = display->pixelcolor; else color = display->backcolor; SIM_Color_DrawPiexl(display, color, x, y * 8 + i); } } } SDL_RenderPresent(display->renderer); } void SIM_Color_ImgFromBuffer(SIM_Display_t *display, uint32_t *buf, uint16_t x, uint16_t y, uint16_t width, uint16_t height) { SIM_Color_t color; for (int y_i = 0; y_i < height; y_i++) { for (int x_i = 0; x_i < width; x_i++) { color.full = *buf; SIM_Color_DrawPiexl(display, color, x + x_i, y + y_i); buf++; } } SDL_RenderPresent(display->renderer); } void SIM_Color_FillFromBuffer(SIM_Display_t *display, uint32_t *buf, uint16_t xs, uint16_t ys, uint16_t xe, uint16_t ye) { SIM_Color_t color; for (int y_i = ys; y_i < ye; y_i++) { for (int x_i = xs; x_i < xe; x_i++) { color.full = *buf; SIM_Color_DrawPiexl(display, color, x_i, y_i); buf++; } } SDL_RenderPresent(display->renderer); } void SIM_Display_STOP(SIM_Display_t *display) { SDL_DestroyRenderer(display->renderer); SDL_DestroyWindow(display->window); SDL_Quit(); } #endif