Přidat otázku mezi oblíbenéZasílat nové odpovědi e-mailem Arduino timer

Zdravím.
Zkouším timer a asi jsem nepochopil princip

Timer

#include "Timer.h"
  
Timer t;
int pin = 2;
int pin1 = 13;
 
void setup()
{
  Serial.begin(9600);
  pinMode(pin1,INPUT_PULLUP);
  pinMode(pin,INPUT_PULLUP);
  pinMode(pin, OUTPUT); 
}
 
 
void loop()
{
  if (digitalRead(pin1)== LOW){  
    t.pulse(pin, 10 * 10 * 1000, LOW);
    Serial.println("hups");
 }
t.update();  
Serial.println("ja si dělam co chci");
}

Co je špatně?

Předmět Autor Datum
V tom příkladu mají pulse v setupu a ne v loopu. nový
Wikan 07.02.2016 20:12
Wikan
Ano, protože se to asi ma spustit jednou při startu. Ja chci aby se ten timer spoustil,až když bude… nový
kikoš 07.02.2016 20:19
kikoš
Ale ty tam ten timer furt inicializujes pri kazdom prechode loop. Uloz si ze uz si ho raz inicializo… nový
MM.. 07.02.2016 20:46
MM..
if (digitalRead(pin1)== LOW){ if(!uzsomtoinicializoval) { t.pulse(pin, 10 * 10 * 1000, LOW); uzsomt… nový
MM.. 07.02.2016 20:48
MM..
No takto to take nefunguje. Takto ho vytvořím timer t.pulse(pin, 10 * 10 * 1000, LOW); Takto ho spu… nový
kikoš 07.02.2016 21:18
kikoš
t.update musi byt mimo if Neviem co na tom nechapes, je to uplne jednoduche. t.pulse inicializuje t… nový
MM.. 07.02.2016 21:27
MM..
A hlavne t.pulse(pin, 10 * 10 * 1000, LOW); nesmie byť volané dookola v loop-e - inicializuje doneko… nový
pme 07.02.2016 21:35
pme
Ved som mu to uz pisal vyssie tucne aj s prikladom :) Neviem ci pisem bielou farbou alebo co :-D nový
MM.. 07.02.2016 21:37
MM..
Teda netuším, čo presne potrebuje, ale ak sa má timer spustiť len pri určitej podmienke, potom volať… nový
pme 07.02.2016 21:39
pme
A nastavujes si tam 100 sekund, tak si to preber ci chces 100sekund (10*10*1000ms) nový
MM.. 07.02.2016 21:32
MM..
#include "Timer.h" Timer t; int pin = 2; int pin1 = 13; boolean uzsomtoinicializoval; void setup()… nový
kikoš 07.02.2016 21:38
kikoš
No a co na tom nejde? Ked pride pulz na pin 13, tak to urobi na pine2 LOW na 100sekund (1minuta 40se… nový
MM.. 07.02.2016 21:43
MM..
A v inicializacii si musis dat boolean uzsomtoinicializoval = 0; aby si nepouzival neinicializovane… nový
MM.. 07.02.2016 21:43
MM..
A mas tam blbo zatvorku, mas v tom uplny gulas. Spravne (pridal som tam aj dalsie nech to je uplne j… nový
MM.. 07.02.2016 21:46
MM..
boolean uzsomtoinicializoval = 0; Zapnu arduino, zmačknu tlačítko, relé se sepne. A je furt seple.… nový
kikoš 07.02.2016 21:48
kikoš
Mam to tak jak jste to tu dal Vý. Rele furt seple. nový
kikoš 07.02.2016 21:52
kikoš
Čakáš 100 sekúnd? Ani potom nič? nový
pme 07.02.2016 21:58
pme
čekam už 20 minut a rele furt seple. nový
kikoš 07.02.2016 22:09
kikoš
Tak si ten kod mozno nenahral do arduina alebo nieco tam mas asi blbo. Ten pin 13 je urcite uz na hi… nový
MM.. 07.02.2016 22:13
MM..
Skus este to uzsomtoinicializoval = 1; zmenit na uzsomtoinicializoval = TRUE; a = 0 na =FALSE, ked… nový
MM.. 07.02.2016 22:14
MM..
Pre istotu to skúšaj napr. s LED-kou, že ako sa bude tváriť... a toto máš prečo? pinMode(pin,INPUT_P… nový
pme 07.02.2016 22:16
pme
pripadne zniz si ten cas na povedzme len 100milisekund t.pulse(pin, 100, LOW); ze jak dlho to bude… nový
MM.. 07.02.2016 22:19
MM..
Alebo aj uplne vyhod to else uzsomtoinizializoval = 0 aby sa ten timer nabeton inicializoval len ra… nový
MM.. 07.02.2016 22:20
MM..
Pre istotu to skúšaj napr. s LED-kou, že ako sa bude tváriť... a toto máš prečo? pinMode(pin,INPUT_P… nový
kikoš 07.02.2016 22:56
kikoš
Takže s LED-kou ten kód tiež nefunguje? Toto s rele funguje? digitalWrite(12, LOW); delay(1000); d… nový
pme 07.02.2016 23:08
pme
pinMode(Relay1, OUTPUT); digitalWrite(Relay1, HIGH); Ano ale když arduino nadjíždí, relé procvaknou… nový
kikoš 07.02.2016 23:14
kikoš
Tak nastavuj priamo registre uC a precitaj si datasheet, a nepouzivaj dementne funckie pre BFU a pre… nový
MM.. 08.02.2016 00:57
MM..
pinMode(pin,INPUT_PULLUP); pinMode(pin, OUTPUT); tam mozes nechat, ak to sposobi ze pre prepnuti na… nový
MM.. 08.02.2016 01:08
MM..
Uz si uplne vyhodil to } else { //pin1 je HIGH uzsomtoinicializoval = 0; } a skusil si to uz bez… nový
MM.. 08.02.2016 01:10
MM..
Skus este do toho setup() pridat to tucne: pinMode(pin,INPUT_PULLUP); pinMode(pin, OUTPUT); digitalW… nový
MM.. 08.02.2016 01:16
MM..
http://www.ebay.com/sch/i.html?_from=R40&_trksid=p 2050601.m570.l1313.TR0.TRC0.H0.X8+relay.TRS0&_nkw… nový
kikoš 07.02.2016 23:16
kikoš
Skus este do toho setup() pridat to tucne: pinMode(pin,INPUT_PULLUP); pinMode(pin, OUTPUT); digitalW… nový
kikoš 08.02.2016 08:31
kikoš
Jezisikriste skus co som pisal, alebo to zabal a daj to robit niekomu inemu. Ja to nepisem zo srandy… nový
MM.. 08.02.2016 10:06
MM..
Ked chces thready tak si pouzi thready, ale msuis potom pre mechnicky vstup urobit debouncing (aspon… nový
MM.. 08.02.2016 10:21
MM..
Skus toto (copypastni to cele tak jak je), je tam zabranene aby sa zavolal timer znova (kvoli bounci… nový
MM.. 08.02.2016 11:06
MM..
A to t.pulse nefunguje mozno aj preto lebo pretazujes vystup, a ta funkcia po uplynuti doby invertuj… nový
MM.. 08.02.2016 11:14
MM..
Tak to poslední funguje jak má :-) už se mi to podařilo udělat i pomocí threadu if(myThread.should… nový
kikoš 08.02.2016 11:32
kikoš
Tak pouzivaj radsej to posledni, je to asi bezpecnejsie. Ked spustas thread mechanickym tlacitkom,… nový
MM.. 08.02.2016 11:43
MM..
JJ, děkují ;-) poslední
kikoš 08.02.2016 13:56
kikoš

Ale ty tam ten timer furt inicializujes pri kazdom prechode loop. Uloz si ze uz si ho raz inicializoval a potom to zas ulozene zmen ked bude ten pin zas high. Nemozes timer inicializovat pri kazdom prechode loopom, potom samozrejme nikdy neskonci.

(asi to nechapes, on ten timer nebude cakat na tom riadku pulse, on sa hned vrati a t.update() to updatuje periodicky v loope).

No takto to take nefunguje.

Takto ho vytvořím timer t.pulse(pin, 10 * 10 * 1000, LOW);
Takto ho spustim t.update();
Na tom pinu 13 není furt LOW, jen dostane impulz.

Asi nechapu princip tohoto timeru

void loop()
{
if (digitalRead(pin1)== LOW){
t.pulse(pin, 10 * 10 * 1000, LOW);
t.update();
Serial.println("hups");
}

}

t.update musi byt mimo if

Neviem co na tom nechapes, je to uplne jednoduche. t.pulse inicializuje timer a hned sa vrati, a t.update musi byt volane periodicky (z loop() bez nejakych if)
t.pulse nesmie byt volane periodicky.

Ked to urobis presne jak som pisal, tak to urcite bude fungovat.

#include "Timer.h"

Timer t;
int pin = 2;
int pin1 = 13;
boolean uzsomtoinicializoval;
void setup()
{
Serial.begin(9600);
pinMode(pin1,INPUT_PULLUP);
pinMode(pin,INPUT_PULLUP);
pinMode(pin, OUTPUT);
}

void loop()
{
if (digitalRead(pin1)== LOW){
if(!uzsomtoinicializoval) {
t.pulse(pin, 10 * 10 * 1000, LOW);
uzsomtoinicializoval = 1;
Serial.println("hups");
}
else //pin je high
uzsomtoinicializoval = 0;
}
t.update();
}

A mas tam blbo zatvorku, mas v tom uplny gulas.
Spravne (pridal som tam aj dalsie nech to je uplne jasne):

void loop()
{
 if (digitalRead(pin1)== LOW){
  if(!uzsomtoinicializoval) {
   t.pulse(pin, 10 * 10 * 1000, LOW);
   uzsomtoinicializoval = 1;
   Serial.println("hups");
  }
 } else { //pin1 je HIGH
  uzsomtoinicializoval = 0;
 }

 t.update();
}

Skus este to
uzsomtoinicializoval = 1;
zmenit na
uzsomtoinicializoval = TRUE;

a = 0 na =FALSE, ked to je boolean, preistotu. Ale to by na to nemalo mat vplyv.
Skopiruj ten posledny kod co som sem daval, nech mas nabeton zatvorky tak jak treba.
A zniz si to na 10sekund (10*1000), nech na to nemusis cakat minuty

Pre istotu to skúšaj napr. s LED-kou, že ako sa bude tváriť...
a toto máš prečo?
pinMode(pin,INPUT_PULLUP); <----- toto hádam vyhoď
pinMode(pin, OUTPUT); <----- potrebuješ iba tento riadok - výstup !!!

Jsou tam připojené ty činské rele moduly které spinaji při 0
Když přepnu piny na výstup, okamžitě se rele sepnou.
Proto ty NPUT_PULLUP.

Problem bude tady t.pulse(pin, 10 * 10 * 1000, LOW);

Ono to funguje jen s HIGH t.pulse(pin,10000, HIGH);

A stejnak je to na houby.
Ono se to sepme, po chvilce rozepne a po par vteřínach sepne a seple to zustane.
Ja potřebují timer nebo hread do ktereho strčím

digitalWrite(12, LOW);
delay(1000);
digitalWrite(13, HIGH);

Takže s LED-kou ten kód tiež nefunguje?

Toto s rele funguje?

digitalWrite(12, LOW);
delay(1000);
digitalWrite(13, HIGH);

Tiež mám doma "čínske relé", ja ho najprv inicializujem:
pinMode(Relay1, OUTPUT);
digitalWrite(Relay1, HIGH);

a až následne ho spínam:
digitalWrite(Relay1, LOW); zapne
delay(2000);
digitalWrite(Relay1, HIGH); vypne

pochopiteľne je potrebné vedieť čo je to za relé a ako funguje - pri akom zapojení...

Tak nastavuj priamo registre uC a precitaj si datasheet, a nepouzivaj dementne funckie pre BFU a pre deti, ked to chces mat profesionalne.
Ono bud si to vsetk nastudujes do detailu a venujes tomu XY dni-tyzdnov-rokov (zavisi na urovni aktualnych znalosti), alebo budes len lepit veci pre deti.

pinMode(pin,INPUT_PULLUP);
pinMode(pin, OUTPUT);

tam mozes nechat, ak to sposobi ze pre prepnuti na output to rele nepreklepne, je to vporiadku (suvisi to prave s tymi registrami uC a bitmi v nich, ktore si si mal uz davno nastudovat).

To neni tvoj problem. Tvoj problem je ze tam mas najskor nahraty blby program, alebo mas nieco blbo zapojene. Ten program ktory som tu dal nemoze robit to co pises.

Skus este do toho setup() pridat to tucne:
pinMode(pin,INPUT_PULLUP);
pinMode(pin, OUTPUT);
digitalWrite(pin, HIGH);
nejaka zmena?

S telatky jsem už vyzkoušel vše
Ono to funguje takto spolehlivě.
pinMode(pin,INPUT_PULLUP);
pinMode(pin, OUTPUT);
Relatka při najíždění arduina aní necvaknou.

Já řeším problém, jak sepnout rele třeba na 10 minut, tak aby arduino vykonávalo další přikazy.

Princip tohohle timeru jsem nepochopil, no škoda :.(

Ja myslel že timer v arduinu funguje stejně jako v delphi

Timer1.Interval : = 300; nastavím čas
timer1.Enabled:=true; a spustím si ho.
a klidně si ho v procedure TForm1.Timer po prvním pruchodu mužu zastavit.
timer1.Enabled:=false
No asi ne.

Ale koukám na ArduinoThread co by mnělo muj problem vyřešít.

To vlakna dam

digitalWrite(2, LOW);
delay(1000);
digitalWrite(2, HIGH);

A pak v te podminfe to vlakno spustím

if(myThread.shouldRun())
myThread.run();

Jezisikriste skus co som pisal, alebo to zabal a daj to robit niekomu inemu. Ja to nepisem zo srandy ale preto ze napr. dementna funkcia v nejakej kniznici moze mat problem ak predtym nezavolas outpu high, apod., alebo ak sa zavola 2x, apod, zavisi od dementnej funkcie.

(a mas tam nieco zasadne blbo, a zatial len tapes v tme a hladas problem niekde inde ako skutocne je, a ani nerobis nic pre to aby si problem nasiel - debugging, mas tam debug vystupy, tie vyisuju co? atd)
Napr. kvoli bouncingu spinaca sa ti moze ta fcia zavolat viackrat, a ked potom viackrat invertuje vystup, potom by si mal efekt jak popisujes. Apod. Ked to enchces urobit poriadne tak to nerob vobec, ptz to potom nebude fungovat nikdy ptz nemas znalosti urobit to okamzite spravne - ked tam mas mechanicky spinac tak je potrebne toho hodne viac jak len jedno if a jedna funkcia.

Skus toto (copypastni to cele tak jak je), je tam zabranene aby sa zavolal timer znova (kvoli bouncingu tlacitka) ked timer uz bezi.

#include "Timer.h"
  
Timer t;
int pin = 2;
int pin1 = 13;
int stav = 0;

void setup()
{
  Serial.begin(9600);
  pinMode(pin1,INPUT_PULLUP);
  pinMode(pin,INPUT_PULLUP);
  pinMode(pin, OUTPUT); 
}

void vratPinNaHigh()
{
  digitalWrite(pin, HIGH);
  stav = 0;
}
 
void loop()
{
  if (digitalRead(pin1)== LOW && stav == 0){
     digitalWrite(pin, LOW);
     t.after(10*1000, vratPinNaHigh) 
     Serial.println("hups");
     stav = 1;
    }

  t.update();
}

to funguje jak?
Da sa to urobit blbovzdorne X roznymi sposobmi, da sa urobit debouncing len pomocou delay(10) a nechat povodny kod, da sa to urobit komplikovany debouncing s ratatnim alebo dalsim timerom ak je prechod cez loop casovo kriticky, atd.

Alebo ked pouzijes tie tvoje thready, tak musis urobit debouncing tlacitka. V tomto co som pisal to neni nutne ptz je to fuk, pocas celeho pulzu som v stav = 1 (a pisal si ze vstupny pulz je kratsi jak vystupny).

A to t.pulse nefunguje mozno aj preto lebo pretazujes vystup, a ta funkcia po uplynuti doby invertuje vystup, a zrejme tak ze si precita stav na vystupe a invertuje ho. Ked ale vystup pretazis ze pri hodnote HIGH cita z neho napatie LOW, tak ten vystup po uplynuti doby ta funkcia "invertuje" na nespravnu hodnotu. Nechce sa mi teraz citat zdrojaky tych fcii ale tipujem ze to robi tak. Zdrojak ktory som dal teraz tu do predch.odpovede nema tento problem.
Ked nieco robis tak to musis chapat, inac nebudes schopny nikdy garantovat ze to na 100% pojde vzdy spravne.

Tak pouzivaj radsej to posledni, je to asi bezpecnejsie.

Ked spustas thread mechanickym tlacitkom, tak musis aspon urobit delay(10) na debouncing. A samozrejme ze musis aj pamata stav, aby si ten thread nevytvoril 1000x (co sice nemusis vidiet hned, ale za urcitych okolnosti to potom moze uplne rohdoit cely system) T.j. napr.
if(digitalRead(pin) == HIGH && stav == 0)
{
spust thread
stav = 1;
delay(10); // debouncing
}

if(digitalRead(pin) == LOW && stav == 1)
{
stav = 0;
delay(10); // debouncing
}

Nevyhoda takehoto jednoducheho debouncingu je to ze to zastavi cele arduino na 10ms, ale je to takto najjednoduchsie.
Ked na to nemyslis a mas tam napr. debug vystup tak ten urobi opozdenie kludne aj 10ms a myslis si ze vsetko je super aj bez debouncingu a raz vyhodis ten debug vystup a zistis ze zrazu to blbne :)

Zpět do poradny Odpovědět na původní otázku Nahoru