Glowstick a Go-Go

Bunnie Huang prototypes two kinetic glowsticks: instead of creating a single arc of light, glowsticking dancers can now create their own two-dimensional fantasias.

From the column Bunnie's Workbench

By Bunnie Huang

Bill of Materials

When I'm building these kind of prototypes, I almost never choose any part that I cannot find in stock at Digi-Key. There may be other better or cheaper inductors, but they were too hard to acquire for a project like this one.

Qty Digikey P/N Description
10399-1100-1-ND0.1uF 0603 Capacitor
2311-1.0KGCT-ND1k 0603 resistor
1X928CT-ND4 MHz ceramic resonator
1308-11771-1-ND22uH inductor, SMT
3311-47KGCT-ND47k 0603 resistor
2399-1556-1-ND47uF, 6.3V "C" tantalum capacitor
1311-80.6KHCT-ND82k 0603 resistor
1311-100KGCT-ND100k 0603 resistor
1311-200GCT-ND200 ohm 0603 resistor
1311-221KHCT-ND221k 0603 resistor
2311-240KHCT-ND240k 0603 resistor
25230TRK-NDBoard-mount battery connector ends
1H2131-ND6-pin programming header
4743C083181JCT-ND180 ohm resistor array (optional)
16160-1436-1-NDRed LED, 0603 case
867-1820-1-NDRGB combo LED (optional)
3MA3J70000LCT-NDSchottky diode, SOT-23 package
1MAX1676EUB-NDVoltage regulator / MAX1676EUB
4MM74HC595M-ND8-bit shift-register
1PIC16LF876A-I/SS-NDPIC microcontroller
3P8045SCT-NDPush-button switch

Code Listings

Listing 1: code used to implement the FPGA on the first prototype

module top(hdc, led);

    output    hdc;
	 output [15:0] led;

	 reg [23:0] 	 count;
    wire 				 clk, to_bufg;
	 wire [4:0] 	 spriteCnt;
	 wire [3:0] 	 frameCnt;
	 reg [15:0] 	 ledinv;

	 OSC4 oscut (.F8M(), .F500K(), .F16K(to_bufg), .F490(), .F15() ); 
  BUFG bufut (.I(to_bufg), .O(clk)); 

	 assign 			 led[15] = !ledinv[15];
	 assign 			 led[14] = !ledinv[14];
	 assign 			 led[13] = !ledinv[13];
	 assign 			 led[12] = !ledinv[12];
	 assign 			 led[11] = !ledinv[11];
	 assign 			 led[10] = !ledinv[10];
	 assign 			 led[ 9] = !ledinv[ 9];
	 assign 			 led[ 8] = !ledinv[ 8];
	 assign 			 led[ 7] = !ledinv[ 7];
	 assign 			 led[ 6] = !ledinv[ 6];
	 assign 			 led[ 5] = !ledinv[ 5];
	 assign 			 led[ 4] = !ledinv[ 4];
	 assign 			 led[ 3] = !ledinv[ 3];
	 assign 			 led[ 2] = !ledinv[ 2];
	 assign 			 led[ 1] = !ledinv[ 1];
	 assign 			 led[ 0] = !ledinv[ 0];
	 
  always @(posedge clk) begin
			count <= count + 1;
	 end

	 assign spriteCnt[4:0] = count[9:5];
	 assign frameCnt[3:0] = count[19:16];
	 // 130 bpm = 2.167 bps = 0.4615 seconds per beat
	 // four bars = 34.67 seconds
	 // 19 64  about one minute
	 // 18 32 // 16 bars
	 // 17 16 // 8 bars
	 // 16 8  // about four bars  <== set point at four bar points
	 // 15 4  // 2 bars
	 // 14 2  // about one bar
	 // 13 1 second
	 // 12 500 milliseconds
	 // 11 250
	 // 10 125
	 // 9 62.5
	 // 8 31.25 milliseconds
	 // 7 15
	 // 6 7.5  ms

	 always @(spriteCnt or frameCnt) begin
			case( frameCnt )
				4'b000: begin
					casex( spriteCnt ) // smiley face
						5'bx0000:
							ledinv <= 16'b0000001111000000;
						5'bx0001:
							ledinv <= 16'b0000110000110000;
						5'bx0010:
							ledinv <= 16'b0001000000001000;
						5'bx0011:
							ledinv <= 16'b0011000000001100;
						5'bx0100:
							ledinv <= 16'b0110011001100110;
						5'bx0101:
							ledinv <= 16'b0100011001100010;
						5'bx0110:
							ledinv <= 16'b1100000000000011;
						5'bx0111:
							ledinv <= 16'b1000000000000001;
						5'bx1000:
							ledinv <= 16'b1000000000000001;
						5'bx1001:
							ledinv <= 16'b1100100000010011;
						5'bx1010:
							ledinv <= 16'b0100010000100010;
						5'bx1011:
							ledinv <= 16'b0110001111000110;
						5'bx1100:
							ledinv <= 16'b0011000000001100;
						5'bx1101:
							ledinv <= 16'b0001000000001000;
						5'bx1110:
							ledinv <= 16'b0000110000110000;
						5'bx1111:
							ledinv <= 16'b0000001111000000;
					endcase // case( spriteCnt )
				end // case: 4'b000
				4'b001: begin
					 case( spriteCnt ) // rabbit
						 5'b00000:
						 5'b11111:			         
							 ledinv <= 16'b1100110000000011;
					 endcase // case( spriteCnt )
				end
			endcase // case( frameCnt )
			
	 end // always @ (spriteCnt or frameCnt)
	 
	 assign hdc = 1'b1; // always high, so configuration status LED is off

endmodule

Listing 2: Snippet of C code of a PIC function call for displaying data using the second prototype's scheme.

#include <16F876A.h>
#device ICD=TRUE
#use delay(clock=4000000)
#fuses XT,NOWDT,NOPROTECT

#define SD_CLR_MSK 0x10
#define SD_CLK_MSK 0x08
#define SD_RCK_MSK 0x20

void display_green(unsigned long data) {
 char i;
 char db = 0;

 port_c = SD_CLR_MSK;

 // shift the bits in
 for( i = 0; i < 16; i++ ) {
  db = SD_CLR_MSK;
  ((data & 0x8000) == 0x8000) ? (db |= 1) : (db |= 0);
  data <<= 1;

  port_c = db;
  db |= SD_CLK_MSK;
  port_c = db;
  db &= ~SD_CLK_MSK;
  port_c = db;
 }

 // now make it show up
 port_c = SD_RCK_MSK | SD_CLR_MSK;
 port_c = SD_CLR_MSK;

}

Join the conversation -- every MAKE article has an online page that includes a place for discussion. We've made these RSS and Atom feeds to help you watch the discussions: subscribe.

Advertise here with FM.

Why advertise on MAKE?
Read what folks are saying about us!

Click here to advertise on MAKE!

Subscribe to MAKE Magazine!
Important please read

Search the pages of MAKE

Raves for MAKE!

“Now we've got geek DIY (do it yourself) porn. Just as would-be Emerils pore over lushly illustrated cookbooks with recipes involving hard-to-find morels and complicated instructions for roux, Tom Swift wanna-bes are devouring MAKE.”
— Steven Levy, Newsweek

“...O'Reilly Media recently launched what has already become the bible of this new movement, a magazine called MAKE.”
— Daniel Roth, FORTUNE

“If you're the type who views the warnings not to pry open your computer as more a challenge than admonition, MAKE is for you.”
— Rolling Stone

“One of the most innovative magazines I've seen in a long time.”
— Steve Riggio, CEO Barnes & Noble

“The kind of magazine that would impress MacGyver”
— Marcus Chan, San Francisco Chronicle

More Raves for MAKE

Subscribe


Advertise here.
Why advertise on MAKE?
Read what folks are saying about us!

Click here to advertise on MAKE!
Subscribe to MAKE Magazine!