DZone Snippets is a public source code repository. Easily build up your personal collection of code snippets, categorize them with tags / keywords, and share them with the world

Snippets has posted 5883 posts at DZone. View Full User Profile

Fading LEDs With Arduino's Pulse Width Modulation Pins

04.25.2006
| 1696 views |
  • submit to reddit
        This is some code to make pins 9, 10 and 11 on the <a href="http://arduino.cc">Arduino microprocessor board</a>'s Digital I/O <em>fly</em> into Pulse Width Modulation (PWM) mode so that instead of high/low or ON/off, they are able to send variable amounts of current to the pins.  If you hook up 3 LEDs, you can make them fade on and off like a sleeping mac LED.  If you use a 3 color LED, you can make it create different colors from the combination of the light. I didn't write much of this, it's mostly 

Copyleft Melvin Ochsmann for Malmö University

and whatever Steve Cooley for http://somejunkwelike.com

#ifndef cbi
#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#endif
#ifndef sbi
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
#endif

int i;

void timer2PWMOn()
{
  // configure timer 2 for normal (non-inverting) pwm operation
  // this attaches the timer to the pwm pin
  sbi(TCCR2, COM21);
  cbi(TCCR2, COM20);
}

void timer2PWMOff()
{
  // disconnect the timer from the pwm pin
  cbi(TCCR2, COM21);
  cbi(TCCR2, COM20);
}

void timer2PWMSet(unsigned char val)
{
  OCR2 = val;
}





/*
 *  ap_ReadAnalog
 *  
 *  Reads an analog input from the input pin and sends the value 
 *  followed by a line break over the serial port. 
 * 
 *  This file is part of the Arduino meets Processing Project:
 *  For more information visit http://www.arduino.cc.
 *
 *  copyleft 2005 by Melvin Ochsmann for Malmö University
 *
 */

// variables for input pin and control LED
int analogInput = 0;

int i = 0;
int j = 30;
int k = 60;
int i_up = 0;
int j_up = 0;
int k_up = 0;
int theDelay = 10;
int incoming = 0;
int modecounter = 0;

// variable to store the value 
int value = 0;

// a threshold to decide when the LED turns on
int threshold = 512;

void setup(){
  timer2Init();

  // configure timer 2 for phase correct pwm
  // this is better for motors as it ensures an even waveform
  // note, however, that fast pwm mode can achieve a frequency of up
  // 8 MHz (with a 16 MHz clock) at 50% duty cycle
  cbi(TCCR2, WGM21);
  sbi(TCCR2, WGM20);
  pinMode(11, OUTPUT);    
  timer2PWMOn();

  // declaration of pin modes
  pinMode(analogInput, INPUT);
  pinMode(11, OUTPUT);
  pinMode(10, OUTPUT);
  pinMode(9, OUTPUT);
  pinMode(0, INPUT);  

  // begin sending over serial port
  beginSerial(9600);
}

int rx=0;

void loop(){
  // read the value on analog input
  incoming = analogRead(analogInput);
  rx = digitalRead(0);
    theDelay = 30;
  // if value greater than threshold turn on LED

// random colors for 1 second
  for(modecounter=0;modecounter<=10;modecounter++)
  {
    theDelay = 1000;
    analogWrite(9,random(0,100));
    analogWrite(10,random(0,100));
    timer2PWMSet(random(0,100));
    delay(theDelay);
  }

// glowy fadey
  for(modecounter=0;modecounter<=1000;modecounter++)
  {
    theDelay = 30;
    analogWrite(9,i);
    analogWrite(10,j);
    timer2PWMSet(k);
    delay(theDelay);

    if(i_up == 0)
    {
      i++;
    }
    else
    {
      i--;
    }
    if(i >= 100)
    {
      i_up=1;
    } 
    if(i <= 0)
    {
      i_up=0;
    }   

    if(j_up == 0)
    {
      j++;
    }
    else
    {
      j--;
    }
    if(j >= 100)
    {
      j_up=1;
    } 
    if(j <= 0)
    {
      j_up=0;
    }  

    if(k_up == 0)
    {
      k++;
    }
    else
    {
      k--;
    }
    if(k >= 100)
    {
      k_up=1;
    } 
    if(k <= 0)
    {
      k_up=0;
    }  
  }

}
}