RaspberryPi: Fade an LED in and Out

822

10

Published

Introduction: RaspberryPi: Fade an LED in and Out

About: Jack passed away May 20, 2018 after a long battle with cancer. His Instructables site will be kept active and questions will be answered by our son-in-law, Terry Pilling. Most of Jack's instructables are tu...

The following steps are experiments to illustrate how LEDs work. They show how to dim an LED at an even rate and how to fade it in and out.

You will need:

  • RaspberryPi (I used an older Pi, my Pi-3 is in use, but any Pi will work.)
  • Breadboard
  • 5 mm red LED
  • 330 Ω Resistor (Not critical 220-560 Ω will work.)
  • Hookup Wire

The Pi-cobbler I used from Adafruit is not necessary, but it makes breadboarding easier.

WiringPi is a set of libraries for programming the RaspberryPi in C.
Instructions for download, install and use are located at http://www.wiringpi.com/

To install wiringPi follow the instructions on this page: http://wiringpi.com/download-and-install/

To get a list of wiringPi pin numbers enter gpio readall at the command line.

In newer versions of Raspian wiringPi is installed by default.

Step 1: Pulse Width Modulation

LEDs always run at the same voltage regardless of the brightness. The brightness is determined by a square wave oscillator and the amount of time that the voltage is high determines the brightness. This is called Pulse Width Modulation (PWM). This is controlled by the wiringPi pwmWrite(pin, n) function where n has a value from 0 to 255. If n=2 the LED will be twice as bright as n=1. The brightness always doubles when n doubles. So n=255 will be twice as bright as n=128.

The value of n is often expressed as a percentage called the duty cycle. The pictures show oscilloscope traces for 25, 50 and 75% duty cycles.

Step 2: LED and Resistor

This is not necessary, but having a few of these handy can make breadboarding a lot easier.

Solder a resistor to the short led of an LED. Use a 220-560 Ohm resistor.

Step 3: Un-even Dimming

Build the circuit like in the diagram. This is just like the circuit
to blink an LED. It uses wiringPi pin 1 because you need to use a PWM enabled pin. Compile the program and run it. You will notice that the brighter the LED is the slower it dims. As it gets near the dimmest it will be getting dimmer very fast.

/******************************************************************
 * Compile: gcc -o fade1 -Wall -I/usr/local/include -L/usr/local/lib 
 * fade1.c -lwiringPi
 * 
 * Execute: sudo ./fade1
 *
 * All pin numbers are wiringPi numbers unless otherwise specified.
 ******************************************************************/

#include <wiringPi.h>

int main()
{
  wiringPiSetup();              // Setup required by wiringPi
  pinMode (1, PWM_OUTPUT);      // 
  pwmSetMode(PWM_MODE_MS);      // Mark/Space mode
 
  int i;
 
  while(1)
  {
    for (i = 255; i > -1; i--)
    {
      pwmWrite(1, i);
      delay(10);
    } 

    for (i = 0; i < 256; i++)
    {
      pwmWrite(1, i);
      delay(10);
    }
  }
}

The next step shows how to dim the LED at a constant rate, and in one for statement.

Step 4: Step 4: Up and Down in One For(), and at an Even Rate.

For the LED to dim at a constant rate the delay() must increase at an exponential rate because half the duty cycle will always produce half the brightness.

The line:

int d = (16-i/16)^2;

calculates the inverse square of the brightness to determine the length of the delay. Compile and run this program and you will see that the LED will fade in and out at a constant rate.

/******************************************************************
 * Compile: gcc -o fade1 -Wall -I/usr/local/include -L/usr/local/lib 
 * fade2.c -lwiringPi
 * 
 * Execute: sudo ./fade2
 *
 * All pin numbers are wiringPi numbers unless otherwise specified.
 ******************************************************************/
#include <wiringPi.h>

int main()
{
  wiringPiSetup();              // Setup required by wiringPi
  pinMode (1, PWM_OUTPUT);      // 
  pwmSetMode(PWM_MODE_MS);      // Mark/Space mode

  while(1) 
  {
    int i;
    int x = 1;
    for (i = 0; i > -1; i = i + x)
    {
      int d = (16-i/16)^2;     // calc inverse square of index
      pwmWrite(1, i);
      delay(d);
      if (i == 255) x = -1;   // switch direction at peak
    }
  } 
}

Share

    Recommendations

    • Creative Misuse Contest

      Creative Misuse Contest
    • Oil Contest

      Oil Contest
    • Water Contest

      Water Contest

    Discussions