Thanks in advance, been working on this for way too long and it has to be something simple.
My apologies if my searching skills aren't up to par.
The goal here is to have a few lights blinking in order.
I currently have it set with two but if I can make two blink in order I believe I can increase that.
When the button is pushed it speeds up the blinking. That's working.
My problem is:
I want it to check to see if the button is depressed after every HIGH / LOW.
As it currently is it needs to complete the entire loop before it checks again.
I've tried putting the code that checks the button in more places but always get errors.
This is probably on the "left a semi colon out" level of dumb so thanks ahead of time.
Loving this community. Code below.
-Jered
int delay_value = 1000; //set initial delay
int led_pin1 = 3; //set led pin1
int led_pin2 = 4; //set led pin2
int button_pin = 2; //set button pin
void setup() {
pinMode(led_pin1, OUTPUT);
pinMode(button_pin, INPUT);
pinMode(led_pin2, OUTPUT); //set pins to in/out
}
void loop() {
digitalWrite(led_pin1, HIGH); //light 1 on
delay(delay_value);
digitalWrite(led_pin1, LOW); //light 1 off
delay(delay_value);
digitalWrite(led_pin2, HIGH); //light 2 on
delay(delay_value);
digitalWrite(led_pin2, LOW); //light 2 off
delay(delay_value);
int button_state = digitalRead(button_pin); //read button state
if (button_state == HIGH) { //speed up if button pressed
delay_value = 30;
} else {
delay_value = 100;
}
}
AWOL:
All those calls to delay() are making your code unresponsive.
Time to read the famous "blink without delay" example in the IDE.
For sure, I tried that originally but it was a bit complicated so figured do it this way then switch to without delay.
If you think that's the cure I could just scrap using delay.
Problem is the code isn't compiling due to an error so probably have the same issue trying to check for input multiple times without delay.
It is possible to check that button 10 times in the loop if I want to correct?
Edit: guess you can't change text color in the code box, makes sense haha
Added the red text below in the code.
Error I'm getting is:
sketch_dec17a.ino: In function 'void loop()':
sketch_dec17a:30: error: redeclaration of 'int button_state'
sketch_dec17a:18: error: 'int button_state' previously declared here
Going to make the switch to without delay when I get home in 8 hours or so but figuring out that error might save me from making the same on without delay.
Thanks again for the help.
Jered
int delay_value = 1000; //set initial delay
int led_pin1 = 3; //set led pin1
int led_pin2 = 4; //set led pin2
int button_pin = 2; //set button pin
void setup() {
pinMode(led_pin1, OUTPUT);
pinMode(button_pin, INPUT);
pinMode(led_pin2, OUTPUT); //set pins to in/out
}
void loop() {
digitalWrite(led_pin1, HIGH); //light 1 on
delay(delay_value);
digitalWrite(led_pin1, LOW); //light 1 off
delay(delay_value);
[color=red] int button_state = digitalRead(button_pin); //read button state
if (button_state == HIGH) { //speed up if button pressed
delay_value = 30;
} else {
delay_value = 100;
} [/color]
digitalWrite(led_pin2, HIGH); //light 2 on
delay(delay_value);
digitalWrite(led_pin2, LOW); //light 2 off
delay(delay_value);
int button_state = digitalRead(button_pin); //read button state
if (button_state == HIGH) { //speed up if button pressed
delay_value = 30;
} else {
delay_value = 100;
}
}
It is possible to check that button 10 times in the loop if I want to correct?
You could do that if you really wanted to but frankly it is better to check the button state once each time through loop() but keep loop() repeating by not using blocking code such as delay()
Something like this
const byte led1 = 3; //set led pin1
const byte led2 = 4; //set led pin2
const byte button = 2; //set button pin
unsigned long period = 1000;
unsigned long blinkStart = 0;
unsigned long currentMillis;
byte state = 0;
void setup()
{
pinMode(led1, OUTPUT);
pinMode(button, INPUT_PULLUP);
pinMode(led2, OUTPUT); //set pins to in/out
digitalWrite(led1, LOW);
}
void loop()
{
switch (state)
{
case 0: //led 1 is off
currentMillis = millis();
if (currentMillis - blinkStart >= period) //time to turn it on
{
digitalWrite(led1, HIGH);
blinkStart = currentMillis;
state = 1;
}
break;
case 1: //led 1 is on
currentMillis = millis();
if (currentMillis - blinkStart >= period) //time to turn it off
{
digitalWrite(led1, LOW);
blinkStart = currentMillis;
state = 2;
}
break;
case 2: //led 2 is off
currentMillis = millis();
if (currentMillis - blinkStart >= period) //time to turn it on
{
digitalWrite(led2, HIGH);
blinkStart = currentMillis;
state = 3;
}
break;
case 3: //led 2 is on
currentMillis = millis();
if (currentMillis - blinkStart >= period) //time to turn it off
{
digitalWrite(led2, LOW);
blinkStart = currentMillis;
state = 0;
}
break;
}
//code to be read each time through loop can go here but it must not block
period = 1000;
if (digitalRead(button) == LOW)
{
period = 30;
}
}
Note that all the timing variables are unsigned longs and that the test for the end of blink periods subtracts the value of millis() when the action started from the current millis() value. This combination prevents problems when millis() rolls over to zero after 49 and a bit days.
Also I changed the pin number variables to const because they will not change in the program and byte to save memory compared to ints.
The program is a simple example of a finite state machine and the principle could be expanded much further with more states and more events to change states. If you added many more LEDs it would make sense to use an array of LED pin numbers rather than individual variables to keep the code smaller and easier to understand.
I really wish they'd take the "Blink" sketch out of the examples that come with the Arduino IDE. It is a useless way to blink LEDs. What it can do, I can do with a 555 timer and a 4017 (and have) without any programming. Just about as flexible.