char state = LOW;
void setup() {
// put your setup code here, to run once:
pinMode(2,INPUT_PULLUP);
pinMode(6,OUTPUT);
attachInterrupt(0,blink,LOW);
}
void loop() {
// put your main code here, to run repeatedly:
digitalWrite(6,state);
}
blink(){
state = !state;
}
I am a beginner.Now I have some questions about this program.
If I keep pressing the switch and not releasing it, will attachInterrupt continue to read the interrupt signal, repeatedly executing the blink function, causing the loop function to fail? Because when I run the program, I press the button and sometimes it works, sometimes it doesn't. So, is a continuous interrupt signal treated as an interrupt signal?
I would be grateful if you could give me an answer.
Oh yes, I see what you mean. This is a program I found on the Internet for learning "interrupt".The program is not perfect,then I have the question .I wonder how this program works if I keep pressing the switch and not releasing it.
You took care of my immediate needs.I have looked carefully at the link you provided.That's great!Thank you very much for enabling me to continue my study.
Oh yes, I see what you mean ! I changed the program. I added a delay function to make the error more obvious.When I pressed the button and did not release, the LED kept flashing ! I think I understand.
int state = LOW;
void setup() {
// put your setup code here, to run once:
pinMode(2,INPUT_PULLUP);
pinMode(6,OUTPUT);
attachInterrupt(0,blink,LOW);
}
void loop() {
// put your main code here, to run repeatedly:
digitalWrite(6,state);
delay(1000);
}
void blink(){
state = !state;
}
I haven't.I replaced "LOW" in attachInterrupt with "RISING".Sometimes it still doesn't work, but the frequency is lower than before. Maybe I should give up using interrupt.
I'm trying to solve this problem with a millis(). Press and release the switch once, the LED changes once (from on to off or off to on).
But now I can only achieve the following :Press or release the switch once, the LED changes once (from on to off or off to on).
Check the state change detect example in the IDE. Better to modify it to use input pullups compared to the hard-wired pulldowns it expects. Then look for the button to be released (low to high) and toggle the led.
Note all variables that are used both inside and outside of an interrupt must be declared volatile, and you should not use an int type variable unless you surround the access to it with a noInterrupts at the start and interrupts when you have finished.
volatile bool state = false;
Anything else with the rest of that code shows you what a crap tutorial you were following.
// constants won't change. They're used here to set pin numbers:
const int buttonPin = 2; // the number of the pushbutton pin
const int ledPin = 13; // the number of the LED pin
// variables will change:
int buttonState = 0; // variable for reading the pushbutton status
void setup() {
// initialize the LED pin as an output:
pinMode(ledPin, OUTPUT);
// initialize the pushbutton pin as an input:
pinMode(buttonPin, INPUT);
}
void loop() {
// read the state of the pushbutton value:
buttonState = digitalRead(buttonPin);
// check if the pushbutton is pressed. If it is, the buttonState is HIGH:
if (buttonState == HIGH) {
// turn LED on:
digitalWrite(ledPin, HIGH);
} else {
// turn LED off:
digitalWrite(ledPin, LOW);
}
}
The reason why I use this variable type is the above program(I found an example in the IDE) also uses an int.
Why not indeed, that’s what digitalRead returns, but you don’t need it as a global variable (could be local to the loop() function) and really you don’t need it at all (the compiler/optimizer likely gets rid of it) as you could write
void loop() {
// check if the pushbutton is pressed. If it is, the buttonState is HIGH:
if (digitalRead(buttonPin) == HIGH) {
// turn LED on:
digitalWrite(ledPin, HIGH);
} else {
// turn LED off:
digitalWrite(ledPin, LOW);
}
}
And you could go one step further if you notice that the led takes the state of the button and so the loop could just be
If you want to stay true to the programming interface, digitalRead() returns an int, so as the spec does not say the range taken by HIGH and LOW (you have to look at the source code to know it’s an int defined as 1 and 0) then using an int is the right way.
This way what you store is really a truth value, the result of a comparison making no assumption whatsoever about the type ot values of HIGH and LOW.
You can go one step further to accommodate a pull-up or pulldown situation by defining at the start of the code what pressed means this way you have only one place to change the code if you change the hardware setup
#define PRESSED HIGH // using an external pulldown resistor for the button
….
bool buttonIsPressed = (digitalRead(butyonPin) == PRESSED);
if (buttonIsPressed) {
….
} else {
….
}
….