Serwisy partnerskie:
Close icon
Serwisy partnerskie

Kurs Arduino odcinek 20c - biblioteki do obsługi wyświetlaczy graficznych

Ten odcinek zaczniemy od kolejnego przykładu wykorzystania znanej już biblioteki MD_UISwitch, stworzonej przez Marco Colli (MajicDesigns).
Article Image
1. Kurs Arduino: wprowadzenie 2. Kurs Arduino odcinek 1 - co to jest i jak zacząć? (sprzęt, schematy, programowanie) 3. Kurs Arduino odcinek 2 - termometry: 'diodowy', pokojowy oraz 'scalony' analogowy 4. Kurs Arduino odcinek 3 - moduł wyświetlacza LCD (HD44780) 5. Kurs Arduino odcinek 4 - czujnik BME280 (pomiar ciśnienia, wilgotności i temperatury) 6. Kurs Arduino odcinek 5 - biblioteki do trzyfunkcyjnego czujnika BME280 7. Kurs Arduino odcinek 6 - wykorzystanie łącza I2C (TWI) 8. Kurs Arduino odcinek 7 - wykorzystanie łącza SPI (karty pamięci, MAX31865, MAX31855) 9. Kurs Arduino odcinek 8 - wykorzystanie czujnika dwutlenku węgla (MH-Z19) 10. Kurs Arduino odcinek 9 - wykorzystanie modułów do odmierzania czasu 11. Kurs Arduino odcinek 10 - wykorzystanie czujników temperatury (DS18B20) 12. Kurs Arduino odcinek 11 - budowa loggera (rejestratora danych) 13. Kurs Arduino odcinek 12 - rejestracja i prezentacja danych oraz obsługa karty SD 14. Kurs Arduino odcinek 13 - rejestracja danych (wykorzystanie modułu OpenLog) 15. Kurs Arduino odcinek 14 - czym zastąpić płytkę Arduino Uno? 16. Kurs Arduino odcinek 15 - budowa rejestratora (chiński klon Arduino Pro Mini) 17. Kurs Arduino odcinek 16 - problemy z kwadratowym modułem Strong 18. Kurs Arduino odcinek 17 - czujniki do pomiaru wilgotności gleby (instalacja, konfiguracja) 19. Kurs Arduino odcinek 18 - protokół MODBUS i łącze RS-485 20. Kurs Arduino odcinek 19 - wyświetlacze od podstaw (matrycowe, 7-segmentowe, MAX7219) 21. Kurs Arduino odcinek 20a - wyświetlacze matrycowe i biblioteki MD_MAX 22. Kurs Arduino odcinek 20b - przyciski i biblioteki do obsługi wyświetlaczy 23. Kurs Arduino odcinek 20c - biblioteki do obsługi wyświetlaczy graficznych 24. Kurs Arduino odcinek 21 - moduł wyświetlacza OLED 25. Kurs Arduino odcinek 22 - moduł wyświetlacza 1,3 cala 26. Kurs Arduino odcinek 23 - przygotowanie bitmap do wyświetlania 27. Kurs Arduino odcinek 24 - omówienie fontu podstawowego (Adafruit GFX) 28. Kurs Arduino odcinek 25 - font podstawowy biblioteki Adafruit GFX 29. Kurs Arduino odcinek 26 - wykorzystanie bitmapowych fontów GFX 30. Kurs Arduino odcinek 27 - polskie znaki w glcdfont.c 31. Kurs Arduino odcinek 28 - zmiana ulepszonych fontów GFX

Jeżeli masz klawiaturę matrycową 4×4, dołącz ją do płytki Arduino według rysunku 16 i fotografii okładkowej. Niestety potrzeba do tego aż ośmiu pinów, które musisz wskazać, jak pokazuje szkic 11, gdzie widać też, że klawiaturę matrycową można dołączyć do dowolnych pinów Arduino.

Rys.16 Klawiatura matrycowa 4×4, dołączona do płytki Arduino - zdjęcie

Ja skompilowałem tak zmodyfikowany szkic MD_UISwitch_Example.ino z jedynką w linii:

#define TEST_MATRIX_4b4 1

Po otwarciu na komputerze Monitora portu szergowego (Ctrl+Shift+M) możemy testować reakcje poszczególnych klawiszy. Jak wskazuje szkic 11, definiujemy tablicę znaków o nazwie kt, w której zawarte są oznaczenia klawiszy: cyfry, litery A, B, C, D oraz symbole * i #. Dlatego naciśniecie klawisza powoduje zwrócenie i wyświetlenie na ekranie znaku z tego klawisza. A konkretnie znaku ASCII i jego numeru w kodzie szesnastkowym.

Szkic 11

(...) #if TEST_MATRIX_4b4
#define TITLE "Matrix 4x4"
uint8_t rowPins[] = { 9, 8, 7, 6 }; // rzędy
uint8_t colPins[] = {5, 4, 3, 2 }; // kolumny
const uint8_t ROWS = sizeof(rowPins);
const uint8_t COLS = sizeof(colPins);
char kt[(ROWS*COLS) + 1] = "123A456B789C*0#D"; //symbole
MD_UISwitch_Matrix S(ROWS, COLS, rowPins, colPins, kt);
#endif (...)

Co ważne, dla każdego klawisza dostępne są wszystkie wcześniejsze możliwości: naciśnięcie krótkie, długie, "dwuklik" i naciskanie ciągłe. Przykładowy zrzut ekranu konsoli monitora pokazany jest na rysunku 18. Możliwości są duże, ale niestety, sposoby wykorzystania tej biblioteki nie są najłatwiejsze. Zapewne poradzisz sobie jednak z adaptacją ich w swoich szkicach, by wykorzystać wartości zwracane przez funkcje – metody: numer-nazwa przycisku oraz jego stan, badany instrukcją switch-case. Możesz zacząć od wyczyszczenia przykładowych szkiców z tego, co nie jest konieczne i wtedy pozostanie sama esencja, którą możesz przenieść do własnych szkiców.

Rys.18 Zrzut konsoli po otwarciu monitora portu szeregowego

Możesz zacząć od pojedynczego przycisku. Kluczową funkcją – metodą jest .read(), określająca rodzaj naciśnięcia. Zwraca ona stan przycisku za pomocą własnego typu wyliczeniowego keyResult_t. W przypadku większej liczby przycisków trzeba też określić, który z nich został naciśnięty, co zwykle jest realizowane za pomocą wcześniej określonej tablicy.

Możesz też zapoznać się z łatwiejszą do wykorzystania biblioteką MD_REncoder do obsługi obrotowego enkodera (elektronicznego potencjometru – Rotary Encoder) ze strony. Zwraca ona nie tylko impulsy wskazujące aktywność i kierunek obrotu, ale też prędkość pokręcania, co można wykorzystać do wzbogacenia funkcji takiego enekodera.

Jaką bibliotekę wybrać do obsługi wyświetlacza?

Oprócz bibliotek omówionych w tym artykule, Marco Colli (MajicDesigns) udostępnił też szereg innych bibliotek i projektów. Mają one bardzo dobrą jakość i mogą okazać się bardzo przydatne. Jednak nie przywiązuj się zbytnio do skądinąd znakomitych bibliotek MD_MAX72xx,MD_MAXPanel i MD_Parola. Są one przeznaczone tylko dla wyświetlaczy matrycowych LED z kostką MAX7219.

Wyświetlacze takie niewątpliwie są bardzo atrakcyjne, ale nas ciągnie też do wyświetlaczy graficznych LCD i OLED o wyższej rozdzielczości. A niestety, tam te trzy biblioteki nie są przydatne. Dlatego powinniśmy przyjrzeć się zupełnie innym bibliotekom do obsługi wyświetlaczy matrycowych i graficznych. Pozostańmy jeszcze przy matrycach LED, ale zainteresujmy się biblioteką Adafruit GFX oraz biblioteką arduino-Max72xxPanel, której twórcą jest Mark Ruys z Holandii.

Wcześniej mieliśmy podstawową bibliotekę MD_MAX72xx, która zapewniała komunikację z kostką (kostkami) MAX7219 i wyświetlaczem, a do tego biblioteki pomocnicze, które realizowały bardziej zaawansowane funkcje. Teraz jest podobnie: mamy sprzętową bibliotekę arduino-Max72xxPanel, a do tego pomocniczą bibliotekę Adafruit GFX, która realizuje bardziej zaawansowane funkcje związane z rysowaniem elementarnych figur geometrycznych, grafik oraz napisów z wykorzystaniem (fontów-czcionek).

Biblioteka Adafruit GFX, jak wskazuje nazwa, powstała w znanej firmie Adafruit, ale wcale nie dla kostki MAX7219. Adafruit ma w swej bogatej ofercie handlowej mnóstwo większych i mniejszych wyświetlaczy graficznych: kolorowych i monochromatycznych. Można to sprawdzić na stronie.

Biblioteka Adafruit GFX do wyświetlaczy graficznych

Biblioteka Adafruit GFX jest uniwersalna, bo realizuje „wyższe” funkcje, wspólne dla wszystkich wyświetlaczy graficznych. Nie ma ona natomiast możliwości bezpośredniej współpracy z jakimkolwiek wyświetlaczem, bo jest tylko swego rodzaju nakładką, która ma współpracować z oddzielną biblioteką sprzętową, przeznaczoną do konkretnego wyświetlacza, a raczej do konkretnego scalonego sterownika.

Adafruit udostępnia biblioteki sprzętowe do wszystkich sprzedawanych przez siebie wyświetlaczy graficznych LCD i OLED – będziemy z niektórych korzystać. A zapoznanie się z biblioteką GFX jest absolutnie niezbędne, ponieważ będzie ona potrzebna, gdy będziemy chcieli wykorzystać różne wyświetlacze graficzne.

Inne biblioteki do obsługi wyświetlaczy graficznych

Firma Adafruit ma dobrą opinię, jej sprzęt i oprogramowanie także, więc także Ty możesz z powodzeniem skorzystać z udostępnionych przez nią bibliotek. Ale trzeba też wiedzieć, że są i inne możliwości obsługi wyświetlaczy graficznych. Na przykład od szeregu lat znana jest biblioteka U8glib, obecnie zastąpiona przez U8g2 (wraz z U8x8), która realizuje „wyższe” funkcje graficzne i tekstowe, a jednocześnie zapewnia bezpośrednią współpracę z szeregiem wyświetlaczy graficznych, ale tylko monochromatycznych, a nie kolorowych.

Dla zainteresowanych: biblioteka U8g2 w wersji dla Arduino jest dostępna pod adresem, ale można ją też zainstalować z pomocą Menedżera bibliotek. My pominiemy bibliotekę U8g2, a bliżej zainteresujemy się bardziej uniwersalną biblioteką Adafruit GFX, bowiem przyda się ona też do wyświetlaczy kolorowych.

A na razie wracamy do matrycowego wyświetlacza LED 32 × 8 z czterech modułów FC16. Podłączenie jest identyczne jak wcześniej (rysunek 7). Mark Ruys, twórca biblioteki arduino-Max72xxPanel, napisał ją tak, żeby współpracowała z popularną biblioteką Adafruit-GFX-Library, którą możemy zainstalować przez Menedżera bibliotek. Natomiast sprzętową bibliotekę arduino-Max72xxPanel trzeba zainstalować ręcznie, po ściągnięciu jej ze strony.

czyli po prostu rozpakować do katalogu .../Dokumenty/Arduino/libraries/

W bibliotece arduino-Max72xxPanel-master jest katalog /examples/, a w nim katalog /Snake ze szkicem o starym rozszerzeniu (Snake.pde) realizującym popularnego węża, który wije się po całym wyświetlaczu. Najpierw możesz skompilować i wgrać oryginalny szkic (Snake.pde). Gdyby nie chciał się skompilować, zapisz go pod inną nazwą. Na wyświetlaczu zobaczysz cztery jednakowe węże.

Aby uzyskać prawidłowy efekt, musisz podać odpowiednie informacje, jak widać w spolszczonym szkicu A2006.ino i w szkicu 12: liczbę modułów poziomo (4) i pionowo (1) oraz rozmieszczenie modułów za pomocą funkcji .setPosition() (gdzie pierwszy wyświetlacz o numerze 0 jest najbliższy Arduino) i ich „obrót” – setRotation(), gdzie dla FC16 należy wpisać 1 (obrót o 90°).

Szkic 12

#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Max72xxPanel.h>
int pinCS = 10; // który pin ma być CS w sprzetowym łaczu SPI?
int ModulowPoziomo = 4; // cztery moduły
int ModulowPionowo = 1; // w jednym rzedzie
// tworzymy tylko obiekt wyświetlacza = wysw
Max72xxPanel wysw = Max72xxPanel(pinCS, ModulowPoziomo, ModulowPionowo);
const int pinRandom = A0; //"ziarno" dla gen. pseudolosowego
const int wait = 100; // opóźnienie w milisekundach
const int length = 12; //długość węża
int x[length], y[length]; //pozycja
int ptr, nextPtr; // dwa wskaźniki
void setup() { // jednorazowo w funkcji setup():
wysw.setIntensity(1); // jasność (0...15)
// określamy, jak połączone i obrócone są cztery moduły o nr 0...3
wysw.setPosition(0, 0, 0); // najbliższy płytki Arduino
wysw.setPosition(1, 1, 0); // następny jest drugi w tym samym rzędzie
wysw.setPosition(2, 2, 0); // trzeci jest następny w tym samym rzędzie
wysw.setPosition(3, 3, 0); // czwarty - następny w tym samym rzędzie
wysw.setRotation(0, 1); // w czteromodułoej płytce wszystkie cztery FC16
wysw.setRotation(1, 1); // są niejako obrócone o 90 stopni w prawo
wysw.setRotation(2, 1); //stąd we wszystkich czterech przypadkach
wysw.setRotation(3, 1); // liczba 1, czyli "rotated 90o clockwise"

Gdy pobawisz się wężem, możesz wykorzystać inne zawarte w tej bibliotece przykłady. Nie namawiam do analizy treści tych szkiców. Koniecznie musisz się jednak zapoznać z biblioteką Adafruit GFX, której najnowszy opis znajdziesz pod adresem.

Na początku wspomniane jest tam o instalacji biblioteki o nazwie Adafruit_ZeroDMA, co miałoby sens w przypadku wycofanej już ze sprzedaży płytki Arduino Zero z potężnym 32-bitowym procesorem Atmel’s SAMD21 (ARM), a nie z płytkami Arduino zawierającymi ATmega328P, gdzie nie ma DMA.

Rys.19 Numeracja pikseli w wyświetlaczach graficznych

Raz na zawsze trzeba zapamiętać, że w wyświetlaczach graficznych piksele numeruje się, począwszy od górnego, lewego rogu, jak pokazuje pochodzący z tego pliku PDF rysunek 19 i tak trzeba podawać w funkcjach współrzędne x, y (w pikselach).

Biblioteka GFX wykorzystuje 16-bitowy model koloru (65536 odcieni) według rysunku 20. W wyświetlaczach monochromatycznych mamy tylko dwa kolory piksela: 0 (wyłączony) i 1 (aktywny).

Szkic 13

drawPixel(x, y, color);
drawLine(x0, y0, x1, y1, color);
drawFastVLine(x0, y0, length, color);
drawFastHLine(x0, y0, length, color);
drawRect(x0, y0, w, h, color);
fillRect(x0, y0, w, h, color);
drawCircle(x0, y0, r, color);
fillCircle(x0, y0, r, color);
drawRoundRect(x0, y0, w, h, radius, color);
fillRoundRect(x0, y0, w, h, radius, color);
drawTriangle(x0, y0, x1, y1, x2, y2, color);
fillTriangle(x0, y0, x1, y1, x2, y2, color);
fillScreen(color);
drawChar(x, y, char c, color, bg, size);
setCursor(x0, y0);
setTextColor(color);
setTextColor(color, backgroundcolor);
setTextSize(size);
setTextWrap(w);
print("napis do wyswietlenia");

Jak pokazuje szkic 13, w bibliotece GFX mamy szereg funkcji-metod do rysowania na ekranie podstawowych elementów graficznych: punktów, linii, (szybkich) linii pionowych i poziomych, prostokątów, wypełnionych prostokątów, okręgów i kół, prostokątów z zaokrąglonymi rogami oraz trójkątów. W każdym przypadku podajemy wymagane współrzędne i rozmiary oraz kolor.

Rys.20 16-bitowy model koloru

Ekran możemy zawsze wyczyścić / wypełnić kolorem za pomocą funkcji

fillScreen(color)

W bibliotece Adafruit GFX wbudowany jest jeden podstawowy font (czcionka). Mamy dwie funkcje „tekstowe”. Pierwsza z nich:

drawChar(x, y, char c, color, bg, size)

wyświetla tylko jeden znak (character). Jako argumenty do funkcji przekazujemy: współrzędne x, y, gdzie ma on zostać wyświetlony, znak do wyświetlenia (w pojedynczym cudzysłowie), kolor – color, kolor tła – bg (background) oraz wielkość – size (1, 2 lub 3).

Współrzędne x, y w przypadku podstawowego, wbudowanego fontu wskazują górny, lewy róg znaku, jak widać na rysunku 21.

Rys.21 x, y wskazują górny, lewy róg znaku - wbudowany font

Druga funkcja „tekstowa” jest dobrze znana z wcześniejszych ćwiczeń:

print("tekst do wyswietlenia")

Ona tylko wypisze na ekranie tekst umieszczony w podwójnym cudzysłowie. Ale gdzie i jak?

Jak pokazuje szkic 12, przed jej użyciem trzeba określić, w którym punkcie ekranu należy zacząć pisać, trzeba ustawić kolor i kolor tła oraz wielkość czcionki. Można też włączyć zawijanie tekstu do następnego wiersza (TekstWrap).

Znaki podstawowego fontu mają wielkość 5 × 7 pikseli, ale wpisując ich rozmiar (size) 2 lub 3, powiększymy rozmiar 2- lub 3-krotnie.

Aby poćwiczyć te podstawowe funkcje, przygotowałem szkic A2007.ino (dostępny w Elportalu), gdzie możesz też wpisać dodatkowo własny tekst za pomocą Monitora portu szeregowego według rysunku 22. Wykorzystałem fragment kodu ze strony. Warto tam zajrzeć, bowiem Autor pokazuje, jak ten sam efekt zrealizować za pomocą różnych bibliotek. Modyfikuj szkic A2007.ino i w ten sposób zapoznaj się z podstawowymi funkcjami biblioteki Adafruit-GFX. oraz z ograniczeniami związanymi z małą liczbą pikseli naszego matrycowego wyświetlacza LED.

Rys.22 Wyświetlanie tekstu za pomocą Monitora portu szeregowego

Zwróć uwagę, że polecenia biblioteki arduino-Max72xxPanel-master nie powodują od razu wyświetlenia na ekranie tego, co określa rozkaz. Dlatego w naszym szkicu po każdym takim rozkazie za każdym razem dodatkowo używamy funkcji:

wysw.write();

Dopiero ona powoduje wyświetlenie czegoś na ekranie. Jest to normalne, ponieważ przy obsłudze takich wyświetlaczy wykorzystujemy tak zwany bufor: pamięć pomocniczą treści całego obrazu. Funkcje rysowania/pisania modyfikują tylko treść bufora (pamięci), a nie wyświetlają go na ekranie. Zawartość bufora zostaje wyświetlona na ekranie dopiero po wykonaniu funkcji wysw.write();

Dlatego możesz zrealizować kilka funkcji rysowania/pisania, a dopiero potem wyświetlić je na ekranie.

Na razie pomijamy problem polskich liter, natomiast chcemy wykorzystać bardziej pojemny wyświetlacz, choćby najbardziej obecnie popularny OLED 128 × 64 pikseli.

W szkicu A2007.ino trzeba tylko zmienić informacje o wyświetlaczu, a kluczowe fragmenty programu pozostaną te same. W zasadzie tak, ale w grę wchodzi kilka dodatkowych szczegółów, dlatego wyświetlaczami tymi zajmiemy się w następnym odcinku naszego kursu.

1. Kurs Arduino: wprowadzenie 2. Kurs Arduino odcinek 1 - co to jest i jak zacząć? (sprzęt, schematy, programowanie) 3. Kurs Arduino odcinek 2 - termometry: 'diodowy', pokojowy oraz 'scalony' analogowy 4. Kurs Arduino odcinek 3 - moduł wyświetlacza LCD (HD44780) 5. Kurs Arduino odcinek 4 - czujnik BME280 (pomiar ciśnienia, wilgotności i temperatury) 6. Kurs Arduino odcinek 5 - biblioteki do trzyfunkcyjnego czujnika BME280 7. Kurs Arduino odcinek 6 - wykorzystanie łącza I2C (TWI) 8. Kurs Arduino odcinek 7 - wykorzystanie łącza SPI (karty pamięci, MAX31865, MAX31855) 9. Kurs Arduino odcinek 8 - wykorzystanie czujnika dwutlenku węgla (MH-Z19) 10. Kurs Arduino odcinek 9 - wykorzystanie modułów do odmierzania czasu 11. Kurs Arduino odcinek 10 - wykorzystanie czujników temperatury (DS18B20) 12. Kurs Arduino odcinek 11 - budowa loggera (rejestratora danych) 13. Kurs Arduino odcinek 12 - rejestracja i prezentacja danych oraz obsługa karty SD 14. Kurs Arduino odcinek 13 - rejestracja danych (wykorzystanie modułu OpenLog) 15. Kurs Arduino odcinek 14 - czym zastąpić płytkę Arduino Uno? 16. Kurs Arduino odcinek 15 - budowa rejestratora (chiński klon Arduino Pro Mini) 17. Kurs Arduino odcinek 16 - problemy z kwadratowym modułem Strong 18. Kurs Arduino odcinek 17 - czujniki do pomiaru wilgotności gleby (instalacja, konfiguracja) 19. Kurs Arduino odcinek 18 - protokół MODBUS i łącze RS-485 20. Kurs Arduino odcinek 19 - wyświetlacze od podstaw (matrycowe, 7-segmentowe, MAX7219) 21. Kurs Arduino odcinek 20a - wyświetlacze matrycowe i biblioteki MD_MAX 22. Kurs Arduino odcinek 20b - przyciski i biblioteki do obsługi wyświetlaczy 23. Kurs Arduino odcinek 20c - biblioteki do obsługi wyświetlaczy graficznych 24. Kurs Arduino odcinek 21 - moduł wyświetlacza OLED 25. Kurs Arduino odcinek 22 - moduł wyświetlacza 1,3 cala 26. Kurs Arduino odcinek 23 - przygotowanie bitmap do wyświetlania 27. Kurs Arduino odcinek 24 - omówienie fontu podstawowego (Adafruit GFX) 28. Kurs Arduino odcinek 25 - font podstawowy biblioteki Adafruit GFX 29. Kurs Arduino odcinek 26 - wykorzystanie bitmapowych fontów GFX 30. Kurs Arduino odcinek 27 - polskie znaki w glcdfont.c 31. Kurs Arduino odcinek 28 - zmiana ulepszonych fontów GFX
AUTOR
Źródło
Elektronika dla Wszystkich styczeń 2020
Udostępnij
UK Logo