Pages: 1 [2] 3 4   Go Down
Author Topic: Pianola con Arduino  (Read 2614 times)
0 Members and 1 Guest are viewing this topic.
Rome
Offline Offline
God Member
*****
Karma: 1
Posts: 636
La mia prima bromografata!!
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

mi sa che l'errore è l'utilizzo di = per comparare. devi usare ==.
E' vero, non ci avevo fatto caso neanch'io  smiley-wink

Quote
a questo punto, visto che Do e tutte le altre sono dei valori boolean (o Vero o Falso), è uno spreco usare le 'int'. dichiarali come boolean (
Oppure un byte, tanto anche il boolean occupa comunque 1 byte in memoria.
ma dai! questa non la sapevo, pensavo stupidamente che potesse occupare solo un bit.. quindi è così perchè non si può indirizzare un solo bit, o perchè insieme al bit del valore viene registrato dell'altro?
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21657
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Oppure un byte, tanto anche il boolean occupa comunque 1 byte in memoria.
ma dai! questa non la sapevo, pensavo stupidamente che potesse occupare solo un bit.. quindi è così perchè non si può indirizzare un solo bit, o perchè insieme al bit del valore viene registrato dell'altro?
Il resto del byte è inutilizzato. Per questo spesso si consiglia di utilizzare gli operatori sui bit se si devono memorizzare più flag che devono avere solo il valore 1 o 0.
Logged


Rome
Offline Offline
God Member
*****
Karma: 1
Posts: 636
La mia prima bromografata!!
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Oppure un byte, tanto anche il boolean occupa comunque 1 byte in memoria.
ma dai! questa non la sapevo, pensavo stupidamente che potesse occupare solo un bit.. quindi è così perchè non si può indirizzare un solo bit, o perchè insieme al bit del valore viene registrato dell'altro?
Il resto del byte è inutilizzato. Per questo spesso si consiglia di utilizzare gli operatori sui bit se si devono memorizzare più flag che devono avere solo il valore 1 o 0.
Giusto, così non si spreca spazio..
Francesco, potrebbe essere l'occasione per imparare una cosa nuova! registri le 7 note come sette bit di un byte, e controlli i singoli valori dei byte. non cambia niente come risultato, ma utilizzi un metodo molto più elegante. io ci proverei.
Logged

Firenze, Italy
Offline Offline
Full Member
***
Karma: 0
Posts: 104
Dislessia portami via
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Interessante lo sviluppo che ha preso la discussione.
Bravo dab77 per aver beccato l'errore sul while!
Logged

The brightest flame burns quickest

Padova, Italy
Offline Offline
Newbie
*
Karma: 0
Posts: 14
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Allora... Ho sostituito gli = con == e adesso suona  smiley-draw Però la nota non torna mai bassa. Se premo il Do questo suona finchè non premo un'altra nota che a sua volta farà lo stesso. Ho prova a mettere dopo ogni nota:
Code:
else
{
   noTone(Buzzer);
}
...ma peggio che prima. Ho ottenuto delle frequenze altissime senza spiegarmi il perchè.

Per quanto riguarda quello che ha detto dab77, come faccio a registrare le note come bit?
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21657
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Francesco, potrebbe essere l'occasione per imparare una cosa nuova! registri le 7 note come sette bit di un byte, e controlli i singoli valori dei byte. non cambia niente come risultato, ma utilizzi un metodo molto più elegante. io ci proverei.
Un passo alla volta. Per ora non gli serve questo, gli serve come imparare a gestire i pulsanti  smiley-grin
Anche perché ha già dei byte che contengono i livelli logici dei pin accessibili a singoli bit, sono i registri del microcontrollore. Le porte sono infatti mappate in alcuni registri e leggere un registro equivale a leggere un gruppo di 8 porte tutte insieme.
http://www.arduino.cc/en/Reference/PortManipulation
Ma qui si entra in un livello più elevato di programmazione, mentre ora deve imparare a programmare correttamente.
Logged


Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21657
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Allora... Ho sostituito gli = con == e adesso suona  smiley-draw Però la nota non torna mai bassa. Se premo il Do questo suona finchè non premo un'altra nota che a sua volta farà lo stesso. Ho prova a mettere dopo ogni nota:
Code:
else
{
   noTone(Buzzer);
}
...ma peggio che prima. Ho ottenuto delle frequenze altissime senza spiegarmi il perchè.
Forse perché si sommano più frequenze insieme. Oppure perché fai un'alternanza superveloce fra nota/no nota....
Un altro problema che nessuno ha sollevato è il debounce dei pulsanti. Ogni pulsante dà dei "rimbalzi" elettrici, che possono essere letti come false pressioni. Anche questo tema è da sviluppare.

Poi secondo me dovresti provare un altro approccio. Semplifica il programma e fai suonare una singola nota per un determinato lasso di tempo, metti cioè un flag per verificare che non sia già in esecuzione la riproduzione di una nota.
Poi il secondo passo potrebbe essere quello di far suonare una nota finché il tasto è premuto.
Logged


Rome
Offline Offline
God Member
*****
Karma: 1
Posts: 636
La mia prima bromografata!!
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Allora... Ho sostituito gli = con == e adesso suona  smiley-draw Però la nota non torna mai bassa. Se premo il Do questo suona finchè non premo un'altra nota che a sua volta farà lo stesso. Ho prova a mettere dopo ogni nota:
Code:
else
{
   noTone(Buzzer);
}
...ma peggio che prima. Ho ottenuto delle frequenze altissime senza spiegarmi il perchè.
Forse perché si sommano più frequenze insieme. Oppure perché fai un'alternanza superveloce fra nota/no nota....
Un altro problema che nessuno ha sollevato è il debounce dei pulsanti. Ogni pulsante dà dei "rimbalzi" elettrici, che possono essere letti come false pressioni. Anche questo tema è da sviluppare.

Poi secondo me dovresti provare un altro approccio. Semplifica il programma e fai suonare una singola nota per un determinato lasso di tempo, metti cioè un flag per verificare che non sia già in esecuzione la riproduzione di una nota.
Poi il secondo passo potrebbe essere quello di far suonare una nota finché il tasto è premuto.
Si, si hai perfettamente ragione, lo suggerivo solo per dopo, cioè quando hai fatto funzionare tutto e vuoi migliorare.
Secondo me però aveva colto il punto col 'while', e non capisco perchè non si può usare. in fondo finchè è 'Vero' deve suonare, poi manca la condizione di uscita, ovvero quando il pin è falso. Non è così?
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21657
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Esistono 2 modi per intendere il "finché è vero deve suonare":
1) finché non stacca il pulsante, deve suonare
2) finché non viene premuto un altro tasto, deve suonare

Nel 1° caso può usare il while (e va messo appunto il controllo del cambio di stato del pin per l'uscita), nel secondo caso, non può usare il while ma deve usare un ciclo per cambiare nota solo quando viene premuto un altro pulsante.
Logged


Firenze, Italy
Offline Offline
Full Member
***
Karma: 0
Posts: 104
Dislessia portami via
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Allora... Ho sostituito gli = con == e adesso suona  smiley-draw Però la nota non torna mai bassa. Se premo il Do questo suona finchè non premo un'altra nota che a sua volta farà lo stesso. Ho prova a mettere dopo ogni nota:
Code:
else
{
   noTone(Buzzer);
}
...ma peggio che prima. Ho ottenuto delle frequenze altissime senza spiegarmi il perchè.

hai provato a mettere una roba del genere?
Code:
if(digitalRead(Do) == HIGH){
 tone(Buzer, 262, duration); // suona il DO per duration ms (duration lo dichiari come const int )
 delay(duration); //attende che il do abbia finito di suonare
 noTone(Buzer); //smette di far suonare il Buzer
}
[\code]
Logged

The brightest flame burns quickest

Padova, Italy
Offline Offline
Newbie
*
Karma: 0
Posts: 14
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

x IngHooch
Se ho capito bene però "duration" ha valore fisso e la nota rimane attiva per un lasso di tempo predefinito, nel caso volessi prolungare la nota tenendo premuto il pulsante non posso farlo...

x leo72
Da quello che dici capisco che è più corretto usare i while... Usando gli if ottengo appunto quello che ho ottenuto; ogni nota suona finchè non ne premo un'altra.
Logged

Firenze, Italy
Offline Offline
Full Member
***
Karma: 0
Posts: 104
Dislessia portami via
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

x IngHooch
Se ho capito bene però "duration" ha valore fisso e la nota rimane attiva per un lasso di tempo predefinito, nel caso volessi prolungare la nota tenendo premuto il pulsante non posso farlo...

Nì, perché se il codice è fatto così

Code:
void loop(){

if(digitalRead(Do) == HIGH){
 tone(Buzer, 262, duration); // suona il DO per duration ms (duration lo dichiari come const int )
 delay(duration); //attende che il do abbia finito di suonare
 noTone(Buzer); //smette di far suonare il Buzer
}

}

Se tu tiene premuto il bottone ogni volete che passa dall'if trova i bottone premuto e continua a suonare la stessa nota, nel momento in cui lo lasci questo continua a suonare per duration e poi smette
Logged

The brightest flame burns quickest

Padova, Italy
Offline Offline
Newbie
*
Karma: 0
Posts: 14
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

mmm... qualcosa non mi torna... tutto quello che dici però accade se il tasto è premuto. Supponiamo che imposto il delay a 10ms... Appena premo il tasto suona il do per 20ms (10ms per la funzione tone + 10ms per il delay successivo) e poi si spegne... Indipendentemente che io rilascio o meno il pulsante... Corretto?
Logged

Padova, Italy
Offline Offline
Newbie
*
Karma: 0
Posts: 14
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Funziona facendo così!!!

Code:
if(ValueDo==HIGH)
{   tone(Buzzer,262);
delay(10);
noTone(Buzzer);
}

IngHooch come dici tu però senza impostare il tempo alla funzione tone.

Però ora si tratta solo di trovare il delay giusto perchè a 10 è troppo basso e distorce... Però a 100 si sente il buzzer staccare e attaccare velocemente.
Logged

Firenze, Italy
Offline Offline
Full Member
***
Karma: 0
Posts: 104
Dislessia portami via
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

No l'istruzione
Code:
if(digitalRead(Do) == HIGH){
tone(Buzer, 262, duration);
delay(duration);
noTone(Buzer);
}

if(digitalRead(La) == HIGH){
//codice LA
}
da il via al Buzer per duration, ma non aspetta che finisce! Passa subito all'istruzione successiva, che nel nostro caso è un delay di duration.
Quindi le due righe di codice forzano il programma ad aspettare che il do abbia finito di suonare prima di procedere ad altri controlli (nel nostro caso controllare se il La è premuto ed eventualmente farlo suonare)
Logged

The brightest flame burns quickest

Pages: 1 [2] 3 4   Go Up
Jump to: