Rtc és eltelt idő számítása.

Processing/Wiring (illetve C) nyelvű programozási fogások, tippek. (AVR-Duino, Arduino, EthDuino, Diecimila, Severino, Nano, LilyPad)
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Sziasztok!

Építek egy tojáskeltetőt, amiben igen fontos lenne az eltelt idő pontos mérése.
Amit meg szeretnék valósítani, hogy az rtc-ből kiolvasom az elinduláskor az időt és tárolom egy változóban, amihez hasonlítom a jelenlegi időt. Ebből szeretném kiszámolni, hogy hány nap telt el az indítás óta.

Az alapokkal tisztában vagyok, de ez meghaladja a képességeimet...

Próbáltam, hogy a ciklusokoat számoltam. Egy ciklus 6mp volt. Így egy nap 14400 ciklus lett. 5 percig számoltam és 1mp késés jött ki, ami egy keltetés alatt elenyésző. Azonban futtattam egy napig a rendszert probaképp, és 12 óra alatt már 3 napnyi ciklus futott le!?!? Ergo egyáltalán nem megbízható.

Az arduino egy uno, az rtc pedig egy ds3231.
_______________________________________________________
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Ez a timing dolog nekem nem teljesen tiszta, mert nem tudom, hogy a kiolvasott idő/dátum értéket hogy tudom vizsgáltatni, úgy, hogy nem egy adott dátummal hasonlítom össze, hanem az indulási időponthoz képest pl 2 nappal...
Remélem érti valaki, hogy mire gondolok :D
_______________________________________________________
vargham
Chipgyilok
Hozzászólások: 308
Csatlakozott: 2014. január 8. szerda, 8:32

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: vargham »

Nem, nem értem.
Induláskor kiolvasod az időt az órából, elteszed egy változóba.
Rendszeres időközönként újra kiolvasod az időt, és összehasonlítod az eltárolttal.
Semmilyen ciklusidőt nem kell méregetni.
De van ebben az óra IC-ben lehetőség 2 riasztás beállítására is. Amikor eléri a beállított időt, megszakítást küld az MCU-nak. Az MCU pedig akár aludhat is, majd felébreszti a megszakítás. Elvégzi a teendőket, beállítja az újabb riasztást, majd vissza alszik.
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Az megvan, hogy kiolvasom, de milyen típusú változóba teszem? Illetve hogy tudok hozzáadni, hogy utána az összehasonlításhoz elő tudjam kapni?

A 2 riasztás kevés sajnos. Több változás van egy keltetési ciklus alatt. Páratartalom egy 17 napos ciklus alatt 1x, hűmérséklet 3x változik.
Illetve a riasztáshoz is a kiolvasott és elmentett időhöz kellene hozzáadnom, amit még mindig nem tudok, hogy álljak neki.

Illetve az se tiszta, hogy az indulás után eltelt órákat hogy tudom számolni?
_______________________________________________________
vargham
Chipgyilok
Hozzászólások: 308
Csatlakozott: 2014. január 8. szerda, 8:32

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: vargham »

> hogy tudok hozzáadni, hogy utána az összehasonlításhoz elő tudjam kapni?
Google "arduino rtc elapsed time"
Első két találat:
https://playground.arduino.cc/Code/Time
http://forum.arduino.cc/index.php?topic=227313.0

> A 2 riasztás kevés sajnos.
Annyi riasztást kezelsz szoftveresen, amennyit akarsz. Megnézed, hogy mikor esedékes a következő esemény, beállítod a riasztást az RTC-ben, és altatod az MCU-t. Az RTC-nek mindig csak a KÖVETKEZŐ riasztást kell tudnia, nem az összeset.
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Ha jól értem, akkor így lesz jó nekem:

Kód: Egész kijelölése

t = rtc.getTime();
const int heat1 = t+24;
int maxTemp = 37.5;

loop{
now = rtc.getTime();
if(now = heat1){
	maxTemp = 37.8;}
	if (temp < maxTemp) {digitalWrite(heating, HIGH)};
		else {digitalWrite(heating, LOW);}
}
HA jól értem! :D Bár még mindig nem tudom, hogy tudom hozzáadni pontosan óraszámot...
_______________________________________________________
Avatar
csegebiga
Chipgyilok
Hozzászólások: 288
Csatlakozott: 2015. március 27. péntek, 21:27

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: csegebiga »

Én a helyedben beírnám a keresőbe itt a fórumon, hogy ds3231 és megnézném, mit diskuráltak erről a chipről mások.
Akkor nem kellene mindent egymagad kitalálnod.
Pl: viewtopic.php?f=23&t=1918&hilit=ds3231
https://learn.adafruit.com/adafruit-ds3 ... uino-usage
Avatar
Robert
Elektronbűvölő
Hozzászólások: 10191
Csatlakozott: 2005. december 9. péntek, 7:00

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: Robert »

Még 1 ötlet:
A startidőtől kezdve mindent másodperc alapon kezelsz.
Linux time: 1970.01.01 00:00 óta eltelt idő mp-ben. (2041-ben lesz tólcsordulása csak).
http://www.tavir.hu - a gazda :)
Avatar
csegebiga
Chipgyilok
Hozzászólások: 288
Csatlakozott: 2015. március 27. péntek, 21:27

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: csegebiga »

mégegyszerűbb:
mivel a tojásnak tökmindegy , hogy milyen dátumot írunk, ezért az rtc-t nem is kell az aktuális dátumra beállítani.
induljon a keltetési szekvencia 01.01.0100:00:00 kor, tartson az első szakasz pl 01.01.07 12:00.00ig
kétféleképpen +sütheted el az áramkört a cél időpontban:
1. beállítod az rtc alarm regisztereit, és a chip által generált int jelet lekezeled, majd beállítod a következő alarm idöpontot
2. figyeled, hogy a rtcDay egyenlő-e a célDay értékkel? ha igen, a rtcHour=a célJour-ral, ha igen, a rtcMin= a célMin-nel? ha igen, idő van! elvégzed a teendőket, és beállítod a következő cél időpontot
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

csegebiga írta:mégegyszerűbb:
mivel a tojásnak tökmindegy , hogy milyen dátumot írunk, ezért az rtc-t nem is kell az aktuális dátumra beállítani.
induljon a keltetési szekvencia 01.01.0100:00:00 kor, tartson az első szakasz pl 01.01.07 12:00.00ig
kétféleképpen +sütheted el az áramkört a cél időpontban:
1. beállítod az rtc alarm regisztereit, és a chip által generált int jelet lekezeled, majd beállítod a következő alarm idöpontot
2. figyeled, hogy a rtcDay egyenlő-e a célDay értékkel? ha igen, a rtcHour=a célJour-ral, ha igen, a rtcMin= a célMin-nel? ha igen, idő van! elvégzed a teendőket, és beállítod a következő cél időpontot
A kettes megoldás ami nekem szimpatikus. Józan ésszel átgondolva, úgy látom hogy így ki lehet hagyni egy lépést, az alarm beállítást.
Még egy hülye kérdés: nekem nem kell másodperc pontosan, továbbgondoltam és szerintem elég lesz napos ciklusban is. Az az 1-2% rossz kikelési arány mindenképp megmarad sajnos.

Akkor ez így lenne jó? Illetve rednesen lereagálja a véltozóm, hogy pl 29-én hozzáadok 6-ot? Értem úgy, hogy nem lesz belőle 35 és nem teljesül soha a ciklus?

Kód: Egész kijelölése

startDay = x;
célDay = startDay;
loop{

if (célDay = startDay){
tedd amit kell;
célDay = célDay +2;}

if (célDay = rtcDay){
tedd amit kell;
célDay = célDay + 4;}

if (célDay = rtcDay){
tedd amit kell;
célDay = célDay + 2;}

_______________________________________________________
Avatar
kapu48
Elektronbűvölő
Hozzászólások: 3375
Csatlakozott: 2008. augusztus 29. péntek, 6:00

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: kapu48 »

Itt sok mindent megtanulhatsz:
[PDF]talk22: A DS1307 és DS3231 valósidejű órák használata (Arduino)
http://megtestesules.info/hobbielektron ... talk22.pdf


Kód: Egész kijelölése

void setup() {
  // put your setup code here, to run once:
startDay = x;
célDay = startDay + kovetkezo;
}

void loop() {
  // put your main code here, to run repeatedly:
if (célDay == startDay){ // Helyesen. A feltétel vizsgálat jele == egyenlő e?
tedd amit kell;
célDay = célDay +2;}

if (célDay == rtcDay){
tedd amit kell;
célDay = célDay + 4;}

if (célDay == rtcDay){
tedd amit kell;
célDay = célDay + 2;}
}
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Köszönöm nagyon hasznos a motyó és a javításod is :)
_______________________________________________________
Avatar
Robert
Elektronbűvölő
Hozzászólások: 10191
Csatlakozott: 2005. december 9. péntek, 7:00

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: Robert »

A program az utasításaid szerint működik.

29+4 = 33. Azaz _soha_ nem teljesül, mert az ÓraIC tudja belül, ha átcsordulás van, akkor bizony a nap léptet....
És így soha nem teljesül a nap eltelése...

Miért nem maradsz másodperc v. perc alapon az _indítás óta_ eltelt idővel?


Amivel számolj még:
- áramszünet/reset és az Arduino újraindul (hol tartottál? Mi a köv. lépés?),
- távoli debug/hozzáférés - eseménykövetés,
- hiányzik a folyamatlogolás (hőfok és páratartalom).
http://www.tavir.hu - a gazda :)
Avatar
kapu48
Elektronbűvölő
Hozzászólások: 3375
Csatlakozott: 2008. augusztus 29. péntek, 6:00

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: kapu48 »

Példa, Egyszerű keltető:
DHT22 hő és páratartalom mérő
DS3231 RTC
I2C_LCD 16*2 kijelző.
ventilátor relé
izzó1 relé
izzó2 relé
párásító relé

Kód: Egész kijelölése

// keltetogep.ino
#include <Wire.h>
#include "ds3231.h"
#include <LiquidCrystal_I2C.h>
#include "DHT.h"
#include "math.h"
 
int maxHum = 80;
int maxTemp = 37.3;
long cnt = 0;
int osztott = 0;

LiquidCrystal_I2C lcd(0x27,16,2);
#define BUFF_MAX 128
#define DHTPIN 2     // szenzorpin
#define DHTTYPE DHT22   // DHT 22  (AM2302)
#define fan 8 // ventilátor relé
#define heat1 9 // izzó1 relé
#define heat2 10  //izzó2 relé
#define hum 11  // párásító relé

uint8_t time[8];
char recv[BUFF_MAX];
unsigned int recv_size = 0;
unsigned long prev, interval = 1000;

DHT dht(DHTPIN, DHTTYPE);

void setup()
{
    Serial.begin(9600);
    Wire.begin();
    dht.begin();
    pinMode(fan, OUTPUT);
    pinMode(heat1, OUTPUT);
    pinMode(heat2, OUTPUT);
    pinMode(hum, OUTPUT);
    DS3231_init(DS3231_INTCN);
    memset(recv, 0, BUFF_MAX);
    lcd.init();
    lcd.backlight();
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print(" TYUKANYO  v1.1");
}

void loop()
{
    delay (1800);
    char in;
    char tempF[6]; 
    float temperature;
    char buff[BUFF_MAX];
    unsigned long now = millis();
    struct ts t;
    float hu = dht.readHumidity();
    float tm = dht.readTemperature();

    if (isnan(hu) || isnan(tm)) {
    Serial.println("Szenzorhiba 02!");
    lcd.clear();
    lcd.print("Szenzorhiba 02!");
    return;
    }

//rendszerszámláló, forgatásjelző    
osztott = (cnt/2400)+1;
round(osztott);
   lcd.clear();
   lcd.setCursor(5,0);
   lcd.print(osztott);
   lcd.print(". nap");
   lcd.setCursor(0,1);
   lcd.print (cnt);
   lcd.print (" ciklus");
if (osztott >= 2 && osztott <= 16) {lcd.setCursor(0,1);
                         lcd.print("Ma forgatni kell!");}
            
delay(1800);

//időarányos hűmérséklet és párabeállítás

if (osztott <= 16) {maxHum = 60;}
if (osztott > 16) {maxHum = 80;}
if (osztott <= 8) {maxTemp = 37.8;}
if (osztott <= 15) {maxTemp = 37.5;}
if (osztott > 15) {maxTemp = 37.2;}

//fűtés és páratartalom vezérlés 
    if(tm > maxTemp) {digitalWrite(fan, HIGH);
                      digitalWrite(heat1, HIGH);
                      digitalWrite(heat2, HIGH);
                      Serial.print (" FŰTÉS KIKAPCSOLVA!");
                      lcd.clear();
                      lcd.setCursor(0,0);
                      lcd.print(tm);
                      lcd.print((char)223);
                      lcd.print("C ");
                      lcd.print("Futes ki");}

                      else {digitalWrite(fan, LOW);
                            digitalWrite(heat1, LOW);
                            digitalWrite(heat2, LOW);
                            Serial.print (" FŰTÉS BEKAPCSOLVA!");
                            lcd.clear();
                            lcd.setCursor(0,0);
                            lcd.print(tm);
                            lcd.print((char)223);
                            lcd.print("C ");
                            lcd.print("Futes be");}
                                                  
    if (hu < maxHum) {digitalWrite(hum,LOW);
                      lcd.setCursor(0,1);
                      lcd.print(hu);
                      lcd.print((char)37);
                      lcd.print(" Para be");
                      Serial.print (" PÁRA BEKAPCSOLVA!");}
                        
                      else {digitalWrite(hum,HIGH);
                            lcd.setCursor(0,1);
                            lcd.print(hu);
                            lcd.print((char)37);
                            lcd.print(" Para ki");
                            Serial.print (" PÁRA KIKAPCSOLVA!");}
                         
delay (1900);

// idő és rendszerhőmérséklet kiírása
    if ((now - prev > interval) && (Serial.available() <= 0)) {
        DS3231_get(&t); //Get time
        parse_cmd("C",1);
        temperature = DS3231_get_treg(); //Get temperature
        dtostrf(temperature, 5, 1, tempF);

        lcd.clear();
        
        lcd.setCursor(2,0);
        
        lcd.print(t.year);
        printMonth(t.mon);
        lcd.print(t.mday);
                 
        lcd.setCursor(0,1); 
        lcd.print(t.hour);
        lcd.print(":");
        if(t.min<10)
        {
          lcd.print("0");
        }
        lcd.print(t.min);
        lcd.print(":");
        if(t.sec<10)
        {
          lcd.print("0");
        }
        lcd.print(t.sec);
        
        lcd.print(' ');
        lcd.print(tempF);
        lcd.print((char)223);
        lcd.print("C ");
        prev = now;
    }
Serial.print("Beállított hőmérséklet: ");
Serial.print(maxTemp);
Serial.print(" Beállított páratartalom: ");
Serial.println(maxHum);
Serial.print("Jelenlegi hőmérséklet: ");
Serial.print(tm);
Serial.print(" Jelenlegi páratartalom: ");
Serial.println(hu);
Serial.print("Üzemciklus: ");
Serial.print(cnt);
Serial.print(" Üzemnap: ");
Serial.println(osztott);
Serial.print(t.hour);
Serial.print(":");
        if(t.min<10)
        {
          Serial.print("0");
        }
        Serial.print(t.min);
        Serial.print(":");
        if(t.sec<10)
        {
          Serial.print("0");
        }
Serial.println(t.sec);
   
cnt = ++cnt;
}

void parse_cmd(char *cmd, int cmdsize)
{
    uint8_t i;
    uint8_t reg_val;
    char buff[BUFF_MAX];
    struct ts t;
}

void printMonth(int month)
{
  switch(month)
  {
    case 1: lcd.print(" Jan ");break;
    case 2: lcd.print(" Feb ");break;
    case 3: lcd.print(" Mar ");break;
    case 4: lcd.print(" Apr ");break;
    case 5: lcd.print(" Maj ");break;
    case 6: lcd.print(" Jun ");break;
    case 7: lcd.print(" Jul ");break;
    case 8: lcd.print(" Aug ");break;
    case 9: lcd.print(" Sept ");break;
    case 10: lcd.print(" Oct ");break;
    case 11: lcd.print(" Nov ");break;
    case 12: lcd.print(" Dec ");break;
    default: lcd.print(" Error ");break;
  } 
}
karolyia
DrótVégénSzéndarab
Hozzászólások: 18
Csatlakozott: 2017. április 14. péntek, 7:47

Re: Rtc és eltelt idő számítása.

Hozzászólás Szerző: karolyia »

Van egy lanshield ami megoldja, hogy ne kelljen az lcd kijelzőt figyelni. Áramszünet elméletileg kizárva, egy bazi nagy teherautóaksiról megy az egész motyó, amin rajta van a töltő is. A relépanel 5V, de az is megoldva egy 12V - 5V stepdown elektronikával.
Ha esetleg újraindul a motyó, akkor a lanshield sd kártyára ment és az utolsó mentésből futtatom az utolsó állás szerinti változókat. Ha nullázni akarom, akkor azt majd a webfelületen megoldom.

Pára és a hőmérséklet alapon működik jelnleg a cucc. Pont ezt szeretném automatizálni, hogy idő függvényében automatikusan ő állítson magának mindent, ne csak statív legyen a dolog.

De kezdek agyf@xt kapni. Hogy tudok hozzáadni egy kiolvasott dátumhoz? Globál változót hogy tudok egy rtc.now() parancsból csinálni, ami nem DateTime, hogy kezelhető legyen? Lehet érthetetlen amit írok, de lassan végigolvasom a netet, de nem találok ilyet.

Ami a fórumról be lett másolva, konkrétan én csináltam....
_______________________________________________________
Válasz küldése