| @@ -49,6 +49,8 @@ struct swwApp | |||
| { | |||
| struct termios term; | |||
| uint8_t* fb; | |||
| int fbfd; | |||
| int xres; | |||
| int yres; | |||
| @@ -68,12 +70,15 @@ struct swwWindow | |||
| { | |||
| swwImage* surface; | |||
| /* Poistion on display(framebuffer) */ | |||
| uint32_t x, y; | |||
| /* common data */ | |||
| swwWindowCallback callback; | |||
| void* userdata; | |||
| }; | |||
| swwApp g_app = {{0}, 0, 0, 0, 0, 0, NULL, {-1}, 0, {0}, {0}}; | |||
| swwApp g_app = {{0}, NULL, 0, 0, 0, 0, 0, NULL, {-1}, 0, {0}, {0}}; | |||
| /* Signal Handler */ | |||
| typedef enum | |||
| @@ -291,8 +296,6 @@ void swwApp_Initialize() | |||
| // EnableRawMode(); | |||
| struct fb_var_screeninfo vinfo; | |||
| struct fb_fix_screeninfo finfo; | |||
| long int screensize = 0; | |||
| char* fbp = 0; | |||
| g_app.fbfd = open("/dev/fb0", O_RDWR); | |||
| if (g_app.fbfd == -1) { | |||
| @@ -315,6 +318,13 @@ void swwApp_Initialize() | |||
| exit(4); | |||
| } | |||
| g_app.fb = (uint8_t*)mmap(0, g_app.xres * g_app.yres * 4, PROT_READ | PROT_WRITE, MAP_SHARED, | |||
| g_app.fbfd, 0); | |||
| if (g_app.fb == (void*)-1) { | |||
| perror("Error: failed to map framebuffer device to memory"); | |||
| exit(5); | |||
| } | |||
| g_app.xres = vinfo.xres; | |||
| g_app.yres = vinfo.yres; | |||
| @@ -354,6 +364,8 @@ void swwApp_Cleanup() | |||
| close(g_app.event_source[i].fd); | |||
| } | |||
| } | |||
| munmap(g_app.fb, g_app.xres * g_app.yres * 4); | |||
| close(g_app.fbfd); | |||
| // DisableRawMode(); | |||
| } | |||
| @@ -391,22 +403,11 @@ swwWindow* swwWindow_Create(const char* title, uint32_t width, uint32_t height) | |||
| assert(width > 0 && height > 0 && width < g_app.xres && height < g_app.yres); | |||
| int screensize = g_app.xres * g_app.yres * 4; | |||
| uint8_t* fbp = (uint8_t*)mmap(0, screensize, PROT_READ | PROT_WRITE, MAP_SHARED, g_app.fbfd, 0); | |||
| if (fbp == (void*)-1) { | |||
| perror("Error: failed to map framebuffer device to memory"); | |||
| exit(5); | |||
| } | |||
| o = (swwWindow*)malloc(sizeof(swwWindow)); | |||
| memset(o, 0, sizeof(swwWindow)); | |||
| o->surface = swwImage_Create(10, 10, 4); | |||
| // NOTE(donkey): An guly patch, the buffer will be allocated by mmap | |||
| free(o->surface->buffer); | |||
| o->surface->buffer = fbp; | |||
| o->surface->width = g_app.xres; | |||
| o->surface->height = g_app.yres; | |||
| o->surface = swwImage_Create(width, height, 4); | |||
| o->x = (g_app.xres - width) >> 1; // divided by 2 | |||
| o->y = (g_app.yres - height) >> 1; // divided by 2 | |||
| g_app.window = o; | |||
| ++g_app.window_count; | |||
| @@ -417,15 +418,34 @@ swwWindow* swwWindow_Create(const char* title, uint32_t width, uint32_t height) | |||
| void swwWindow_Destroy(swwWindow* o) | |||
| { | |||
| if (o != NULL) { | |||
| munmap(o->surface->buffer, o->surface->width * o->surface->height * 4); | |||
| swwImage_Destroy(o->surface); | |||
| free(o); | |||
| --g_app.window_count; | |||
| g_app.window = NULL; | |||
| } | |||
| } | |||
| void swwWindow_Present(swwWindow* window) | |||
| {} | |||
| void swwWindow_Present(swwWindow* o) | |||
| { | |||
| int i = 0; | |||
| /* Start position: <fb4pixels>[y][x] */ | |||
| uint8_t* start = g_app.fb + (((o->y * g_app.xres) + o->x) << 2); | |||
| uint8_t* buf = o->surface->buffer; | |||
| size_t line_size = o->o->surface->width << 2; | |||
| // VSYNC | |||
| int zero = 0; | |||
| int ret = ioctl(g_app.fbfd, FBIO_WAITFORVSYNC, &zero); | |||
| if (ret != 0) { | |||
| perror("Failed to do VSYNC!"); | |||
| } | |||
| /* Copy the window buffer to framebuffer line by line */ | |||
| for (; i < o->height; ++i, start += (g_app.xres << 2), buf += line_size) { | |||
| memcpy(start, buf, line_size); | |||
| } | |||
| } | |||
| uint8_t* swwWindow_LockBuffer(swwWindow* o) | |||
| { | |||