Go Down

Topic: Comandare uscite con un Keypad (Read 4287 times) previous topic - next topic

nid69ita

#15
Mar 31, 2016, 12:17 pm Last Edit: Mar 31, 2016, 12:18 pm by nid69ita
Con delay() è una cavolata. Non è molto pratico, il delay è bloccante.  Devi imparare a usare millis() ma non è semplice se hai più rele da controllare.
E' solo una domanda di curiosità o DEVI farlo per forza ? Se si spiega bene quel che vuoi realizzare.
my name is IGOR, not AIGOR

marcosilve95

Alla fine ho due relè da controllare si,  però intanto pensavo di usare uno per capire  come funziona questo funzione millis ()

nid69ita

#17
Mar 31, 2016, 02:05 pm Last Edit: Mar 31, 2016, 02:06 pm by nid69ita
L'hai mai usata?  Il consiglio è sempre quello di partire da esempio più semplice.
Ti consiglio di partire da http://www.leonardomiliani.com/2013/programmiamo-i-compiti-con-millis/
Poi puoi arrivare anche ad una macchina a stati finiti, di solito concetto utile per avere una o più variabili che memorizzano lo "stato" di un qualcosa o più cose da monitorare e che può cambiare in base a input oppure in base al tempo.
my name is IGOR, not AIGOR

marcosilve95

Mai usato,  sembra complessa come cosa...
Quindi mi dici che usando la funzione  delay non si riesce a fare la stessa cosa?

nid69ita

Si e no.     Nel momento in cui Arduino esegue la delay(2000)   tutto è bloccato per 2 secondi, per 2 secondi anche se premi un tasto Arduino è bloccato.
my name is IGOR, not AIGOR

marcosilve95

Di fatti avevo notato che si bloccava tutto per il tempo impostato in delay..
Nell'esempio che mi hai mandato il link cè lo sketch per eseguire un blink, ima io esattamente nel mio sketch dove devo mettere esattamente il tutto per poter spegnere l'uscita attivata tramite pulsante del Keypad?

nid69ita

Conviene usare una variabile di stato 0 o 1 , la metti a 1 quando premi il pulsante (nello switch)
Poi dopo lo switch, se stato==1 allora conti con la millis e dopo 2 secondi (contati con millis) allora spegni rele e riponi stato=0.
my name is IGOR, not AIGOR

marcosilve95

Grazie per la risposta, ma come dovrei fare esattamente tutto questo? Perché non sono molto pratico.. La variabile di stato è la funzione int?

nid69ita

#23
Apr 01, 2016, 11:05 am Last Edit: Apr 01, 2016, 11:13 am by nid69ita
dichiari una variabile di tipo int (non è una funzione) che puoi chiamare   statoRele1 e la inizializzi a 0

nel programma quando premi il tasto che ti interessa, quindi nello switch...case  ramo giusto  statoRele1=1;  e memorizzi millis()

fuori e dopo lo switch()   metti un if che verifica se statoRele1==1, se si allora verifichi se passati 2 secondi.   
Questo il codice aggiuntivo rispetto al tuo, la parte iniziale fino a #define ledpin 13 va bene.
L'ho scritto senza provarlo !!
Code: [Select]

...   la parte iniziale non la riporto, va bene
#define ledpin 13 
int StatoRele1=0;
unsigned long previousMillis = 0;

void setup()
{ pinMode(ledpin,OUTPUT);
  digitalWrite(ledpin, HIGH);
  statoRele1=0;
  Serial.begin(9600);
  delay(1000);
}

void loop()
{ char key = kpd.getKey();
  if(key) Serial.println(key);
  switch (key)
  { case '1':
        statoRele1=1;                 // attivare rele e conteggio
        previousMillis = millis();  // istante in cui ha premuto
        break;
  }
  if(statoRele1==1)
  { if( millis()- previousMillis > 2000 )    // passati 2 secondi ? da quando hai premuto
    { statoRele1=0;    // disattivare rele e conteggio
    }
    digitalWrite(ledpin,statoRele1);
  }
my name is IGOR, not AIGOR

marcosilve95

#24
Apr 01, 2016, 12:21 pm Last Edit: Apr 01, 2016, 01:03 pm by marcosilve95
Grazie mille per il codice. Provandolo mi funzionava al contrario, cioè il relè restava sempre acceso e quando premevo restava spento per 2 secondi, e si riaccendeva. Allora ho invertito tutti i valori  di statoRelè e adesso funziona correttamente tutto.
Adesso se io volessi comandare anche il secondo relè, sempre con questo procedimento, come devo fare?

nid69ita

crei un altro statoRele2,   ed anche un'altra  previousMillis2
(e cambia la previousMillis in previousMillis1)
Poi raddoppi il pezzo alla fine dove fai if su statoRele1 ma lavori con statoRele2 e previouseMillis2
Ovviamente nello switch dovrai aggiungere un case per il rele2 gestendo sempre statoRele2 e previouseMillis2
my name is IGOR, not AIGOR

marcosilve95

E per quanto riguarda il #define ledpin 13, dovrei fare #define ledpin 12 anche, però come devo scriverlo questo pezzetto?  Perché se lo metto sotto mi lavora solo con il 12 dopo

nid69ita

#27
Apr 01, 2016, 05:32 pm Last Edit: Apr 01, 2016, 05:38 pm by nid69ita
E per quanto riguarda il #define ledpin 13, dovrei fare #define ledpin 12 anche, però come devo scriverlo questo pezzetto?  Perché se lo metto sotto mi lavora solo con il 12 dopo
fai due define, anche qui ledpin1 e ledpin2     cosi hai "associato" le varie variabili/define 1 e 2 tra loro

Code: [Select]
#define LEDPIN1 13 
#define LEDPIN2 12
byte StatoRele1,StatoRele2;
unsigned long prevMillis1,prevMillis2;

void setup()
{ pinMode(LEDPIN1,OUTPUT);
  pinMode(LEDPIN2,OUTPUT);
  statoRele1=LOW;       // LOW è uguale a 0, HIGH uguale a 1
  statoRele2=LOW;
  digitalWrite(LEDPIN1, statoRele1);
  digitalWrite(LEDPIN2, statoRele2);
  Serial.begin(9600);
  delay(1000);
}

void loop()
{ char key = kpd.getKey();
  if(key) Serial.println(key);
  switch (key)
  { case '1':
        statoRele1=HIGH;         // attivare rele e conteggio   
        prevMillis1 = millis();     // istante in cui ha premuto
        break;
    case '2':
        statoRele2=HIGH;         // attivare rele e conteggio   
        prevMillis2 = millis();     // istante in cui ha premuto
        break;
  }
  if(statoRele1==HIGH)
  { if( millis()- prevMillis1 > 2000 )    // passati 2 secondi ? da quando hai premuto
    { statoRele1=LOW;    // disattivare rele e conteggio
    }
    digitalWrite(LEDPIN1,statoRele1);
  }
  if(statoRele2==HIGH)
  { if( millis()- prevMillis2 > 2000 )    // passati 2 secondi ? da quando hai premuto
    { statoRele2=LOW;    // disattivare rele e conteggio
    }
    digitalWrite(LEDPIN2,statoRele2);
  }
}
my name is IGOR, not AIGOR

brunello22

Quote
Grazie mille, funziona!
Vorrei vedere, ci mancava solo che venisse pure a digitartelo.
E daglielo almeno un Karma a @nid69ita

marcosilve95

Adesso vorrei chiederti un'altra cosa: se volessi attivare statoRèle con due pulsanti, cioè magari premendo 1 si attiva il relè per 2 secondi, e magari premendo il tasto 2 si attiva sempre lo stesso relè per 4 secondi... Dovrei usare un altro previousMillis2, però non riesco a far in modo che si attivi il relè...

Go Up