diff options
Diffstat (limited to 'lib/liboda')
-rw-r--r-- | lib/liboda/include/liboda/input.h | 74 | ||||
-rw-r--r-- | lib/liboda/include/liboda/oda.h | 18 | ||||
-rw-r--r-- | lib/liboda/src/input.c | 88 | ||||
-rw-r--r-- | lib/liboda/src/window.c | 108 |
4 files changed, 288 insertions, 0 deletions
diff --git a/lib/liboda/include/liboda/input.h b/lib/liboda/include/liboda/input.h new file mode 100644 index 0000000..c74a304 --- /dev/null +++ b/lib/liboda/include/liboda/input.h @@ -0,0 +1,74 @@ +/* + * Copyright (c) 2023-2025 Ian Marco Moffett and the Osmora Team. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Hyra nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef LIBODA_INPUT_H +#define LIBODA_INPUT_H + +#include <stdint.h> +#include <stddef.h> + +/* + * Macros to help extract scancode and + * character + */ +#define ODA_SCANCODE(KEY) ((KEY) >> 8) +#define ODA_KEYCHAR(KEY) ((char )(KEY) & 0xFF) + +/* + * Key defines + */ +#define ODA_KEY_OTHER 0x0000 +#define ODA_KEY_ESCAPE 0x0001 +#define ODA_KEY_TAB 0x0002 +#define ODA_KEY_BACKSPACE 0x0003 + +/* + * Represents a key press + * + * @type: Key types (see ODA_KEY_*) + * @scancode: Scancode + * @ch: Character + */ +struct oda_key { + uint16_t type; + uint8_t scancode; + char ch; +}; + +/* + * ODA keyboard object for managing keyboard + * input. + */ +struct oda_kbd { + int(*handle_keyev)(struct oda_kbd *kbd, struct oda_key *key); +}; + +int oda_kbd_dispatch(struct oda_kbd *kbd); + +#endif /* !LIBODA_INPUT_H */ diff --git a/lib/liboda/include/liboda/oda.h b/lib/liboda/include/liboda/oda.h index d807a50..10738a9 100644 --- a/lib/liboda/include/liboda/oda.h +++ b/lib/liboda/include/liboda/oda.h @@ -80,8 +80,26 @@ struct oda_wattr { odadimm_t w, h; }; +/* + * A pixel point that can be plotted + * onto a window. + * + * @x,y: Point position + * @rgb: Color (RGB) + * @window: Window this will be plotted to + * + * Just set x, y, the color (rgb) then point it + * to a window! + */ +struct oda_point { + odapos_t x, y; + odacolor_t rgb; + struct oda_window *window; +}; + int oda_reqwin(struct oda_wattr *params, struct oda_window **res); int oda_termwin(struct oda_state *state, struct oda_window *win); +int oda_plotwin(struct oda_state *state, const struct oda_point *point); int oda_start_win(struct oda_state *state, struct oda_window *win); int oda_init(struct oda_state *res); diff --git a/lib/liboda/src/input.c b/lib/liboda/src/input.c new file mode 100644 index 0000000..797a9d4 --- /dev/null +++ b/lib/liboda/src/input.c @@ -0,0 +1,88 @@ +/* + * Copyright (c) 2023-2025 Ian Marco Moffett and the Osmora Team. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Hyra nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#include <sys/ascii.h> +#include <sys/errno.h> +#include <sys/param.h> +#include <liboda/oda.h> +#include <liboda/input.h> +#include <stdint.h> +#include <stdio.h> + +/* + * Convert key scancode/char values to fixed + * ODA key constants + */ +static inline uint16_t +oda_map_key(const struct oda_key *key) +{ + uint16_t type = ODA_KEY_OTHER; + + switch (key->ch) { + case ASCII_ESC: + type = ODA_KEY_ESCAPE; + break; + case ASCII_HT: + type = ODA_KEY_TAB; + break; + case ASCII_BS: + type = ODA_KEY_BACKSPACE; + break; + } + + return type; +} + +/* + * Dispatch keyboard events. This is typically + * called in an event loop so that keyboard events + * are handled per iteration. + * + * @kbd: Keyboard to monitor + */ +int +oda_kbd_dispatch(struct oda_kbd *kbd) +{ + struct oda_key key; + int input; + + if (kbd == NULL) { + return -EINVAL; + } + + /* Attempt to grab the input */ + if ((input = getchar()) < 0) { + return -EAGAIN; + } + + key.scancode = ODA_SCANCODE(input); + key.ch = ODA_KEYCHAR(input); + key.type = oda_map_key(&key); + return kbd->handle_keyev(kbd, &key); +} diff --git a/lib/liboda/src/window.c b/lib/liboda/src/window.c index 876f89e..9a8b799 100644 --- a/lib/liboda/src/window.c +++ b/lib/liboda/src/window.c @@ -36,6 +36,114 @@ #include <libgfx/gfx.h> /* + * Check if a point is within the bounds of + * a surface. + * + * @wp: Surface to check with point + * @point: Point to check with surface + * + * Returns 0 if the check has passed, + * otherwise a less than zero value. + */ +static int +oda_check_point(struct oda_window *wp, struct oda_point *point) +{ + struct gfx_shape *surf; + scrpos_t win_startx; + scrpos_t win_starty; + scrpos_t win_endx; + scrpos_t win_endy; + + /* Compute start positions */ + surf = &wp->surface; + win_startx = surf->x; + win_starty = surf->y; + + /* Compute end positions */ + win_endx = surf->x + surf->width; + win_endy = surf->y + surf->height; + + /* Check X bounds */ + if (point->x < win_startx || point->x > win_endx) { + return -1; + } + + /* Check Y bounds */ + if (point->y < win_starty || point->y > win_endy) { + return -1; + } + + /* All good */ + return 0; +} + +/* + * Plot a pixel onto a window + * + * @state: ODA state pointer + * @point: Point to plot + * + * Returns 0 on success, otherwise a less than + * zero value. + * + * XXX: The x/y params in the 'point' argument must be + * relative to the start of the window. In other words, + * (0,0) refers to the top left corner of the window. + */ +int +oda_plotwin(struct oda_state *state, const struct oda_point *point) +{ + struct gfx_point pixel; + struct oda_point point_new; + struct oda_window *window; + struct gfx_shape *surf; + odapos_t plotx, ploty; + int error; + + if (state == NULL || point == NULL) { + return -EINVAL; + } + + /* Validate cookie */ + if ((error = oda_cookie_verify(state)) != 0) { + return error; + } + + /* Try to grab the window */ + if ((window = point->window) == NULL) { + return -EINVAL; + } + + surf = &window->surface; + plotx = surf->x + point->x; + ploty = surf->y + point->y; + + /* + * We are going to need to transform the coordinates + * as they are supposed to be coming in relative to + * the window bounds, e.g., (0,0) being the top left + * corner of a window. + */ + point_new = *point; + point_new.x = plotx; + point_new.y = ploty; + + /* Initialize the pixel to plot */ + pixel.x = plotx; + pixel.y = ploty; + pixel.rgb = point->rgb; + + /* Is the point within bounds? */ + error = oda_check_point(window, &point_new); + if (error < 0) { + return error; + } + + gfx_plot_point(&state->gctx, &pixel); + return 0; +} + +/* * Request a window from the OSMORA Display * Architecture (ODA). * |