Go Down

Topic: Porque no funciona este codigo (Read 2409 times) previous topic - next topic

riscking

Jun 16, 2011, 07:02 pm Last Edit: Jun 18, 2011, 12:18 am by riscking Reason: 1
Volviendo a lo mismo he reducido mi codigo a un ejemplo simplificado, mas o menos , el caso esque lee de 0 a 9 y de a a e y dependiendo q insertes por la consola suena un sonido u otro, el caso esque una a una no hay problema pero ya cuando pongo todas las canciones en un switch o con ifs ya empiezan los problemas, si quito las canciones largas como la de knighrider o macgyver(era la 8) la cosa mejora pero hasta la cancion 10 si añades de la 10 a la 16 ya simplemente no va, y esque no lo entiendo. Si alguien prueba el codigo borrando todas menos las 7 primeras va perfecto.
Yo no se si son los char q no aguantan tantos caracteres o que, he probado con punteros y sin ellos pero la cosa no va a mejor, me estoy volviendo loco y yo quiero q funcionen todas, estoy por regalar 5€ jaja al q me lo solucione, y si esta cerca le invito a un par e cañas.

Code: [Select]

#define OCTAVE_OFFSET 0
#define TONE_PIN 6

#define NOTE_C4  262
#define NOTE_CS4 277
#define NOTE_D4  294
#define NOTE_DS4 311
#define NOTE_E4  330
#define NOTE_F4  349
#define NOTE_FS4 370
#define NOTE_G4  392
#define NOTE_GS4 415
#define NOTE_A4  440
#define NOTE_AS4 466
#define NOTE_B4  494
#define NOTE_C5  523
#define NOTE_CS5 554
#define NOTE_D5  587
#define NOTE_DS5 622
#define NOTE_E5  659
#define NOTE_F5  698
#define NOTE_FS5 740
#define NOTE_G5  784
#define NOTE_GS5 831
#define NOTE_A5  880
#define NOTE_AS5 932
#define NOTE_B5  988
#define NOTE_C6  1047
#define NOTE_CS6 1109
#define NOTE_D6  1175
#define NOTE_DS6 1245
#define NOTE_E6  1319
#define NOTE_F6  1397
#define NOTE_FS6 1480
#define NOTE_G6  1568
#define NOTE_GS6 1661
#define NOTE_A6  1760
#define NOTE_AS6 1865
#define NOTE_B6  1976
#define NOTE_C7  2093
#define NOTE_CS7 2217
#define NOTE_D7  2349
#define NOTE_DS7 2489
#define NOTE_E7  2637
#define NOTE_F7  2794
#define NOTE_FS7 2960
#define NOTE_G7  3136
#define NOTE_GS7 3322
#define NOTE_A7  3520
#define NOTE_AS7 3729
#define NOTE_B7  3951

int notes[] = { 0,
NOTE_C4, NOTE_CS4, NOTE_D4, NOTE_DS4, NOTE_E4, NOTE_F4, NOTE_FS4, NOTE_G4, NOTE_GS4, NOTE_A4, NOTE_AS4, NOTE_B4,
NOTE_C5, NOTE_CS5, NOTE_D5, NOTE_DS5, NOTE_E5, NOTE_F5, NOTE_FS5, NOTE_G5, NOTE_GS5, NOTE_A5, NOTE_AS5, NOTE_B5,
NOTE_C6, NOTE_CS6, NOTE_D6, NOTE_DS6, NOTE_E6, NOTE_F6, NOTE_FS6, NOTE_G6, NOTE_GS6, NOTE_A6, NOTE_AS6, NOTE_B6,
NOTE_C7, NOTE_CS7, NOTE_D7, NOTE_DS7, NOTE_E7, NOTE_F7, NOTE_FS7, NOTE_G7, NOTE_GS7, NOTE_A7, NOTE_AS7, NOTE_B7
};


void setup() {

 Serial.begin(9600);

 
}

void loop()
{

if (Serial.available() > 0) {
// read the incoming byte:
char u = Serial.read();
Serial.println(u);
if(u=='1'){
     char *song="Entertainer:d=4,o=5,b=140:8d,8d#,8e,c6,8e,c6,8e,2c.6,8c6,8d6,8d#6,8e6,8c6,8d6,e6,8b,d6,2c6,p,8d,8d#,8e,c6,8e,c6,8e,2c.6,8p,8a,8g,8f#,8a,8c6,e6,8d6,8c6,8a,2d6";
     play_rtttl(song);
     }
   if(u=='2'){
     char *jk="Looney:d=4,o=5,b=140:32p,c6,8f6,8e6,8d6,8c6,a.,8c6,8f6,8e6,8d6,8d#6,e.6,8e6,8e6,8c6,8d6,8c6,8e6,8c6,8d6,8a,8c6,8g,8a#,8a,8f";
     play_rtttl(jk);
     }
   if(u=='3'){
     char *song3="20thCenFox:d=16,o=5,b=140:b,8p,b,b,2b,p,c6,32p,b,32p,c6,32p,b,32p,c6,32p,b,8p,b,b,b,32p,b,32p,b,32p,b,32p,b,32p,b,32p,b,32p,g#,32p,a,32p,b,8p,b,b,2b,4p,8e,8g#,8b,1c#6,8f#,8a,8c#6,1e6,8a,8c#6,8e6,1e6,8b,8g#,8a,2b";
     play_rtttl(song3);
     }
   if(u=='4'){
     char *song4="Blue:d=8,o=5,b=140:a,a#,d,g,a#,c6,f,a,4a#,g,a#,d6,d#6,g,d6,c6,a#,d,g,a#,c6,f,a,4a#,g,a#,d6,d#6,g,d6,c6,a#,d,g,a#,c6,f,a,4a#,g,a#,d6,d#6,g,d6,c6,a#,d,g,a#,a,c,f,2g";
     play_rtttl(song4);
     }
   if(u=='5'){
     char *song5="Canon:d=16,o=6,b=125:8a#.,g.,g#.,8a#.,g.,g#.,a#.,a#.5,c.,d.,d#.,f.,g.,g#.,8g.,d#.,f.,8g.,g.5,g#.5,a#.5,c.,a#.5,g#.5,a#.5,g.5,g#.5,a#.5,8g#.5,c.,a#.5,8g#.5,g.5,f.5,g.5,f.5,d#.5,f.5,g.5,g#.5,a#.5,c.,8g#.5,c.,a#.5,8c.,d.,d#.,a#.5,c.,d.,d#.,f.,g.,g#.,8a#";
     play_rtttl(song5);
     }
   if(u=='6'){
     char *song6="TakeOnMe:d=4,o=4,b=160:8f#5,8f#5,8f#5,8d5,8p,8b,8p,8e5,8p,8e5,8p,8e5,8g#5,8g#5,8a5,8b5,8a5,8a5,8a5,8e5,8p,8d5,8p,8f#5,8p,8f#5,8p,8f#5,8e5,8e5,8f#5,8e5,8f#5,8f#5,8f#5,8d5,8p,8b,8p,8e5,8p,8e5,8p,8e5,8g#5,8g#5,8a5,8b5,8a5,8a5,8a5,8e5,8p,8d5,8p,8f#5,8p,8f#5,8p,8f#5,8e5,8e5";
     play_rtttl(song6);
     }
   if(u=='7'){
     char *song7="The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6";
     play_rtttl(song7);
     }
   if(u=='8'){
     }
   if(u=='9'){
     char *song9 = "KnightRider:d=4,o=5,b=125:16e,16p,16f,16e,16e,16p,16e,16e,16f,16e,16e,16e,16d#,16e,16e,16e,16e,16p,16f,16e,16e,16p,16f,16e,16f,16e,16e,16e,16d#,16e,16e,16e,16d,16p,16e,16d,16d,16p,16e,16d,16e,16d,16d,16d,16c,16d,16d,16d,16d,16p,16e,16d,16d,16p,16e,16d,16e,16d,16d,16d,16c,16d,16d,16d";
   play_rtttl(song9);
     }
   if(u=='a'){
     char *son10="Fido:d=16,o=6,b=800:f,4p,f,4p,f,4p,f,4p,c,4p,c,4p,c,4p,c,1p,1p,1p,1p";
     play_rtttl(son10);
     }
   if(u=='b'){
     char *son11="Gadget:d=16,o=5,b=50:32d#,32f,32f#,32g#,a#,f#,a,f,g#,f#,32d#,32f,32f#,32g#,a#,d#6,4d6,32d#,32f,32f#,32g#,a#,f#,a,f,g#,f#,8d#";
     play_rtttl(son11);
     }
   if(u=='c'){
     char *son12="Smurfs:d=32,o=5,b=200:4c#6,16p,4f#6,p,16c#6,p,8d#6,p,8b,p,4g#,16p,4c#6,p,16a#,p,8f#,p,8a#,p,4g#,4p,g#,p,a#,p,b,p,c6,p,4c#6,16p,4f#6,p,16c#6,p,8d#6,p,8b,p,4g#,16p,4c#6,p,16a#,p,8b,p,8f,p,4f#";
     play_rtttl(son12);
     }
   if(u=='d'){
     char *son13="LeisureSuit:d=16,o=6,b=56:f.5,f#.5,g.5,g#5,32a#5,f5,g#.5,a#.5,32f5,g#5,32a#5,g#5,8c#.,a#5,32c#,a5,a#.5,c#.,32a5,a#5,32c#,d#,8e,c#.,f.,f.,f.,f.,f,32e,d#,8d,a#.5,e,32f,e,32f,c#,d#.,c#";
     play_rtttl(son13);
     }
}
}
#define isdigit(n) (n >= '0' && n <= '9')

void play_rtttl(char *p)
{
 // Absolutely no error checking in here

 byte default_dur = 4;
 byte default_oct = 6;
 int bpm = 63;
 int num;
 long wholenote;
 long duration;
 byte note;
 byte scale;

 // format: d=N,o=N,b=NNN:
 // find the start (skip name, etc)

 while(*p != ':') p++;    // ignore name
 p++;                     // skip ':'

 // get default duration
 if(*p == 'd')
 {
   p++; p++;              // skip "d="
   num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   if(num > 0) default_dur = num;
   p++;                   // skip comma
 }

 Serial.print("ddur: "); Serial.println(default_dur, 10);

 // get default octave
 if(*p == 'o')
 {
   p++; p++;              // skip "o="
   num = *p++ - '0';
   if(num >= 3 && num <=7) default_oct = num;
   p++;                   // skip comma
 }

 Serial.print("doct: "); Serial.println(default_oct, 10);

 // get BPM
 if(*p == 'b')
 {
   p++; p++;              // skip "b="
   num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   bpm = num;
   p++;                   // skip colon
 }

 Serial.print("bpm: "); Serial.println(bpm, 10);

 // BPM usually expresses the number of quarter notes per minute
 wholenote = (60 * 1000L / bpm) * 4;  // this is the time for whole note (in milliseconds)

 Serial.print("wn: "); Serial.println(wholenote, 10);


 // now begin note loop
 while(*p)
 {
   // first, get note duration, if available
   num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   
   if(num) duration = wholenote / num;
   else duration = wholenote / default_dur;  // we will need to check if we are a dotted note after

   // now get the note
   note = 0;

   switch(*p)
   {
     case 'c':
       note = 1;
       break;
     case 'd':
       note = 3;
       break;
     case 'e':
       note = 5;
       break;
     case 'f':
       note = 6;
       break;
     case 'g':
       note = 8;
       break;
     case 'a':
       note = 10;
       break;
     case 'b':
       note = 12;
       break;
     case 'p':
     default:
       note = 0;
   }
   p++;

   // now, get optional '#' sharp
   if(*p == '#')
   {
     note++;
     p++;
   }

   // now, get optional '.' dotted note
   if(*p == '.')
   {
     duration += duration/2;
     p++;
   }
 
   // now, get scale
   if(isdigit(*p))
   {
     scale = *p - '0';
     p++;
   }
   else
   {
     scale = default_oct;
   }

   scale += OCTAVE_OFFSET;

   if(*p == ',')
     p++;       // skip comma for next note (or we may be at the end)

   // now play the note

    if(note)
   {
     Serial.print("Playing: ");
     Serial.print(scale, 10); Serial.print(' ');
     Serial.print(note, 10); Serial.print(" (");
     Serial.print(notes[(scale - 4) * 12 + note], 10);
     Serial.print(") ");
     Serial.println(duration, 10);
     tone(TONE_PIN, notes[(scale - 4) * 12 + note]);
     delay(duration);
     noTone(TONE_PIN);
   }
   else
   {
     Serial.print("Pausing: ");
     Serial.println(duration, 10);
     delay(duration);
   }
   
 }
}

curro92

Hola,
en la primera declaración de song creas un puntero a una cadena de 693+1 caracteres (bytes). Para copiar otro valor en esa cadena puedes usar
Code: [Select]

strcpy(song, "The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6");
teniendo cuidado de que lo que copias no sea mayor que la primera cadena.
Si sabes cuál es la longitud de la cadena más larga, puedes definir una variable global como
Code: [Select]
char song[700]; // suponiendo que esta sea la longitud máxima y luego copias lo que te interese en ella con strcpy()


flico

Quote
MacGyver:d=4,o=6,b=150:8b4,8e5,8a5,8b5,a5,8e5,8b4,8p,8e5,8a5,8b5,8a5,8e5,b4,8p,8e5,8a5,8b5,a5,8e5,8b4,8p,8a5,8d,8c,8d,8c,8b5,8a5,8b4,8e5,8a5,8b5,a5,8e5,8b4,8p,8e5,8a5,8b5,8a5,8e5,b4,8p,8e5,8a5,8b5,a5,8e5,8b4,8p,8a5,8d,8c,8d,8c,8b5,8a5,b5,8p,2b5,8p,b5,8p,a5,d.,b5,8p,2b5,8p,8b5,8p,2a5,p,8c,8c,8c,8c,8c,8c,2b5,16p,8f#5,8a5,8p,2g5,8p,8c,8c,8p,b5,8a5,8b5,8a5,8g5,8p,e,2a5,16p,8c,8c,8p,2b5,8p,8f#5,8a5,8p,2g5,8p,8c,8c,8p,4b5,8a5,8b5,8a5,8g5,8p,4e,2a5,2b5,32p,8c,8b5,8a5,c,8b5,8a5,8d,8c,8b5,d,8c,8b5,e,8d,8e,f#,b5,g,8p,f#,f,b5,8g,8e,8b5,8f#,8d,8a5,8e,8c,8g5,8d,8b5,8g5,8c,8e5,8b5,8d5,8c,8b5,8a5,8g5,a#5,a5,8g,8g5,8d,8g5,8d#,8d#5,8a#5,8a5,8g5,8g4,8d5,8g4,8d#5,8g4,8a#4,8a4,8g4,8g4,8g4,8g4,8g4,8g4,8g4";


Perdona por ser tan torpon, como haces para hacer la melodía con arduino.

Saludos.
Trabajando en ...

    * Control Domotico (En montaje ...)
    http://casitadomotica.blogspot.com/
 

[url=https://bitbucket.org/fmalpartida

riscking

#3
Jun 16, 2011, 11:03 pm Last Edit: Jun 16, 2011, 11:06 pm by riscking Reason: 1
Cuando pueda pruebo a ver si me sale como dices, flico ahora esque tengo el codigo todo mezclado, a ver si te encentro la pagina de donde saque que estaba muy bien, la verdad q me costo encontrar un codigo al q se le pueden añadir mas de una cancion, yo la verdad las canciones no las hago, la musica no es mi campo y con todas las notas q hay como para componer.
Nos vemos.

xDD le doy a enviar y lo encuentro, el codigo de este foro, va de maravilla.
http://arduino.cc/forum/index.php?topic=53358.0

riscking

No consigo hacer lo basico con un switch o con if para selecionar la cancion que quiero y no entiendo el problema si son la capacidad de los char o que , el caso esque una a una funcion y en conjunto no, en la consolas empiezan a aparecer cosas q no deberian como si se desbordase y no se por donde, y porque solas funcionan.

curro92

Hola,
creo que el parseo de la cadena que contiene la melodía está bien.
Yo en tu lugar probaría primero con una sola melodía, cortita, sin seleccionar nada con  if() o switch()

riscking

con una solo melodia va perfecto el problema es al darle la capacidad de selecionar q se desborda o algo y no entiendo la razon, gracias.

curro92

#7
Jun 18, 2011, 07:22 pm Last Edit: Jun 18, 2011, 07:24 pm by curro92 Reason: 1
Hola,
cada vez que se ejecuta loop() estás creando una cadena (memoria ocupada) que luego no se libera. Crea una variable global a
Code: [Select]

char song[333]; // o la longitud que haga falta para la cadena más larga


Y luego utiliza esa variable para copiar las melodías
Code: [Select]

if(u=='1'){
strcpy(song, "Entertainer:d=4,o=5,b=140:8d,8d#,8e,c6,8e,c6,8e,2c.6,8c6,8d6,8d#6,8e6,8c6,8d6,e6,8b,d6,2c6,p,8d,8d#,8e,c6,8e,c6,8e,2c.6,8p,8a,8g,8f#,8a,8c6,e6,8d6,8c6,8a,2d6";
     play_rtttl(song);
     }
   if(u=='2'){
    strcpy(song, "Looney:d=4,o=5,b=140:32p,c6,8f6,8e6,8d6,8c6,a.,8c6,8f6,8e6,8d6,8d#6,e.6,8e6,8e6,8c6,8d6,8c6,8e6,8c6,8d6,8a,8c6,8g,8a#,8a,8f";
     play_rtttl(jk);
     }
etc.


También podrías definir un puntero global char *psong, y usar malloc() cada vez que vayas a copiar una cadena; y liberar luego con free()

De todas formas, no sé para qué usas esa variable, podrías hacer directamente

play_rtttl("Entertainer:d=4,o=5,b=140:8d,8d#,8e,c6,8e,c6,8e,2c.6,8c6,8d6,8d#6,8e6,8c6,8d6,e6,8b,d6,2c6,p,8d,8d#,8e,c6,8e,c6,8e,2c.6,8p,8a,8g,8f#,8a,8c6,e6,8d6,8c6,8a,2d6");


riscking

#8
Jun 19, 2011, 12:22 am Last Edit: Jun 19, 2011, 12:54 am by riscking Reason: 1
Hola curro92, con la primera opcion q me has dado me pasa lo mismo  y poniendo play_rtttl( la cancion ); tambien tengo el mismo problema, no entiendo nada xDD.
Queda probar lo del malloc y free pero no encuentro mucha informacion al respecto.

poniendo esto antes del loop que es lo q ponen en todos sitios me da un error q no entiendo "expected constructor, destructor, or type conversion before '=' token
"

char *song;
song = (char *)malloc(3*sizeof(char)); // se sopne que reservas el espacio de 3 char para song q yo creo q no deberia haber problemas.


riscking

Lo he intentado asi:

int stringLength = strlen("The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6");
      p = (char*)malloc(stringLength * sizeof(char));
       strcpy( song,"The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6");
play_rtttl(song);
      free(p);

Pero sigo teniendo problemas, estoy empezando a darlo por imposible.

curro92

Hola,
no sé si esto tendrá importancia en tu caso, pero cuando se hace malloc() para una cadena char, hay que poner un carácter de más, para el '\0' final de cadena:

int stringLength = strlen("The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6");
      p = (char*)malloc(stringLength * sizeof(char) + 1);


riscking

Curro92 si paso la cancion asi: play_rtttl("Entertainer:d=4,o=5,b=140:8d,8d#,8e,c6,8e,c6,8e,2c.6,8c6,8d6,8d#6,8e6,8c6,8d6,e6,8b,d6,2c6,p,8d,8d#,8e,c6,8e,c6,8e,2c.6,8p,8a,8g,8f#,8a,8c6,e6,8d6,8c6,8a,2d6");

no me debería saturar la memoria no? el caso es que si lo hace, el problema no sera el char *p de la funcion o algo??
Un saludo.

greenlanternx

yo ya hice algo parecido, lo que hice fue crear un array con 35 o 37 tonos diferentes, y por medio del teclado le ingreso el numero de la cancion que quiero reproducir y un enter, si hay alguna sonando en ese momento, la detiene y corre la seleccionada, si alguna llega al final la reproduccion se detiene, hasta que ingresa algun numero valido:
Code: [Select]

#include <Tone.h>
#include <stdlib.h>
Tone tone1;
#define OCTAVE_OFFSET 0
int notes[] = { 0,
NOTE_C4, NOTE_CS4, NOTE_D4, NOTE_DS4, NOTE_E4, NOTE_F4, NOTE_FS4, NOTE_G4, NOTE_GS4, NOTE_A4, NOTE_AS4, NOTE_B4,
NOTE_C5, NOTE_CS5, NOTE_D5, NOTE_DS5, NOTE_E5, NOTE_F5, NOTE_FS5, NOTE_G5, NOTE_GS5, NOTE_A5, NOTE_AS5, NOTE_B5,
NOTE_C6, NOTE_CS6, NOTE_D6, NOTE_DS6, NOTE_E6, NOTE_F6, NOTE_FS6, NOTE_G6, NOTE_GS6, NOTE_A6, NOTE_AS6, NOTE_B6,
NOTE_C7, NOTE_CS7, NOTE_D7, NOTE_DS7, NOTE_E7, NOTE_F7, NOTE_FS7, NOTE_G7, NOTE_GS7, NOTE_A7, NOTE_AS7, NOTE_B7
};

char *song[] = {"The Simpsons:d=4,o=5,b=160:c.6,e6,f#6,8a6,g.6,e6,c6,8a,8f#,8f#,8f#,2g,8p,8p,8f#,8f#,8f#,8g,a#.,8c6,8c6,8c6,c6",
"Indiana:d=4,o=5,b=250:e,8p,8f,8g,8p,1c6,8p.,d,8p,8e,1f,p.,g,8p,8a,8b,8p,1f6,p,a,8p,8b,2c6,2d6,2e6,e,8p,8f,8g,8p,1c6,p,d6,8p,8e6,1f.6,g,8p,8g,e.6,8p,d6,8p,8g,e.6,8p,d6,8p,8g,f.6,8p,e6,8p,8d6,2c6",
"Looney:d=4,o=5,b=140:32p,c6,8f6,8e6,8d6,8c6,a.,8c6,8f6,8e6,8d6,8d#6,e.6,8e6,8e6,8c6,8d6,8c6,8e6,8c6,8d6,8a,8c6,8g,8a#,8a,8f",
"20thCenFox:d=16,o=5,b=140:b,8p,b,b,2b,p,c6,32p,b,32p,c6,32p,b,32p,c6,32p,b,8p,b,b,b,32p,b,32p,b,32p,b,32p,b,32p,b,32p,b,32p,g#,32p,a,32p,b,8p,b,b,2b,4p,8e,8g#,8b,1c#6,8f#,8a,8c#6,1e6,8a,8c#6,8e6,1e6,8b,8g#,8a,2b",
"Bond:d=4,o=5,b=80:32p,16c#6,32d#6,32d#6,16d#6,8d#6,16c#6,16c#6,16c#6,16c#6,32e6,32e6,16e6,8e6,16d#6,16d#6,16d#6,16c#6,32d#6,32d#6,16d#6,8d#6,16c#6,16c#6,16c#6,16c#6,32e6,32e6,16e6,8e6,16d#6,16d6,16c#6,16c#7,c.7,16g#6,16f#6,g#.6",
"StarWars:d=4,o=5,b=45:32p,32f#,32f#,32f#,8b.,8f#.6,32e6,32d#6,32c#6,8b.6,16f#.6,32e6,32d#6,32c#6,8b.6,16f#.6,32e6,32d#6,32e6,8c#.6,32f#,32f#,32f#,8b.,8f#.6,32e6,32d#6,32c#6,8b.6,16f#.6,32e6,32d#6,32c#6,8b.6,16f#.6,32e6,32d#6,32e6,8c#6",
"A-Team:d=8,o=5,b=125:4d#6,a#,2d#6,16p,g#,4a#,4d#.,p,16g,16a#,d#6,a#,f6,2d#6,16p,c#.6,16c6,16a#,g#.,2a#",
"Flinstones:d=4,o=5,b=40:32p,16f6,16a#,16a#6,32g6,16f6,16a#.,16f6,32d#6,32d6,32d6,32d#6,32f6,16a#,16c6,d6,16f6,16a#.,16a#6,32g6,16f6,16a#.,32f6,32f6,32d#6,32d6,32d6,32d#6,32f6,16a#,16c6,a#,16a6,16d.6,16a#6,32a6,32a6,32g6,32f#6,32a6,8g6,16g6,16c.6,32a6,32a6,32g6,32g6,32f6,32e6,32g6,8f6,16f6,16a#.,16a#6,32g6,16f6,16a#.,16f6,32d#6,32d6,32d6,32d#6,32f6,16a#,16c.6,32d6,32d#6,32f6,16a#,16c.6,32d6,32d#6,32f6,16a#6,16c7,8a#.6",
"Gadget:d=16,o=5,b=50:32d#,32f,32f#,32g#,a#,f#,a,f,g#,f#,32d#,32f,32f#,32g#,a#,d#6,4d6,32d#,32f,32f#,32g#,a#,f#,a,f,g#,f#,8d#",
"MissionImp:d=16,o=6,b=95:32d,32d#,32d,32d#,32d,32d#,32d,32d#,32d,32d,32d#,32e,32f,32f#,32g,g,8p,g,8p,a#,p,c7,p,g,8p,g,8p,f,p,f#,p,g,8p,g,8p,a#,p,c7,p,g,8p,g,8p,f,p,f#,p,a#,g,2d,32p,a#,g,2c#,32p,a#,g,2c,a#5,8c,2p,32p,a#5,g5,2f#,32p,a#5,g5,2f,32p,a#5,g5,2e,d#,8d",
"BadTouch:d=8,o=5,b=125:4f,f,d#,4f,f,f,f,16f,16f,f,f,f,f,f,f,4d#,d#,d,4d#,d#,d#,c#,16c#,16c#,c#,c#,c#,c#,c#,16c#",
"Mario:d=16,o=6,b=100:32p,e,e,p,e,p,c,e,p,g,8p.,g5,8p.,c,8p,g5,8p,e5,8p,a5,p,b5,p,a#5,a5,p,g5,e,g,a,p,f,g,p,e,p,c,d,b5,4p,g,f#,f,d#,p,e,p,g#5,a5,c,p,a5,c,d,8p,8d#,p,d,8p,8c",
"MrRoboto:d=32,o=6,b=50:p,b.5,8a5,d.,8c#,a.5,8g5,p,d.,d.,d.,16e,p,d.,d.,d.,d.,e.",
"HareHare:d=8,o=5,b=164:g,a,g,a,4a,a,4a,a,4g,f,g,2a,a,4a,a,4a,a,4a#,a,a#,4c.6,c,c6,4a#,a,4f.,c6,c6,4a#,a,4f.,c6,c6,4a#,g#,4g,4f,2g"};
char *p;
bool reproducir=false,nuevo=false;
byte default_dur = 4;
byte default_oct = 6;
int bpm = 63;
int num;
long wholenote;
long duration;
byte note;
byte scale;

#include <PS2Keyboard.h>

const int DataPin = 8;
const int IRQpin =  2;
String comando;
PS2Keyboard keyboard;


void setup(void)
{
 Serial.begin(9600);
 tone1.begin(9);
 
 pinMode(13, OUTPUT);
 keyboard.begin(DataPin, IRQpin);
}

#define isdigit(n) (n >= '0' && n <= '9')
void inicializar_tono()
{
 while(*p != ':') p++;    // ignore name
 p++;                     // skip ':'

 // get default duration
 if(*p == 'd')
 {
   p++; p++;              // skip "d="
   num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   if(num > 0) default_dur = num;
   p++;                   // skip comma
 }
 Serial.print("ddur: "); Serial.println(default_dur, 10);

 // get default octave
 if(*p == 'o')
 {
   p++; p++;              // skip "o="
   num = *p++ - '0';
   if(num >= 3 && num <=7) default_oct = num;
   p++;                   // skip comma
 }

 Serial.print("doct: "); Serial.println(default_oct, 10);

 // get BPM
 if(*p == 'b')
 {
   p++; p++;              // skip "b="
   num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   bpm = num;
   p++;                   // skip colon
 }

 Serial.print("bpm: "); Serial.println(bpm, 10);
 // BPM usually expresses the number of quarter notes per minute
 wholenote = (60 * 1000L / bpm) * 4;  // this is the time for whole note (in milliseconds)

 Serial.print("wn: "); Serial.println(wholenote, 10);
}

void sonar(){
num = 0;
   while(isdigit(*p))
   {
     num = (num * 10) + (*p++ - '0');
   }
   
   if(num) duration = wholenote / num;
   else duration = wholenote / default_dur;  // we will need to check if we are a dotted note after

   // now get the note
   note = 0;

   switch(*p)
   {
     case 'c':
       note = 1;
       break;
     case 'd':
       note = 3;
       break;
     case 'e':
       note = 5;
       break;
     case 'f':
       note = 6;
       break;
     case 'g':
       note = 8;
       break;
     case 'a':
       note = 10;
       break;
     case 'b':
       note = 12;
       break;
     case 'p':
     default:
       note = 0;
   }
   p++;

   // now, get optional '#' sharp
   if(*p == '#')
   {
     note++;
     p++;
   }

   // now, get optional '.' dotted note
   if(*p == '.')
   {
     duration += duration/2;
     p++;
   }
 
   // now, get scale
   if(isdigit(*p))
   {
     scale = *p - '0';
     p++;
   }
   else
   {
     scale = default_oct;
   }

   scale += OCTAVE_OFFSET;

   if(*p == ',')
     p++;       // skip comma for next note (or we may be at the end)

   // now play the note

   if(note)
   {
     Serial.print("Playing: ");
     Serial.print(scale, 10); Serial.print(' ');
     Serial.print(note, 10); Serial.print(" (");
     Serial.print(notes[(scale - 4) * 12 + note], 10);
     Serial.print(") ");
     Serial.println(duration, 10);
     tone1.play(notes[(scale - 4) * 12 + note]);
     delay(duration);
     tone1.stop();
   }
   else
   {
     Serial.print("Pausing: ");
     Serial.println(duration, 10);
     delay(duration);
   }
}
void play_rtttl()
{
 // Absolutely no error checking in here

 

 // format: d=N,o=N,b=NNN:
 // find the start (skip name, etc)
 if (nuevo){
   inicializar_tono();
   nuevo=false;
 }
 
 // now begin note loop
 if(*p)
 {
   // first, get note duration, if available
   sonar();
   
 }else{reproducir=false;}
}

void loop(void)
{
 digitalWrite(13, HIGH);
 if (reproducir){play_rtttl();}
 if (keyboard.available()) {
   
   // read the next key
   char c = keyboard.read();
   
   // check for some of the special keys
   if (c == PS2_ENTER) {
     Serial.println(comando);
     char this_char[comando.length() + 1];
     comando.toCharArray(this_char, sizeof(this_char));
     p=song[atoi(this_char)];
     nuevo=true;
     reproducir=true;
     comando="";
   } else if (c == PS2_TAB) {
     Serial.print("[Tab]");
   } else if (c == PS2_ESC) {
     Serial.print("[ESC]");
   } else if (c == PS2_PAGEDOWN) {
     Serial.print("[PgDn]");
   } else if (c == PS2_PAGEUP) {
     Serial.print("[PgUp]");
   } else if (c == PS2_LEFTARROW) {
     Serial.print("[Left]");
   } else if (c == PS2_RIGHTARROW) {
     Serial.print("[Right]");
   } else if (c == PS2_UPARROW) {
     Serial.print("[Up]");
   } else if (c == PS2_DOWNARROW) {
     Serial.print("[Down]");
   } else if (c == PS2_DELETE) {
     Serial.print("[Del]");
   } else {
     
     // otherwise, just print all normal characters
     Serial.print(c);
     comando.concat(c);
   }
 }
 digitalWrite(13, LOW);
 //delay(500);
}





aclaro que el codigo es una combinacion entre el ejemplo que hay en el sitio de la libreria tone, y el ejemplo de la ultima version de la libreria keyboard
saludos

riscking

#13
Jun 22, 2011, 11:07 pm Last Edit: Jun 23, 2011, 01:49 am by riscking Reason: 1
Greenlanternx, gracias por contestar estoy intentando amoldar tu codigo al mio y he puesto q lea por la consola lo que metas por teclado, de momento no consigo que funcione y esque  no me queda muy claro lo hace el string comando, de todas formas el arduino te permite meter 37 tonos en el array?? yo q con 7 ya tengo problemas serios y esque seria justo lo que quiero.

Code: [Select]
void loop(void)
{
  digitalWrite(7, HIGH);
  if (reproducir){play_rtttl();}
  if (Serial.available() > 0) {
   
    // read the next key
    char c =  Serial.read();
   
    // check for some of the special keys
    if (c == 'd') {
      Serial.println(comando);
      char this_char[comando.length() + 1];
      comando.toCharArray(this_char, sizeof(this_char));
      p=song[atoi(this_char)];
      nuevo=true;
      //reproducir=true;
      comando="";
    } else if (c == '1') {
      Serial.print("1");
    } else if (c == '2') {
      Serial.print("2");
    } else if (c == '3') {
      Serial.print("3");
    } else if (c == '4') {
      Serial.print("4");
    } else if (c == '5') {
      Serial.print("5");
    } else if (c =='6') {
      Serial.print("6");
    } else if (c == '7') {
      Serial.print("7");
    } else if (c == '8') {
      Serial.print("8");
    } else if (c == '9') {
      Serial.print("9");
    } else {
     
      // otherwise, just print all normal characters
      Serial.print(c);
      comando.concat(c);
    }
  }
  digitalWrite(7, LOW);
  //delay(500);
}


riscking

He puesto mi version con un array y si me hincho a poner canciones en el array song se me llena la ram y ya la cosa no pinta bien, yo lo estoy probando en el atmega328p.

Go Up