Skocz do zawartości

HC-SR04 - Wielofunkcyjność programowa na podstawie czujnika odległości. Modyfikacja programu


Forseti

Pomocna odpowiedź

(edytowany)

Na obecną chwilę warto podsumować i zebrać w jeden post rozwiązanie kwestii wielofunkcyjności programowej, dającej możliwość przełączania trybów pracy za pomocą przełącznika ON/OFF/ON, zgodnie z poniższym diagramem:

Diagram sterujący.jpg

Rozwiązanie powyższego zagadnienia zależy od tego czy chcemy sterować za pomocą przycisków monostabilnych (microswitch) czy bistabilnych (np. przełącznik suwakowy czy kołyskowy). 

Wersja 1 - Przełącznik bistabilny ON/OFF/ON

Program oparty o warunkowanie IF-ELSE-IF:

Schemat_ONOFF.thumb.png.a51b6fb74de6e73fa8f2edcd52083560.png

 

//Program symulujący pracę dwóch programów przełączanych za pomocą przełącznika ON/OFF/ON lub suwakowego.
//Nie dotyczy przycisków typu microswitch
//Program_1 - LED 1
//Program_2 - LED 2

#define Przycisk_1 8 //Przełącznik_1
#define Przycisk_2 9 //Przełącznik_2
#define Przycisk_3 10 //Przełącznik_3
#define LED_1 2 //LED zielona 1
#define LED_2 3 //LED zielona 2

void setup () {
  //Wyprowadzenie przycisków
  pinMode(Przycisk_1, INPUT_PULLUP); //Wejście przycisku 1 w trybie PULLUP
  pinMode(Przycisk_2, INPUT_PULLUP); //Wejście przycisku 2 w trybie PULLUP
  pinMode(Przycisk_3, INPUT_PULLUP); //Wejście przycisku 3 w trybie PULLUP

  //Wyprowadzenia LED
  pinMode(LED_1, OUTPUT); //Wyjście na LED zielona 1
  pinMode(LED_2, OUTPUT); //Wyjście na LED zielona 2

  //Ustawienie wyjściowego stanu LED
  digitalWrite(LED_1, LOW); //Stan diody LED1 - wyłączona
  digitalWrite(LED_2, LOW); //Stan diody LED2 - wyłączona
}

void loop() {

  if (digitalRead(Przycisk_1) == LOW) { //Jeśli Przycisk_1 jest włączony - Program_2
    digitalWrite(LED_1, HIGH);
    digitalWrite(LED_2, LOW);
    //Włącz LED zielona 1 - PROGRAM 1

  } else if (digitalRead(Przycisk_2) == LOW) { //Jeśli Przycisk_2 jest włączony - Program_2

    digitalWrite(LED_1, LOW);
    digitalWrite(LED_2, HIGH);
    //Włącz LED zielona 2 - PROGRAM 2

  } else if (digitalRead(Przycisk_3) == LOW) { //Jeśli Przycisk_3 jest włączony - Stan OFF

    digitalWrite(LED_1, LOW);
    digitalWrite(LED_2, LOW);
    //Wyłącz LED - Symulacja Stan OFF

  } else {
    digitalWrite(LED_1, LOW); //Wyłącz LED zielona 1
    digitalWrite(LED_2, LOW); //Wyłącz LED zielona 2
  }
}

 

Wersja 2 - Przełącznik monostabilny (microswitch)

Schemat_przycisk.thumb.png.c92f4e5360f4b306dd5a32141de8cc77.png

Program oparty o warunkowanie switch case. 

//Program symulujący pracę dwóch programów przełączanych za pomocą przełącznika monostabilnego
//Przyciski typu microswitch
//Program_1 - LED 1
//Program_2 - LED 2

#define Przycisk_1 8 //Microswitch_1
#define Przycisk_2 9 //Microswitch_2
#define Przycisk_3 10 //Microswitch_3
#define LED_1 2 //LED zielona 1
#define LED_2 3 //LED zielona 2

uint8_t tryb_program = 0; //Zmienna trybu programu

void setup () {
  //Wyprowadzenie przycisków
  pinMode(Przycisk_1, INPUT_PULLUP); //Wejście przycisku 1 w trybie PULLUP
  pinMode(Przycisk_2, INPUT_PULLUP); //Wejście przycisku 2 w trybie PULLUP
  pinMode(Przycisk_3, INPUT_PULLUP); //Wejście przycisku 3 w trybie PULLUP

  //Wyprowadzenia LED
  pinMode(LED_1, OUTPUT); //Wyjście na LED zielona 1
  pinMode(LED_2, OUTPUT); //Wyjście na LED zielona 2


  //Ustawienie wyjściowego stanu LED
  digitalWrite(LED_1, LOW); //Stan diody LED1 - wyłączona
  digitalWrite(LED_2, LOW); //Stan diody LED2 - wyłączona

}

void loop () {

  if (digitalRead(Przycisk_1) == LOW) {
    tryb_program = 1; //Warunek - sprawdzenie stanu - jeśli Przycisk_1 włączony
  }
  if (digitalRead(Przycisk_2) == LOW) {
    tryb_program = 2; //Warunek - sprawdzenie stanu - jeśli Przycisk_2 włączony
  }
  if (digitalRead(Przycisk_3) == LOW) {
    tryb_program = 3; //Warunek - sprawdzenie stanu - jeśli Przycisk_3 włączony
  }

  switch (tryb_program) {

    case 1:
      digitalWrite(LED_1, HIGH);
      digitalWrite(LED_2, LOW);
      //Włącz LED zielona 1 - PROGRAM 1
      break;
    case 2:
      digitalWrite(LED_1, LOW);
      digitalWrite(LED_2, HIGH);
      //Włącz LED zielona 2 - PROGRAM 2
      break;
    case 3:
      digitalWrite(LED_1, LOW);
      digitalWrite(LED_2, LOW);
      //Wyłącz LED - Stan OFF
      break;
  }
}

 

Przykład implementacji jednego z powyższych rozwiązań do bardziej zaawansowanego kodu.

Oczywiście kod ten można usprawnić co, zgodnie z sugestiami, zamierzam zrobić 🙂

Edytowano przez Forseti
  • Lubię! 1
Link do komentarza
Share on other sites

@farmaceuta  A zdecydowanie tak. Jeszcze nie wiem jak to zrobić ale jak wspominałem ten kod jest rozwojowy. Przypuszczam, że powinienem się kierować w stronę takiego założenia:

  1. Jeśli przycisnę pierwszy raz przycisk - Program_1
  2. Jeśli przycisnę drugi raz przycisk - Program_2
  3. Jeśli przycisnę trzeci raz przycisk - OFF

Czyli zapamiętanie i porównanie stanu przycisku ? 

Link do komentarza
Share on other sites

Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

8 minut temu, Forseti napisał:

Jeśli przycisnę pierwszy raz przycisk - Program_1

  1. Jeśli przycisnę drugi raz przycisk - Program_2
  2. Jeśli przycisnę trzeci raz przycisk - OFF

Dokladnie tak...wystarczy zrobic jeden if i za kazdym wcisnieciem guzika dodawac o 1 do "tryb_programu"...ale tu juz trzeba zrobic jakis "opuzniacz" dla guzika zeby nie wystepowal negatywny skutek drgan stykow...(teraz ten efekt wystepuje ale jest nie istotny bo za kazdym razem w if przypisujesz ta sama wartosc do zmiennej) tylko w takiej opcji mozesz zmieniac tylko kolejno, czyli program..0/1/2/3..0/1/2/3 itd. 

Mozna tez sie polakomic i zrobic tak ze powiedzmy przez 2s sprawdzasz ile razy guzik wcisniety a po uplywie tego czasu odpowiednio wykonujesz...taki sposob daje Ci mozliwosc przeskoku z kazdego podprogramu do dowolnie innego np...0/1/3/2/3/0/1/3 itp...

15 minut temu, _LM_ napisał:

Farmaceucie pewnie chodziło o to że co klik przycisku przełącza się funkcja no czyli tak jak napisałeś 

Dokladnie😉 puki pinow nie brakuje to taki sposob moze byc zbedy..w przeciwnym razie to juz koniecznosc..

Link do komentarza
Share on other sites

(edytowany)

@farmaceuta  Walczę z tematem 🙂 Uzupełniłem kod o metodę "zatrzasku" @Gieneq i idę w kierunku odczytania stanu przycisku. Póki co jeszcze nie doszedłem jak zawrócić program. Przełącza się pomiędzy case ale nie rozpoczyna na nowo.

//Program symulujący pracę dwóch programów przełączanych za pomocą przełącznika monostabilnego
//Przyciski typu microswitch
//Program_1 - LED 1
//Program_2 - LED 2

#define Przycisk_1 8 //Microswitch_1
#define LED_1 2 //LED zielona 1
#define LED_2 3 //LED zielona 2

uint8_t tryb_program = 0; //Zmienna trybu programu
int ostatniStan = HIGH; //PULLUP

void setup () {
  //Wyprowadzenie przycisków
  pinMode(Przycisk_1, INPUT_PULLUP); //Wejście przycisku 1 w trybie PULLUP

  //Wyprowadzenia LED
  pinMode(LED_1, OUTPUT); //Wyjście na LED zielona 1
  pinMode(LED_2, OUTPUT); //Wyjście na LED zielona 2

  //Ustawienie wyjściowego stanu LED
  digitalWrite(LED_1, LOW); //Stan diody LED1 - wyłączona
  digitalWrite(LED_2, LOW); //Stan diody LED2 - wyłączona

}

void loop () {

  int aktualnyStan = digitalRead(Przycisk_1);

  if (ostatniStan == HIGH &&  aktualnyStan == LOW)  {//Jeśli ostatni stan był wyłączony i aktualny stan jest włączony to:
    tryb_program += 1; //Warunek - sprawdzenie stanu - jeśli Przycisk_1 włączony
  }

  switch (tryb_program) {

    case 1:
      digitalWrite(LED_1, HIGH);
      digitalWrite(LED_2, LOW);
      //Włącz LED zielona 1 - PROGRAM 1
      break;
    case 2:
      digitalWrite(LED_1, LOW);
      digitalWrite(LED_2, HIGH);
      //Włącz LED zielona 2 - PROGRAM 2
      break;
    case 3:
      digitalWrite(LED_1, LOW);
      digitalWrite(LED_2, LOW);
      //Wyłącz LED - Stan OFF
      break;
  }
  ostatniStan = aktualnyStan;
  delay(50);
}

 

Edytowano przez Forseti
Link do komentarza
Share on other sites

Narazie dodaj taka poprawke...

if (ostatniStan == HIGH &&  aktualnyStan == LOW)  {//Jeśli ostatni stan był wyłączony i aktualny stan jest włączony to:
    tryb_program++; //inkrementacja(dodaj 1)
  if (tryb_program > 3) { //jesli przekroczysz ilosc podprogramow to zacznij liczyc odnowa..
    tryb_program = 0;
    }
  }

I bedziesz mial opcje..0/1/2/3/0/1/2/3 etc..😉

  • Pomogłeś! 1
Link do komentarza
Share on other sites

2 minuty temu, farmaceuta napisał:

Wszystko na spokojnie ogarniesz😊 a nastepnie to jeszcze ta ilosc klikniec sie zrobi i bedzie do wyboru..

Myślałem, o zmiennej byte (mało zajmuje miejsca w pamięci) do zapamiętywania ilości kliknięć ale to na następny raz - pewnie znów mi się popierniczy ale grunt, że coś wychodzi i niewiele brakuje mi do rozwiązania danego problemu - to cieszy 🙂

Link do komentarza
Share on other sites

Cytat

Myślałem, o zmiennej byte (mało zajmuje miejsca w pamięci) do zapamiętywania ilości kliknięć 

Do zapamiętywania małych liczb możesz użyć ośmiobitowego integera: 

int zmienna_1; //"zwykły" int, zajmuje 2 bajty pamięci(16 bit) i przyjmuje wartości od -32768 do 32767
uint8_t zmienna_2; //int ośmiobitowy(1 bajt), przyjmuje wartości od 0 do 255.

Oczywiście trzeba uważać, żeby nie przekroczyć zakresu tej zmiennej.

  • Lubię! 1
Link do komentarza
Share on other sites

coś wam pokażę 😉

if(!digitalRead(Przycisk_1))tryb_program++;

switch(tryb_program % 4){
  case 0:...
    ....
}

P.S jest tu drobny BUG. Gdzie?

 

Edytowano przez _LM_
post script
  • Lubię! 1
Link do komentarza
Share on other sites

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Anonim
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.

×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.