Dodawanie przetwornika ADC do Raspberry Pi: Co musisz wiedzieć
Kluczowe wnioski
Raspberry Pi nie jest w stanie bezpośrednio przetwarzać sygnałów analogowych; można go jednak wyposażyć w zewnętrzne przetworniki analogowo-cyfrowe (ADC) w celu przekształcenia fizycznych wartości napięcia w format cyfrowy odpowiedni do przechowywania danych, manipulowania nimi i zarządzania nimi.
Popularne przetworniki analogowo-cyfrowe (ADC) obejmują MCP3004/MCP3008, które oferują równowagę między szybkością i dokładnością, a także ADS111x, który zapewnia 16-bitową rozdzielczość przy niższej częstotliwości próbkowania.
ADS1115, dostępny za pośrednictwem Adafruit, to eleganckie rozwiązanie wyposażone w programowalny wzmacniacz wzmocnienia (PGA), umożliwiający wykrywanie niewielkich różnic napięcia przy jednoczesnym ułatwieniu dynamicznej regulacji wzmocnienia podczas pracy. Integracja z Raspberry Pi poprzez I2C nie stanowi żadnego wyzwania.
Początkowy brak Raspberry Pi w dostarczaniu wejść analogowych odróżnia go od platform zorientowanych na mikrokontrolery, takich jak Arduino, co może ograniczać jego możliwości w porównaniu z tymi alternatywami.
Chociaż może się to wydawać zniechęcające, istnieją różne alternatywy do zbadania. Możesz zacząć od wykorzystania Raspberry Pi wraz z zewnętrznym przetwornikiem analogowo-cyfrowym (ADC) do płynnego działania.
Po co dodawać wejścia?
W świecie przyrody istnieje wiele zjawisk, które można wygodnie zamknąć w formie potencjałów elektrycznych. Przekształcając te potencjały w ich binarne odpowiedniki, można je archiwizować, manipulować nimi i wykorzystywać jako środki do regulowania dodatkowych czynników i aktywowania dalszych mechanizmów.
Ktoś może chcieć nadzorować wilgotność swojej ziemi, ciepło swojej cieplarni lub wagę swojego gryzonia. Ktoś może chcieć włączyć regulator poziomu na swoim Raspberry Pi, skonstruować całą gamę suwaków lub stworzyć joystick de novo. Potencjalne zastosowania są bardzo szerokie i zróżnicowane.
Opcje przetworników ADC
Który przetwornik ADC jest najlepszy dla początkujących?
Do najpopularniejszych i najprostszych opcji należą układy MCP3004 (i MCP3008 ) firmy Microchip. Otrzymasz cztery (lub osiem) kanałów po 10 bitów każdy, które mogą odczytywać do 200 kSPS. Z drugiej strony są urządzenia ADS111x od Texas Instruments, które odczytują 16 bitów przy 860 SPS. Istnieje więc kompromis między szybkością a precyzją (i oczywiście ceną).
Kilka mikrokontrolerów jest wyposażonych w zintegrowane przetworniki analogowo-cyfrowe (ADC). Na przykład, powszechnie stosowana ATMega obecna w większości Arduinos zapewnia wiele kanałów o rozdzielczości 10 bitów wraz z innymi funkcjami.Możliwość ta pozwala platformie Arduino na obsługę analogowych sygnałów wejściowych, które przekraczają ograniczenia możliwości Raspberry Pi. W przypadkach, gdy istniejące Arduino jest włączone do projektu, a 10-bitowa rozdzielczość wystarcza do uzyskania wymaganej dokładności, użycie łatwo dostępnego rozwiązania Arduino może okazać się najprostszym sposobem działania.
Rzeczywiście, dla uproszczenia wykorzystamy w tym przypadku ADS1115, dzięki uprzejmości Adafruit.
Co to jest programowalny wzmacniacz wzmocnienia?
Układ scalony może pochwalić się kilkoma intrygującymi możliwościami, w szczególności wbudowanym programowalnym wzmacniaczem wzmocnienia (PGA), który umożliwia cyfrowe ustawienie preferowanego spektrum amplitudy. PGA pozwala na specyfikację zakresu napięcia aż do ułamków wolta, umożliwiając wykrywanie drobnych zmian, tak małych jak kilka mikrowoltów, dzięki szerokiej gamie wartości reprezentowanych przez 16-bitową rozdzielczość.
Jedną z zalet tego konkretnego układu jest możliwość regulacji wzmocnienia podczas pracy. W przeciwieństwie do tego, niektóre inne urządzenia, takie jak MCP3004, stosują alternatywną strategię, włączając dodatkowy pin, do którego można przyłożyć napięcie odniesienia.
Co z multipleksowaniem?
Multiplekser, znany również jako mux, służy jako urządzenie przełączające, które umożliwia wykorzystanie pojedynczego przetwornika analogowo-cyfrowego (ADC) do próbkowania danych z wielu źródeł. W przypadkach, gdy układ scalony ADC posiada wiele zacisków wejściowych, staje się oczywiste, że wewnętrzny proces multipleksowania odbywa się wewnętrznie. Na przykład, ADS1115 zawiera komponent mux z możliwością pomieszczenia do czterech różnych sygnałów wejściowych, które mogą być selektywnie wybierane poprzez manipulację jego nieodłączną konfiguracją rejestru.
Radzenie sobie z rejestrami
ADS1115 oferuje szereg funkcji, do których można łatwo uzyskać dostęp poprzez manipulację kilkoma ustawieniami sterowania. Obejmują one możliwość zarządzania wieloma
Mechanizm aktywacji każdej indywidualnej funkcji jest ukryty w granicach opakowania produktu, objawiając się jako miniaturowe repozytoria danych znane jako “rejestry”. Aby włączyć określoną funkcję, wystarczy zmienić odpowiedni rejestr z domyślnego stanu zero na wartość jeden.
Patrząc na arkusz danych ADS111x , okaże się, że modele te są wyposażone w cztery rejestry, w tym rejestry konfiguracyjne, które regulują zachowanie urządzenia.
W tym kontekście bity od 14 do 12 są wykorzystywane do sterowania działaniem multipleksera. Wykorzystując te trzy cyfry binarne, można wybrać jedną z ośmiu różnych konfiguracji. W szczególności pożądaną konfiguracją w tym przypadku jest “100”, ponieważ określa ona sygnał różnicowy między kanałem wejściowym 0 a masą. Z kolei bity od 7 do 5 odpowiadają za regulację częstotliwości próbkowania. Aby osiągnąć najwyższą możliwą częstotliwość próbkowania wynoszącą 860 próbek na sekundę, ustawienie tych bitów na “111” byłoby idealne.
Po określeniu odpowiednich ustawień, które należy zastosować, użytkownik będzie miał dostęp do dwóch bitów, które można przesłać do przetwornika analogowo-cyfrowego. W przypadku późniejszej chęci zmodyfikowania poszczególnych bitów, można to zrobić za pomocą operacji bitowych w izolacji.
Reprezentacja poszczególnych stanów przełącznika w systemie binarnym może powodować pewne zamieszanie. Podczas gdy sam kod binarny nie reprezentuje bezpośrednio konkretnej wartości liczbowej, może być użyty do wskazania stanu każdego pojedynczego przełącznika. Informacje te mogą być wyrażone w różnych formatach, takich jak notacja dziesiętna lub szesnastkowa; jednak w celu ułatwienia zrozumienia i uniknięcia potencjalnych komplikacji, często lepiej jest zachować format binarny.
Okablowanie
To urządzenie można wygodnie podłączyć do płytki prototypowej. Zakres dodatniego napięcia wejściowego wynosi od 2 do 5,5 V, co zapewnia kompatybilność z 3,3-woltowym zasilaniem Raspberry Pi.
Aby rozpocząć pracę, podłącz piny SDA i SCL z MCP3008 do odpowiednich portów na Raspberry Pi, jednocześnie podłączając uziemienie i połączenia 3,3 V. Dodatkowo należy umieścić potencjometr szeregowo pomiędzy liniami masy i napięcia, po czym podłączyć jeden koniec środkowego przewodu potencjometru do pierwszego wejścia przetwornika analogowo-cyfrowego (ADC). Po wykonaniu tych czynności konfiguracja jest gotowa do użycia.
Radzenie sobie z I2C
Różne przetworniki analogowo-cyfrowe (ADC) wykorzystują do działania różne protokoły komunikacyjne. Na przykład, w kontekście naszego ADS1115, wykorzystamy konkretny interfejs znany jako Inter-Integrated Circuit (I2C) do celów komunikacji i przesyłania danych.
Aby wykorzystać Python do połączenia z przetwornikiem analogowo-cyfrowym (ADC) na Raspberry Pi, muszą być spełnione pewne warunki wstępne. Na szczęście ostatnie iteracje systemu operacyjnego Raspberry Pi znacznie usprawniły ten proces.Aby rozpocząć procedurę konfiguracji, przejdź do “Preferencji” w menu systemowym i wybierz “Konfiguracja Raspberry Pi”. Następnie przejdź do zakładki “Interfaces” i aktywuj opcję “I2C”.
Aby upewnić się, że wszystkie komponenty działają poprawnie, uruchom interfejs wiersza poleceń, otwierając okno terminala i wykonując następujące polecenie:
sudo i2cdetect -y 1
Podany tekst opisuje scenariusz, w którym wykonanie określonej komendy wygeneruje na siatce dane wyjściowe, zawierające informacje odnoszące się do adresu przetwornika analogowo-cyfrowego (ADC). Autor podkreśla, że ta wartość szesnastkowa musi być poprzedzona “0x”, zanim zostanie wykorzystana w kolejnym kodzie. W tym przypadku wartość jest reprezentowana jako 0x48.
Wykorzystując uzyskany adres, można wykorzystać bibliotekę SMBus do przesyłania poleceń I2C za pomocą dwóch różnych procedur. Jedna z tych metod polega na użyciu funkcji write\_word\_data(), która wymaga trzech danych wejściowych, a mianowicie adresu urządzenia, konkretnego rejestru, do którego jest zapisywany, oraz żądanej wartości danych, która zostanie wpisana we wspomnianej lokalizacji.
Funkcja read_word_data()
pobiera jako dane wejściowe adres urządzenia i rejestr oraz powoduje, że przetwornik analogowo-cyfrowy (ADC) w sposób ciągły próbkuje i zapisuje wartości napięcia w określonym rejestrze. Pozwala to na późniejsze pobranie zapisanych danych z rejestru.
Można zdecydować się na ulepszenie wizualnej prezentacji danych wyjściowych, a następnie ich wyświetlenie. Przed ponownym wejściem w cykl iteracyjny można zaimplementować krótką przerwę lub opóźnienie. Takie podejście pomaga zapobiegać przeładowaniu informacjami.
from smbus import SMBus
import time
addr = 0x48
bus = SMBus(1)
# set the registers for reading
CONFIGREG = 1
CONVERSIONREG = 0
# set the address register to point to the config register
# write to the config registers
bus.write_word_data(addr, CONFIGREG, (0b100 << 8 | 0b10000010))
# define the top of the range
TOP = 26300
while True:
# read the register
b = bus.read_word_data(addr, CONVERSIONREG)
# swap the two bytes
b = ((b & 0xFF) << 8) | ((b >> 8) & 0xFF)
# subtract half the range to set ground to zero
b -= 0x8000
# divide the result by the range to give us a value between zero and one
b /= TOP
# cap at one
b = min(b, 1)
# bottom is zero
b = max(b, 0)
# two decimal places
b = round(b, 2)
print(b)
time.sleep(.01)
Po przekonwertowaniu typu danych zmiennej w celu dopasowania do preferowanego formatu, konieczne jest zmapowanie wynikowych wartości do ich odpowiedników w oryginalnej skali. Pozwala to na znaczące porównania między dwoma zestawami wartości. Następnie można odrzucić wszelkie nadmiarowe cyfry, ustawiając odpowiednią liczbę miejsc dziesiętnych. Aby wyświetlać tylko zaktualizowane wyniki, należy zmodyfikować funkcję drukowania tak, aby wyświetlała nowe wartości tylko wtedy, gdy różnią się one od poprzednio wyświetlanych. Aby uzyskać więcej informacji na temat funkcji max, min i round, zapoznaj się z naszą kompilacją 20 najważniejszych funkcji Pythona.
Radzenie sobie z hałasem
W przypadkach, gdy w środowisku brakuje wysokiego stopnia organizacji i uporządkowania, może się okazać, że w gromadzonych danych obecne są pewne niepożądane elementy.Zjawisko to można przypisać faktowi, że wykorzystanie mniejszego zakresu wartości, takiego jak rozdzielczość 16-bitowa zamiast 10-bitowej, prowadzi do zwiększonego prawdopodobieństwa napotkania tych zakłóceń lub “szumów”.
Podłączając wejście pierwsze do masy i ustawiając urządzenie na porównywanie wejść pierwszego i drugiego, uzyskuje się większą stabilność odczytów. Dodatkowo, krótsze kable połączeniowe o zwiększonej pojemności mogą być używane zamiast dłuższych, zaszumionych wersji. Co więcej, regulacja poziomu rezystancji potencjometru może również wpłynąć na wydajność.
Alternatywnie, można wykorzystać rozwiązania programowe do zarządzania wahaniami danych. Możliwe podejście obejmuje obliczenie średniej ruchomej lub całkowite odrzucenie drobnych zmian. Taki sposób działania wiąże się jednak z dodatkowym obciążeniem obliczeniowym. Podczas pracy z językami programowania wysokiego poziomu, takimi jak Python i przetwarzania wielu próbek na sekundę, wydatki te mogą kumulować się w coraz szybszym tempie.
Idź dalej z wieloma możliwymi kolejnymi krokami
Wykorzystanie I2C do celów odczytu jest stosunkowo prostym procesem, podobnie jak w przypadku alternatywnych podejść, takich jak SPI. Pomimo pozornych rozbieżności między różnymi alternatywami ADC, rzeczywistość jest taka, że po pomyślnym wdrożeniu którejkolwiek z tych opcji, zdobytą wiedzę można łatwo zastosować do pozostałych.
Dlaczego nie przesunąć granic nowo skonstruowanego sterownika potencjometru jeszcze dalej? Łącząc wiele potencjometrów szeregowo lub próbując mierzyć zmienne, takie jak światło, dźwięk lub temperatura, można odkrywać nowe możliwości interakcji z systemem Raspberry Pi. Wyrusz w ekscytującą podróż, rozszerzając możliwości swojego obecnego projektu i tworząc w pełni interaktywne doświadczenie poprzez praktyczne eksperymenty.