Go Down

### Topic: Simple: LEDs & buttons (Read 1 time)previous topic - next topic

#### aharasewych

##### Feb 21, 2012, 05:40 amLast Edit: Feb 21, 2012, 06:44 am by CrossRoads Reason: 1
I have been experimenting with pieces of code, but haven't been able to figure out - how can I use the button state to change direction (so that I do not have to hold the button to change direction, as I wrote it - but instead press it once to change back and forth (forward sequence and backward sequence).

Tried using if statements to essentially reverse the equation on a button state change - but have yet to get that working.

Second question

can I get the code working the way it is, so that you hold the button, but instead of waiting until the end of the sequence (forward:1234, backward:4321) to change directions, it changes directions as soon as I hold down the button (i.e. 123(holdbutton)2143214321(releasebutton)2341234)

Below is the instructions for this simple program, and the code thus far, which technically works for what I need, just curious about the above questions.

Thanks in advance for at least taking a look!

Instructions:
1. Only one LED should light up at one time. At least one LED should be lighted up.
2. Each LED should light up for half a second.
3. The sequence should be L1, L2, L3, L4, L1 and so on.
4. Put in a button for direction control. If the button is pressed, the LED's should light up in reverse sequency, i.e. L4, L3, L2, L1, L4 and so on.

Code:

Code: [Select]
`const int  buttonPin = 10;    int buttonState = 0;        int lastButtonState = 0;     int timer = 500;           void setup() {    pinMode(buttonPin, INPUT);    for (int thisPin = 2; thisPin < 8; thisPin++)  {    pinMode(thisPin, OUTPUT);        }}void loop() {    if (buttonState == HIGH) {      for (int thisPin = 2; thisPin < 6; thisPin++) {      digitalWrite(thisPin, HIGH);      delay(timer);                          digitalWrite(thisPin, LOW);buttonState = digitalRead(buttonPin);         } }    else {        for (int thisPin = 5; thisPin >= 2; thisPin--) {        digitalWrite(thisPin, HIGH);    delay(timer);        digitalWrite(thisPin, LOW);    buttonState = digitalRead(buttonPin);  }}}` (code tags added by moderator)

#### liuzengqiang

#1
##### Feb 21, 2012, 07:23 am
Couldn't choose a better file name?

Let's be clear. You have forward sequence. Then press down the button and hold it down, the sequence goes reverse. Release the button, the sequence runs forward. If you really want to see reverse sequence, your finger will get tired. Are you sure you don't want one click then reverse, next click then forward...?
Serial LCD keypad panel,phi_prompt user interface library,SDI-12 USB Adapter

#### PaulS

#2
##### Feb 21, 2012, 12:45 pm
Put each { on a new line.
Each } goes on it's own line, too.
Use Tools + Auto Format to make that code readable.

That, along with a clarification of your requirements, will get you some help.
The art of getting good answers lies in asking good questions.

#### aharasewych

#3
##### Feb 21, 2012, 07:38 pmLast Edit: Feb 21, 2012, 08:29 pm by CrossRoads Reason: 1
My code thus far:

Basically, I am having trouble understanding how to make button presses work. The code I have currently I have to hold the button to change LED sequence. How would I set that to simple reverse every time I press the button?

(aharasewych, adds these tags next time you post:  [ code ] & [/ code ], without the spaces  - Moderator)
Code: [Select]
`const int  buttonPin = 10;    int buttonState = 0;  int timer = 500;           void setup() {    pinMode(buttonPin, INPUT);    for (int thisPin = 2; thisPin < 8; thisPin++)  {    pinMode(thisPin, OUTPUT);        }}void loop() {  if (buttonState == HIGH)  {  for (int thisPin = 2; thisPin < 6; thisPin++)  {    digitalWrite(thisPin, HIGH);      delay(timer);                      digitalWrite(thisPin, LOW);buttonState = digitalRead(buttonPin);         }    }else {  for (int thisPin = 5; thisPin >= 2; thisPin--) {    digitalWrite(thisPin, HIGH);    delay(timer);        digitalWrite(thisPin, LOW);    buttonState = digitalRead(buttonPin);  }}}`

#### PaulS

#4
##### Feb 21, 2012, 08:50 pm
Do you have a reading comprehension issue?
The art of getting good answers lies in asking good questions.

#### CrossRoads

#5
##### Feb 21, 2012, 09:27 pm
Change this part:
Code: [Select]
`buttonState = digitalRead(buttonPin);`
to
Code: [Select]
`if (digitalRead (buttonPin) == 0){  // assumes buttonPin declared as INPUTwith internal pullup enabledbuttonState = 1-buttonState;  // result is 1,0,1,0,1,0delay(50);  // crude debounce}`
then you change direction & keep that change after a button press

@PaulS, that was uncalled for.
Designing & building electrical circuits for over 25 years.  Screw Shield for Mega/Due/Uno,  Bobuino with ATMega1284P, & other '328P & '1284P creations & offerings at  my website.

#### aharasewych

#6
##### Feb 21, 2012, 10:12 pm
Thanks crossroads, and no thank you Paul.

Figured the question was simple enough. I listed the requirements, the specific code didnt matter, just wanted a prod in the right direction. Sorry i didn't simplify it further for you Paul. Between all the sarcasm and the condescension, im sure it is hard for you to find time to read and be helpful.

#### PaulS

#7
##### Feb 22, 2012, 10:09 am
Quote
@PaulS, that was uncalled for.

Really? I asked that the poster make the code readable, and OP posted the same unreadable mess again. What's the problem with making code readable before posting it?

Often times, when the { and } are lined up, and the code properly indented, it is then obvious that else blocks are associated to the wrong if statement, because the poorly positioned { and } did not make it clear what ended where.

Since OP's issue seemed to be related to program structure, I thought that reformatting the code would make it more apparent what the problem was.

I do not apologize for, or retract, my comment in any way.
The art of getting good answers lies in asking good questions.

#### aharasewych

#8
##### Feb 22, 2012, 04:06 pmLast Edit: Feb 22, 2012, 04:11 pm by aharasewych Reason: 1
Paul, I do autoformat and I get this. Compare the two, it was damn close if not right. If you feel I post unreadable messes - then you can feel free not to respond. Thank you.

Sorry I didn't have [ code ] in there - didn't know. - Thanks for editing that into the last posts CrossRoads. People like you are why I'll be back.

Code: [Select]
`const int  buttonPin = 10;    int buttonState = 0;  int timer = 500;           void setup() {  pinMode(buttonPin, INPUT);  for (int thisPin = 2; thisPin < 8; thisPin++)  {    pinMode(thisPin, OUTPUT);        }}void loop() {  if (buttonState == HIGH)  {    for (int thisPin = 2; thisPin < 6; thisPin++)    {      digitalWrite(thisPin, HIGH);        delay(timer);                        digitalWrite(thisPin, LOW);      buttonState = digitalRead(buttonPin);        }  }  else {    for (int thisPin = 5; thisPin >= 2; thisPin--) {      digitalWrite(thisPin, HIGH);      delay(timer);          digitalWrite(thisPin, LOW);      buttonState = digitalRead(buttonPin);    }  }}`

#### aharasewych

#9
##### Feb 22, 2012, 04:22 pm
CrossRoads - this button press works great - however the direction change can only occur at the beginning of the loop.

How could I adjust the code to alter direction from the point it the button is pressed during the loop? i.e. instead of 1234123412(press)3443214321, it would go 1234123412(press)143214321 (does that make sense - not sure if I am asking the question correctly)

Code: [Select]
`const int  buttonPin = 13;    int buttonState = 0;  int timer = 500;           void setup() {  pinMode(buttonPin, INPUT);  for (int thisPin = 3; thisPin < 13; thisPin++)  {    pinMode(thisPin, OUTPUT);        }}void loop() {  if (buttonState == HIGH)  {    for (int thisPin = 3; thisPin < 13; thisPin++)     {      digitalWrite(thisPin, HIGH);         delay(timer);                        digitalWrite(thisPin, LOW);      if (digitalRead (buttonPin) == 0){  // assumes buttonPin declared as INPUTwith internal pullup enabled        buttonState = 1-buttonState;  // result is 1,0,1,0,1,0        delay(50);  // crude debounce      }    }   }  else {    for (int thisPin = 12; thisPin >= 3; thisPin--) {       digitalWrite(thisPin, HIGH);      delay(timer);          digitalWrite(thisPin, LOW);      if (digitalRead (buttonPin) == 0){  // assumes buttonPin declared as INPUTwith internal pullup enabled        buttonState = 1-buttonState;  // result is 1,0,1,0,1,0        delay(50);  // crude debounce      }    }  }}`

#### xl97

#10
##### Feb 22, 2012, 07:41 pm

@PaulS, that was uncalled for.

typical 'mo/style'..  (sigh)

not to mention the auto format doesnt even 'format' the code in a way Paul 'requires' to be helpful.  (ie: does NOT put { or } on new lines)

nobody 'requires' anybody to surf threads here, help or do anything.. just skip it, if its not 'for you'...

#### liuzengqiang

#11
##### Feb 22, 2012, 08:03 pm
You can't break out of a complete cycle since you have no statement to do it. Your current program only uses the button status at the start of a complete cycle, so what do you expect?

There's a reason Paul lashed out on your formatting. Paul probably puts the left brace on a separate line and lines it up with the corresponding right brace, which is also what I do by the way. It won't take you much effort to do it and will save time for everyone reading your code. Your current code is already alright but we can be picky. So here's what I would do, to make it work for you. Replace your loop with this:

Code: [Select]
`int lit_LED=3;int LED_direction=1;while(1){  //do the button sensing stuff here  LED_direction=buttonState==HIGH?1:-1;  digitalWrite(lit_LED,HIGH);  delay(timer);  digitalWrite(lit_LED,LOW);  lit_LED+=LED_direction;  if (lit_LED==1) lit_LED=5;  if (lit_LED==6) lit_LED=2;}`

Serial LCD keypad panel,phi_prompt user interface library,SDI-12 USB Adapter

#### CrossRoads

#12
##### Feb 22, 2012, 09:48 pm
To get out of the loop, set your test condition to the end state when the button is pressed:
Code: [Select]
`      if (digitalRead (buttonPin) == 0){  // assumes buttonPin declared as INPUTwith internal pullup enabled        buttonState = 1-buttonState;  // result is 1,0,1,0,1,0thisPin = 13;        delay(50);  // crude debounce`
and
Code: [Select]
`      if (digitalRead (buttonPin) == 0){  // assumes buttonPin declared as INPUTwith internal pullup enabled        buttonState = 1-buttonState;  // result is 1,0,1,0,1,0thispin = 2;        delay(50);  // crude debounce`

The code as posted looked autoformatted to me already. I had no trouble following it.

Designing & building electrical circuits for over 25 years.  Screw Shield for Mega/Due/Uno,  Bobuino with ATMega1284P, & other '328P & '1284P creations & offerings at  my website.

#### PaulS

#13
##### Feb 23, 2012, 01:38 pm
Quote
Paul, I do autoformat and I get this. Compare the two, it was damn close if not right. If you feel I post unreadable messes - then you can feel free not to respond. Thank you.

What I asked you to do was:
Quote
Put each { on a new line.
Each } goes on it's own line, too.
Use Tools + Auto Format to make that code readable.

You managed one out of three.

Properly formatted code is much easier to read AT A GLANCE. If you prefer to study code to line up { and }, to find where operators are (this==that is a lot harder to process than this == that), etc. then fine. If you want other people to help you, it isn't asking that much to make their job easier.
The art of getting good answers lies in asking good questions.

Go Up