diff --git a/docs/library/framebuf.rst b/docs/library/framebuf.rst index 149f4d6609be9..1d5bd2cb95dfd 100644 --- a/docs/library/framebuf.rst +++ b/docs/library/framebuf.rst @@ -112,12 +112,15 @@ The following methods draw shapes onto the FrameBuffer. Drawing text ------------ -.. method:: FrameBuffer.text(s, x, y[, c]) +.. method:: FrameBuffer.text(s, x, y[, c[, size]]) Write text to the FrameBuffer using the the coordinates as the upper-left corner of the text. The color of the text can be defined by the optional - argument but is otherwise a default value of 1. All characters have + ``c`` argument but is otherwise a default value of 1. Characters have base dimensions of 8x8 pixels and there is currently no way to change the font. + The optional ``size`` argument (which defaults to ``8``) allows a font size + to be specified. The standard 8x8 font will be crudely scaled, so integer + multiples of 8 (e.g., ``16``) will work best. Other methods diff --git a/extmod/modframebuf.c b/extmod/modframebuf.c index cd0f50d104427..63fe89d01a80b 100644 --- a/extmod/modframebuf.c +++ b/extmod/modframebuf.c @@ -812,6 +812,10 @@ static mp_obj_t framebuf_text(size_t n_args, const mp_obj_t *args_in) { if (n_args >= 5) { col = mp_obj_get_int(args_in[4]); } + mp_int_t size = 8; + if (n_args >= 6) { + size = mp_obj_get_int(args_in[5]); + } // loop over chars for (; *str; ++str) { @@ -823,13 +827,16 @@ static mp_obj_t framebuf_text(size_t n_args, const mp_obj_t *args_in) { // get char data const uint8_t *chr_data = &font_petme128_8x8[(chr - 32) * 8]; // loop over char data - for (int j = 0; j < 8; j++, x0++) { + for (int j = 0; j < size; j++, x0++) { if (0 <= x0 && x0 < self->width) { // clip x - uint vline_data = chr_data[j]; // each byte is a column of 8 pixels, LSB at top - for (int y = y0; vline_data; vline_data >>= 1, y++) { // scan over vertical column - if (vline_data & 1) { // only draw if pixel set + uint vline_data = chr_data[j * 8 / size]; // each byte is a column of 8 pixels, LSB at top + if (vline_data) { // skip empty columns + for (int i = 0, y = y0; i < size; i++, y++) { if (0 <= y && y < self->height) { // clip y - setpixel(self, x0, y, col); + // scan over vertical column + if (vline_data & (1 << (i * 8 / size))) { // only draw if pixel set + setpixel(self, x0, y, col); + } } } } @@ -838,7 +845,7 @@ static mp_obj_t framebuf_text(size_t n_args, const mp_obj_t *args_in) { } return mp_const_none; } -static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(framebuf_text_obj, 4, 5, framebuf_text); +static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(framebuf_text_obj, 4, 6, framebuf_text); #if !MICROPY_ENABLE_DYNRUNTIME static const mp_rom_map_elem_t framebuf_locals_dict_table[] = { diff --git a/tests/extmod/framebuf1.py b/tests/extmod/framebuf1.py index f5e92579f2fd7..035a2e89686fe 100644 --- a/tests/extmod/framebuf1.py +++ b/tests/extmod/framebuf1.py @@ -94,6 +94,12 @@ fbuf.text("hello", 0, 0, 0) # clear print(buf) + # scaled text + fbuf.text("*", 0, 0, 1, 16) + print(buf) + fbuf.text("*", 0, 0, 0, 16) # clear + print(buf) + # char out of font range set to chr(127) fbuf.text(str(chr(31)), 0, 0) print(buf) diff --git a/tests/extmod/framebuf1.py.exp b/tests/extmod/framebuf1.py.exp index 4f18e48eca6f1..3800c0ff47551 100644 --- a/tests/extmod/framebuf1.py.exp +++ b/tests/extmod/framebuf1.py.exp @@ -18,6 +18,8 @@ bytearray(b'\x00\x00@\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x7f\x7f\x04\x04\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') +bytearray(b'\xc0\xc0\xcc\xcc\xfc\x00\x00\x0c\x0c\x0f\x00\x00\x00\x00\x00\x00') +bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\xaaU\xaaU\xaa\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') MONO_HLSB @@ -40,6 +42,8 @@ bytearray(b'\x00\x00\x00\x00\x00\x00 \x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x08\x00\x00\x00\x00\x00\x00\x00') bytearray(b'``x````\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') +bytearray(b'\x00\x0088\x08\x08\xf8\xf8\x08\x0888\x00\x00\x00\x00') +bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'P\xa8P\xa8P\xa8P\xa8\x00\x00\x00\x00\x00\x00\x00\x00') MONO_HMSB @@ -62,6 +66,8 @@ bytearray(b'\x00\x00\x00\x00\x00\x00\x04\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x10\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x06\x06\x1e\x06\x06\x06\x06\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') +bytearray(b'\x00\x00\x1c\x1c\x10\x10\x1f\x1f\x10\x10\x1c\x1c\x00\x00\x00\x00') +bytearray(b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') bytearray(b'\n\x15\n\x15\n\x15\n\x15\x00\x00\x00\x00\x00\x00\x00\x00') ValueError