0

I am trying to write a sketch wherein the led brightness increases in increments of 15 until it reaches 255. At that point I want to make decrements of 15 until it reaches 0. The increment part of the program works well but the decrement part goes haywire. It gets stuck between 255 & 240. I am not sure how can I fix it. Could you please tell how can I make it work?

Here is my sketch:

int led = 9; //led pin
int fade = 0; // pwm value

void setup() {
  // put your setup code here, to run once:

  Serial.begin(9600);
  pinMode(led, OUTPUT);
}

void loop() {
  // put your main code here, to run repeatedly:

   analogWrite(led,fade);
   fade += 15;
   Serial.println(fade);
   delay(250);

  if (fade >= 240){
    fade = fade - 15;
    analogWrite(led, fade);
    Serial.println(fade);
    delay(250);
  }

} 
5
  • the decrement part is not haywire ... it is doing exactly what you told it to do
    – jsotola
    Commented Mar 1, 2020 at 23:55
  • see the Fading example in Arduino IDE
    – Juraj
    Commented Mar 2, 2020 at 14:24
  • Perhaps with a for loop it's easier to implement as in Fading example but I was trying to do it using a conditional statement.
    – Zaffresky
    Commented Mar 2, 2020 at 22:19
  • sorry, I thought the example is better
    – Juraj
    Commented Mar 3, 2020 at 6:46
  • Does this answer your question? PWM delay without blocking the code
    – Juraj
    Commented Mar 3, 2020 at 6:49

2 Answers 2

4

The problem is that you add 15, and than if it's >= 240, you decrease 15, so it will not change (I wouldn't consider it haywire though).

You can better use a direction sign. Below is only the relevant code (not the GPIO functionality). What it does in the loop is, in case up is true, it adds fifteen, otherwise it subtracts 15. When 255 is reached, it starts counting down (up is false), when reaching 0, it starts counting up (up is true). This only works if 255 / the amount to add/subtracts reaches exactly 255, otherwise you have to check for <= 0 and >= 255.

bool up = true;
int fade = 0;

void loop()
{
    fade += up ? 15 : -15;
    if (fade == 0)
    {
      up = true;
    }
    else if (fade == 255)
    {
      up = false;
    }
}

Not considered good coding practices:

The last if statement can be substituted for the following line, which means: if going up and 255 is reached, go down, else if going down and 0 is reached, go up, otherwise don't change direction. But it is much less readable, so I prefer the longer if statement.

up = (up && (fade == 255)) ? false : ((!up && (fade == 0)) ? true : up);

Another version: if fade is 0 or 255 (only two possibilities), go up if 0 is reached, else (can only be 255) go down, else don't change.

up = (fade % 255 == 0) ? (fade == 0) : up;
2
  • 1
    Thanks. Yes I realized why the decrement loop was stuck. It wasn't going haywire. I am new to programming and loops within loops are not really my forte :) Need to practice more but thanks for explaining.
    – Zaffresky
    Commented Mar 2, 2020 at 22:15
  • You're welcome. Just follow the first part (the 'good pcoding practice'), use good variable names, and break your problems in small steps. Good luck with your project. Commented Mar 2, 2020 at 23:41
1

The if condition is causing the issue. When the global variable fade reaches 240, upon entering the loop(), you are incrementing it by 15, making fade = 255. So, the if condition becomes true and 15 is subtracted from 255 making fade to be equal to 240 again. This keeps repeating and hence the value fade variable is stuck between the values 240 and 255.

2
  • Thanks. I see the error in my logic now :)
    – Zaffresky
    Commented Mar 2, 2020 at 22:09
  • Great! Good luck!
    – techenthu
    Commented Mar 4, 2020 at 10:15

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.