Fade Sketch 250513

Hello Arduino forum,

Have been working on a circuit based on
https://www.arduino.cc/en/Tutorial/BuiltInExamples/Fade

The circuit fades seven LEDs from bright to off
over eight seconds.

The sketch has been studied and some tests done
changing the 'brightness' and the 'fadeAmount'
variables as well as the 'delay(120)' statement
at the end of the sketch.

++++ Tests of the Fade Sketch ++++
The Fade sketch is one of the built in examples
that come with the Arduino IDE:
File > Examples > Basic > Fade

Preconditions:

  1. Circuit shown in JPG titled 'SPSF ATtiny85, Schematic
    dated 250509.
  2. Fade sketch, Fade.ino

Action: Apply power, 5.1 VDC to circuit

Test 250512.1 Sketch as copied from Arduino Examples
Brightness: 0
fadeAmount: 5
Delay: 120
Result: Interval: 12 secs; LEDs: Bright

Test 250512.2
Brightness: 10
fadeAmount: 15
Delay: 120
Result: Interval: 3.8 secs; LEDs: Bright

Test 250512.3
Brightness: 5
fadeAmount: 20
Delay: 120
Result: Interval: 3.3 secs; LEDs: Medium Bright

Test 250512.4
Brightness: 10
fadeAmount: 20
Delay: 500
Result: Interval: 13.5 secs; LEDs: Bright
Change increments visible.

Test 250512.5
Brightness: 0
fadeAmount: 5
Delay: 120

Result: Interval: 12 secs; LEDs: Bright

Test 250512.6
Brightness: 5
fadeAmount: 5
Delay: 120
Result: Interval: 11.5 secs; LEDs: Bright

Test 250512.7
Brightness: 10
fadeAmount: 5
Delay: 120
Result: Interval: 12 secs; LEDs: Medium Bright

Test 250512.8
Brightness: 10
fadeAmount: 5
Delay: 80
Result: Interval: 8 secs; LEDs: Bright

The brightness variable seems to control how far down
the light from the LEDs goes. Above zero the LEDs
never completely turn off

The fadeAmount determines how far the brightness
changes with each increment.

There is strong correlation between Delay values
of ten and the number of seconds the cycle takes.
That is, Delay:80 is about eight seconds and Delay:120
is twelve seconds.

The variable setup in the sketch seems fairly
straight forward as does the void setup {

And I believe I get the statement in the
void loop {
brightness = brightness + fadeAmount;
This is saying "Increment (increase or decrease) the brightness
by the fadeAmount."

The statement that is less clear is

// reverse the direction of the fading at the ends of the fade:
if (brightness <= 0 || brightness >= 255) {
fadeAmount = -fadeAmount;
I think this statement is saying
If
brightness is less than or equal to zero
or
brightness is greater than or equal to 255
then
fadeAmount is equal to minus fadeAmount

But if the statement is always incrementing the brightness
by minus fadeAmount how do the LEDs ever get brighter?
The statement seems to start off decreasing the brightness.
But how does it increase the brightness?

At the heart of the statement is the double pipe
C++ logical operator which is used to combine
multiple boolean expressions. The double pipe
returns true if either of the expressions are
true.

How does this first decrease the brightness and then
increase the brightness?

Thanks.

Allen

When this statement is executed

fadeAmount = -fadeAmount;

the value of fadeAmount is negated. Negating a negative value makes it positive. If it has a positive value, such as say 8 then its value becomes -8. If it has a negative value such as -8 then its value becomes 8. Try printing it to see what is going on

To make it easier for us to help, could you post the code you are using?

To post code:

Hello @UKHeliBob , @ruilviana , and the Arduino forum,

The code from the Arduino IDE Version: 2.3.5
is copied herewith below.

/*
  Fade

  This example shows how to fade an LED on pin 9 using the analogWrite()
  function.

  The analogWrite() function uses PWM, so if you want to change the pin you're
  using, be sure to use another PWM capable pin. On most Arduino, the PWM pins
  are identified with a "~" sign, like ~3, ~5, ~6, ~9, ~10 and ~11.

  This example code is in the public domain.

  https://docs.arduino.cc/built-in-examples/basics/Fade/
*/

int led = 9;         // the PWM pin the LED is attached to
int brightness = 0;  // how bright the LED is
int fadeAmount = 5;  // how many points to fade the LED by

// the setup routine runs once when you press reset:
void setup() {
  // declare pin 9 to be an output:
  pinMode(led, OUTPUT);
}

// the loop routine runs over and over again forever:
void loop() {
  // set the brightness of pin 9:
  analogWrite(led, brightness);

  // change the brightness for next time through the loop:
  brightness = brightness + fadeAmount;

  // reverse the direction of the fading at the ends of the fade:
  if (brightness <= 0 || brightness >= 255) {
    fadeAmount = -fadeAmount;
  }
  // wait for 30 milliseconds to see the dimming effect
  delay(30);
}

"||"

Also known as OR (gate)


Do you have more questions? (did you get your answers for "||" and "+/- fadeAmount")

Hello @xfpd and the Arduino forum,

Shout out to xfpd. The explanation of
C++ double pipe logical operator
and the representation of the operator
as an OR gate is most edifying.

I am not a C++ programmer. I am an
architect and so not only are such abstract
concepts not familiar to one
one who lives in a world of three
dimensional phenomenon like wood,
steel and concrete, these concepts
require more than a little concentration
to grasp.

Based on xfpd's excellent explanation
the study of the double pipe in the
void loop() in the fade.ino sketch
was extended. To make the ethereal ideas
more explicit a tool for simplifying
complex abstract concepts is employed:
UML (Unified Modeling Language),
specifically, the UML Activity Diagram.

It is realized that the following explanation
is not adding to the knowledge of experts
like xfpd but the exposition could perhaps
help a reader without expert proficiency.
More importantly, by the act of thinking
about the OR gate logically enough to
explain the OR gate in writing
to another human being
a better understanding
by this scribe is attained.
Finally, by detailing a perception of
the OR gate defects in that perception
could be pointed out.

When the loop begins brightness is
zero and so the double pipe evaluation
meets the criteria of the decision
result marked 'decision result 1'
in the activity diagram. That is,
brightness is zero and so the
expression 'brightness is less
than or equal to 0 or brightness
is greater than or equal to 255'
is met. And so the fadeAmount,
which is initially set to 5
is made negative and becomes
minus 5.

Ok, sorry this was meant to be
a complete explanation of the void loop()
but I am already stuck so instead
of an exposition this becomes a question.

When the double pipe evaluates to true
then fadeAmount is turned negative or
a minus 5.
So when the loop happens the second
time brightness becomes 0 plus
a minus five which is minus five.
So how can brightness be less than
zero?

Thanks

Allen

PS Or perhaps the question stems from a misunderstanding
of the operation of the code. That is, it was thought that
the code begins brightness at zero which is low or off.
But this contradicts the observation of the system. That is,
when the system is powered the LEDs are at full brightness
and begin by dimming.
The code says brightness begins at zero. But when the
circuit is turned on the LEDs are as bright as they
ever are. Is not full brightness 255 and completelt
din zero?
Beginning brightness at 255 would make sense in
the operation of the code because the result
of double pipe decision result 1 would be a
reduction of the fadeAmount. The reduction
would continue until brightness = 0 and
then decision result 4 would change fadeAmount
positive and the LEDs would begin getting brighter.

How could the brightness begin at 255 when
the code clearly sets the initial brightness to zero?

Negative brightness can not happen. However; a "-1" byte might be represented as "0xFF" and cause a PWM LED to be highest brightness.

If you have calculations that you want to be only positive values from 0 to 255 (inclusive), you can use the function constrain(val, 0, 255) https://docs.arduino.cc/language-reference/en/functions/math/constrain/

void setup() {
  Serial.begin(115200);
  Serial.println(constrain(256, 0, 255));
  Serial.println(constrain(-1, 0, 255));
}

void loop() {}

Result:

255
0