From 68b5f182af145fdd9e62c9dde3eedcb9108f5ba4 Mon Sep 17 00:00:00 2001 From: Tobias Wiese Date: Mon, 3 May 2021 23:58:30 +0200 Subject: Initial commit Signed-off-by: Tobias Wiese --- chars/chars.c | 118 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 118 insertions(+) create mode 100644 chars/chars.c (limited to 'chars/chars.c') diff --git a/chars/chars.c b/chars/chars.c new file mode 100644 index 0000000..de72a10 --- /dev/null +++ b/chars/chars.c @@ -0,0 +1,118 @@ +#include +#include +#include + +#include "../libleds.h" +#include "chars.h" + +#include "space.xbm" +#include "0.xbm" +#include "1.xbm" +#include "2.xbm" +#include "3.xbm" +#include "4.xbm" +#include "5.xbm" +#include "6.xbm" +#include "7.xbm" +#include "8.xbm" +#include "9.xbm" + +static unsigned char *get_char_bits(char c) { + switch (c) { + case ' ': + return cspace_bits; + case '0': + return c0_bits; + case '1': + return c1_bits; + case '2': + return c2_bits; + case '3': + return c3_bits; + case '4': + return c4_bits; + case '5': + return c5_bits; + case '6': + return c6_bits; + case '7': + return c7_bits; + case '8': + return c8_bits; + case '9': + return c9_bits; + default: + return NULL; + } +} + +static char is_active(unsigned char const *bits, unsigned int const i) +{ + /* + * The first led is in the top left corner. + * After that it goes down the column, then up the next and so on. + * + * This means all columns with an even index count down. + * Those with an odd index count up. + * + * + * With a height of 8 the led numbers would look like this: + * + * 00 0F 10 1F 20 ... + * 01 0E 11 1E 21 ... + * 02 0D 12 1D ... + * 03 0C 13 1C ... + * 04 0B 14 1B ... + * 05 0A 15 1A ... + * 06 09 16 19 ... + * 07 08 17 18 ... + */ + + unsigned int const bytes_per_row = ceil(char_width / 8.0); + unsigned int col = i / char_height; + unsigned int row = i % char_height; + if (col % 2) + row = char_height - 1 - row; + + // calculate byte to access + unsigned int byte = row * bytes_per_row; + byte += col / 8; + + unsigned char data = bits[byte]; + unsigned char mask = 1<<(col % 8); + return data & mask; +} + +static char leds_write_char(const struct led_color color, char c, struct led_color *buf) +{ + unsigned char *bits = get_char_bits(c); + if (bits == NULL) + return 0; + + for (unsigned int i = 0; i < char_length; i++) { + if (is_active(bits, i)) + buf[i] = color; + else + buf[i] = (struct led_color){0, 0, 0}; + } + + return 1; +} + +struct led_color *leds_text(struct led_color const color, const char *text) +{ + unsigned int const len = strlen(text); + struct led_color *buf = calloc( + sizeof(struct led_color), len * char_length + ); + + for (unsigned int i = 0; i < len; i++) { + if (!leds_write_char(color, text[i], buf + i*char_length)) { + // Invalid char + free(buf); + return NULL; + } + } + + return buf; +} -- cgit v1.2.3