Skocz do zawartości

Programator czasowy – wykorzystanie Arduino w automatyce domowej


Pomocna odpowiedź

Często zdarza się że potrzebne jest załączenie urządzenia na określony czas np. oświetlenia zewnętrznego. Do tego celu stosuje się programatory czasowe nazywane często wyłącznikami czasowymi. Są to urządzenia, dzięki którym możemy w skuteczny sposób zarządzać działaniem różnych urządzeń elektrycznych i zaoszczędzić zużycie energii.

Ten artykuł bierze udział w naszym konkursie! 🔥
Na zwycięzców czekają karty podarunkowe Allegro, m.in.: 2000 zł, 1000 zł i 500 zł.

konkurs_forbot_nagrody_1-350x147.png

Potrafisz napisać podobny poradnik? Opublikuj go na forum i zgłoś się do konkursu!
Czekamy na ciekawe teksty związane z elektroniką i programowaniem. Sprawdź szczegóły »

W tym artykule dowiesz się jak zbudować własny programator czasowy z wykorzystaniem Arduino oraz modułu DS1302. Dodatkowo zapoznasz się z obsługą modułu czasowego oraz wykorzystaniem pamięci EEPROM w praktyce.

IMG_20210324_143304.thumb.jpg.773b36a57aafebc8d38f5bbbe4be96ce.jpg

Potrzebne elementy:

  • płytka Arduino
  • płytka stykowa
  • przewody do płytki stykowej
  • moduł RTC DS1302
  • wyświetlacz LCD Nokia 5110
  • przekaźnik 5V
  • rezystory 2 x 220 Ω, 5 x 10 kΩ
  • dioda LED
  • 5 przycisków chwilowych     

IMG_20210324_145739.thumb.jpg.7198ec3ec5763aa6f54c24310b29fad3.jpgIMG_20210324_152623.thumb.jpg.339ff28434c13faa52f0532544a85b5b.jpg

 

Wykonanie układu

 

Zaczynamy od wyprowadzenia zasilania z Arduino na płytkę stykową

IMG_20210324_153229.thumb.jpg.b348c10050d5b8aa217d74c5e041dff8.jpg

 

Następnie umieszczamy wyświetlacz, przyciski oraz diodę LED

IMG_20210324_155202.thumb.jpg.9477f2cda41b7d9d1832897b69e7d0cd.jpg

 

Podłączamy moduł DS1302 (VCC do +5V, GND do masy, CLK do pinu A1, DAT do pinu A2, RST do pinu A3)

IMG_20210324_160325.thumb.jpg.024288c3b2f7c6f0556035fc4a9d19cd.jpg

 

Następnie podłączamy wyświetlacz (RST do pinu 3, CE do pinu 4, DC do pinu 5, DIR do pinu 6, CLK do pinu 7,  VCC do +5V,  GND do masy). Pin BL podłączamy do +5V poprzez rezystor 220 Ω

IMG_20210324_161549.thumb.jpg.faa20009fb4d7e8e5864189143c6019a.jpg

 

Łączymy diodę LED z pinem 13 poprzez rezystor 220 Ω oraz do każdego z przełączników podłączamy +5V oraz podłączamy je do pinów 8, 9, 10, 11, 12

IMG_20210324_163002.thumb.jpg.e3f4a2350c4975b92e1a3fa41205e790.jpg

 

Łączymy piny 8, 9, 10, 11, 12 z masą poprzez rezystory 10 kΩ

IMG_20210324_163445.thumb.jpg.df315ca07abb9d5befe27bc2ed302091.jpg

 

Podłączamy moduł przekaźnika 5V (VCC do +5V, GND do masy, IN do pinu A0)

IMG_20210324_163857.thumb.jpg.09f79f15d4e9817465a011e9d782f850.jpg

 

Gotowy układ prezentuje się następująco:

IMG_20210324_170754.thumb.jpg.9907ada315bed974f24d0e585d37071b.jpg

 

Tak wygląda schemat połączeń układu:

schemat.thumb.png.44891a784aa4487b7cc6accd42d9c2a7.png

 

Programowanie Arduino

Na początku wywołujemy biblioteki do obsługi modułu DS1302, wyświetlacza oraz pamięci EEPROM

#include <virtuabotixRTC.h> 
#include <Adafruit_GFX.h>
#include <Adafruit_PCD8544.h>
#include <EEPROM.h>

 

 

Następnie podajemy piny pod które podłączony jest wyświetlacz i moduł czasowy

Adafruit_PCD8544 display = Adafruit_PCD8544(7, 6, 5, 4, 3);
virtuabotixRTC myRTC(A1, A2, A3);

 

Dodajemy niezbędne zmienne oraz określamy piny pod które podłączone są przyciski do nastawy czasu, dioda LED oraz przekaźnik

int godzina1;
int godzina2;
int minuta1;
int minuta2;
int stang1;
int stang2;
int stanm1;
int stanm2;
int stanzm;
int zmiana;
int zmienna;
int odczytg1;
int odczytg2;
int odczytm1;
int odczytm2;
#define przyciskg1 8
#define przyciskg2 9
#define przyciskm1 10
#define przyciskm2 11
#define przyciskzm 12
#define dioda 13
#define przekaznik A0

 

W funkcji startowej inicjalizujemy wyświetlacz oraz definiujemy wejścia/wyjścia

void setup() {
  display.begin();
  display.setContrast(50);
  display.clearDisplay();
  pinMode(przyciskg1, INPUT);
  pinMode(przyciskg2, INPUT);
  pinMode(przyciskm1, INPUT);
  pinMode(przyciskm2, INPUT);
  pinMode(przyciskzm, INPUT);
  pinMode(dioda, OUTPUT);
  pinMode(przekaznik, OUTPUT);
  digitalWrite(przekaznik, HIGH);
}

 

Warto też dodać fragment umożliwiający wpisanie nastaw czasowych do pamięci przy pierwszym programowaniu wykorzystując funkcję EEPROM.write() oraz ustawienie godziny modułu czasu rzeczywistego (należy pamiętać, aby po ustawieniu tych wartości wgrać kod jeszcze raz ze skomentowanym tym fragmentem)

//EEPROM.write(0, 16); //ustawianie domyślengo czasu 
//EEPROM.write(1, 16); 
//EEPROM.write(2, 18);
//EEPROM.write(3, 20);
//myRTC.setDS1302Time(00, 23, 41, 5, 12, 3, 2021); //ustawianie czasu sekundy, minuty, godziny, dzień tygodnia, dzień miesiąca, miesiąc, rok

 

W funkcji loop na początku dodajemy funkcje if która będzie służyć do odczytu danych z pamięci EEPROM oraz porównywania ich z czasem rzeczywistym (domyślna praca)

if(zmiana==0) {            //odczyt danych z pamięci EEPROM oraz porównywanie ich z czasem rzeczywistym (domyślna praca)
 display.clearDisplay();
 display.setTextColor(BLACK);
 display.setTextSize(1);
 odczytg1 = EEPROM.read(0);
 odczytg2 = EEPROM.read(1);
 odczytm1 = EEPROM.read(2);
 odczytm2 = EEPROM.read(3);
 display.setCursor(0,0);
 display.print("Zalacz o:");
 display.setCursor(0,10);
 display.print(odczytg1);
 display.print(":");
 display.print(odczytm1);
 display.setCursor(0,20);
 display.print("Wylacz o:");
 display.setCursor(0,30);
 display.print(odczytg2);
 display.print(":");
 display.print(odczytm2);
 display.setCursor(0,40);
 display.print("zmiana:");
 display.print("OFF");
 display.display();
 myRTC.updateTime();
 delay(1000);
 if(myRTC.hours>=odczytg1 && myRTC.minutes>=odczytm1 && myRTC.minutes<odczytm2) {
  digitalWrite(dioda, HIGH);
  digitalWrite(przekaznik, LOW);
 }
 else if(myRTC.hours>=odczytg1 && myRTC.minutes>=odczytm1 && myRTC.hours<odczytg2) {
  digitalWrite(dioda, HIGH);
  digitalWrite(przekaznik, LOW);
 }
 if(myRTC.hours>=odczytg2 && myRTC.minutes>=odczytm2) { 
  digitalWrite(dioda, LOW);
  digitalWrite(przekaznik, HIGH);
 }
 }

 

Następnie dodajemy funkcje if która będzie sprawdzać czy przycisk umożliwiający zmianę nastaw czasowych został wciśnięty oraz będzie dodawać jedynkę do zmiennej  „zmiana”. Zmienną tą wykorzystamy do możliwości zmiany czasu

stanzm = digitalRead(przyciskzm);
 if(stanzm==HIGH){
  zmiana++;
  delay(500);
 }

 

Kolejna funkcja if będzie miała za zadanie wpisanie nowych nastaw czasowych do pamięci EEPROM wykorzystując funkcję EEPROM.update() oraz wyzerowanie wybranych zmiennych

if(zmiana==2) {
  EEPROM.update(0, godzina1); //zapis nowych nastaw czasowych
  EEPROM.update(1, godzina2);
  EEPROM.update(2, minuta1);
  EEPROM.update(3, minuta2);
  delay(200);
  zmiana=0;
  zmienna=0;
  godzina1=0;
  godzina2=0;
  minuta1=0;
  minuta2=0;
 }

 

Tworzymy funkcję o nazwie „zmianaczasu” która będzie służyć do zmiany nastaw czasowych. W tej funkcji zastosujemy między innymi funkcję EEPROM.read() służącą do odczytu bajtu danych z pamięci EEPROM

void zmianaczasu() {
  if(zmiana==1) {            //ustawianie nowych nastaw czasowych
  stang1 = digitalRead(przyciskg1);
  stang2 = digitalRead(przyciskg2);
  stanm1 = digitalRead(przyciskm1);
  stanm2 = digitalRead(przyciskm2);
  odczytg1 = EEPROM.read(0);
  odczytg2 = EEPROM.read(1);
  odczytm1 = EEPROM.read(2);
  odczytm2 = EEPROM.read(3);
  while(zmienna < 1) {      //dodawanie do zmiennych globalnych odczytu z pamięci EEPROM
  godzina1=godzina1+odczytg1;
  godzina2=godzina2+odczytg2;
  minuta1=minuta1+odczytm1;
  minuta2=minuta2+odczytm2;
  zmienna++;
  }
  display.clearDisplay();
  display.setTextColor(BLACK);
  display.setTextSize(1);
  display.setCursor(0,0);
  display.print("Zalacz o:");
  display.setCursor(0,10);
  display.print(godzina1);
  display.print(":");
  display.print(minuta1);
  display.setCursor(0,20);
  display.print("Wylacz o:");
  display.setCursor(0,30);
  display.print(godzina2);
  display.print(":");
  display.print(minuta2);
  display.setCursor(0,40);
  display.print("zmiana:");
  display.print("ON");
  display.display();
  if(stang1==HIGH) {
    godzina1++;
    delay(500);
    if(godzina1==24) {
      godzina1=0;
    }
  }
  if(stang2==HIGH) {
    godzina2++;
    delay(500);
     if(godzina2==24) {
      godzina2=0;
     }
  }
  if(stanm1==HIGH) {
    minuta1++;
    delay(500);
    if(minuta1==60) {
      minuta1=0;
    }
  }
  if(stanm2==HIGH) {
    minuta2++;
    delay(500);
    if(minuta2==60) {
      minuta2=0;
    }
  }
  }
}

 

Tak wygląda gotowy program:

#include <virtuabotixRTC.h> 
#include <Adafruit_GFX.h>
#include <Adafruit_PCD8544.h>
#include <EEPROM.h>

Adafruit_PCD8544 display = Adafruit_PCD8544(7, 6, 5, 4, 3);
virtuabotixRTC myRTC(A1, A2, A3);

int godzina1;
int godzina2;
int minuta1;
int minuta2;
int stang1;
int stang2;
int stanm1;
int stanm2;
int stanzm;
int zmiana;
int zmienna;
int odczytg1;
int odczytg2;
int odczytm1;
int odczytm2;
#define przyciskg1 8
#define przyciskg2 9
#define przyciskm1 10
#define przyciskm2 11
#define przyciskzm 12
#define dioda 13
#define przekaznik A0

void setup() {
  display.begin();
  display.setContrast(50);
  display.clearDisplay();
  pinMode(przyciskg1, INPUT);
  pinMode(przyciskg2, INPUT);
  pinMode(przyciskm1, INPUT);
  pinMode(przyciskm2, INPUT);
  pinMode(przyciskzm, INPUT);
  pinMode(dioda, OUTPUT);
  pinMode(przekaznik, OUTPUT);
  digitalWrite(przekaznik, HIGH);
  //EEPROM.write(0, 16); //ustawianie domyślengo czasu 
  //EEPROM.write(1, 16); 
  //EEPROM.write(2, 18);
  //EEPROM.write(3, 20);
  //myRTC.setDS1302Time(00, 23, 41, 5, 12, 3, 2021); //ustawianie czasu sekundy, minuty, godziny, dzień tygodnia, dzień miesiąca, miesiąc, rok
}

void loop() {
 if(zmiana==0) {            //odczyt danych z pamięci EEPROM oraz porównywanie ich z czasem rzeczywistym (domyślna praca)
 display.clearDisplay();
 display.setTextColor(BLACK);
 display.setTextSize(1);
 odczytg1 = EEPROM.read(0);
 odczytg2 = EEPROM.read(1);
 odczytm1 = EEPROM.read(2);
 odczytm2 = EEPROM.read(3);
 display.setCursor(0,0);
 display.print("Zalacz o:");
 display.setCursor(0,10);
 display.print(odczytg1);
 display.print(":");
 display.print(odczytm1);
 display.setCursor(0,20);
 display.print("Wylacz o:");
 display.setCursor(0,30);
 display.print(odczytg2);
 display.print(":");
 display.print(odczytm2);
 display.setCursor(0,40);
 display.print("zmiana:");
 display.print("OFF");
 display.display();
 myRTC.updateTime();
 delay(1000);

 if(myRTC.hours>=odczytg1 && myRTC.minutes>=odczytm1 && myRTC.minutes<odczytm2) {
  digitalWrite(dioda, HIGH);
  digitalWrite(przekaznik, LOW);
 }
 
 else if(myRTC.hours>=odczytg1 && myRTC.minutes>=odczytm1 && myRTC.hours<odczytg2) {
  digitalWrite(dioda, HIGH);
  digitalWrite(przekaznik, LOW);
 }
 
 if(myRTC.hours>=odczytg2 && myRTC.minutes>=odczytm2) { 
  digitalWrite(dioda, LOW);
  digitalWrite(przekaznik, HIGH);
 }
 }
 
 stanzm = digitalRead(przyciskzm);
 if(stanzm==HIGH){
  zmiana++;
  delay(500);
 }
 
 if(zmiana==2) {
  EEPROM.update(0, godzina1); //procedura zapisu gdy przycisk zmiany zostanie wciśnięty 2 raz
  EEPROM.update(1, godzina2);
  EEPROM.update(2, minuta1);
  EEPROM.update(3, minuta2);
  delay(200);
  zmiana=0;
  zmienna=0;
  godzina1=0;
  godzina2=0;
  minuta1=0;
  minuta2=0;
 }
zmianaczasu();
}

void zmianaczasu() {
  if(zmiana==1) {            //ustawianie nowych nastaw czasowych
  stang1 = digitalRead(przyciskg1);
  stang2 = digitalRead(przyciskg2);
  stanm1 = digitalRead(przyciskm1);
  stanm2 = digitalRead(przyciskm2);
  odczytg1 = EEPROM.read(0);
  odczytg2 = EEPROM.read(1);
  odczytm1 = EEPROM.read(2);
  odczytm2 = EEPROM.read(3);
  
  while(zmienna < 1) {      //dodawanie do zmiennych globalnych odczytu z pamięci EEPROM
  godzina1=godzina1+odczytg1;
  godzina2=godzina2+odczytg2;
  minuta1=minuta1+odczytm1;
  minuta2=minuta2+odczytm2;
  zmienna++;
  }
  
  display.clearDisplay();
  display.setTextColor(BLACK);
  display.setTextSize(1);
  display.setCursor(0,0);
  display.print("Zalacz o:");
  display.setCursor(0,10);
  display.print(godzina1);
  display.print(":");
  display.print(minuta1);
  display.setCursor(0,20);
  display.print("Wylacz o:");
  display.setCursor(0,30);
  display.print(godzina2);
  display.print(":");
  display.print(minuta2);
  display.setCursor(0,40);
  display.print("zmiana:");
  display.print("ON");
  display.display();
  
  if(stang1==HIGH) {
    godzina1++;
    delay(500);
    if(godzina1==24) {
      godzina1=0;
    }
  }
  
  if(stang2==HIGH) {
    godzina2++;
    delay(500);
     if(godzina2==24) {
      godzina2=0;
     }
  }
  
  if(stanm1==HIGH) {
    minuta1++;
    delay(500);
    if(minuta1==60) {
      minuta1=0;
    }
  }
  
  if(stanm2==HIGH) {
    minuta2++;
    delay(500);
    if(minuta2==60) {
      minuta2=0;
    }
  }
  }
}

 

Krótki opis zasady działania układu

Po włączeniu układu na wyświetlaczu ukazują się aktualne nastawy czasowe (czas załączenia oraz czas wyłączenia) oraz informacja o włączeniu lub wyłączeniu możliwości zmiany tych nastaw. Układ załącza oraz wyłącza przekaźnik o określonej godzinie i minucie. Aby zmienić czas załączenia oraz wyłączenia należy przytrzymać przycisk zmiany. Na wyświetlaczu ukaże się informacja o możliwości zmiany czasów „zmiana: ON”. Przyciskami możemy ustawiać godzinę oraz minutę o której ma się załączyć oraz wyłączyć przekaźnik. Aby zapisać nowe ustawienia naciskamy przycisk zmiany. Na wyświetlaczu ukaże się informacja o wyłączeniu możliwości zmiany czasów „zmiana: OFF”. Odłączenie zasilania lub jego awaria nie spowoduje zaburzenia działania układu oraz utraty zapisu aktualnie zapisanych nastaw czasowych.

 

Materiały potrzebne do odtworzenia opisywanego projektu

programator czasowy.rar

 

Podsumowanie

W tym artykule postarałem się przedstawić jedno z wielu zastosowań Arduino w automatyce domowej. Prezentowany układ można wykorzystać do sterowania dowolnym urządzeniem elektrycznym, ogranicza nas tylko wyobraźnia. Zachęcam do samodzielnego eksperymentowania i szukania nowych założeń i rozwiązań omówionego układu. Powodzenia!

  • Lubię! 2
Link to post
Share on other sites

@Qubix witam na forum 🙂 Twój wpis został właśnie zaakceptowany i jest już widoczny publicznie 🚀

Link to post
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.