Further bringup and drawing routines

This commit is contained in:
Juhani Krekelä 2021-11-16 06:29:24 +02:00
parent ab10b418bb
commit 072ebb5632
1 changed files with 208 additions and 6 deletions

214
sortix.c
View File

@ -8,35 +8,237 @@
#ifdef GRDRV_SORTIX
#include <display.h>
#include <err.h> //debg
#include <errno.h>
#include <stdint.h>
#include <display.h>
#include <framebuffer.h>
#include "links.h"
struct display_connection* sortix_display;
static int default_window_width = 600;
static int default_window_height = 500;
unsigned char *sortix_init_driver(unsigned char *param, unsigned char *display)
static struct display_connection* connection;
static struct display_event_handlers event_handlers;
struct graphics_driver sortix_driver;
static void sortix_process_events(void *data)
{
(void) data;
warnx("sortix_process_events");//debg
while (display_poll_event(connection, &event_handlers) == 0);
}
static unsigned char *sortix_init_driver(unsigned char *param, unsigned char *display)
{
if (param && *param)
errx(1, "param %s", param);
if (display && *display)
errx(1, "display %s", display);
sortix_display = display_connect_default();
if (!sortix_display && errno == ECONNREFUSED)
connection = display_connect_default();
if (!connection && errno == ECONNREFUSED)
return "TODO: display_spawn";
if ( !sortix_display )
if (!connection)
return "TODO: Proper error reporting";
sortix_driver.get_color = get_color_fn(sortix_driver.depth);
set_handlers(display_connection_fd(connection), sortix_process_events, NULL, NULL);
return NULL;
}
struct window_data
{
uint32_t window_id;
struct framebuffer fb;
};
static struct graphics_device *sortix_init_device(void)
{
struct graphics_device *dev = mem_calloc(sizeof(struct graphics_device));
dev->size.x1 = 0;
dev->size.y1 = 0;
dev->size.x2 = default_window_width;
dev->size.y2 = default_window_height;
dev->clip = dev->size;
struct window_data *window_data = mem_calloc(sizeof(struct window_data));
dev->driver_data = window_data;
window_data->window_id = 0;
// TODO: Overflow when multiplying
window_data->fb.buffer = mem_calloc(dev->size.x2 * dev->size.y2 * sizeof(uint32_t));
window_data->fb.xres = dev->size.x2;
window_data->fb.yres = dev->size.y2;
window_data->fb.pitch = dev->size.x2;
display_create_window(connection, window_data->window_id);
display_resize_window(connection, window_data->window_id, dev->size.x2, dev->size.y2);
display_show_window(connection, window_data->window_id);
return dev;
}
static void sortix_shutdown_device(struct graphics_device *dev)
{
struct window_data *window_data = dev->driver_data;
display_destroy_window(connection, window_data->window_id);
free(window_data);
}
static void sortix_shutdown_driver(void)
{
display_disconnect(connection);
}
static void sortix_after_fork(void)
{
if (connection)
display_disconnect(connection);
}
static unsigned char *sortix_get_driver_param(void)
{
return NULL; //TODO: driver parameters?
}
static int sortix_get_empty_bitmap(struct bitmap *dest)
{
// TODO: Overflow when multiplying
dest->data = mem_alloc_mayfail((size_t)dest->x * (size_t)dest->y * sizeof(uint32_t));
if (!dest->data)
return -1;
// TODO: Overflow when multiplying
dest->skip = (ssize_t)dest->x * sizeof(uint32_t);
dest->flags = 0;
return 0;
}
static void sortix_register_bitmap(struct bitmap *bmp)
{
}
static void *sortix_prepare_strip(struct bitmap *bmp, int top, int lines)
{
if (!bmp->data)
return NULL;
// TODO: Overflow when multiplying
return ((unsigned char *)bmp->data) + bmp->skip * top;
}
static void sortix_commit_strip(struct bitmap *bmp, int top, int lines)
{
}
static void sortix_unregister_bitmap(struct bitmap *bmp)
{
if (bmp->data)
mem_free(bmp->data);
}
static void sortix_draw_bitmap(struct graphics_device *dev, struct bitmap *bmp, int x1, int y1)
{
struct window_data *window_data = dev->driver_data;
warnx("sortix_draw_bitmap(%p, %p, %i, %i)", dev, bmp, x1, y1); //debg
size_t width = bmp->x;
size_t height = bmp->y;
for (size_t y = 0; y < height; y++) {
if (window_data->fb.yres <= y1 + y) continue;
for (size_t x = 0; x < width; x++) {
if (window_data->fb.xres <= x1 + x) continue;
void *pixel_data = ((unsigned char*)bmp->data) + y * bmp->skip + x * sizeof(uint32_t);
uint32_t pixel;
memcpy(&pixel, pixel_data, sizeof(uint32_t));
// Set the alpha channel (see sortix_fill_area() for further details)
pixel |= 0xff000000;
window_data->fb.buffer[(y1 + y) * window_data->fb.pitch + x + x1] = pixel;
}
}
display_render_window(connection, window_data->window_id, 0, 0, window_data->fb.xres, window_data->fb.yres, window_data->fb.buffer);
}
static void sortix_fill_area(struct graphics_device *dev, int x1, int y1, int x2, int y2, long color)
{
struct window_data *window_data = dev->driver_data;
size_t width = x2 - x1;
size_t height = y2 - y1;
// Links uses a pixel format where the top byte is clear
// Sortix stores alpha there, so set it to 255
uint32_t pixel = color | 0xff000000;
for (size_t y = 0; y < height; y++) {
for (size_t x = 0; x < width; x++)
window_data->fb.buffer[(y1 + y) * window_data->fb.pitch + x + x1] = pixel;
}
display_render_window(connection, window_data->window_id, 0, 0, window_data->fb.xres, window_data->fb.yres, window_data->fb.buffer);
}
static void sortix_draw_hline(struct graphics_device *dev, int x1, int y, int x2, long color)
{
sortix_fill_area(dev, x1, y, x2, y, color);
}
static void sortix_draw_vline(struct graphics_device *dev, int x, int y1, int y2, long color)
{
sortix_fill_area(dev, x, y1, x, y2, color);
}
static void sortix_set_title(struct graphics_device *dev, unsigned char *title)
{
struct window_data *window_data = dev->driver_data;
display_title_window(connection, window_data->window_id, title);
}
struct graphics_driver sortix_driver =
{
(unsigned char *)"sortix",
sortix_init_driver,
sortix_init_device,
sortix_shutdown_device,
sortix_shutdown_driver,
NULL, // emergency_shutdown
sortix_after_fork,
sortix_get_driver_param,
NULL, // get_af_unix_name
NULL, // get_margin
NULL, // set_margin
sortix_get_empty_bitmap,
sortix_register_bitmap,
sortix_prepare_strip,
sortix_commit_strip,
sortix_unregister_bitmap,
sortix_draw_bitmap,
NULL, // get_color, set in sortix_init_driver()
sortix_fill_area,
sortix_draw_hline,
sortix_draw_vline,
NULL, // scroll
NULL, // set_clip_area
NULL, // flush
NULL, // block
NULL, // unblock
NULL, // set_palette
NULL, // get_real_colors
sortix_set_title,
NULL, // exec
NULL, // set_clipboard_text
NULL, // get_clipboard_text
(24 << 3) | 4, // depth: 24bpp, 4 bytes per pixel
0, 0, // size (x, y), unused
GD_DONT_USE_SCROLL, //flags
NULL, // param
};
#endif /* GRDRV_SORTIX */