Lab 2: Serial Communication with Three LED Lights
This assignment expanded and modified the circuit created for Lab 1 by connecting three LED lights (one red, one blue, one green) to the PWM output ports on my Arduino UNO board. After playing around with (pseudo-)analog auto-fading effects for a while, I wrote a serial communication program that allows a computer user to vary the brightness of each LED light by typing the letter "R" (red,) "B" (blue,) or "G" (green,) into the Serial Monitor feature of the Arduino software. The code is written so that the brightness of each light will increase in different increments (Red by 15, Green by 7, Blue by 30) with each keystroke entered.
After completing the program, I created a light diffuser from a semi-translucent plastic drinking cup and a few small wads of cotton. The cup is placed upside-down over the lights to create a "dome" effect. Cotton is placed inside the cup, both to prevent LED glare from reflecting too sharply off the top of the "dome" and to create a shadow texture against which the light pulsates.
Components used:
1 - Arduino UNO Board
3 - 220-ohm resistors
3 - LED lights (1 red, 1 blue, 1 green)
1 - Semi-Translucent Plastic Drinking Cup
1 - USB Power Supply
A few loose pieces of cotton fluff
Code:
/*
* Serial RGB LED
* ---------------
* Serial commands control the brightness of R,G,B LEDs
*
* Command structure is "<colorCode><colorVal>", where "colorCode" is
* one of "r","g",or "b" and "colorVal" is a number 0 to 255.
* E.g. "r0" turns the red LED off.
* "g127" turns the green LED to half brightness
* "b64" turns the blue LED to 1/4 brightness
*
* Created 18 October 2006
* copyleft 2006 Tod E. Kurt <tod@todbot.com
* http://todbot.com/
*/
char serInString[100]; // array that will hold the different bytes of the string. 100=100characters;
// -> you must state how long the array will be else it won't work properly
char colorCode;
int colorVal;
int redPin = 10; // Red LED, connected to digital pin 9
int greenPin = 11; // Green LED, connected to digital pin 10
int bluePin = 9; // Blue LED, connected to digital pin 11
int rValue = 0;
int gValue = 0;
int bValue = 0;
void setup() {
pinMode(redPin, OUTPUT); // sets the pins as output
pinMode(greenPin, OUTPUT);
pinMode(bluePin, OUTPUT);
Serial.begin(9600);
analogWrite(redPin, 127); // set them all to mid brightness
analogWrite(greenPin, 127); // set them all to mid brightness
analogWrite(bluePin, 127); // set them all to mid brightness
Serial.println("enter color command (e.g. 'r43') :");
}
void loop () {
// clear the string
memset(serInString, 0, 100);
//read the serial port and create a string out of what you read
readSerialString(serInString);
for(int i = 0; i < 100; i++){
if(serInString[i] == 'r'){
rValue = rValue + 15;}
if(serInString[i] == 'g'){
gValue = gValue + 7;}
if(serInString[i] == 'b'){
bValue = bValue + 30;}
}
analogWrite(redPin, rValue);
analogWrite(greenPin, gValue);
analogWrite(bluePin, bValue);
delay(100); // wait a bit, for serial data
}
//read a string from the serial and store it in an array
//you must supply the array variable
void readSerialString (char *strArray) {
int i = 0;
if(!Serial.available()) {
return;
}
while (Serial.available()) {
strArray[i] = Serial.read();
i++;
}
}
(Personally, though, I find it more therapeutic just to set the LED to auto-fade and watch the lights pulsate on their own. Ultimately, I would like to be able to create interfaces that allow for complex LED behavior that might produce similar "relaxation" effects while also allowing for user input, but I will need to learn a great deal more about coding before I will be able to do that.)
Code for Fade Effect:
/*
* Code for cross-fading 3 LEDs, red, green and blue, or one tri-color LED, using PWM
* The program cross-fades slowly from red to green, green to blue, and blue to red
* The debugging code assumes Arduino 0004, as it uses the new Serial.begin()-style functions
* Clay Shirky <clay.shirky@nyu.edu>
*/
// Output
int redPin = 9; // Red LED, connected to digital pin 9
int greenPin = 10; // Green LED, connected to digital pin 10
int bluePin = 11; // Blue LED, connected to digital pin 11
// Program variables
int redVal = 255; // Variables to store the values to send to the pins
int greenVal = 1; // Initial values are Red full, Green and Blue off
int blueVal = 1;
int i = 0; // Loop counter
int wait = 2; // 50ms (.05 second) delay; shorten for faster fades
int DEBUG = 0; // DEBUG counter; if set to 1, will write values back via serial
void setup()
{
pinMode(redPin, OUTPUT); // sets the pins as output
pinMode(greenPin, OUTPUT);
pinMode(bluePin, OUTPUT);
if (DEBUG) { // If we want to see the pin values for debugging...
Serial.begin(9600); // ...set up the serial ouput on 0004 style
}
}
// Main program
void loop()
{
i += 1; // Increment counter
if (i < 255) // First phase of fades
{
redVal -= 1; // Red down
greenVal += 1; // Green up
blueVal = 1; // Blue low
}
else if (i < 509) // Second phase of fades
{
redVal = 1; // Red low
greenVal -= 1; // Green down
blueVal += 1; // Blue up
}
else if (i < 763) // Third phase of fades
{
redVal += 1; // Red up
greenVal = 1; // Green low
blueVal -= 1; // Blue down
}
else // Re-set the counter, and start the fades again
{
i = 1;
}
analogWrite(redPin, redVal); // Write current values to LED pins
analogWrite(greenPin, greenVal);
analogWrite(bluePin, blueVal);
if (DEBUG) { // If we want to read the output
DEBUG += 1; // Increment the DEBUG counter
if (DEBUG > 10) // Print every 10 loops
{
DEBUG = 1; // Reset the counter
Serial.print(i); // Serial commands in 0004 style
Serial.print("\t"); // Print a tab
Serial.print("R:"); // Indicate that output is red value
Serial.print(redVal); // Print red value
Serial.print("\t"); // Print a tab
Serial.print("G:"); // Repeat for green and blue...
Serial.print(greenVal);
Serial.print("\t");
Serial.print("B:");
Serial.println(blueVal); // println, to end with a carriage return
}
}
delay(wait); // Pause for 'wait' milliseconds before resuming the loop
}
- Login to post comments