alba tramonto

Iooooooooo sono ancoraaaa qua….. eeeeegià

Buongiorno a tutti, 
per fortuna la frustrazione non e' una sensazione che mi colpisce….. PERO' !!!!!!!!!!!!!!!!
Ho provato a sistemare le cose, con consigli, ricerche ecc ecc. niente da fare….
tra le altre varie, anche le righe compilate da Standardoil che però, nonostante commentate per i dummies, non sono riuscito a implementare.

La mia idea e' che questi timer righe 49/52, facessero da ritardo tra gli step incrementali e decrescenti sui led  righe 5/7. 
Invece no, vanno a MANETTA.
Inoltre dopo poco tempo si inchioda tutto. 
Ho letto che per evitare l'overflow si poteva usare il sistema nelle righe 86/93.
E' evidente che non ho capito un ……
Anche perché, su serial monitor, ho stampato i millis e non mi sembra che sia un problema di overflow, capita dopo pochi min, o comunque poco tempo.
dimenticavo di dire che sto usando un arduino DUE.

LOST…..LOST......LOST…..!!!!!!!

codeforforum.ino (8.88 KB)

Visto brevemente il codice. Il mio parere e che se si utilizza una state machine basata su switch in ogni case si deve esplicitare il cambio di stato. Tradotto vuole dire che in ogni case deve essere del codice simile a night = nuovo stato.

Diversamente nascondendo dentro funzioni richiamate il cambio stato risulta complicato seguire il comportamento dello switch.

Ti consiglio di ripartire da zero, postando del codice di base da sviluppare con l'aiuto del forum.

Rileggendo il codice non capisco questo:

time2sec ();  {
          redblue--;
        }

Non ha senso ed è fuorviante.

Il codice dentro le parentesi graffe si chiama blocco di codice, dentro questa porzione di codice delimitato le variabili sono locali se dichiarate al loro interno. reedblue non è dichiarata locale per cui non ha senso {}.

Ciao.

ciao, grazie del consiglio,
purtroppo non so piu', ho toccato troppo e dappertutto.
mi spieghi solo una cosa pero'?
parlavi di graffe e blocco di codice se all'interno.
io credevo che tra le tonde mettevi le condizioni per eseguire quello che avevi tra le graffe.
In ordine di scrittura e quindi di escecuzione.

Le graffe delimitano una porzione di codice, ognuna può essere annidata dentro l'altra, cioè,

void loop() {
    {
        porzione 1
        {
             porzione 2 annidata 
        }
    
    } 
}

All'interno di una porzione di codice le variabili dichiarate al loro interno sono locali e quindi visibili solo al loro interno, vedi "Ambito di visibilità" o in inglese variable scope: link

Come detto chiamiamo per convenzione la porzione di codice delimitata da graffe con il nome "blocco di codice".

Un blocco di codice può essere o meno associato ad una istruzione (o comando), cioè l'istruzione if (condizione) ha ad esso associata una solo riga, diciamo che il blocco di codice associato implicitamente ad if non può essere più di una riga al cui termine c'è ";". Per estendere il blocco di codice della if lo esplicitiamo con le parentesi graffe. Questa è l'associazione di un blocco di codice ad una istruzione.

Una funzione ad esempio richiede per forza di cose un modo per esplicitare quale porzione di codice appartiene alla funzione, ecco che il blocco di codice viene usato per assegnare una porzione di codice ad un nome di funzione.

Se sai quello che stai facendo puoi anche usare blocchi di codice annidati e non associati, raramente ciò si fa.

io credevo che tra le tonde mettevi le condizioni per eseguire quello che avevi tra le graffe.

mmmh...
Tra le tonde puoi esplicitare la condizione, ma puoi elencare anche gli argomenti di una funzione, coma fai appunto in

void setColor(int redblue, int Uv, int bianco)

Riguardo al tuo progetto fai una sola animazione e postala. Se ci riesci metti l'animazione dentro il case 0. Sempre se ci riesci non usare while. for ed in generale istruzioni di ciclo. Quando l'animazione deve terminare assegna alla nightvariabile un valore diverso da zero.

Se ti servono i cicli usa una variabile per ogni ciclo e usa if e l'incremento come da esempio:

if (contatoreCiclo1 < 20) 
   contatoreCiclo1++;

contatoreCiclo1 verrà incrementata di uno fino al valore 19 (se parte da zero).

Puoi anche usare contatoreCiclo1 per terminare l'animazione, es:

if (contatoreCiclo1 == 19)
    night = 1;

Nel realizzare l'animazione mantieni semplice il codice poiché potrebbe (è desiderabile) essere necessario scomporre il codice in più di uno switch case.

Se non usi for, while, do while e delay dentro il case puoi mettere fine prematura all'animazione spedendo da seriale un simbolo che una volta ricevuto da arduino mette tramite if (simbolo) night = 1;

Se te la senti dai una lettura e prova a sperimentare con il codice presente in questo thread

PS: c'è un piccolo errore in ciò che ho scritto, ma se OP sperimenta si accorge subito di ciò.

Ciao.

ma questo?

  if ( t.hour >= Hoursunrise && t.min >= Minsunrise && t.sec >= Secsunrise && t.hour >= !Hourday && t.min >= !Minday && t.sec >= !Secday) {//6.1.00

è illeggibile, oltre che "non chiaramente" sbagliato

dico non "chiaramente" perché essendo quasi illeggibile non ci si accorge al primo colpo
leggiamo:
se
ora maggiore o uguale di soglia
e
minuto maggiore o uguale di soglia
e
secondo maggiore o uguale di soglia
e perché? devi proprio badare al secondo? al minuto ancora ancora, ma al secondo?
comunque adesso viene il bello:

e
ora maggiore o uguale di NOT soglia

che sarà sempre vero:
NOT soglia (dato che hai messo la soglia a 6) significa 0, e qualsiasi ora sia sarà sempre maggiore o uguale a zero
stessa cosa per i minuti, subito dopo

insomma è sbagliato
e di queste righe ne hai 4

poi hai una loop "veneta": "faso tuto mi"
mi perdonino i veneti, ma se ci vuole ci vuole

quando hai finito di leggerla non ti ricordi più come era cominciata

tu devi suddividere le varie "operazioni" e richiamare nella loop le varie funzioni che avrai individuato nella suddivisione

un "grosso" consiglio:

una funzione fa una cosa, non due
una cosa viene fatta da una funzione, non da due

cosa significa:
se controlli l'ora non tocchi le luminosità
se devi regolare le luminosità non guardi l'orologio

ma sopratutto
regoli la luminosità con una sola funzione, non tocchi i led da nessuna altra parte

dubbio forte dubbio
io avevo capito che lo OP aveva letto e compreso, non dico l'intera storia del mio "albe ed aurore fin boreali...", ma almeno il principio...
non è così, vedo la re-iterazione (sempre meglio che la ri-corsione :slight_smile: ) delle tecniche del post originale

OK, proviamo lo stesso

bene dice ducem barr (sembra uno scioglilingua...) a dire che la loop è troppo ciccia
mi ricorda quando mio padre mi parlava della costruzione di una acciaieria nell'Orinoco: quando avevano finito di costruire la strada era il momento di ricominciare: la giungla se la era ripresa

Ecco: loop alla "Orinoco": quando hai finito di leggerla non te ne ricordi più l'inizio, grazie a ducembarr, questa la faccio mia

quindi dicevo proviamo lo stesso:

  1. basta usare ore minuti e secondi
    come dice anche ducembarr i secondi non servono a una cippa, calcola i "minuti" dalla mezzanotte e fai un solo test, non 4 test uno dopo l'altro

  2. io credo che tu faccia 4 test per vedere se sei in un dato intervallo di orari, ma non ti serve
    se ti limiti ad aggiornare la variabile di switch se l'ora è passata, alla fine dalla catena di if avrai comunque la variabile aggiornata correttamente, prova a "pensare a mano" al ciclo, ovvero fare a ente i conti che fai fare ad arduino

  3. te lo hanno già detto in tre (almeno):
    fai una sola cosa per volta ma falla bene (Unix docet)
    Prima testi gli orari per sapere in che fase della giornata sei
    poi stabilisci i valori di illuminazione
    poi li applichi
    se mischi tra di loro queste cose non ne esci più

questa roba cosa che è:

void time2sec () {
  if (millis() > time_2 + timer2) {
    time_2 = millis();
  }
}
void time3sec () {
  if (millis() > time_3 + timer3) {
    time_3 = millis();
  }
}

void time4sec () {
  if (millis() > time_4 + timer4) {
    time_4 = millis();
  }
}

3 funzioni chiaramente simili, che bastava passare argomenti a una funzione parametrizzata comune

ma che non si capisce cosa fanno?
cosa sono un tentativo di fare dei delay senza usare dei delay, pur rimanendo bloccanti?
e perché lo fai
forse per creare una rampa di luminosità? a salire / scendere
hai ripetuto codice simile per tre led in 4 possibili casi per due possibili segni della variazione, 4 *3 *2 fa 4 fattoriale ovvero 24, non ti sei stancato le dita?

ultimo consiglio:
specifica cosa vuoi fare: cosa deve accadere
perché che tu voglia fare una rampa di accensione (accensione graduale) lo ho solo ipotizzato
se lo vuoi fare lo devi specificare

ultimo consiglio 2 la vendetta:
i nomi: usa nomi che descrivano quello che rappresentano le variabili, ma usa dei nomi che non facciano a botte tra di loro
se devi gestire tre led Bianco Ultravioletto e RossoBlu non usare tre nomi con tre differenti lunghezze
BI UV e RB vanno benissimo e i pezzi di programma si incolonnano da soli, facili da leggere, confrontare, debuggare

Ho parlato

bossfra:
Iooooooooo sono ancoraaaa qua….. eeeeegià

Cortesemente, modifica il tuo primo post togliendo i tag "code" dal tuo messaggio (altrimenti viene formattato come codice...), mentre il vero codice, se non eccessivamente grande, puoi metterlo appunto nei tag "code" invece che come allegato... :wink:

bah, io e Massimo abbiamo provato a fare il programma

di una banalità disarmante

ci si mette di più a scrivere le varie ore e luminosità che a fare il programma vero e proprio
anche perché per venire incontro a inesperti abbiamo usato tanti array elementari invece che un array di strutture

adesso capisco perché @standard ha usato quella brutta cosa "tutta tempestata di X( e #define"

per non "intrecciarsi tutti i diti" sulla tastiera, come direbbe Fracchia

alla fine due sono le cose da ricordarsi:

  1. non eseguire nulla se non cambia il minuto
  2. aggiornare a un passo per volta la luminosità

a proposito di minuti, ma l'autore ha specificato che libreria DS usa? perché noi ne abbiamo trovata una che non espone i metodi usati dall'autore
quindi non possiamo compilare

dai, fatta anche questa, il problema non riveste ulteriore interesse

ah, per @standard
Orinoco flow la canzone di Enya
usa pure Orinoco-loop -> quando "hai finito si leggerla non ricordi più come comincia"
non ci dispiace sapere di venire "copiati"
come la "Settimana Enigmistica": sempre copiati, mai eguagliati

Buongiorno docdoc,
mi diceva che era troppo grande, per questo l'ho messo come allegato.
Avro' sbagliato di sicuro.

bossfra:
mi diceva che era troppo grande, per questo l'ho messo come allegato.
Avro' sbagliato di sicuro.

No, non hai sbagliato, infatti ho anche scritto che il codice lo potevi mettere nel testo "se non eccessivamente grande". :wink:
Però se vedi il tuo primo post, quello che hai scritto è ancora formattato come codice con i tag "code": per renderlo più leggibile, modificalo e togli semplicemente i due tag (quello di apertura e quello di chiusura), tutto qui..