Zakres materiału:
- biblioteki arduino – link
- interfejs komunikacyjny UART – biblioteka Serial
- biblioteka do LCD – LiquidCrystal
- moduł RFID RC522 – komunikacja SPI – bilioteka MFRC522
- obsługa serwomechanizmu – biblioteka Servo
- przetwornik analogowo-cyfrowy – biblioteka Analog
Zadanie 1 (ocena 3):
podłączyć serwomechanizm do płytki złącze J32 (przewód brązowy do GND). Następnie podłączyć kanał “PWM1” na złączu J31 do odpowiedniego wyprowadzenia mikrokontolera. Wykorzystać bibliotekę “Servo” do sterowania serwomechanizmem w zakresie 0-180 stopni. Napisać program, który na wyświetlaczu LCD wyświetla aktualną pozycję serwa. Pozycję serwa możemy zmieniać przy pomocy przycisków SW_1 i SW_2.
Zadanie 2 (3.5):
podłączyć moduł czytnika RFID do płytki według tabelki:
Opis | Płytka EduTar | Moduł RFID-MFRC522 |
Zasilanie +3.3V | 3V3 | 3.3V |
Zasilanie GND | GND | GND |
MISO | D12 | MISO |
MOSI | D11 | MOSI |
SCK | D13 | SCK |
CS | D10 | SDA |
RST | D9 | RST |
ściągnąć i dodać do projektu bibliotekę “MFRC522”. Pliki z katalogu “src” należy dodać do folderu z naszym projektem. Załadować przykład obsługi czytnika z przykładu “DumpInfo”. Jak działa ten program? jakie informacje odczytuje z karty?
Zadanie 3 (ocena 4):
Napisać program, który będzie naśladował system dostępu do pomieszczenia. W programie na stałe zapisane są dane o 2 kartach RFID, które umożliwiają dostęp. Pozostałe karty nie będą otwierały pomieszczenia.
Po uruchomieniu system jest w trybie oczekiwania-wyświetla nazwę pomieszczenia i oczekuje na odczytanie karty.
Wczytanie karty dającej dostęp powoduje uruchomienie zamka (serwomechanizm obraca się do wybranej pozycji), na wyświetlaczu pojawia się komunikat odblokowania pomieszczenia. Stan ten trwa przez 10 sekundach. Po tym czasie system blokuje ponownie pomieszczenie i przechodzi do trybu oczekiwania.
Wczytanie karty bez przyznanego dostępu powoduje tylko wyświetlenie na LCD odpowiedniego komunikatu.
Zadanie 4 (ocena 4.5):
Ulepszyć program z zadania 3 tak aby była możliwość zapisywania/kasowania do 4 kart w systemie.
W systemie występuje dodatkowa karta administracyjna (dane karty administracyjnej można zapisać na stałe w programie)-po zeskanowania której, na wyświetlaczu pojawia się menu serwisowe umożliwiające:
- dodawanie nowej karty,
- usuwanie wybranej karty,
- przeglądanie numerów zapisanych kart,
- podgląd numeru zeskanowanej karty, program wyświetla numer przyłożonej karty.
Zadanie 5 (ocena 5.0):
Ulepszyć program z zadania 4 tak aby informacje o kartach były zapisywane do pamięci nieulotnej. Czyli system będzie odporny na zanik zasilania.
Zakres laboratorium 2017-2021 (nie aktualne)
Zajęcia stacjonarne:
- STM32 – porty jako wejścia
- komunikacja UART
- komunikacja I2C
- obsługa modułu IMU MPU6050 (dokumentacja techniczna, mapa rejestrów)
- wyświetlanie typu float przy użyciu funkcji “sprintf”: link
Zadanie 1 – 3 – jeszcze raz GPIO
podłączyć do wyprowadzeń D9 i D10 dwa przewody. Z drugiej strony przewody należy podpinać do GND – symulacja naciśnięcia przycisku.
skonfigurować odpowiednie piny jako wejścia mikrokontrolera z ustawionym pull-up.
Wykorzystać funkcję do odczytu stanu pinów “HAL_GPIO_ReadPin()”, napisać program, który reaguje na odpowiednie zbocza:
- przycisk monostabilny, jedno wciśnięcie przycisku 1 – dioda LED świeci, drugie wciśnięcie dioda LED nie świeci. Dłuższe przytrzymanie przycisku nic nie zmienia, zapewnić odporność na drgania styków.
- przycisk bistabilny – zmiana stanu przycisku na wciśnięty powoduje wysłanie na terminal komunikatu “Przycisk włączony”, zmiana stanu na przycisk wyłączony powoduje wysłanie komunikatu “Przycisk wyłączony”. Dłuższe przytrzymanie przycisku nic nie zmienia, zapewnić odporność na drgania styków.
Zadanie 2 – 4 – pierwsze kroki w I2C
Podłączyć moduł MPU6050 do płytki za pomocą interfejsu I2C:
- VCC – > nucleo 5V
- GND -> nucleo GND
- SCL -> nucleo D5
- SDA -> nucleo D4
Skonfigurować projekt STM32:
- uruchomić układ komunikacji I2C1
- upewnić się, że interfejs I2C jest skonfigurowany na wyprowadzeniach D4 i D5
Zapoznać się z instrukcją i mapą rejestrów do układu MPU6050. Zapoznać się z komunikacją po interfejsie I2C.
- do obsługi modułu podłączone po interfejsie I2C potrzebujemy znać jego adres (dokumentacja techniczna – 9.2). Moduł posiada AD0 podpięte do GND.
- uruchomić funkcję readAndShow() – co robi ta funkcja, jaka wartość powinna być w rejestrze “Who Am I” mapy rejestrów?
- “<<—-” – komentarze tak oznaczone należy uzupełnić odpowiednimi wartościami
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
void readAndShow() { char bufforText[30]; uint8_t adresMPU6050=0x00<<1...; //Adres modulu MPU6050 uint8_t adresRejestru; //Adres rejestru jaki chcemy odczytac adresRejestru=....; //<<---- podac adres rejestru Who Am I //Ustawienie adresu rejestru jaki chcemy odczytac if(HAL_I2C_Master_Transmit(&hi2c1, adresMPU6050, &adresRejestru, 1, 100) !=HAL_OK) { sprintf(bufforText,"ERROR: blad adresu modulu\r\n"); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } //Odczytanie jednego bajtu danych z wczesniej ustawionego rejestru uint8_t wartosc=0; if(HAL_I2C_Master_Receive(&hi2c1, adresMPU6050, &wartosc, 1, 100)!=HAL_OK) { sprintf(bufforText,"ERROR: blad odczytu rejestru\r\n"); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } sprintf(bufforText,"Wartosc w rejestrze: %d \r\n",wartosc); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } |
Zadanie 3 – 4.5 – odczyt temperatury
Odczytać temperaturę z modułu i przesłać ją na terminal w postaci stopni Celsjusza. Uzupełnić funkcję “readTemp()”.
Odczyt temperatury dokonujemy z rejestrów “TEMP_OUT_H” i “TEMP_OUT_L” – dokładne informacje znajdują się w rozdziale 4.18 dokumentacja mapy rejestrów.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
float readTemp() { char bufforText[30]; uint8_t adresMPU6050=0x00<<1...; //<<----Adres modulu MPU6050 uint8_t adresRejestru; //Adres rejestru jaki chcemy odczytac //Aktywacja modulu MPU6050 uint8_t tab[2]; tab[0]=...; //<<---- podać adres rejestru PWR_MGMT_1 tab[1]=0; if(HAL_I2C_Master_Transmit(&hi2c1, adresMPU6050,tab, sizeof(tab), 100)!=HAL_OK) { sprintf(bufforText,"ERROR: blad aktywacji modulu\r\n"); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } adresRejestru=...; //<<---- podać adres rejestru TEMP_OUT[15:8] //Ustawienie adresu rejestru jaki chcemy odczytac if(HAL_I2C_Master_Transmit(&hi2c1, adresMPU6050, &adresRejestru, 1, 100) !=HAL_OK) { sprintf(bufforText,"ERROR: blad adresu modulu\r\n"); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } //Odczytanie dwoch bajtow danych z wczesniej ustawionego rejestru uint8_t wartosc[2]={0}; if(HAL_I2C_Master_Receive(&hi2c1, adresMPU6050, wartosc, 2, 100)!=HAL_OK) { sprintf(bufforText,"ERROR: blad odczytu rejestru\r\n"); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } int16_t tempOut= ...; //<<---- dokonczyc składanie temperatury do zmiennej typu int16_t float temperatura= tempOut; //<<---- dokonczyc wzor na przeliczenie temperatury return temperatura; } |
Zadanie 4 – 5 – poziomnica (link1, link2)
Utworzyć program, który będzie wyświetlał na terminalu położenie kątowe moduły w jednej osi.
- Dołączyć bibliotekę “math.h” (#include “math.h”)
- uzupełnić i uruchomić funkcję poziomnica() – co robi ta funkcja?
- jakie wady posiada tak wyznaczone położenie modułu?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
void poziomnica() { char bufforText[30]; uint8_t adresMPU6050 = 0x00 << 1...; //<<----Adres modulu MPU6050 uint8_t adresRejestru; //Adres rejestru jaki chcemy odczytac //<<----Aktywacja modulu MPU6050 //<<---- odczytac wartosci z rejestrow od ACCEL_XOUT[15:8] do ACCEL_ZOUT[7:0] uint8_t wartosc[6] = { 0 }; //<<----przekonwertowac na liczby w formacie int16_t int16_t acc_x = 0..; int16_t acc_y = 0..; int16_t acc_z = 0..; float poziom = atan2(acc_x, acc_z) * (180 / M_PI); sprintf(bufforText, "Poziom: %f \r\n", poziom); HAL_UART_Transmit(&huart2, bufforText, strlen(bufforText), 100); } |
Zajęcia zdalne:
Zakres laboratorium:
- zapoznanie się z ekosystemem Arduino
- obsługa przerwań zewnętrznych
- poznanie interfejsu transmisji danych UART
Środowisko programistyczne: arduino
Jak wyciągnąć plik hex/elf z kompilacji Arduino IDE: link
Zapoznać się z zbiorem funkcji dostępnych w Arduino: link
W celu uruchomienia terminala należy kliknąć PPM Arduino i wybrać “Open serial Monitor.”
Zadanie 1 – ocena 3
Zapoznać się z obsługa przerwań w Arduino: link
- stworzyć symulację z płytką Arduino Uno, dodać dwa przyciski dołączone do pinów 2 i 3, oddać 2 diody LED,
- utworzyć program, który za pomocą przerwania z przycisku 1 będzie włączył/wyłączał diodę 1,
- analogicznie do poprzedniego punktu, uruchomić przycisk 2 i diodę 2.
Zadanie 2 – ocena 3,5
Zapoznać się z możliwościami biblioteki do komunikacji Serial: link
- na podstawie programu z zadania 1, należy uruchomić obsługę komunikacji UART,
- ustawić prędkość komunikacji UART na 9600
- na początku programu (tylko jeden raz), należy wysłać do terminala napis “Hello world – numer indeksu”, gdzie za napis numer indeksu podstawiamy swój numer,
- w pętli głównej programu utworzyć licznik zliczający o 1, co 1 sekundę
- na każdą zmianę licznika powinien zostać przesłany po interfejsie uart napis “dziala: n”, gdzie n to stan licznika,
- każdy kolejny napis powinien być w nowej linijce,
- dodać do obsługi przerwań przesyłanie komunikatu po UART o zmianie stanu diody LED.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
int i=0; void setup() { //Initialize serial and wait for port to open: Serial.begin(9600); // prints title with ending line break Serial.println("PTM-testowy program"); } void loop() { Serial.print("Dziala: "); Serial.println(i++); delay(1000); } |
Zadanie 3 – ocena 4
Zapoznać się z kodowaniem znaków ASCII: link
Utworzyć nowy program i skonfigurować komunikację UART jak w zadaniu 2.
- na początku programu (tylko jeden raz), należy wysłać do terminala napis “Hello world – numer indeksu”, gdzie za napis numer indeksu podstawiamy swój numer,
- program co 1 sekundę sprawdza czy został wysłane do mikrokontrolera jakiś znak po UART, jeśli tak to odbiera go i wyświetla na ekranie napis “Odebralem: x-nn”, gdzie x to przesłany znak w postaci znaku ASCII, a nn to jego kod liczbowy,czyli dla przesłanego znaku “a” ma zostać wyświetlony komunikat “Odebrałem: a-97”
- co każde 10 sekund jeśli nie został przesłany jakiś znak, wyświetla na ekranie napis “Czekam na znak, pospiesz się…”
Zadanie 4 – ocena 4,5
Utworzyć program, który oblicza wiek osoby na podstawie wprowadzonego roku urodzenia.
- Po uruchomieniu program przedstawia się, krótkim komunikatem z nazwą programu i opisem co robi,
- następnie prosi o podanie roku urodzenia,
- wczytane dane zamienia na liczbę i dokonuje obliczenia wieku osoby (dla uproszczenia proszę przyjąć rok obecny na 2020),
- wyświetla na ekranie komunikat, gdzie x to obliczony wiek, a “…” to miejsce na wymyślony komentarz, logiczne dokończenie komunikatu:
- jeśli wiek <18 – “Masz x lat, ale jesteś …”,
- dla 18<=wieku < 25 – “Masz x lat, jesteś …”,
- dla 25<=wieku < 65 – “Masz x lat, czy już …”,
- dla 65<=wieku – “Masz x lat, czy to już …”,
- następnie program ponownie rozpoczyna działanie od początku.
Zadanie 5 – ocena 5
Utworzyć program, który na podstawie wprowadzonej daty urodzenia określa czy osoba jest pełnoletnia.
- program prosi o podanie daty urodzenia w formacie dd.mm.yyyy, czyli 01.05.2000,
- oblicza czy osoba ma skończone 18 lat, dla uproszczenia proszę przyjąć dzisiejszą datę jako 08.02.2021,
- wyświetla na ekranie komunikat “Jesteś już pełnoletni.” lub “Jeszcze nie masz 18 lat, musisz poczekać: xxx dni”, gdzie xxx to ilość dni jaka pozostała aby dana osoba osiągnęła pełnoletność.