Jan
30
2009
0

Project: LED Firefly Lights – Post #5 Real Firefly Test

Click here to see the entire LED FireFly Lights Project.

Now that I’ve got my firefly test LEDs to fade in and out randomly (Project: LED Firefly Lights – Post #4 Random Fade Test) I’ve decided to try to replicate what real fireflies look like when they flash.  I’ve found this video on youtube that shows how they flash and it also shows a some LED firefly lights a company in California has made called FireFly Magic.

Get the Flash Player to see the wordTube Media Player.

For the code I mostly just inverted the DelayOn and DelayOff. I did add an extra #define to take the place of the direction 1 or -1 so I could easily change the speed at which I change the LED brightness. I also changed the name of the fade variable in the LED structure to FadeDelay. To see the old version of the code check out Post #4.

Here is what the test fireflies look like now; they don’t blink as fast as real fireflies my wife prefers them to go a bit slower. The speed can easily be changed by changing the #define constants.

Get the Flash Player to see the wordTube Media Player.

Here is the new code:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
#include <avr/io.h>
#include <avr/interrupt.h>
#include <stdlib.h>
 
volatile unsigned int vCount = 0;
volatile unsigned char vPORTA = 0;
volatile unsigned char vPORTB = 0;
volatile unsigned char vPORTC = 0;
volatile unsigned char vPORTD = 0;
volatile unsigned char vPORTE = 0;
 
#define cLED_CNT 16
#define cFADEDELAY 3
#define cDELAYOFFMAX 1500
#define cDELAYON 1
#define cBRIGHTMAX 100
#define cFADESPEED 5
 
struct LED
{
  char Port;
  char Bit;
  int Brightness;
  int Direction;
  int DelayOn;
  int DelayOff;
  int FadeDelay;
};
 
volatile struct LED LEDArray[cLED_CNT];
 
 
/* Main Function */
int main(void)
{
  int vI;
 
  /* Initialize Timer0 */
 
    // Enable timer0 compare interrupt
  TIMSK0 = (1<<OCIE0A);
 
    // Sets the compare value
  OCR0A = 12;
 
  // Set Clear on Timer Compare (CTC) mode, prescaler
  TCCR0A = (1<<WGM01)|(0<<WGM00)|(3<<CS00);
 
  /* Initialize Ports for output */
  DDRA = 0xFF;
  DDRB = 0xFF;
  DDRC = 0xFF;
  DDRD = 0xFF;
  DDRE = 0xFF;
 
  /* Initialize LED Array */
  for(vI = 0; vI < cLED_CNT; vI++)
  {
    if (vI < 8)
    {
      LEDArray[vI].Port = 'B';
      LEDArray[vI].Bit = vI;
    }
    else
    {
      LEDArray[vI].Port = 'D';
      LEDArray[vI].Bit = vI - 8;
    }
    LEDArray[vI].Brightness = 0;
    LEDArray[vI].Direction = cFADESPEED;
    LEDArray[vI].DelayOff = (rand() % cDELAYOFFMAX) + 1;
    LEDArray[vI].DelayOn = cDELAYON;
    LEDArray[vI].FadeDelay = cFADEDELAY;
  }   
 
  // Enable Interrupts
  sei();
 
   // Main program loop
   while(1) {   }
 
   return 0;
}
 
/* Handle Timer Interrupt */
ISR (TIMER0_COMP_vect)
{
  int vI = 0;
 
  vCount++;
  if (vCount >= 100) vCount = 0;
  if (vCount == 0) 
  {
    //vPORTA = 0xFF;
    vPORTB = 0xFF;
    //vPORTC = 0xFF;
    vPORTD = 0xFF;
    //vPORTE = 0xFF;
  }
 
  for (vI = 0; vI < cLED_CNT; vI++)
  {
    if ((LEDArray[vI].Brightness <= 0) | (LEDArray[vI].Brightness == vCount))
    {
      switch (LEDArray[vI].Port)
      {
        case 'A': vPORTA &= ~(1 << LEDArray[vI].Bit);break;
        case 'B': vPORTB &= ~(1 << LEDArray[vI].Bit);break;
        case 'C': vPORTC &= ~(1 << LEDArray[vI].Bit);break;
        case 'D': vPORTD &= ~(1 << LEDArray[vI].Bit);break;
        case 'E': vPORTE &= ~(1 << LEDArray[vI].Bit);break;
      }
    }
    if (vCount == 0) 
    {
      LEDArray[vI].DelayOff--;
      if (LEDArray[vI].DelayOff == 0)
      {
        LEDArray[vI].DelayOff = 1;
        LEDArray[vI].FadeDelay--;
        if (LEDArray[vI].FadeDelay == 0)
        {
          LEDArray[vI].FadeDelay = cFADEDELAY;
          LEDArray[vI].Brightness += LEDArray[vI].Direction;
          if (LEDArray[vI].Brightness >= cBRIGHTMAX) 
          {
            LEDArray[vI].Brightness = cBRIGHTMAX-1;
            LEDArray[vI].DelayOn--;
            if (LEDArray[vI].DelayOn == 0)
            {
              LEDArray[vI].Direction = -1 * cFADESPEED;
              LEDArray[vI].DelayOn = cDELAYON;
            }
          }
          if (LEDArray[vI].Brightness <= 0) 
          {
            LEDArray[vI].Direction = cFADESPEED;
            LEDArray[vI].DelayOff = (rand() % cDELAYOFFMAX) + 1;
          }  
        }
      }
    }
  }
  //PORTA = vPORTA;
  PORTB = vPORTB;
  //PORTC = vPORTC;
  PORTD = vPORTD;
  //PORTE = vPORTE;
}
Jan
29
2009
0

Project: LED Firefly Lights – Post #4 Random Fade Test

Click here to see the entire LED FireFly Lights Project.

In the previous post I showed how I faded an entire bank of LED lights. Since then I’ve added another bank of LEDs to make sure my code works with multiple banks. So the total LED count is 16. I connected the LEDs through a resistor to Ports B & D on the AVR Butterfly as shown in the picture below. I had to disconnect the piezo speaker on the back of the Butterfly since it is also connected to pin 5 of Port B.

fireflytestbutterflyportsbd-thumb fireflytestledbanksbd-thumb


I’ve been playing around with randomizing the LEDs so they don’t all turn on and off at the same time.

To create a random number in C you can use the rand( ) function declared in the stdlib.h library. In my code I use the following statement to generate a random delay for each LED.

LEDArray[vI].DelayOn = (rand() % cDELAYONMAX) + 1;

LEDArray[vI].DelayOn is an integer variable that is part of my LED structure used to store the random number in.

rand( ) function returns a pseudo-random integral number in the range 0 to RAND_MAX where RAND_MAX = 0x7FFF which is declared in the stdlib.h library.

% Modulus computes the remainder that results from performing integer division.

cDELAYONMAX is a constant I declare to give me the maximum random number I want to generate. Currently I’ve set this to 1500.

I’ve created an LED structure to group the variable I need to control the LEDs.

struct LED
{
  char Port;
  char Bit;
  int Brightness;
  int Direction;
  int DelayOn; 
  int DelayOff;
  int FadeSpeed;
};

Port variable sets the Port the LED is located on.
Bit variable sets which pin the LED is located on.
Brightness variable controls the current brightness of the LED in percent 0 to 100.
Direction variable controls whether the LED is fading in or out. 1 is in and -1 is out.
DelayOn contains a random number that sets how long the LED will stay on.
DelayOff contains how long the LED will stay off.
FadeSpeed controls how fast the LED will fade on and off.

Here is a video that shows the LEDs randomly fading in and out:

Get the Flash Player to see the wordTube Media Player.

Here is my code, it may not be the best way to do it but it works:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
#include <avr/io.h>
#include <avr/interrupt.h>
#include <stdlib.h>
 
volatile unsigned int vCount = 0;
volatile unsigned char vPORTA = 0;
volatile unsigned char vPORTB = 0;
volatile unsigned char vPORTC = 0;
volatile unsigned char vPORTD = 0;
volatile unsigned char vPORTE = 0;
 
#define cLED_CNT 16
#define cFADESPEED 5
#define cDELAYONMAX 1500
#define cDELAYOFF 5
#define cBRIGHTMAX 100
 
struct LED
{
  char Port;
  char Bit;
  int Brightness;
  int Direction;
  int DelayOn; 
  int DelayOff;
  int FadeSpeed;
};
 
volatile struct LED LEDArray[cLED_CNT];
 
/* Main Function */
int main(void)
{
  int vI;
 
  /* Initialize Timer0 */
 
  // Enable timer0 compare interrupt
  TIMSK0 = (1 << OCIE0A);
 
  // Sets the compare value
  OCR0A = 12;
 
  // Set Clear on Timer Compare (CTC) mode, prescaler
  TCCR0A = (1 << WGM01) | (0 << WGM00) | (3 << CS00);
 
  /* Initialize Ports for output */
  DDRA = 0xFF;
  DDRB = 0xFF;
  DDRC = 0xFF;
  DDRD = 0xFF;
  DDRE = 0xFF;
 
  /* Initialize LED Array */
  for(vI = 0; vI < cLED_CNT; vI++)
  {
    if (vI < 8)
    {
      LEDArray[vI].Port = 'B';
      LEDArray[vI].Bit = vI;
    }
    else
    {
      LEDArray[vI].Port = 'D';
      LEDArray[vI].Bit = vI - 8;
    }
      LEDArray[vI].Brightness = cBRIGHTMAX;
      LEDArray[vI].Direction = -1;
      LEDArray[vI].DelayOn = (rand() % cDELAYONMAX) + 1;
      LEDArray[vI].DelayOff = cDELAYOFF;
      LEDArray[vI].FadeSpeed = cFADESPEED;
  }
 
  // Enable Interrupts
  sei();
 
  // Main program loop
  while(1) {   }
 
  return 0;
}
 
/* Handle Timer Interrupt */
ISR (TIMER0_COMP_vect)
{
  int vI = 0;
 
  vCount++;
  if (vCount >= 100) vCount = 0;
  if (vCount == 0)
  {
    //vPORTA = 0xFF;
    vPORTB = 0xFF;
    //vPORTC = 0xFF;
    vPORTD = 0xFF;
    //vPORTE = 0xFF;
  }
 
  for (vI = 0; vI < cLED_CNT; vI++)
  {
    if ((LEDArray[vI].Brightness <= 0) | (LEDArray[vI].Brightness == vCount))
    {
      switch (LEDArray[vI].Port)
      {
        case 'A': vPORTA &= ~(1 << LEDArray[vI].Bit);break;
        case 'B': vPORTB &= ~(1 << LEDArray[vI].Bit);break;
        case 'C': vPORTC &= ~(1 << LEDArray[vI].Bit);break;
        case 'D': vPORTD &= ~(1 << LEDArray[vI].Bit);break;
        case 'E': vPORTE &= ~(1 << LEDArray[vI].Bit);break;
      }
    }
    if (vCount == 0)
    {
      LEDArray[vI].DelayOn--;
      if (LEDArray[vI].DelayOn == 0)
      {
        LEDArray[vI].DelayOn = 1;
        LEDArray[vI].FadeSpeed--;
        if (LEDArray[vI].FadeSpeed == 0)
        {
          LEDArray[vI].FadeSpeed = cFADESPEED;
          LEDArray[vI].Brightness += LEDArray[vI].Direction;
          if (LEDArray[vI].Brightness <= 0)
          {
            LEDArray[vI].Brightness = 0;
            LEDArray[vI].DelayOff--;
            if (LEDArray[vI].DelayOff == 0)
            {
              LEDArray[vI].Direction = 1;
              LEDArray[vI].DelayOff = cDELAYOFF;
            }
          }
          if (LEDArray[vI].Brightness == cBRIGHTMAX)
          {
            LEDArray[vI].Direction = -1;
            LEDArray[vI].DelayOn = (rand() % cDELAYONMAX) + 1;
          }
        }
      }
    }
  }
  //PORTA = vPORTA;
  PORTB = vPORTB;
  //PORTC = vPORTC;
  PORTD = vPORTD;
  //PORTE = vPORTE;
}
Jan
21
2009
0

Project: LED Firefly Lights – Post #3 LED Fade Test

Well I’ve finally made some progress on my LED FireFly Lights Project.

First I’m using the AVR Butterfly to prototype it, which has the ATmega169 AVR. It doesn’t come with any connectors so I got some samples from Samtec (their sudden service is great for fast overnight free samples!)

I then setup a bank of LEDs on my solderless bread board.

I connected each LED to a pin on Port D of the AVR Butterfly plus power & ground:

I then struggled a bit trying to figure out how to get the timer on the ATmega169 to work. After figuring out the timer I wrote a quick little program that fades the bank of LEDs on and off. I’m using pulse width modulation (PWM) to vary the brightness of the LEDs by changing the duty cycle. I decided to start with 100Hz for the PWM frequency which I may change later.

Here is what is looks like…sorry so dark:

Get the Flash Player to see the wordTube Media Player.

Here is what the output signal looks like on an oscilloscope:

Get the Flash Player to see the wordTube Media Player.

And here is my code:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#include <avr/io.h>
#include <avr/interrupt.h>
 
volatile unsigned char vDuty = 1;
volatile unsigned char vCount = 0;
volatile unsigned int vDimm = 0;
volatile unsigned int vSpeed = 400;
volatile char vDir = 1;
 
/* Main Function */
int main(void)
{
  /* Initialize Timer0 */
  // Enable timer0 compare interrupt
  TIMSK0 = (1 << OCIE0A);
  OCR0A = 12;  // Sets the compare value
  // Set clear on timer compare (CTC) mode, prescaler
  TCCR0A = (1 << WGM01) | (0 << WGM00) | (3 << CS00);
 
  /* Initialize PortD */
  DDRD = 0xFF;  // Set PortD for all Outputs
  PORTD = 0x00;  // Clear PortD Pins
  sei();  // Enable Interrupts
 
  /* Main Program Loop */
  while(1) { /* Do Nothing */}
 
  return 0;
}
 
/* Handle Timer Interrupt */
ISR (TIMER0_COMP_vect)
{
  vCount++;
  if (vCount >= 100) vCount = 0;
  if (vCount == 0) PORTD = 0xFF;
  if (vCount == vDuty) PORTD = 0x00;
  vDimm++;
  if (vDimm == vSpeed)
  {
    vDimm = 0;
    vDuty += vDir;
    if (vDuty == 75) vDir = -1;
    if (vDuty == 1) vDir = 1;
  }
}

Click here to see the rest of my Project: LED Firefly Lights.

Jan
14
2009
0

Project: LED Firefly Lights – Post #2 Store Bought Jar

My wife found this jar that contains 4 LEDs made to look like fireflies on a twig.  My wife likes how they fade in and out so this is the effect she is looking for.  She found the jar at a craft store, I don’t remember the name of the store.  She asked if they make them in a larger strand but unfortunately they don’t, so I guess it’s up to me to build it.  (I’m not going to put wings and legs on the LEDs my wife can do that if she really wants to.)  I have not torn this apart yet to see what is controlling it but I’m sure I will someday.  Here is what the jar looks like:

fireflyjar

 

I could try to describe how the LEDs fade in and out but it’s easier just to post a video:

Get the Flash Player to see the wordTube Media Player.

In the video it looks like the LED flickers but I think that is just a product of the video frame rate, they really don’t flicker just fade out and then back in. I’m not sure how many I need in the playhouse tree…I’m thinking maybe about 20 will be enough.

Click here to see the rest of my Project: LED Firefly Lights.

Jan
14
2009
0

Project: LED Firefly Lights – Post #1 Introduction

My wife has been “bugging” me for some time to make her some Firefly Lights out of LEDs.  She has made a playhouse in our basement for our son and it has a fantasy theme.  On one side of the playhouse there is a tree that looks like it has grown out of the playhouse and into the ceiling.  She has done a great job and it is looking really cool.  Now she wants it to look like there are fireflies in the tree that randomly blink on and off.

playhouse

Now that I have the AVR tools I think it will be pretty easy to do this using a microcontroller.  More to come.

LED Firefly Lights – Project Index

  1. 01-14-2009 – Project Introduction
  2. 01-14-2009 – Store Bought Jar
  3. 01-21-2009 – LED Fade Test
  4. 01-29-2009 – Random Fade Test
  5. 01-30-2009 – Real Firefly Test

Powered by WordPress. Theme: Aeros 2.0 by TheBuckmaker.com.