Hello, i have a sketch that play a sound from buzzer and lights up the led.
The code's like this:
#include <Tone.h>
Tone solo;
Tone bass;
Tone rythm;
const int buttonPin = 16; // the number of the pushbutton pin
int buttonState = 0; // variable for reading the pushbutton status
const int t = 650; // quater note duration
const int tt = t*2;
const int t14 = round(t*1/4);
const int t24 = round(t*2/4);
const int t34 = round(t*3/4);
const int bassLedPin = 15; // bass led signal pin (aka A1)
const int rythmLedPin = 17; // rythm led signal pin (aka A3)
const int soloLedPin = 19; // solo led signal pin (aka A5)
void wait(Tone t)
{
while (t.isPlaying()) { }
}
int bassLedState = random(120) < 80;
void switchBassLed()
{
if (bassLedState == random(120) < 80)
bassLedState = random(120) < 80;
else
bassLedState = random(120) < 80;
digitalWrite(bassLedPin, random(120) < 80);
}
int rythmLedState = random(120) < 80;
void switchRythmLed()
{
if (rythmLedState == random(120) < 80)
rythmLedState = random(120) < 80;
else
rythmLedState = random(120) < 80;
digitalWrite(rythmLedPin, random(120) < 80);
}
int soloLedState = random(120) < 80;
void switchSoloLed()
{
if (soloLedState == random(120) < 80)
soloLedState = random(120) < 80;
else
soloLedState = random(120) < 80;
digitalWrite(soloLedPin, random(120) < 80);
}
void setup(void)
{
// Switch ground reference
pinMode(buttonPin, INPUT);
pinMode(14, OUTPUT); // led ground pin (aka A0)
pinMode(18, OUTPUT); // led ground pin (aka A4)
pinMode(bassLedPin, OUTPUT); // bass led signal pin
pinMode(rythmLedPin, OUTPUT); // rythm led signal pin
pinMode(soloLedPin, OUTPUT); // solo led signal pin
pinMode(3, OUTPUT); // solo buzzer ground pin
pinMode(9, OUTPUT); // rythm buzzer ground pin
solo.begin(6); // solo buzzer signal pin
bass.begin(0); // bass buzzer signal pin
rythm.begin(12); // rythm buzzer signal pin
}
void loop(void)
{ buttonState = digitalRead(buttonPin);
if (buttonState == LOW){
solo.play(NOTE_D4, t34); switchSoloLed(); buttonState = digitalRead(buttonPin);
wait(solo);
solo.play(NOTE_D4, t14); switchSoloLed();
wait(solo);
bass.play(NOTE_D3, t); switchBassLed(); buttonState = digitalRead(buttonPin);
rythm.play(NOTE_G4, t24); switchRythmLed();
solo.play(NOTE_G4, t); switchSoloLed();
wait(rythm);
rythm.play(NOTE_B4, t14); switchRythmLed();
wait(rythm);
rythm.play(NOTE_D5, t14); switchRythmLed();
wait(rythm);
bass.play(NOTE_FS3, t); switchBassLed(); buttonState = digitalRead(buttonPin);
rythm.play(NOTE_D5, t24); switchRythmLed();
solo.play(NOTE_A4, t); switchSoloLed();
wait(rythm);
wait(rythm);
rythm.play(NOTE_FS5, t14); switchRythmLed();
wait(rythm);
rythm.play(NOTE_A5, t14); switchRythmLed();
wait(rythm);
else
{ digitalWrite(bassLedPin, LOW);
digitalWrite(soloLedPin, LOW);
digitalWrite(rythmLedPin, LOW);
buttonState = digitalRead(buttonPin);}
}
I want when the push button is pressed the buzzer stop plays a sound immediately, led off and the arduino do nothing until the arduino resetted. But when i tried push the button, the buzzer and the led stop when the buzzer finish the sound.
Can somebody help me with this?
Thanks
Well, don't wait until the tone has finished playing I guess?
void wait(Tone t)
{
while (t.isPlaying()) { }
}
Instead, check if the last tone has finished playing before enabling a new one.
LightuC:
Well, don't wait until the tone has finished playing I guess?
void wait(Tone t)
{
while (t.isPlaying()) { }
}
Instead, check if the last tone has finished playing before enabling a new one.
So i must add check button state in the "void wait" function?
Sorry I'm a newbie in this world
The trick is to keep loop() going. It should keep checking the inputs and making decisions thousands of times per second.
Most of those times the decision is not to change anything. But when a button becomes pressed or becomes released or the tune finished playing, then the output should change.
Currently after every call to play you call wait which will wait for the tone to finish playing. This stalls the arduino cpu, it is doing nothing else then waiting until the tone has finished playing. Because of this all the tones will finish playing, then it will reenter the loop and might find the button to be pressed and disables the led and tone (but they have finished playing anyways).
What you really should do (this involves a little more effort), is to queue up your tones. You can use the QueueArray library for that but your really should look into coding this yourself (also because most librarys use dynamic memory allocation, which should be avoided if possible).
Now if you have all the tones/notes or whatever queued up, in every iteration of the loop function you check the head of the queue for the tone to play. Then you check, if that tone has finished playing. If it has, you can remove it from the queue and start the next one. Now before you do all that you can check your button state and enable/disable the output pins accordingly
MorganS:
The trick is to keep loop() going. It should keep checking the inputs and making decisions thousands of times per second.
Most of those times the decision is not to change anything. But when a button becomes pressed or becomes released or the tune finished playing, then the output should change.
So i think i must add a function to check the input in every line right?
LightuC:
Currently after every call to play you call wait which will wait for the tone to finish playing. This stalls the arduino cpu, it is doing nothing else then waiting until the tone has finished playing. Because of this all the tones will finish playing, then it will reenter the loop and might find the button to be pressed and disables the led and tone (but they have finished playing anyways).
What you really should do (this involves a little more effort), is to queue up your tones. You can use the QueueArray library for that but your really should look into coding this yourself (also because most librarys use dynamic memory allocation, which should be avoided if possible).
Now if you have all the tones/notes or whatever queued up, in every iteration of the loop function you check the head of the queue for the tone to play. Then you check, if that tone has finished playing. If it has, you can remove it from the queue and start the next one. Now before you do all that you can check your button state and enable/disable the output pins accordingly
Wow its getting more complex. So i must use a QueueArray function? Is there any more simpler solution for that?
girifir:
So i think i must add a function to check the input in every line right?
No. If this is required you should reconsider your concept.
girifir:
Wow its getting more complex. So i must use a QueueArray function? Is there any more simpler solution for that?
You don't necessarily need to use a queue. Storing your tones in a simple array should also work. Your program might look something like this:
void loop()
{
if (button is pressed)
{
disable tone
disable led
return
}
if (current tone has finished playing)
{
start next tone
}
}
Here is the main loop from a very large Arduino program that took several years to write.
void loop() {
checkInputs();
doCalculations();
setOutputs();
doSerial();
}
Each of those functions is quite large but takes at most 2 milliseconds to run each time.