Teraz możesz kupić zestaw ponad 70 elementów niezbędnych do przeprowadzenia ćwiczeń z kursu u naszych dystrybutorów!

Podobne dokumenty
Notatka lekcja_#3_1; na podstawie W.Kapica 2017 Strona 1

LABORATORIUM - ELEKTRONIKI Układy mikroprocesorowe cz.2

Uwaga: dioda na wyjściu 13 świeci gdy na wyjście podamy 0.

ze względu na jego zaokrąglony kształt musimy go umieścić w innych bloczkach np. ze zmienną: lub jeśli chcemy sprawdzić jaki właśnie znak odczytujemy:

Pomiar odległości z Arduino czujniki, schematy, przykładowe kody

Rafał Staszewski Maciej Trzebiński, Dominik Derendarz

Po uruchomieniu programu nasza litera zostanie wyświetlona na ekranie

Projekt współfinansowany ze środków Unii Europejskiej w ramach Europejskiego Funduszu Społecznego

Nazwa implementacji: Nauka języka Python wyrażenia warunkowe. Autor: Piotr Fiorek. Opis implementacji: Poznanie wyrażeń warunkowych if elif - else.

Kurs Arduino #2 podstawy programowania, porty I/O. 2 //Zawartość programu. 1 int main() { void setup() { //Instrukcje, które wykonają się jeden raz

znajdowały się różne instrukcje) to tak naprawdę definicja funkcji main.

Kl 7-8 Szkoła Podstawowa

Projekt współfinansowany ze środków Unii Europejskiej w ramach Europejskiego Funduszu Społecznego

sygnałów cyfrowych przetwornikiem analogowo-cyfrowym Krótki wstęp teoretyczny Wysokim niskim chcielibyśmy poznać dokładną odległość od przeszkody

Lekcja 3: Pierwsze kroki z Pythonem. Pętle

Język C. Wykład 9: Mikrokontrolery cz.2. Łukasz Gaweł Chemia C pokój 307

Oscyloskop (007; ; arduino; processing)

lekcja 8a Gry komputerowe MasterMind

Zmierzyć się z żywiołami, czyli jak zbudować własną stację badawczą! Zaczynamy! Pole komunikatów programu. Nawigacja w programie Arduino

Wyniki (prawie)końcowe - Elektroniczne warcaby

1. Opis aplikacji. 2. Przeprowadzanie pomiarów. 3. Tworzenie sprawozdania

Scenariusz lekcji Ozobot w klasie: Tabliczka mnożenia

Instrukcja warunkowa i złoŝona.

Liczby losowe i pętla while w języku Python

tinyesp WiFi Kontroler

kodowanienaekranie.pl

Schemat blokowy architektury AVR

2.1. Duszek w labiryncie

Podstawy programowania Laboratorium. Ćwiczenie 2 Programowanie strukturalne podstawowe rodzaje instrukcji

Bufor danych USB jednorazowego użytku EBI 330-T30/EBI 330-T85 Nr produktu

Dalmierze firmy SHARP na przykładzie 2D120XJ100F

Celem tego projektu jest stworzenie

Kod produktu: MP01105

Programowanie w Baltie klasa VII

Klawiatura matrycowa

SYSTEMY OPERACYJNE I SIECI KOMPUTEROWE

Czym jest sygnał PWM?

Rejestratory Sił, Naprężeń.

INSTRUKCJA OBSŁUGI K3-3. Czytnik kart i zamek kodowy z kontrolerem dostępu i interfejsem Wiegand. Copyright Domster T. Szydłowski

wbudowany system do głosowania Avtek TS Pro3 / Pro4K

głosowanie wbudowany system do głosowania Avtek TS Pro3 / Pro4K

Przykład programowania PLC w języku drabinkowym - ćwiczenie 6

Brain Game. Wstęp. Scratch

MultiTool instrukcja użytkownika 2010 SFAR

Wskaźniki a tablice Wskaźniki i tablice są ze sobą w języku C++ ściśle związane. Aby się o tym przekonać wykonajmy cwiczenie.

Temat 20. Techniki algorytmiczne

Misja#3. Robimy film animowany.

Laboratorium - Podgląd informacji kart sieciowych bezprzewodowych i przewodowych

Zapisywanie w wybranej notacji algorytmów z warunkami i iteracyjnych

Instrukcja obsługi sterownika Novitek Triton

Systemy wbudowane. Uniwersytet Łódzki Wydział Fizyki i Informatyki Stosowanej. Witold Kozłowski

Nawigacja po długim dokumencie może być męcząca, dlatego warto poznać następujące skróty klawiszowe

SONEL ANALIZA MOBILNA

Kalibracja czujnika temperatury zestawu COACH Lab II+. Piotr Jacoń. K-5a I PRACOWNIA FIZYCZNA

MIKROPROCESOROWY ODSTRASZACZ DŹWIĘKOWY V2.0

AKTUATOR DO SYSTEMU DUO Q

Informatyka dla klas I wykresy funkcji

Instrukcja dla: Icomsat v1.0 SIM900 GSM/GPRS shield for Arduino oraz dla GPRS Shield produkcji Seeedstudio.

Schematy blokowe I. 1. Dostępne bloki: 2. Prosty program drukujący tekst.

6.4. Efekty specjalne

Programowanie i techniki algorytmiczne

Programowanie xcomfort Cz. I Eaton Corporation. All rights reserved.

Na początek: do firmowych ustawień dodajemy sterowanie wyłącznikiem ściennym.

Gra Labirynt - Zajęcia 4

LABORATORIUM - ELEKTRONIKA Układy mikroprocesorowe cz.2

Szybki start SAMOOCENA W NOR-STA

Wizualizacja stanu czujników robota mobilnego. Sprawozdanie z wykonania projektu.

Ri-Co informacje techniczne

Uczeń/Uczennica po zestawieniu połączeń zgłasza nauczycielowi gotowość do sprawdzenia układu i wszystkich połączeń.

Skrypt 7. Funkcje. Opracowanie: L1

Szybki start SAMOOCENA W NOR-STA

Obsługa pilota uniwersalnego RCU650

BEZPRZEWODOWY VIDEODOMOFON XT GHz Cyfrowa transmisja

Zastanawiałeś się może, dlaczego Twój współpracownik,

Kod produktu: MP01105T

Krótki wstęp o wyświetlaczach. Jak zmusić wyświetlacz do pracy?

Scenariusz zajęć. Moduł VI. Projekt Gra logiczna zgadywanie liczby

MoboLab roboty i tablety w Twojej szkole Obszar II. Stwórz własnego robota Scenariusze lekcji i zajęć pozalekcyjnych

Badanie diod półprzewodnikowych

Liczby pseudolosowe. #include <stdio.h> #include <stdlib.h> int main() { printf("%d\n", RAND_MAX); return 0; }

1 Wprowadzenie do algorytmiki

Lekcja : Tablice + pętle

BEZDOTYKOWY CZUJNIK ULTRADŹWIĘKOWY POŁOŻENIA LINIOWEGO

Długopis z ukrytą kamerą cyfrową HD

kodowanienaekranie.pl

Sterownik kompaktowy Theben PHARAO II

SONOFF DUAL INSTRUKCJA OBSŁUGI

Podstawowe urządzenia peryferyjne mikrokontrolera ATmega8 Spis treści

Widoczność zmiennych Czy wartości każdej zmiennej można zmieniać w dowolnym miejscu kodu? Czy można zadeklarować dwie zmienne o takich samych nazwach?

Czytanie wykresów to ważna umiejętność, jeden wykres zawiera więcej informacji, niż strona tekstu. Dlatego musisz umieć to robić.

POLITECHNIKA WROCŁAWSKA WYDZIAŁ ELEKTRYCZNY KATEDRA ENERGOELEKTRYKI LABORATORIUM INTELIGENTNYCH INSTALACJI ELEKTRYCZNYCH

Modułowy programowalny przekaźnik czasowy firmy Aniro.

Multi-CZUJNIK 68. Programowany Multi-CZUJNIK zawierający czujnik. położenia, uderzenia i spadku napięcia.

Termometr internetowy

Realizacja algorytmu z warunkiem czy Twój uczeń lubi programować? Grażyna Koba

Przetwornik analogowo-cyfrowy

Część XII C++ Warunki zagnieżdżone Ćwiczenie 1 nazwisko40 2. nie przepisując komentarzy!

Scenariusz lekcji Ozobot w klasie: Prezentacja liczb trójkątnych i kwadratowych

Praca w sieci zagadnienia zaawansowane

Praca i energia Mechanika: praca i energia, zasada zachowania energii; GLX plik: work energy

Transkrypt:

0 Kurs #0 wykresy, liczby losowe, warunki cd. Pora na obiecaną, dodatkową część naszego kursu. Tym razem zajmiemy się kilkoma rzeczami, które usprawnią programowanie. Mowa między innymi o łączeniu warunków oraz losowaniu liczb. Sprawdzimy również, jak łatwo informacje, które trafiają do PC przedstawić w formie wykresu! rysowanie wykresów Oczywiście IDE z czasem się zmienia. Niedawno pojawiła się tam bardzo wygodna opcja, która pozwala na szybkie rysowanie wykresów z informacji przesyłanych przez UART. Aby móc korzystać z tego narzędzia potrzebujemy nowej wersji IDE, jeśli instalowałeś je niedawno i w menu narzędzia widzisz dwie opcje: Szeregowy monitor oraz Monitor portu szeregowego, to nie musisz już nic robić. Nowe pozycje w menu IDE. Niestety, ale nazwy obu opcji w polskiej wersji językowej IDE są delikatnie mówiąc mało intuicyjne i mylące. Poprzednio używany przez nas terminal znajduje się teraz pod opcją: Szeregowy monitor. Jeśli widzisz tylko jedną opcję tego typu, to zaktualizuj swoje IDE. Najnowsza wersja dostępna jest oczywiście za darmo na stronie projektu. Aby rysować wykres musimy, najlepiej w regularnych, odstępach wysyłać do komputera liczby w nowej linii. Na początku stwórzmy układ, który będzie rysował wykres napięcia mierzonego na wejściu A, do którego podłączymy potencjometr w roli dzielnika napięcia. Pamiętaj, że podstawą w zrozumieniu programowania jest praktyka. Nie będziesz umiał wykorzystać zdobytej tu wiedzy, jeśli nie wykonasz ćwiczeń z kursu. Zestaw elementów do przeprowadzenia ćwiczeń Gwarancja pomocy na forum dla osób, które kupią poniższy zestaw! Teraz możesz kupić zestaw ponad 0 elementów niezbędnych do przeprowadzenia ćwiczeń z kursu u naszych dystrybutorów!

Schemat podłączenia układu wygląda następująco: Potencjometr podłączony do A. Standardowa wersja programu wysyłającego dane do terminala wyglądałaby następująco: 0 int odczytanawartosc = 0; Serial.begin(00); //Uruchomienie komunikacji przez USART odczytanawartosc = analogread(a); //Odczytujemy wartość napięcia Serial.println(odczytanaWartosc); //Wysyłamy ją do terminala delay(00); //Czekamy, aby wygodniej odczytywać wyniki Korzystając z opcji Szeregowy monitor, podczas kręcenia potencjometrem, zobaczymy taki efekt: Zmiany napięcia na A. Mało czytelnie prawda? Wystarczy jednak włączyć drugą opcję, czyli Monitor portu szeregowego, a naszym oczom ukaże się znacznie bardziej czytelniejszy efekt. Będzie to wykres, przykład dla pomiarów, gdy zmieniałem ręcznie ustawienia potencjometru:

Pomiar napięcia na A, wykres w. Prawda, że znacznie czytelniej? Kiedy w praktyce przydają się takie opcje? Oczywiście wtedy, gdy korzystamy z czujników (odległości, temperatury itd.). Tak się składa, że w poprzedniej części kursu omówiliśmy obsługę czujnika odległości HC-SR0. Spróbujmy narysować więc wykres mierzonej odległości! wykres odległości od przeszkody W tym celu wracamy do schematu montażowego z poprzedniego artykułu: Schemat podłączenia czujnika odległości. Uruchamiamy również kod napisany podczas poprzedniej lekcji. Należy wprowadzić tylko dwie zmiany. Pierwsza, to wyświetlanie wyniku w nowej linii bez jednostki. Druga, to odrobina większa częstotliwość pomiarów dzięki temu wykres będzie bardziej płynny. 0 #define trigpin #define echopin Serial.begin (00); pinmode(trigpin, OUTPUT); //Pin, do którego podłączymy trig jako wyjście pinmode(echopin, INPUT); //a echo, jako wejście long czas, dystans; digitalwrite(trigpin, LOW); delaymicroseconds(); digitalwrite(trigpin, HIGH); delaymicroseconds(0);

0 digitalwrite(trigpin, LOW); czas = pulsein(echopin, HIGH); dystans = czas / ; Serial.println(dystans); delay(00); Gotowe? Pora uruchomić narzędzie do rysowania wykresów. Tutaj może być różnie czasami zadziała, a czasami nie. Dlaczego? Przy korzystaniu z takich czujników zawsze ryzykujemy, że odbierzemy pewne zakłócenia. W przypadku tego czujnika odległości zakłócenie może spowodować, że wyślemy do komputera informację o błędnym pomiarze. Na poniższym zrzucie ekranu widać, że jeden z pierwszych pomiarów wskazał odległość wynoszącą 000 cm. Nie jest to możliwe, jeśli producent zadeklarował maksymalny pomiar na 00 cm. Błędny odczyt z czujnika. Spowodowało to automatyczne dobranie skali na wykresie, które utrudnia odczytanie późniejszych, poprawnych wyników. Jak temu zaradzić? Najlepiej programowo. Dodajmy prosty warunek, który będzie sprawdzał jaką wartość wysyłamy do komputera. Może on wyglądać np. tak: if (dystans > 00) { //Jeśli obliczona odległość jest większa od 00 dystans = 00; //to ustaw ją na 00 (max wskazane przez producenta) Dzięki temu nigdy nie wyślemy do komputera wartości, która wykracza za zakres czujnika. Zmienna dystans została zadeklarowana jako liczba dodatnia, więc wystarczy sprawdzać górny zakres. Nie musimy kontrolować dolnego. Cały program po zmianach wygląda tak: 0 #define trigpin #define echopin Serial.begin (00); pinmode(trigpin, OUTPUT); //Pin, do którego podłączymy trig jako wyjście pinmode(echopin, INPUT); //a echo, jako wejście long czas, dystans; digitalwrite(trigpin, LOW); delaymicroseconds(); digitalwrite(trigpin, HIGH); delaymicroseconds(0); digitalwrite(trigpin, LOW);

0 czas = pulsein(echopin, HIGH); dystans = czas / ; if (dystans > 00) { //Jeśli obliczona odległość jest większa od 00 dystans = 00; //to ustaw ją na 00 (max wskazane przez producenta) Serial.println(dystans); delay(00); Teraz wykres za każdym razem będzie wyglądał poprawnie: Wykres odległości wersja poprawna. Podczas nagrywania pomiarów przesuwałem szybko przeszkodę przed czujnikiem. Jak widać, kilka razy nasze ograniczenie uchroniło nas przed błędnymi pomiarami. Przy okazji warto zwrócić uwagę, jak rysowanie wykresu ułatwia zauważenie problemów z jakością odczytów z sensora! Tutaj np.: widać stosunkowo duże szumy wartości, odczyty nie są stabilne. wykres kilku wartości Opisana funkcja rysowania wykresów pozwala również na jednoczesne rysowanie kilku wartości na jednej planszy. Aby wykorzystać tę opcję należy wysłać liczby w tej samej linii oddzielonych znakiem tabulatora, a na ich końcu powinien pojawić się znak nowej linii. W praktyce kod będzie wyglądał tak: Serial.print(Wartosc); Serial.print("\t"); // Znak tabulatora Serial.print(Wartosc); Serial.print("\t"); // Znak tabulatora Serial.print(Wartosc); Serial.print("\t"); // Znak tabulatora Serial.print(Wartosc); Serial.println(""); // Przejście do nowej linii Natomiast wykres po podstawieniu wartości losowych wyjdzie przykładowo taki:

Różne dane na jednym wykresie. Rysowanie wykresów może być również szczególnie przydatne, gdy wykorzystujemy czujniki przyspieszenia lub położenia. Zachęcam do przeczytania mojego artykułu, w którym pokazałem jak wykorzystać najnowsze Genuino 0 do obrazowania jego położenia! Tam właśnie wykorzystałem jednoczesne rysowanie wykresu dla kilku wartości: Wizualizacja zmiany położenia układu. Zadanie domowe 0. Wykorzystaj w praktyce możliwość rysowania jednocześnie kilku wykresów. Do podłącz dwa fotorezystory robiliśmy to już w innych lekcjach. Następnie mierz napięcie odzwierciedlające poziom światła padającego na każdy z czujników. Obie wartości zaprezentuj na jednym wykresie. Pochwal się w komentarzu zrzutem ekranu przedstawiającym Twój wykres! liczby losowe Czasami oczekujemy, aby program działał w sposób nieprzewidywalny. Praktyczny przykład? Robot, który po wykryciu przeszkody obraca się o losowy kąt lub prosta gra, w której komputer wykonuje swój ruch z nieprzewidywalnym opóźnieniem. W poprzednim przykładzie użyłem właśnie takich wartości, aby zademonstrować jednoczesne rysowanie wykresów dla różnych danych.

niestety nie może rzucić kośćmi do gry W tym miejscu przydaje się funkcja zwracająca losową wartość. Jednak mówiąc szczerze, liczba ta nie będzie zupełnie nieprzewidywalna. Dlatego w przypadku komputerów/mikrokontrolerów mówimy o liczbach pseudolosowych. Jest to temat dość rozbudowany i nie będziemy się tutaj nim zajmować. Warto jednak zapamiętać, że wartości losowane przez komputer z punktu widzenia statystyki nie są idealnie losowe (w dużym uproszczeniu pisząc). Za zwracanie losowej wartości odpowiedzialna jest funkcjarandom();, która może przyjąć dwa argumenty. Dzięki nim kształtujemy zakres, z jakiego losowane są liczby. W praktyce funkcję najczęściej wykorzystujemy na jeden z dwóch sposobów. Z podaniem wyłącznie górnego zakresu: random(00); //Liczba losowa z zakresu 0- Wtedy zwrócona wartość będzie liczbą z zakresu od 0 do liczby o jeden mniejszej od tej wpisanej w nawiasie. Możemy również wpłynąć na dolne ograniczenie zakresu. W tym celu wystarczy dodać drugi argument: random(00, 00); //Liczba losowa z zakresu 00- Zapamiętaj! Maksymalna wylosowana liczba będzie zawsze o mniejsza od podanego przez nas górnego zakresu! Pora sprawdzić działanie tej funkcji w praktyce. W tym celu napiszmy najbanalniejszy program, jaki tylko można wykonać. Jego zadaniem jest losowanie liczb w odstępach sekundy i wyświetlanie ich w terminalu (opcja Szeregowy monitor w menu Narzędzia ): Serial.begin(00); Serial.println(random(00)); delay(000); Zgodnie z zapowiedzią w terminalu oczekujemy losowych wartości. Sprawdźmy:

Wynik pierwszego uruchomienia programu. Chcieliśmy losowe dane i mamy. Teraz uruchommy wgrany program kilka kolejnych razy. Zgodnie z oczekiwaniami za każdym razem liczby losowe powinny być inne, prawda? trzecie uruchomienie, czwarte uruchomienie,

piąte uruchomienie. Niestety, za każdym razem otrzymujemy identyczny ciąg. Tak jak pisałem losowość zwracanych liczb jest trochę oszukana. Mikrokontroler na pokładzie, to bardzo precyzyjny układ, który wykonuje kolejne, zaprogramowane operacje. W jego świecie nie istnieją wartości losowe. Jak można się domyślać losowe liczby generuje wykonując pewne określone operacje na poprzednio wylosowanej wartości. Stąd taki sam początek sprawia, że kolejne liczby są identyczne. Aby poprawić działanie algorytmu losującego najlepiej byłby przed każdym jego startem zaczynać od podania innej wartości jako tej pierwszej, początkowej. Ta liczba, na podstawie której generowane są następne nosi nazwę ziarna/zarodka, w języku angielskim określona jest ona jako random seed. Więcej na ten temat znaleźć można na Wikipedii (hasło: generator liczb pseudolosowych). Dla nas najważniejsze jest, że w języku występuje również takie pojęcie mamy wpływ na owe ziarno. Służy do tego funkcja: randomseed(wartosc_poczatkowa); W jej argumencie, zaznaczonym tutaj jako wartosc_poczatkowa, należy podać za każdym razem losową wartość. Ale namieszałem, prawda? Aby losować liczby, potrzebujemy losowej wartości. Macie pomysł jak to uzyskać? Jeśli nie, to zerknijcie to lekcji o przetworniku ADC w. Co dzieje się, gdy do odczytywanego wejście nie podłączymy żadnego sygnału? Wtedy zbieramy śmieci z otoczenia, które są właśnie losowe. Do tej pory było to dla nas problemem. Jednak tutaj wykorzystamy te wartości w słusznym celu. Aby nasze korzystało z bardziej losowych liczb możemy na początku zrobić tak: randomseed(analogread(a0)); Dzięki temu, przy każdym starcie programu zmierzymy losowe napięcie panujące na wejściu A0. Dalej wartość ta zostanie podana jako ziarno do generatora liczb pseudolosowych. Oczywiście całość zadziała najlepiej, jeśli wejście A0 nie będzie wykorzystywane jako standardowe wejście/wyjście. Poprawmy szybko nasz program i sprawdźmy go w praktyce: Serial.begin(00); randomseed(analogread(0)); Serial.println(random(00)); delay(000); Od teraz, po każdym uruchomieniu otrzymamy inne wartości:

Pierwsze uruchomienie, drugie uruchomienie, trzecie uruchomienie. Oczywiście nadal nie jest to idealny generator liczb losowych, jednak w takiej formie wystarczy on do wykorzystania w zdecydowanej większości projektów tworzonych na bazie. Zadanie domowe 0. Sprawdź, co stanie się, jeśli zamiast ziarna odczytywanego z wejścia analogowego wpiszemy tam stałą wartość. Jak wtedy zachowa się generator liczb pseudolosowych? Zadanie domowe 0. Napisz program, który działa jak elektroniczna kostka do gry. Do podłącz przycisk. Każde jego wciśnięcie powinno wysyłać do komputera (prze UART) wylosowaną wartość oczywiście z zakresu od do. Losowe miganie diodą 0

Wykorzystajmy zdobytą wiedzą do napisania programu, który będzie migał diodą wbudowaną w w sposób losowy. Załóżmy, że długość świecenia ma wahać się od około 00ms do 0ms. Natomiast czas, gdy dioda jest wyłączona będzie w granicach 0-0ms. Obie wartości powinny zmieniać się w odstępach, co 0 ms. W tym celu potrzebować będziemy dwóch wartości losowych: int czaswlaczona = random(00, 000); int czaswylaczona = random(0, 00); Tak wylosowane wartości moglibyśmy wstawić do funkcji opóźniającej delay, jednak wtedy opóźnienie mogłoby przyjmować wartości np.: od 00 do, czyli nie zachowalibyśmy założonych odstępów o 0ms. Jak to naprawić? Wystarczy, że będziemy losować wartości 0 razy mniejsze, które pomnożymy razy 0 przed podstawieniem ich do funkcji opóźniającej: int czaswlaczona = random(0, 00); //Wartość z zakresu 0 - int czaswylaczona = random(, 0); //Wartość z zakresu - czaswlaczona = czaswlaczona * 0; //Wartość z zakresu 00-0, skok co 0 czaswylaczona = czaswylaczona * 0; //Wartość z zakresu 0-0, skok co 0 Teraz wartości te można podstawić już do programu: 0 pinmode(, OUTPUT); randomseed(analogread(0)); int czaswlaczona = random(0, 00); //Wartość z zakresu 0 - int czaswylaczona = random(, 0); //Wartość z zakresu - czaswlaczona = czaswlaczona * 0; //Wartość z zakresu 00-0, skok co 0 czaswylaczona = czaswylaczona * 0; //Wartość z zakresu 0-0, skok co 0 digitalwrite(, HIGH); delay(czaswlaczona); digitalwrite(, LOW); delay(czaswylaczona); W praktyce dioda miga, tak jak chcieliśmy, czyli zupełnie losowo! Łączenie instrukcji warunkowych Już na samym początku kursu zajęliśmy się instrukcjami warunkowymi, które są używane do sterowania pracą programu w zależności od pewnych informacji. Najczęściej sprawdzaliśmy tylko jeden warunek, np.: Czy przycisk został wciśnięty?. W programie wyglądało to następująco: if (digitalread() == LOW) { //Jeśli przycisk wciśnięty //Zrób coś else { //Jeśli warunek nie został spełniony (przycisk nie jest wciśnięty) //Zrób coś innego... W praktyce często może się zdarzyć, że będziemy chcieli sprawdzić jednocześnie dwa warunki. Najprostszym przykładem będzie sprawdzenie, czy użytkownik wcisnął więcej niż jeden przycisk. Oczywiście można to zrobić tradycyjnie: if (digitalread() == LOW) { //Jeśli pierwszy przycisk wciśnięty, sprawdź... if (digitalread() == LOW) { //...czy wciśnięto również drugi przycisk //Zrób coś Rozwiązanie jest skuteczne, jednak pojawią się pewne problemy z czytelnością takie zapisu, gdy będziemy chcieli sprawdzić jednocześnie jeszcze więcej warunków. Dlatego zdecydowanie łatwiej będzie, gdy poznamy dwa operatory logiczne:

. Iloczyn logiczny &&. Suma logiczna O takiej możliwości wspomniałem już w poprzedniej części kursu. Teraz rozwiniemy ten temat. Pierwszy z nich wykorzystamy, gdy będziemy chcieli sprawdzić, czy: warunek pierwszy i warunek drugi został spełniony if (warunek == && warunek == ) Drugi z nich służy natomiast do sprawdzania, czy: spełniony został warunek pierwszy lub warunek drugi (lub oba) if (warunek == warunek == ) Łączenie warunków w praktyce W tym celu podłączmy do dwie diody (zieloną i czerwoną) oraz dwa przyciski. Schemat montażowy wygląda następująco: Schemat montażowy do przykładu z operatorami logicznymi. Teraz napiszmy program, który będzie włączał diodę zieloną, gdy wciśniemy jeden z dwóch przycisków. Kod może wyglądać np. tak: 0 pinmode(0, INPUT_PULLUP); //Przycisk jako wejście pinmode(, INPUT_PULLUP); //Przycisk jako wejście pinmode(, OUTPUT); //Dioda zielona jako wyjście pinmode(, OUTPUT); //Dioda czerwona jako wyjście digitalwrite(, LOW); //Wyłączenie diody zielonej digitalwrite(, LOW); //Wyłączenie diody czerwonej if (digitalread() == LOW digitalread(0) == LOW) { //Jeśli przycisk pierwszy lub drugi digitalwrite(, HIGH); //Włącz diodę zieloną else { digitalwrite(, LOW); //Wyłącz diodę zieloną W praktyce najważniejsza część tego programu ogranicza się do jednej linijki. Konkretnie warunku, w którym za jednym razem sprawdzamy stany dwóch przycisków. Jeśli przynajmniej jeden z nich został wciśnięty, to dioda zostanie włączona. Nasz program sprawdza, czy spełniono przynajmniej jeden warunek. W związku z tym dioda będzie również świeciła, gdy jednocześnie wciśniemy oba przyciski. Rozbudujmy trochę program i dodajmy osobny warunek, który będzie włączał diodę czerwoną, tylko gdy jednocześnie wciśniemy oba przyciski:

0 0 pinmode(0, INPUT_PULLUP); //Przycisk jako wejście pinmode(, INPUT_PULLUP); //Przycisk jako wejście pinmode(, OUTPUT); //Dioda zielona jako wyjście pinmode(, OUTPUT); //Dioda czerwona jako wyjście digitalwrite(, LOW); //Wyłączenie diody zielonej digitalwrite(, LOW); //Wyłączenie diody czerwonej if (digitalread() == LOW digitalread(0) == LOW) { //Jeśli przycisk pierwszy lub drugi digitalwrite(, HIGH); //Włącz diodę zieloną else { digitalwrite(, LOW); //Wyłącz diodę zieloną if (digitalread() == LOW && digitalread(0) == LOW) { //Jeśli przycisk pierwszy i drugi digitalwrite(, HIGH); //Włącz diodę zieloną else { digitalwrite(, LOW); //Wyłącz diodę zieloną Działanie ostatecznej wersji programu widoczne jest na poniższym filmie: Praktyczny przykład czujnik odległości Powyższe przykłady pokazywały, że układ działa, ale nie były zbyt użyteczne. Spróbujmy teraz zrobić coś bardziej praktycznego. Podłączmy do przycisk, czujnik odległości oraz buzzer. Układ będzie miał piszczeć brzęczykiem, jeśli przeszkoda znajdzie się w odległości między 0, a 0 cm lub, gdy wciśniemy przycisk. Wyjdzie nam z tego połączenie czujników parkowania z klaksonem! Do dzieła, najpierw łączymy potrzebny obwód. Aby było trochę trudniej, tym razem zamiast schematu montażowego podaję listę połączeń + pomocnicze zdjęcie. Na tym etapie kursie wszyscy powinni już dać radę złożyć taki układ samodzielnie: o trigpin czujnika odległości do pinu nr o echopin czujnika odległości do pinu nr o buzzer do pinu nr o przycisk do pinu nr 0 Oczywiście dodatkowo należy podłączyć odpowiednio zasilanie Vcc (szynę dodatnią) do czujnika odległości, natomiast masę do buzzera, przycisku oraz oczywiście również do czujnika. U mnie w praktyce wyglądało to tak: Kurs układ do testowania łączenia warunków w praktyce. Pora na napisanie programu. Odczytywać odległość już potrafimy, tak samo sprawdzanie stanu przycisku nie stanowi już dla nas żadnego problemu. Dlatego skupimy się na przeanalizowaniu warunku. Tak jak napisałem, zależy nam na włączenie buzzera, gdy odczytana odległość znajduje się w zakresie od 0 do 0 cm. W tym celu musimy sprawdzić, czy odczytana wartość jest większa od 0 i jednocześnie mniejsza od 0 cm. Zrobimy to oczywiście w jednym warunku:

if (dystans > 0 && dystans < 0) { digitalwrite(, HIGH); //Włącz buzzer else { digitalwrite(, LOW); //Wyłącz buzzer Teraz pora na obsłużenie przycisku. Oczywiście moglibyśmy rozbić to na dwa osobne warunki: 0 if (dystans > 0 && dystans < 0) { digitalwrite(, HIGH); //Włącz buzzer else { digitalwrite(, LOW); //Wyłącz buzzer if (digitalread(0) == LOW) { //Jeśli przycisk wciśnięty digitalwrite(, HIGH); //Włącz buzzer else { digitalwrite(, LOW); //Wyłącz buzzer Tylko po co? Nie powinniśmy powielać tych samych fragmentów kody, gdy tego nie musimy. W tym wypadku zbędne jest ponowne sterowanie włączeniem i wyłączeniem buzzera. Czy nie możemy warunku połączyć w jeden? Oczywiście, że możemy! Sprawdzimy czy: (zmierzony dystans jest większy od 0 i mniejszy od 0) lub (czy wciśnięto przycisk) Przekładając to na język zrozumiały dla komputera będzie to: if ((dystans > 0 && dystans < 0) digitalread(0) == LOW) { digitalwrite(, HIGH); //Włącz buzzer else { digitalwrite(, LOW); //Wyłącz buzzer Tym samym cały program prezentuje się następująco: 0 0 0 #define trigpin #define echopin pinmode(trigpin, OUTPUT); //Pin, do którego podłączymy trig jako wyjście pinmode(echopin, INPUT); //a echo, jako wejście pinmode(0, INPUT_PULLUP); //Przycisk jako wejście pinmode(, OUTPUT); //Buzzer jako wyjście digitalwrite(, LOW); //Wyłączenie buzzera long czas, dystans; digitalwrite(trigpin, LOW); delaymicroseconds(); digitalwrite(trigpin, HIGH); delaymicroseconds(0); digitalwrite(trigpin, LOW); czas = pulsein(echopin, HIGH); dystans = czas / ; if ((dystans > 0 && dystans < 0) digitalread(0) == LOW) { digitalwrite(, HIGH); //Włącz buzzer else { digitalwrite(, LOW); //Wyłącz buzzer W praktyce program działa dokładnie tak jak przewidywaliśmy. Na poniższym filmie widać, że buzzer wydaje dźwięk, gdy przeszkoda znajduje się w odpowiedniej odległości lub, gdy wciśniemy przycisk:

Pamiętasz wcześniejsze wykresy rysowane z odczytów tego czujnika? To właśnie te zakłócenia/piki sprawiają, że czasami słyszymy delikatne piknięcia. Oczywiście można je programowo filtrować, jeszcze kiedyś do tego wrócimy! Wykorzystanie operatorów logicznych do łączenia warunków jest bardzo proste, a ich odpowiednie użycie pozwala na rozwiązywanie naprawdę zawiłych problemów. Polecam potrenować we własnym zakresie rozbudowane warunki, chociażby rozwiązując poniższe zadanie domowe. Zadanie domowe 0. Napisz programy, które losują liczbę z zakresu 0-00, a następnie sprawdzają, czy wylosowana wartość jest:. mniejsza od 0 lub większa od 0. większa od 0, ale nie mieści się w przedziale 0-. równa 0, 0, 0 lub 0. mieści się w zakresie od 0 do 0 lub od 0 do 00 W każdym przypadku wyświetl na PC wylosowaną liczbę oraz informację, czy spełnia warunek. Podsumowanie Mam nadzieję, że wiedza, którą zdobyłeś podczas wykonywania ćwiczeń z tego odcinka kursu pomoże Ci w pisaniu jeszcze ciekawszych programów. Bardzo często, dla własnej wygody, będziesz korzystał z łączenia warunków oraz rysowania wykresów. Poświęć odpowiednią ilość czasu na opanowanie tego materiału. W kolejnym artykule na zajmiemy się sprawdzeniem zdobytej tu wiedzy! Tak, pora na mały QUIZ, który pozwoli na ocenę swoich umiejętności. Będzie to sygnał dla Was, czy możecie iść już dalej, czy warto wrócić do niektórych lekcji. Pojawią się również konkretne informacje dotyczące kontynuacji kursu, czyli poziomu II.