SSD1306 OLED display driver 1.8.2 This library is developed to control SSD1306/SSD1331/SSD1351/IL9163/PCD8554 RGB i2c/spi LED displays

ssd1306_1bit.c
1 /*
2 MIT License
3
4 Copyright (c) 2016-2019, Alexey Dynda
5
6 Permission is hereby granted, free of charge, to any person obtaining a copy
7 of this software and associated documentation files (the "Software"), to deal
8 in the Software without restriction, including without limitation the rights
9 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 copies of the Software, and to permit persons to whom the Software is
11 furnished to do so, subject to the following conditions:
12
13 The above copyright notice and this permission notice shall be included in all
14 copies or substantial portions of the Software.
15
16 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 SOFTWARE.
23 */
24
28
29 #include "ssd1306.h"
30 #include "ssd1306_fonts.h"
31 #include "lcd/lcd_common.h"
32 #include "intf/i2c/ssd1306_i2c.h"
33 #include "intf/spi/ssd1306_spi.h"
34 #include "intf/ssd1306_interface.h"
35 #include "ssd1306_hal/io.h"
36
37 // TODO: remove
38 #include "lcd/ssd1306_commands.h"
39
40 uint8_t s_ssd1306_invertByte = 0x00000000;
41 extern uint16_t ssd1306_color;
42 const uint8_t *s_font6x8 = &ssd1306xled_font6x8[4];
43 extern lcduint_t ssd1306_cursorX;
44 extern lcduint_t ssd1306_cursorY;
45 extern SFixedFontInfo s_fixedFont;
46 #ifdef CONFIG_SSD1306_UNICODE_ENABLE
47 extern uint8_t g_ssd1306_unicode;
48 #endif
49
50 void ssd1306_fillScreen(uint8_t fill_Data)
51 {
52 fill_Data ^= s_ssd1306_invertByte;
53 ssd1306_lcd.set_block(0, 0, 0);
54 for(lcduint_t m=(ssd1306_lcd.height >> 3); m>0; m--)
55 {
56 for(lcduint_t n=ssd1306_lcd.width; n>0; n--)
57 {
58 ssd1306_lcd.send_pixels1(fill_Data);
59 }
60 ssd1306_lcd.next_page();
61 }
62 ssd1306_intf.stop();
63 }
64
65 void ssd1306_clearScreen()
66 {
67 ssd1306_lcd.set_block(0, 0, 0);
68 for(lcduint_t m=(ssd1306_lcd.height >> 3); m>0; m--)
69 {
70 for(lcduint_t n=ssd1306_lcd.width; n>0; n--)
71 {
72 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte );
73 }
74 ssd1306_lcd.next_page();
75 }
76 ssd1306_intf.stop();
77 }
78
79 uint8_t ssd1306_printFixed(uint8_t xpos, uint8_t y, const char *ch, EFontStyle style)
80 {
81 uint8_t i, j=0;
82 uint8_t text_index = 0;
83 uint8_t page_offset = 0;
84 uint8_t x = xpos;
85 y >>= 3;
86 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
87 for(;;)
88 {
89 uint8_t ldata;
90 if ((x > ssd1306_lcd.width - s_fixedFont.h.width) || (ch[j] == '\0'))
91 {
92 x = xpos;
93 y++;
94 if (y >= (ssd1306_lcd.height >> 3))
95 {
96 break;
97 }
98 page_offset++;
99 if (page_offset == s_fixedFont.pages)
100 {
101 text_index = j;
102 page_offset = 0;
103 if (ch[j] == '\0')
104 {
105 break;
106 }
107 }
108 else
109 {
110 j = text_index;
111 }
112 ssd1306_intf.stop();
113 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
114 }
115 uint16_t unicode;
116 do
117 {
118 unicode = ssd1306_unicode16FromUtf8(ch[j]);
119 j++;
120 } while ( unicode == SSD1306_MORE_CHARS_REQUIRED );
121 SCharInfo char_info;
122 ssd1306_getCharBitmap(unicode, &char_info);
123 ldata = 0;
124 x += char_info.width + char_info.spacing;
125 if (char_info.height > page_offset * 8)
126 {
127 char_info.glyph += page_offset * char_info.width;
128 for( i = char_info.width; i>0; i--)
129 {
130 uint8_t data;
131 if ( style == STYLE_NORMAL )
132 {
133 data = pgm_read_byte(&char_info.glyph[0]);
134 }
135 else if ( style == STYLE_BOLD )
136 {
137 uint8_t temp = pgm_read_byte(&char_info.glyph[0]);
138 data = temp | ldata;
139 ldata = temp;
140 }
141 else
142 {
143 uint8_t temp = pgm_read_byte(&char_info.glyph[1]);
144 data = (temp & 0xF0) | ldata;
145 ldata = (temp & 0x0F);
146 }
147 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
148 char_info.glyph++;
149 }
150 }
151 else
152 {
153 char_info.spacing += char_info.width;
154 }
155 for (i = 0; i < char_info.spacing; i++)
156 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte);
157 }
158 ssd1306_intf.stop();
159 return j;
160 }
161
162 uint8_t ssd1306_printFixed_oldStyle(uint8_t xpos, uint8_t y, const char *ch, EFontStyle style)
163 {
164 uint8_t i, j=0;
165 uint8_t text_index = 0;
166 uint8_t page_offset = 0;
167 uint8_t x = xpos;
168 y >>= 3;
169 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
170 for(;;)
171 {
172 uint8_t c;
173 uint8_t ldata;
174 uint16_t offset;
175 if( (x > ssd1306_lcd.width - s_fixedFont.h.width) || (ch[j] == '\0') )
176 {
177 x = xpos;
178 y++;
179 if (y >= (ssd1306_lcd.height >> 3))
180 {
181 break;
182 }
183 page_offset++;
184 if (page_offset == s_fixedFont.pages)
185 {
186 text_index = j;
187 page_offset = 0;
188 if (ch[j] == '\0')
189 {
190 break;
191 }
192 }
193 else
194 {
195 j = text_index;
196 }
197 ssd1306_intf.stop();
198 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
199 }
200 c = ch[j];
201 if ( c >= s_fixedFont.h.ascii_offset )
202 {
203 c -= s_fixedFont.h.ascii_offset;
204 }
205 ldata = 0;
206 offset = (c * s_fixedFont.pages + page_offset) * s_fixedFont.h.width;
207 for( i=s_fixedFont.h.width; i>0; i--)
208 {
209 uint8_t data;
210 if ( style == STYLE_NORMAL )
211 {
212 data = pgm_read_byte(&s_fixedFont.primary_table[offset]);
213 }
214 else if ( style == STYLE_BOLD )
215 {
216 uint8_t temp = pgm_read_byte(&s_fixedFont.primary_table[offset]);
217 data = temp | ldata;
218 ldata = temp;
219 }
220 else
221 {
222 uint8_t temp = pgm_read_byte(&s_fixedFont.primary_table[offset + 1]);
223 data = (temp & 0xF0) | ldata;
224 ldata = (temp & 0x0F);
225 }
226 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
227 offset++;
228 }
229 x += s_fixedFont.h.width;
230 j++;
231 }
232 ssd1306_intf.stop();
233 return j;
234 }
235
236 uint8_t ssd1306_printFixed2x(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style)
237 {
238 uint8_t i, j=0;
239 uint8_t text_index = 0;
240 uint8_t page_offset = 0;
241 uint8_t x = xpos;
242 y >>= 3;
243 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
244 for(;;)
245 {
246 uint8_t c;
247 uint8_t ldata;
248 uint16_t offset;
249 if( (x > ssd1306_lcd.width - (s_fixedFont.h.width << 1)) || (ch[j] == '\0') )
250 {
251 x = xpos;
252 y++;
253 if (y >= (ssd1306_lcd.height >> 3))
254 {
255 break;
256 }
257 page_offset++;
258 if (page_offset == (s_fixedFont.pages << 1))
259 {
260 text_index = j;
261 page_offset = 0;
262 if (ch[j] == '\0')
263 {
264 break;
265 }
266 }
267 else
268 {
269 j = text_index;
270 }
271 ssd1306_intf.stop();
272 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
273 }
274 c = ch[j];
275 if ( c >= 32 )
276 {
277 c -= 32;
278 }
279 ldata = 0;
280 offset = (c * s_fixedFont.pages + (page_offset >> 1)) * s_fixedFont.h.width;
281 for( i=s_fixedFont.h.width; i>0; i--)
282 {
283 uint8_t data;
284 if ( style == STYLE_NORMAL )
285 {
286 data = pgm_read_byte(&s_fixedFont.primary_table[offset]);
287 }
288 else if ( style == STYLE_BOLD )
289 {
290 uint8_t temp = pgm_read_byte(&s_fixedFont.primary_table[offset]);
291 data = temp | ldata;
292 ldata = temp;
293 }
294 else
295 {
296 uint8_t temp = pgm_read_byte(&s_fixedFont.primary_table[offset + 1]);
297 data = (temp & 0xF0) | ldata;
298 ldata = (temp & 0x0F);
299 }
300 if (page_offset & 1) data >>= 4;
301 data = ((data & 0x01) ? 0x03: 0x00) |
302 ((data & 0x02) ? 0x0C: 0x00) |
303 ((data & 0x04) ? 0x30: 0x00) |
304 ((data & 0x08) ? 0xC0: 0x00);
305 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
306 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
307 offset++;
308 }
309 x += (s_fixedFont.h.width << 1);
310 j++;
311 }
312 ssd1306_intf.stop();
313 return j;
314 }
315
316
317 uint8_t ssd1306_printFixedN(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style, uint8_t factor)
318 {
319 uint8_t i, j=0;
320 uint8_t text_index = 0;
321 uint8_t page_offset = 0;
322 uint8_t x = xpos;
323 y >>= 3;
324 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
325 for(;;)
326 {
327 uint8_t ldata;
328 if( (x > ssd1306_lcd.width - (s_fixedFont.h.width << factor)) || (ch[j] == '\0') )
329 {
330 x = xpos;
331 y++;
332 if (y >= (ssd1306_lcd.height >> 3))
333 {
334 break;
335 }
336 page_offset++;
337 if (page_offset == (s_fixedFont.pages << factor))
338 {
339 text_index = j;
340 page_offset = 0;
341 if (ch[j] == '\0')
342 {
343 break;
344 }
345 }
346 else
347 {
348 j = text_index;
349 }
350 ssd1306_intf.stop();
351 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
352 }
353 uint16_t unicode;
354 do
355 {
356 unicode = ssd1306_unicode16FromUtf8(ch[j]);
357 j++;
358 } while ( unicode == SSD1306_MORE_CHARS_REQUIRED );
359 SCharInfo char_info;
360 ssd1306_getCharBitmap(unicode, &char_info);
361 ldata = 0;
362 x += ((char_info.width + char_info.spacing) << factor);
363 if (char_info.height > (page_offset >> factor) * 8)
364 {
365 char_info.glyph += (page_offset >> factor) * char_info.width;
366 for( i=char_info.width; i>0; i--)
367 {
368 uint8_t data;
369 if ( style == STYLE_NORMAL )
370 {
371 data = pgm_read_byte(char_info.glyph);
372 }
373 else if ( style == STYLE_BOLD )
374 {
375 uint8_t temp = pgm_read_byte(char_info.glyph);
376 data = temp | ldata;
377 ldata = temp;
378 }
379 else
380 {
381 uint8_t temp = pgm_read_byte(char_info.glyph+1);
382 data = (temp & 0xF0) | ldata;
383 ldata = (temp & 0x0F);
384 }
385 if ( factor > 0 )
386 {
387 uint8_t accum = 0;
388 uint8_t mask = ~((0xFF) << (1<<factor));
389 // N=0 -> right shift is always 0
390 // N=1 -> right shift goes through 0, 4
391 // N=2 -> right shift goes through 0, 2, 4, 6
392 // N=3 -> right shift goes through 0, 1, 2, 3, 4, 5, 6, 7
393 data >>= ((page_offset & ((1<<factor) - 1))<<(3-factor));
394 for (uint8_t idx = 0; idx < 1<<(3-factor); idx++)
395 {
396 accum |= (((data>>idx) & 0x01) ? (mask<<(idx<<factor)) : 0);
397 }
398 data = accum;
399 }
400 for (uint8_t z=(1<<factor); z>0; z--)
401 {
402 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
403 }
404 char_info.glyph++;
405 }
406 }
407 else
408 {
409 char_info.spacing += char_info.width;
410 }
411 for (i = 0; i < (char_info.spacing << factor); i++)
412 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte);
413 }
414 ssd1306_intf.stop();
415 return j;
416 }
417
418 size_t ssd1306_write(uint8_t ch)
419 {
420 if (ch == '\r')
421 {
422 ssd1306_cursorX = 0;
423 return 0;
424 }
425 SCharInfo char_info = {};
426 uint8_t gotoNewLine = 1;
427 if (ch != '\n')
428 {
429 uint16_t unicode;
430 unicode = ssd1306_unicode16FromUtf8(ch);
431 if (unicode == SSD1306_MORE_CHARS_REQUIRED) return 0;
432 ssd1306_getCharBitmap(unicode, &char_info);
433 gotoNewLine = (ssd1306_cursorX > (ssd1306_lcd.width - char_info.width));
434 }
435 if ( gotoNewLine )
436 {
437 ssd1306_cursorX = 0;
438 ssd1306_cursorY += s_fixedFont.h.height;
439 if ( ssd1306_cursorY > ssd1306_lcd.height - s_fixedFont.h.height )
440 {
441 ssd1306_cursorY = 0;
442 }
443 ssd1306_clearBlock(0, ssd1306_cursorY >> 3, ssd1306_lcd.width, s_fixedFont.h.height);
444 if (ch == '\n')
445 {
446 return 0;
447 }
448 }
449 ssd1306_drawBitmap( ssd1306_cursorX,
450 ssd1306_cursorY >> 3,
451 char_info.width,
452 char_info.height,
453 char_info.glyph );
454 ssd1306_cursorX += char_info.width + char_info.spacing;
455 return 1;
456 }
457
458 size_t ssd1306_print(const char ch[])
459 {
460 size_t n = 0;
461 while (*ch)
462 {
463 n += ssd1306_write(*ch);
464 ch++;
465 }
466 return n;
467 }
468
469 uint8_t ssd1306_charF6x8(uint8_t x, uint8_t y, const char ch[], EFontStyle style)
470 {
471 uint8_t i, j=0;
472 ssd1306_lcd.set_block(x, y, ssd1306_lcd.width - x);
473 while(ch[j] != '\0')
474 {
475 uint8_t ldata;
476 uint8_t c = ch[j] - 32;
477 if ( c > 224 )
478 {
479 c = 0;
480 }
481 if(x > ssd1306_lcd.width - 6)
482 {
483 x=0;
484 y++;
485 }
486 ldata = 0;
487 for(i=0;i<6;i++)
488 {
489 uint8_t data;
490 if ( style == STYLE_NORMAL )
491 {
492 data = pgm_read_byte(&s_font6x8[c*6+i]);
493 }
494 else if ( style == STYLE_BOLD )
495 {
496 uint8_t temp = pgm_read_byte(&s_font6x8[c*6+i]);
497 data = temp | ldata;
498 ldata = temp;
499 }
500 else
501 {
502 uint8_t temp = pgm_read_byte(&s_font6x8[c*6+i + 1]);
503 data = (temp & 0xF0) | ldata;
504 ldata = (temp & 0x0F);
505 }
506 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
507 }
508 x += 6;
509 j++;
510 }
511 ssd1306_intf.stop();
512 return j;
513 }
514
515 uint8_t ssd1306_charF12x16(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style)
516 {
517 uint8_t i, j=0;
518 uint8_t text_index = 0;
519 uint8_t odd = 0;
520 uint8_t x = xpos;
521 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
522 for(;;)
523 {
524 uint8_t c;
525 uint8_t ldata;
526 if( (x > ssd1306_lcd.width-12) || (ch[j] == '\0') )
527 {
528 x = xpos;
529 y++;
530 if (y >= (ssd1306_lcd.height >> 3))
531 {
532 break;
533 }
534 if (odd)
535 {
536 text_index = j;
537 if (ch[j] == '\0')
538 {
539 break;
540 }
541 }
542 else
543 {
544 j = text_index;
545 }
546 odd = !odd;
547 ssd1306_intf.stop();
548 ssd1306_lcd.set_block(xpos, y, ssd1306_lcd.width - xpos);
549 }
550 c = ch[j] - 32;
551 if ( c > 224 )
552 {
553 c = 0;
554 }
555 ldata = 0;
556 for(i=0;i<6;i++)
557 {
558 uint8_t data;
559 if ( style == STYLE_NORMAL )
560 {
561 data = pgm_read_byte(&s_font6x8[c*6+i]);
562 }
563 else if ( style == STYLE_BOLD )
564 {
565 uint8_t temp = pgm_read_byte(&s_font6x8[c*6+i]);
566 data = temp | ldata;
567 ldata = temp;
568 }
569 else
570 {
571 uint8_t temp = pgm_read_byte(&s_font6x8[c*6+i + 1]);
572 data = (temp & 0xF0) | ldata;
573 ldata = (temp & 0x0F);
574 }
575 if (odd) data >>= 4;
576 data = ((data & 0x01) ? 0x03: 0x00) |
577 ((data & 0x02) ? 0x0C: 0x00) |
578 ((data & 0x04) ? 0x30: 0x00) |
579 ((data & 0x08) ? 0xC0: 0x00);
580 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
581 ssd1306_lcd.send_pixels1(data^s_ssd1306_invertByte);
582 }
583 x += 12;
584 j++;
585 }
586 ssd1306_intf.stop();
587 return j;
588 }
589
590 uint8_t ssd1306_charF6x8_eol(uint8_t left,
591 uint8_t y,
592 const char ch[],
593 EFontStyle style,
594 uint8_t right)
595 {
596 uint8_t len = ssd1306_printFixed(left, y<<3, ch, style);
597 uint8_t text_end_pos = len * 6 + left;
598 if (text_end_pos <= right)
599 {
600 ssd1306_clearBlock(text_end_pos, y, right - text_end_pos + 1, 8);
601 }
602 return len;
603 }
604
605 void ssd1306_putPixel(uint8_t x, uint8_t y)
606 {
607 ssd1306_lcd.set_block(x, y >> 3, 1);
608 ssd1306_lcd.send_pixels1((1 << (y & 0x07))^s_ssd1306_invertByte);
609 ssd1306_intf.stop();
610 }
611
612 void ssd1306_putPixels(uint8_t x, uint8_t y, uint8_t pixels)
613 {
614 ssd1306_lcd.set_block(x, y >> 3, 1);
615 ssd1306_lcd.send_pixels1(pixels^s_ssd1306_invertByte);
616 ssd1306_intf.stop();
617 }
618
619 void ssd1306_putPixel_delayed(uint8_t x, uint8_t y, uint8_t complete)
620 {
621 static uint8_t lx = 0, ly = 0xFF;
622 static uint8_t pixels = 0;
623 if ((lx != x) || ((ly & 0xF8) != (y & 0xF8)) || (complete))
624 {
625 if (ly != 0xFF)
626 {
627 ssd1306_putPixels( lx, ly, pixels );
628 }
629 pixels = 0;
630 ly = 0xFF;
631 }
632 if ( !complete )
633 {
634 pixels |= (1 << (y & 0x07));
635 lx = x; ly = y;
636 }
637 }
638
639 void ssd1306_drawLine(uint8_t x1, uint8_t y1, uint8_t x2, uint8_t y2)
640 {
641 lcduint_t dx = x1 > x2 ? (x1 - x2): (x2 - x1);
642 lcduint_t dy = y1 > y2 ? (y1 - y2): (y2 - y1);
643 lcduint_t err = 0;
644 if (dy > dx)
645 {
646 if (y1 > y2)
647 {
648 ssd1306_swap_data(x1, x2, uint8_t);
649 ssd1306_swap_data(y1, y2, uint8_t);
650 }
651 for(; y1<=y2; y1++)
652 {
653 err += dx;
654 if (err >= dy)
655 {
656 err -= dy;
657 x1 < x2 ? x1++: x1--;
658 }
659 ssd1306_putPixel_delayed( x1, y1, 0 );
660 }
661 ssd1306_putPixel_delayed( 0, 0, 1 );
662 }
663 else
664 {
665 if (x1 > x2)
666 {
667 ssd1306_swap_data(x1, x2, uint8_t);
668 ssd1306_swap_data(y1, y2, uint8_t);
669 }
670 for(; x1<=x2; x1++)
671 {
672 err += dy;
673 if (err >= dx)
674 {
675 err -= dx;
676 if (y1 < y2) y1++; else y1--;
677 }
678 ssd1306_putPixel( x1, y1 );
679 }
680 }
681 }
682
683 void ssd1306_drawHLine(uint8_t x1, uint8_t y1, uint8_t x2)
684 {
685 ssd1306_lcd.set_block(x1, y1 >> 3, x2 - x1 + 1);
686 for (uint8_t x = x1; x <= x2; x++)
687 {
688 ssd1306_lcd.send_pixels1((1 << (y1 & 0x07))^s_ssd1306_invertByte);
689 }
690 ssd1306_intf.stop();
691 }
692
693 void ssd1306_drawVLine(uint8_t x1, uint8_t y1, uint8_t y2)
694 {
695 uint8_t topPage = y1 >> 3;
696 uint8_t bottomPage = y2 >> 3;
697 uint8_t height = y2-y1;
698 uint8_t y;
699 ssd1306_lcd.set_block(x1, topPage, 1);
700 if (topPage == bottomPage)
701 {
702 ssd1306_lcd.send_pixels1( ((0xFF >> (0x07 - height)) << (y1 & 0x07))^s_ssd1306_invertByte );
703 ssd1306_intf.stop();
704 return;
705 }
706 ssd1306_lcd.send_pixels1( (0xFF << (y1 & 0x07))^s_ssd1306_invertByte );
707 for ( y = (topPage + 1); y <= (bottomPage - 1); y++)
708 {
709 ssd1306_lcd.next_page();
710 ssd1306_lcd.send_pixels1( 0xFF^s_ssd1306_invertByte );
711 }
712 ssd1306_lcd.next_page();
713 ssd1306_lcd.send_pixels1( (0xFF >> (0x07 - (y2 & 0x07)))^s_ssd1306_invertByte );
714 ssd1306_intf.stop();
715 }
716
717 void ssd1306_drawRect(uint8_t x1, uint8_t y1, uint8_t x2, uint8_t y2)
718 {
719 ssd1306_drawHLine(x1+1, y1, x2-1);
720 ssd1306_drawHLine(x1+1, y2, x2-1);
721 ssd1306_drawVLine(x1, y1, y2);
722 ssd1306_drawVLine(x2, y1, y2);
723 }
724
725 void ssd1306_drawBufferFast(lcdint_t x, lcdint_t y, lcduint_t w, lcduint_t h, const uint8_t *buf)
726 {
727 uint8_t j;
728 ssd1306_lcd.set_block(x, y >> 3, w);
729 for(j=(h >> 3); j>0; j--)
730 {
731 ssd1306_lcd.send_pixels_buffer1(buf,w);
732 buf+=w;
733 ssd1306_lcd.next_page();
734 }
735 ssd1306_intf.stop();
736 }
737
738 void ssd1306_drawBuffer(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
739 {
740 uint8_t i, j;
741 ssd1306_lcd.set_block(x, y, w);
742 for(j=(h >> 3); j>0; j--)
743 {
744 for(i=w;i>0;i--)
745 {
746 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte^*buf++);
747 }
748 ssd1306_lcd.next_page();
749 }
750 ssd1306_intf.stop();
751 }
752
753 void ssd1306_drawBuffer1_4(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
754 {
755 uint8_t i, j, k;
756 ssd1306_lcd.set_block(x, y>>3, w);
757 uint8_t y_offset = (y & 0x07);
758 uint8_t x_offset = (x & 0x01);
759 for( j = 0; j < ((h + 7 + y_offset) >> 3); j++)
760 {
761 for( i = 0; i < w / 2 + x_offset; i++)
762 {
763 for( k = 0; k < 8; k++)
764 {
765 if ((j*8 + k - y_offset < h) && (k >= y_offset || j != 0))
766 {
767 uint8_t data = (i < w / 2) ? buf[ i + (j * 8 + k - y_offset) * w / 2 ]: 0x00;
768 if ( x_offset )
769 {
770 data <<= 4;
771 if ( i > 0) data |= buf[ i + (j * 8 + k - y_offset) * w / 2 - 1] >> 4;
772 }
773 ssd1306_lcd.send_pixels8( data );
774 }
775 else
776 {
777 ssd1306_lcd.send_pixels8( 0x00 );
778 }
779 }
780 }
781 ssd1306_lcd.next_page();
782 }
783 ssd1306_intf.stop();
784 }
785
786 void ssd1306_drawBitmap(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
787 {
788 uint8_t i, j;
789 uint8_t remainder = (ssd1306_lcd.width - x) < w ? (w + x - ssd1306_lcd.width): 0;
790 w -= remainder;
791 ssd1306_lcd.set_block(x, y, w);
792 for(j=(h >> 3); j>0; j--)
793 {
794 for(i=w;i>0;i--)
795 {
796 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte^pgm_read_byte(buf++));
797 }
798 buf += remainder;
799 ssd1306_lcd.next_page();
800 }
801 ssd1306_intf.stop();
802 }
803
804 void ssd1306_drawBitmap1_4(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
805 {
806 uint8_t i, j, k;
807 ssd1306_lcd.set_block(x, y>>3, w);
808 uint8_t y_offset = (y & 0x07);
809 uint8_t x_offset = (x & 0x01);
810 for( j = 0; j < ((h + 7 + y_offset) >> 3); j++)
811 {
812 for( i = 0; i < w / 2 + x_offset; i++)
813 {
814 for( k = 0; k < 8; k++)
815 {
816 if ((j*8 + k - y_offset < h) && (k >= y_offset || j != 0))
817 {
818 uint8_t data = (i < w / 2) ? pgm_read_byte( &buf[ i + (j * 8 + k - y_offset) * w / 2 ] ) : 0x00;
819 if ( x_offset )
820 {
821 data <<= 4;
822 if ( i > 0) data |= pgm_read_byte( &buf[ i + (j * 8 + k - y_offset) * w / 2 - 1] ) >> 4;
823 }
824 ssd1306_lcd.send_pixels8( data );
825 }
826 else
827 {
828 ssd1306_lcd.send_pixels8( 0x00 );
829 }
830 }
831 }
832 ssd1306_lcd.next_page();
833 }
834 ssd1306_intf.stop();
835 }
836
837 void ssd1306_drawXBitmap(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
838 {
839 uint8_t i, j;
840 lcduint_t pitch = (w + 7) >> 3;
841 ssd1306_lcd.set_block(x, y, w);
842 for(j=(h >> 3); j>0; j--)
843 {
844 uint8_t bit = 0;
845 for(i=w;i>0;i--)
846 {
847 uint8_t data = 0;
848 for (uint8_t k = 0; k<8; k++)
849 {
850 data |= ( ((pgm_read_byte(&buf[k*pitch]) >> bit) & 0x01) << k );
851 }
852 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte^data);
853 bit++;
854 if (bit >= 8)
855 {
856 buf++;
857 bit=0;
858 }
859 }
860 if (bit)
861 {
862 buf++;
863 }
864 buf += pitch * 7;
865 ssd1306_lcd.next_page();
866 }
867 ssd1306_intf.stop();
868 }
869
870 void gfx_drawMonoBitmap(lcdint_t x, lcdint_t y, lcduint_t w, lcduint_t h, const uint8_t *buf)
871 {
872 lcduint_t origin_width = w;
873 uint8_t offset = y & 0x07;
874 uint8_t complexFlag = 0;
875 uint8_t mainFlag = 1;
876 uint8_t max_pages;
877 uint8_t pages;
878 lcduint_t i, j;
879 if (y + (lcdint_t)h <= 0) return;
880 if (y >= ssd1306_lcd.height) return;
881 if (x + (lcdint_t)w <= 0) return;
882 if (x >= ssd1306_lcd.width) return;
883 if (y < 0)
884 {
885 buf += ((lcduint_t)((-y) + 7) >> 3) * w;
886 h += y;
887 y = 0;
888 complexFlag = 1;
889 }
890 if (x < 0)
891 {
892 buf += -x;
893 w += x;
894 x = 0;
895 }
896 max_pages = (lcduint_t)(h + 15 - offset) >> 3;
897 if ((lcduint_t)((lcduint_t)y + h) > (lcduint_t)ssd1306_lcd.height)
898 {
899 h = (lcduint_t)(ssd1306_lcd.height - (lcduint_t)y);
900 }
901 if ((lcduint_t)((lcduint_t)x + w) > (lcduint_t)ssd1306_lcd.width)
902 {
903 w = (lcduint_t)(ssd1306_lcd.width - (lcduint_t)x);
904 }
905 pages = ((y + h - 1) >> 3) - (y >> 3) + 1;
906
907 ssd1306_lcd.set_block(x, y >> 3, w);
908 for(j=0; j < pages; j++)
909 {
910 if ( j == max_pages - 1 ) mainFlag = !offset;
911 for( i=w; i > 0; i--)
912 {
913 uint8_t data = 0;
914 if ( mainFlag ) data |= (pgm_read_byte(buf) << offset);
915 if ( complexFlag ) data |= (pgm_read_byte(buf - origin_width) >> (8 - offset));
916 buf++;
917 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte^data);
918 }
919 buf += origin_width - w;
920 complexFlag = offset;
921 ssd1306_lcd.next_page();
922 }
923 ssd1306_intf.stop();
924 }
925
926
927 void ssd1306_clearBlock(uint8_t x, uint8_t y, uint8_t w, uint8_t h)
928 {
929 uint8_t i, j;
930 ssd1306_lcd.set_block(x, y, w);
931 for(j=(h >> 3); j>0; j--)
932 {
933 for(i=w;i>0;i--)
934 {
935 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte);
936 }
937 ssd1306_lcd.next_page();
938 }
939 ssd1306_intf.stop();
940 }
941
942 void ssd1306_fillRect(lcdint_t x1, lcdint_t y1, lcdint_t x2, lcdint_t y2)
943 {
944 uint8_t templ = ssd1306_color^s_ssd1306_invertByte;
945 if (x1 > x2) return;
946 if (y1 > y2) return;
947 if ((lcduint_t)x2 >= ssd1306_displayWidth()) x2 = (lcdint_t)ssd1306_displayWidth() - 1;
948 if ((lcduint_t)y2 >= ssd1306_displayHeight()) y2 = (lcdint_t)ssd1306_displayHeight() - 1;
949 uint8_t bank1 = (y1 >> 3);
950 uint8_t bank2 = (y2 >> 3);
951 ssd1306_lcd.set_block(x1, bank1, x2 - x1 + 1);
952 for (uint8_t bank = bank1; bank<=bank2; bank++)
953 {
954 uint8_t mask = 0xFF;
955 if (bank1 == bank2)
956 {
957 mask = (mask >> ((y1 & 7) + 7 - (y2 & 7))) << (y1 & 7);
958 }
959 else if (bank1 == bank)
960 {
961 mask = (mask << (y1 & 7));
962 }
963 else if (bank2 == bank)
964 {
965 mask = (mask >> (7 - (y2 & 7)));
966 }
967 for (uint8_t x=x1; x<=x2; x++)
968 {
969 ssd1306_lcd.send_pixels1(templ & mask);
970 }
971 ssd1306_lcd.next_page();
972 }
973 ssd1306_intf.stop();
974 }
975
976
977 void ssd1306_drawSpriteEx(uint8_t x, uint8_t y, uint8_t w, const uint8_t *sprite)
978 {
979 uint8_t i;
980 ssd1306_lcd.set_block(x,y,w);
981 for(i=0;i<w;i++)
982 {
983 ssd1306_lcd.send_pixels1(s_ssd1306_invertByte^pgm_read_byte(&sprite[i]));
984 }
985 ssd1306_intf.stop();
986 }
987
988
989 void ssd1306_drawSprite(SPRITE *sprite)
990 {
991 uint8_t offsety = sprite->y & 0x7;
992 if (sprite->y < ssd1306_lcd.height)
993 {
994 ssd1306_lcd.set_block(sprite->x, sprite->y >> 3, sprite->w);
995 for (uint8_t i=0; i < sprite->w; i++)
996 {
997 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte^(pgm_read_byte( &sprite->data[i] ) << offsety) );
998 }
999 ssd1306_intf.stop();
1000 }
1001 if (offsety && (sprite->y + 8 < ssd1306_lcd.height))
1002 {
1003 ssd1306_lcd.set_block(sprite->x, (sprite->y >> 3) + 1, sprite->w);
1004 for (uint8_t i=0; i < sprite->w; i++)
1005 {
1006 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte^(pgm_read_byte( &sprite->data[i] ) >> (8 - offsety)) );
1007 }
1008 ssd1306_intf.stop();
1009 }
1010 sprite->lx = sprite->x;
1011 sprite->ly = sprite->y;
1012 }
1013
1014
1015 void ssd1306_eraseSprite(SPRITE *sprite)
1016 {
1017 uint8_t posy = sprite->y >> 3;
1018 uint8_t offsety = sprite->y & 0x7;
1019 ssd1306_lcd.set_block(sprite->x, posy, sprite->w);
1020 for (uint8_t i=sprite->w; i > 0; i--)
1021 {
1022 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte );
1023 }
1024 ssd1306_intf.stop();
1025 if (offsety)
1026 {
1027 ssd1306_lcd.set_block(sprite->x, posy + 1, sprite->w);
1028 for (uint8_t i=sprite->w; i > 0; i--)
1029 {
1030 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte );
1031 }
1032 }
1033 ssd1306_intf.stop();
1034 }
1035
1036
1037 void ssd1306_eraseTrace(SPRITE *sprite)
1038 {
1039 uint8_t y1 = sprite->ly >> 3;
1040 uint8_t y2 = (sprite->ly + 7) >> 3;
1041 if (sprite->ly < sprite->y)
1042 y2 = min(y2, (uint8_t)((sprite->y >> 3) - 1));
1043 else if (sprite->y + 8 > sprite->ly)
1044 y1 = max(y1, (sprite->ly + 7) >> 3);
1045 for(uint8_t y = y1; y <= y2; y++)
1046 {
1047 ssd1306_lcd.set_block(sprite->lx, y, sprite->w);
1048 for(uint8_t x = sprite->w; x > 0; x--)
1049 {
1050 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte );
1051 }
1052 ssd1306_intf.stop();
1053 }
1054 if (sprite->lx != sprite->x)
1055 {
1056 uint8_t x1 = sprite->lx;
1057 uint8_t x2 = sprite->lx + sprite->w - 1;
1058 if (sprite->x < sprite->lx)
1059 x1 = max(x1, sprite->x + sprite->w);
1060 else
1061 x2 = min((uint8_t)(sprite->x - 1), x2);
1062 for(uint8_t y = sprite->ly >> 3; y <= (sprite->ly + 7) >> 3; y++)
1063 {
1064 ssd1306_lcd.set_block(x1, y, x2 - x1 + 1 );
1065 for(uint8_t x = x2 - x1 + 1; x > 0; x--)
1066 {
1067 ssd1306_lcd.send_pixels1( s_ssd1306_invertByte );
1068 }
1069 ssd1306_intf.stop();
1070 }
1071 }
1072 }
1073
1074 SPRITE ssd1306_createSprite(uint8_t x, uint8_t y, uint8_t w, const uint8_t *data)
1075 {
1076 return (SPRITE){x,y,w,x,y,data,NULL};
1077 }
1078
1079 void ssd1306_replaceSprite(SPRITE *sprite, const uint8_t *data)
1080 {
1081 sprite->data = data;
1082 }
1083
1084 void ssd1306_negativeMode()
1085 {
1086 s_ssd1306_invertByte = 0xFF;
1087 }
1088
1089 void ssd1306_positiveMode()
1090 {
1091 s_ssd1306_invertByte = 0x00;
1092 }
1093
1094 void ssd1306_setFont6x8(const uint8_t * progmemFont)
1095 {
1096 s_font6x8 = progmemFont + 4;
1097 }
1098
ssd1306_drawBuffer
void ssd1306_drawBuffer(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:738
ssd1306_drawBitmap1_4
void ssd1306_drawBitmap1_4(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:804
ssd1306_displayWidth
lcduint_t ssd1306_displayWidth(void)
Definition: ssd1306_generic.c:63
ssd1306_charF6x8
uint8_t ssd1306_charF6x8(uint8_t x, uint8_t y, const char ch[], EFontStyle style)
Definition: ssd1306_1bit.c:469
ssd1306_putPixels
void ssd1306_putPixels(uint8_t x, uint8_t y, uint8_t pixels)
Definition: ssd1306_1bit.c:612
SCharInfo::height
uint8_t height
char height in pixels
Definition: nano_gfx_types.h:121
ssd1306_positiveMode
void ssd1306_positiveMode()
Definition: ssd1306_1bit.c:1089
SPRITE::data
const uint8_t * data
Pointer to PROGMEM data, representing sprite image.
Definition: nano_gfx_types.h:159
ssd1306_createSprite
SPRITE ssd1306_createSprite(uint8_t x, uint8_t y, uint8_t w, const uint8_t *data)
Definition: ssd1306_1bit.c:1074
lcd_common.h
SFixedFontInfo::primary_table
const uint8_t * primary_table
font chars bits
Definition: nano_gfx_types.h:111
SCharInfo
Definition: nano_gfx_types.h:118
ssd1306_printFixed2x
uint8_t ssd1306_printFixed2x(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style)
Definition: ssd1306_1bit.c:236
ssd1306.h
ssd1306_drawXBitmap
void ssd1306_drawXBitmap(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:837
ssd1306_drawLine
void ssd1306_drawLine(uint8_t x1, uint8_t y1, uint8_t x2, uint8_t y2)
Definition: ssd1306_1bit.c:639
ssd1306_printFixed
uint8_t ssd1306_printFixed(uint8_t xpos, uint8_t y, const char *ch, EFontStyle style)
Definition: ssd1306_1bit.c:79
ssd1306_interface_t::stop
void(* stop)(void)
Definition: ssd1306_interface.h:65
ssd1306_drawSprite
void ssd1306_drawSprite(SPRITE *sprite)
Definition: ssd1306_1bit.c:989
SFontHeaderRecord::width
uint8_t width
width in pixels
Definition: nano_gfx_types.h:90
lcdint_t
int lcdint_t
Definition: io.h:63
ssd1306_drawRect
void ssd1306_drawRect(uint8_t x1, uint8_t y1, uint8_t x2, uint8_t y2)
Definition: ssd1306_1bit.c:717
ssd1306_lcd_t::set_block
void(* set_block)(lcduint_t x, lcduint_t y, lcduint_t w)
Sets block in RAM of lcd display controller to write data to.
Definition: lcd_common.h:114
ssd1306_fillScreen
void ssd1306_fillScreen(uint8_t fill_Data)
Definition: ssd1306_1bit.c:50
lcduint_t
unsigned int lcduint_t
Definition: io.h:65
io.h
ssd1306_i2c.h
ssd1306_lcd_t::send_pixels8
void(* send_pixels8)(uint8_t data)
Sends RGB pixel encoded in 3-3-2 format to OLED driver. Sends RGB pixel encoded in 3-3-2 format to OL...
Definition: lcd_common.h:142
ssd1306_eraseTrace
void ssd1306_eraseTrace(SPRITE *sprite)
Definition: ssd1306_1bit.c:1037
ssd1306_lcd_t::send_pixels_buffer1
void(* send_pixels_buffer1)(const uint8_t *buffer, uint16_t len)
Definition: lcd_common.h:135
ssd1306_drawBitmap
void ssd1306_drawBitmap(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:786
ssd1306xled_font6x8
const PROGMEM uint8_t ssd1306xled_font6x8[]
Definition: ssd1306_fonts.c:42
ssd1306_lcd_t::send_pixels1
void(* send_pixels1)(uint8_t data)
Definition: lcd_common.h:128
SFontHeaderRecord::height
uint8_t height
height in pixels
Definition: nano_gfx_types.h:91
SFixedFontInfo
Definition: nano_gfx_types.h:105
gfx_drawMonoBitmap
void gfx_drawMonoBitmap(lcdint_t x, lcdint_t y, lcduint_t w, lcduint_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:870
SPRITE
Definition: nano_gfx_types.h:146
SFontHeaderRecord::ascii_offset
uint8_t ascii_offset
ascii offset
Definition: nano_gfx_types.h:92
ssd1306_spi.h
ssd1306_commands.h
ssd1306_lcd
ssd1306_lcd_t ssd1306_lcd
Definition: lcd_common.c:33
ssd1306_print
size_t ssd1306_print(const char ch[])
Prints null-terminated string to display at current cursor position.
Definition: ssd1306_1bit.c:458
ssd1306_charF12x16
uint8_t ssd1306_charF12x16(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style)
Definition: ssd1306_1bit.c:515
ssd1306_setFont6x8
void ssd1306_setFont6x8(const uint8_t *progmemFont)
Definition: ssd1306_1bit.c:1094
ssd1306_eraseSprite
void ssd1306_eraseSprite(SPRITE *sprite)
Definition: ssd1306_1bit.c:1015
ssd1306_drawVLine
void ssd1306_drawVLine(uint8_t x1, uint8_t y1, uint8_t y2)
Definition: ssd1306_1bit.c:693
ssd1306_fillRect
void ssd1306_fillRect(lcdint_t x1, lcdint_t y1, lcdint_t x2, lcdint_t y2)
Definition: ssd1306_1bit.c:942
ssd1306_intf
ssd1306_interface_t ssd1306_intf
Definition: ssd1306_interface.c:31
max
#define max(a, b)
Definition: nano_gfx_types.h:40
SPRITE::y
uint8_t y
draw position Y on the screen
Definition: nano_gfx_types.h:151
min
#define min(a, b)
Definition: nano_gfx_types.h:35
ssd1306_lcd_t::height
lcduint_t height
Definition: lcd_common.h:97
SCharInfo::width
uint8_t width
char width in pixels
Definition: nano_gfx_types.h:120
ssd1306_drawSpriteEx
void ssd1306_drawSpriteEx(uint8_t x, uint8_t y, uint8_t w, const uint8_t *sprite)
Definition: ssd1306_1bit.c:977
s_fixedFont
SFixedFontInfo s_fixedFont
Definition: tiler.h:44
SFixedFontInfo::h
SFontHeaderRecord h
record, containing information on font
Definition: nano_gfx_types.h:107
ssd1306_interface.h
SPRITE::x
uint8_t x
draw position X on the screen
Definition: nano_gfx_types.h:149
ssd1306_fonts.h
SCharInfo::glyph
const uint8_t * glyph
char data, located in progmem.
Definition: nano_gfx_types.h:123
ssd1306_printFixedN
uint8_t ssd1306_printFixedN(uint8_t xpos, uint8_t y, const char ch[], EFontStyle style, uint8_t factor)
Definition: ssd1306_1bit.c:317
SPRITE::w
uint8_t w
sprite width
Definition: nano_gfx_types.h:153
ssd1306_drawHLine
void ssd1306_drawHLine(uint8_t x1, uint8_t y1, uint8_t x2)
Definition: ssd1306_1bit.c:683
ssd1306_displayHeight
lcduint_t ssd1306_displayHeight(void)
Definition: ssd1306_generic.c:58
ssd1306_lcd_t::next_page
void(* next_page)(void)
Definition: lcd_common.h:122
SCharInfo::spacing
uint8_t spacing
additional spaces after char in pixels
Definition: nano_gfx_types.h:122
SPRITE::lx
uint8_t lx
last draw position X on the screen
Definition: nano_gfx_types.h:155
ssd1306_clearBlock
void ssd1306_clearBlock(uint8_t x, uint8_t y, uint8_t w, uint8_t h)
Definition: ssd1306_1bit.c:927
ssd1306_getCharBitmap
void ssd1306_getCharBitmap(uint16_t unicode, SCharInfo *info)
returns char data for currently set (active) font.
Definition: ssd1306_generic.c:93
ssd1306_lcd_t::width
lcduint_t width
Definition: lcd_common.h:94
ssd1306_charF6x8_eol
uint8_t ssd1306_charF6x8_eol(uint8_t left, uint8_t y, const char ch[], EFontStyle style, uint8_t right)
Definition: ssd1306_1bit.c:590
ssd1306_clearScreen
void ssd1306_clearScreen()
Definition: ssd1306_1bit.c:65
ssd1306_replaceSprite
void ssd1306_replaceSprite(SPRITE *sprite, const uint8_t *data)
Definition: ssd1306_1bit.c:1079
SSD1306_MORE_CHARS_REQUIRED
#define SSD1306_MORE_CHARS_REQUIRED
Definition: ssd1306_generic.h:43
EFontStyle
EFontStyle
Definition: nano_gfx_types.h:69
ssd1306_drawBufferFast
void ssd1306_drawBufferFast(lcdint_t x, lcdint_t y, lcduint_t w, lcduint_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:725
SFixedFontInfo::pages
uint8_t pages
height in pages (each page height is 8-pixels)
Definition: nano_gfx_types.h:109
ssd1306_swap_data
#define ssd1306_swap_data(a, b, type)
Definition: io.h:69
SPRITE::ly
uint8_t ly
last draw position Y on the screen
Definition: nano_gfx_types.h:157
ssd1306_negativeMode
void ssd1306_negativeMode()
Definition: ssd1306_1bit.c:1084
ssd1306_putPixel
void ssd1306_putPixel(uint8_t x, uint8_t y)
Definition: ssd1306_1bit.c:605
ssd1306_drawBuffer1_4
void ssd1306_drawBuffer1_4(uint8_t x, uint8_t y, uint8_t w, uint8_t h, const uint8_t *buf)
Definition: ssd1306_1bit.c:753
ssd1306_write
size_t ssd1306_write(uint8_t ch)
Prints single character to display at current cursor position.
Definition: ssd1306_1bit.c:418