[052] Wyświetlacze OLED SSD1306 cz. 2

[052] Wyświetlacze OLED SSD1306 cz. 2

Skoro wiemy już czym są wyświetlacze OLED i jak je podłączyć, zróbmy sobie użytek z jednego, tworząc szkoleniową aplikację. Użyjemy do tego peryferiów znajdujących się na płytce edukacyjnej TME-EDU-ARD-2, a konkretnie czterech:


Potencjometru – będziemy mierzyć napięcie związane z położeniem jego suwaka.

Fototranzystora – będziemy mierzyć natężenie światła.

Mikrofonu – będziemy mierzyć natężenie dźwięku.

Termometru – będziemy mierzyć temperaturę.

Przedstawię teraz typowy użytkowy szkic, pokazujący cztery przykładowe parametry korzystające z wymienionych źródeł. Jest to tak naprawdę zmodyfikowany pomysł z biblioteki dołączonej do płytki, który ograniczyłem do naszych zagadnień i praktycznie napisałem na nowo, by był czytelny, choć niekoniecznie optymalny. Zmierzone parametry będziemy wizualizować za pomocą napisów i grafik.

#include <Adafruit_GFX.h>                      // Biblioteka obsługująca rysowanie grafik na wyświetlaczach.
#include <Adafruit_SSD1306.h>                  // Biblioteka obsługująca ten konkretny wyświetlacz.
Adafruit_SSD1306 wyswietlacz(128, 64, &Wire);  // Nazwa wyświetlacza, szerokość, wysokość, interfejs I2C

const byte potencjometr = A1;    // Port, który będzie czytać położenie potencjometru.
const byte fototranzystor = A3;  // Port, który będzie czytać poziom światła.
const byte mikrofon = A0;        // Port, który będzie czytać poziom dźwięku.
const byte termometr = A2;       // Port, który będzie czytać temperaturę.

void setup() {
  wyswietlacz.begin(SSD1306_SWITCHCAPVCC, 0x3C);  // Zasilanie części wyświetlającej z pokładowego źródła napięcia, adres I2C
  wyswietlacz.setTextColor(1);                    // Wybierz biały kolor znaków (widoczny).
  wyswietlacz.clearDisplay();                     // Wyczyść wyświetlacz.

  wyswietlacz.setCursor(0, 0);            // Ustaw kursor w wybranym miejscu.
  wyswietlacz.print(F("POTENCJOMETR"));   // Załaduj tekst do wyświetlenia.
  wyswietlacz.drawRect(0, 8, 128, 5, 1);  // Rysuj prostokąt.
  wyswietlacz.setCursor(0, 16);
  wyswietlacz.print(F("FOTOTRANZYSTOR"));
  wyswietlacz.drawRect(0, 24, 128, 5, 1);
  wyswietlacz.setCursor(0, 32);
  wyswietlacz.print(F("MIKROFON"));
  wyswietlacz.drawRect(0, 40, 128, 5, 1);
  wyswietlacz.setCursor(0, 48);
  wyswietlacz.print(F("TERMOMETR"));
  wyswietlacz.drawRect(0, 56, 128, 5, 1);
  wyswietlacz.display();  // Wyświetl załadowaną grafikę.
}
void loop() {

  int potencjometrWartosc = analogRead(potencjometr);                           // Zmierz wartość położenia potencjometru.
  wyswietlacz.fillRect(104, 0, 23, 7, 0);                                       // Rysuj prostokąt, który wymaże poprzedni wynik.
  wyswietlacz.setCursor(104, 0);                                                // Ustaw kursor w wybranym miejscu.
  wyswietlacz.print(potencjometrWartosc);                                       // Wyświetl zmierzoną wartość.
  wyswietlacz.fillRect(1, 9, 126, 3, 0);                                        // Rysuj prostokąt, który wymaże poprzedni wskaźnik.
  wyswietlacz.fillRect(1, 9, map(potencjometrWartosc, 0, 1023, 0, 126), 3, 1);  // Rysuj prostokąt - wskaźnik.

  int fototranzystorWartosc = analogRead(fototranzystor);  // Zmierz poziom jasności.
  wyswietlacz.fillRect(104, 16, 23, 7, 0);
  wyswietlacz.setCursor(104, 16);
  wyswietlacz.print(fototranzystorWartosc);
  wyswietlacz.fillRect(1, 25, 126, 3, 0);
  wyswietlacz.fillRect(1, 25, map(fototranzystorWartosc, 0, 1023, 0, 126), 3, 1);

  int mikrofonWartosc = analogRead(mikrofon);  // Zmierz poziom dźwięku.
  wyswietlacz.fillRect(104, 32, 23, 7, 0);
  wyswietlacz.setCursor(104, 32);
  wyswietlacz.print(mikrofonWartosc);
  wyswietlacz.fillRect(1, 41, 126, 3, 0);
  wyswietlacz.fillRect(1, 41, map(mikrofonWartosc, 0, 1023, 0, 126), 3, 1);

  int termometrWartosc = analogRead(termometr);  // Zmierz temperaturę.
  wyswietlacz.fillRect(104, 48, 23, 7, 0);
  wyswietlacz.setCursor(104, 48);
  wyswietlacz.print(termometrWartosc * 0.125 - 22, 1);  // Wyświetl zmierzoną wartość z dokładnością do jednej cyfry po przecinku.
  wyswietlacz.fillRect(1, 57, 126, 3, 0);
  wyswietlacz.fillRect(1, 57, map(termometrWartosc, 296, 416, 0, 126), 3, 1);  // Rysuj wskaźnik dla przedziału +15..+30 stopni.

  wyswietlacz.display();  // Wyświetl załadowaną grafikę.
}

Na początku zaimportujemy bibliotekę całej serii wyświetlaczy graficznych oraz dodatek, związany już z naszym, konkretnym układem.

#include <Adafruit_GFX.h>                      // Biblioteka obsługująca rysowanie grafik na wyświetlaczach.
#include <Adafruit_SSD1306.h>                  // Biblioteka obsługująca ten konkretny wyświetlacz.
Adafruit_SSD1306 wyswietlacz(128, 64, &Wire);  // Nazwa wyświetlacza, szerokość, wysokość, interfejs I2C

Kolejno należy skonfigurować parametry posiadanego wyświetlacza, a więc rozdzielczość i interfejs. Można też dodać linię resetu, ale nie jest to konieczne, więc parametr ten pominąłem.

const byte potencjometr = A1;    // Port, który będzie czytać położenie potencjometru.
const byte fototranzystor = A3;  // Port, który będzie czytać poziom światła.
const byte mikrofon = A0;        // Port, który będzie czytać poziom dźwięku.
const byte termometr = A2;       // Port, który będzie czytać temperaturę.

Wymienione peryferia na płytce edukacyjnej przyporządkowano adresom od A0 do A3, więc należy je odpowiednio zadeklarować.

wyswietlacz.begin(SSD1306_SWITCHCAPVCC, 0x3C);  // Zasilanie części wyświetlającej z pokładowego źródła napięcia, adres I2C

Wyświetlacz należy zainicjować, odwołując się do konkretnego adresu na magistrali. Konieczne jest także uruchomienie przetwornicy napięcia dla diod, za pomocą widocznej wyżej komendy.

wyswietlacz.setTextColor(1);  // Wybierz biały kolor znaków (widoczny).

Wymaga się tutaj również określenia koloru znaków jako biały bądź podanie jedynki. Bez tej instrukcji napisy byłyby niewidoczne. Co ciekawe, rysowanie grafik nie wymaga tego wpisu.

wyswietlacz.clearDisplay();  // Wyczyść wyświetlacz.

W końcu czyścimy wyświetlacz. W przypadku braku linii resetu jest to konieczne, inaczej po włączeniu zasilania mogły by się pojawić przypadkowe świecące punkty.

wyswietlacz.setCursor(0, 0);            // Ustaw kursor w wybranym miejscu.
wyswietlacz.print(F("POTENCJOMETR"));   // Załaduj tekst do wyświetlenia.
wyswietlacz.drawRect(0, 8, 128, 5, 1);  // Rysuj prostokąt.

Czas na narysowanie części niezmiennej. To już znamy z poprzednich artykułów. Pierwsza instrukcja ustawia kursor w wybranym miejscu. Druga przesyła teksty do wyświetlenia. Przypominam, użycie parametru F lokuje je w pamięci Flash, a nie w RAM-ie, którego zawsze mamy mniej. Trzecia instrukcja rysuje prostokąt o początku określonym parą liczb i wymiarach – następną parą, w kolorze ostatniego parametru, czyli świecącym. Powtarzamy to cztery razy: w każdej ćwiartce wyświetlacza drukujemy opis parametru oraz prostokąt.

wyswietlacz.display();  // Wyświetl załadowaną grafikę.

Na końcu należy wysłać tę instrukcję, by nasze działania uwidoczniły się.

W głównej pętli będziemy mierzyć kolejne cztery wielkości i osadzać wyniki na wyświetlaczu. Zaczniemy od potencjometru.

int potencjometrWartosc = analogRead(potencjometr);  // Zmierz wartość położenia potencjometru.

Mierzymy jego wielkość i przesyłamy do tej zmiennej potencjometrWartosc. Teraz natrafimy na problem nieznany z wyświetlaczy alfanumerycznych. Tam, rysując nowy znak, wymazywaliśmy poprzedni automatycznie. Tutaj nic takiego się nie dzieje i musimy o to zadbać sami.

wyswietlacz.fillRect(104, 0, 23, 7, 0);  // Rysuj prostokąt, który wymaże poprzedni wynik.
wyswietlacz.setCursor(104, 0);           // Ustaw kursor w wybranym miejscu.
wyswietlacz.print(potencjometrWartosc);  // Wyświetl zmierzoną wartość.

Można to zrobić na różne sposoby, wybrałem rysowanie „czarnego prostokąta” o wymiarach pokrywających napis, który zaraz potem umieszczamy w tym miejscu

wyswietlacz.fillRect(1, 9, 126, 3, 0);                                        // Rysuj prostokąt, który wymaże poprzedni wskaźnik.
wyswietlacz.fillRect(1, 9, map(potencjometrWartosc, 0, 1023, 0, 126), 3, 1);  // Rysuj prostokąt - wskaźnik.

W końcu trzeba narysować bargraf. Dokładnie wewnątrz narysowanego w części wstępnej prostokąta rysujemy kolejny – tym razem wypełniony, ale o długości proporcjonalnej do wartości położenia ślizgacza potencjometru. Ową proporcję wyliczy nam funkcja map, która przerzuci wartość do przedziału od zera do 126. Wcześniej jednak należy wymazać bargraf dla wartości poprzedniej, rysując maksymalny prostokąt atramentem czarnym. Bardziej elegancko byłoby użyć mniej czasochłonnej metody, np. dorysowując czarną, brakującą część bargrafu po rysowaniu części białej, ale w tym przypadku nie ma to znaczenia.

Podobnie postępujemy z wartością zmierzonego światła – przesuwając wszystko o 16 pikseli w dół. Następnie bliźniacza część dotyczy mierzenia poziomu dźwięku no i ostatnia, która mierzy temperaturę.

wyswietlacz.print(termometrWartosc * 0.125 - 22, 1);  // Wyświetl zmierzoną wartość z dokładnością do jednej cyfry po przecinku.

Tutaj jednak postanowiłem wyświetlać wartość w stopniach, a nie bezpośrednio i tę należy przeliczyć za pomocą takiego wzoru.

wyswietlacz.fillRect(1, 57, map(termometrWartosc, 296, 416, 0, 126), 3, 1);  // Rysuj wskaźnik dla przedziału +15..+30 stopni.

Bargraf także przeprojektowałem: minimum pokazuje wartość +15 stopni, a maksimum +30. Tę rzecz tworzy kolejna funkcja mapująca, ograniczająca przedział do wartości wyliczonych z przekształcenia wzoru użytego wyżej.

Na koniec przyjrzyjmy się dodatkowym użytecznym instrukcjom.

wyswietlacz.ssd1306_command(SSD1306_DISPLAYOFF);  // Szybkie wyłączenie wyświetlacza.
wyswietlacz.ssd1306_command(SSD1306_DISPLAYON);   // Ponowne włączenie wyświetlacza.

Ta para pozwala wyłączać i włączać wyświetlacz. Trzeba jednak pamiętać, że proces ten trwa chwilę i opóźnienie może być widoczne.

wyswietlacz.ssd1306_command(SSD1306_SETCONTRAST);  // Możemy też regulować jasność płynnie, w niewielkich granicach.
wyswietlacz.ssd1306_command(255);                  // Zakres: 0...255

Tutaj mamy funkcję wymagającą dwóch instrukcji, która pozwala zmieniać jasność wyświetlacza w sposób płynny. Wbrew nazwie nie zmienia się tutaj kontrastu. Różnica między poziomami minimalnym i maksymalnym nie jest tak duża i może to stanowić problem na przykład w nocy, gdy wyświetlacz będzie świecił zbyt jasno.

wyswietlacz.dim(1);  // W ten sposób możemy przyciemnić wyświetlacz.

Funkcją dodatkową jest ta. Przyjmuje jedynie dwie wartości: jedynka daje przyciemnioną jasność, zero – pełną.

I to już wszystko. Wszelkie inne instrukcje związane z tym wyświetlaczem znajdziemy w artykule o wyświetlaczu z telefonów Nokii. Trzeba tylko pamiętać o różnicach rozdzielczości i brać ją pod uwagę przy przenoszeniu projektów pomiędzy wyświetlaczami.

Płytka edukacyjna TME-EDU-ARD-2Płytka edukacyjna TME-EDU-ARD-2Sprawdź tutaj

Przeczytaj również

Nasi partnerzy

TMETech Master EventTME EducationPoweredby
Copyright © 2024 arduino.pl