Hey everyone,
I'm making a project around an LM355Z temperature sensor module. At the moment, any noise in the sensor makes the LEDs flicker noticeably so I want to do something to fix that.
The Temp sensor connects to an arduino UNO, which drives 3 NPN transistors (R, G and B).
Is there some code I could write to make the flickering smoother? or would it be better to add some kind of capacitor somewhere (either between the sensor and the arduino or between the arduino and the transistor gates)?
Please post real schematics, not toy Fritzings.
When noise is present, attack the noise at the source.
Decoupling capacitors are often needed..... Just to know where to attach them.
Transistors are NPN driven from the arduino with 860 ohm resistors to the gates.
Not sure how to draw a schematic on a computer, so have this whiteboard drawing
D8,9 and 10 are digital pins and A1 and A0 are analog pins to the arduino.
Replied to another comment:
Transistors are NPN driven from the arduino with 860 ohm resistors to the gates.
Not sure how to draw a schematic on a computer, so have this whiteboard drawing
D8,9 and 10 are digital pins and A1 and A0 are analog pins to the arduino.
Now you might post the code here, use the Autoformat tool in the IDE if you need to, then use the Copy for Forum tool in the IDE, then paste here in a new posting.
/*
TEMPERATURE SENSITIVE PC CASE
The aim of this project is to make
a PC case with RGB LEDs that change
colour based on the temperature of
the case. This code was designed on
an arduino UNO/atmega328p using a
TMP36 as the temperature sensor, a
16x2 LCD and NPN transistors to use
for PWM to control the LEDs.
The circuit is designed for 5v.
*/
//import Liquid Crystal library
//this supplies the arduino with the code needed to run the LCD display2
#include <LiquidCrystal.h>
//initialise the LCD
//this tells the arduino which pins to use for sending data to the display
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
//define the sensor pins
//this tells the arduino which pins the inputs are tied to
//sensorPin leads to the TMP36
const int sensorPin = 0;
//potPin leads to the 250k pot
const int potPin = 1;
//define the variables
//this will tell the arduino where to save the sensor data
byte rValue, gValue, bValue;
int switchState, tempReading, potDisplay;
float tempC, Voltage, Kelvin, Celsius, potReading;
//allocate the LED transistors to pins
//these pins must be able to do PWM
const int rPin = 10;
const int bPin = 6;
const int gPin = 9;
void setup()
{
//start the serial monitor
//this allows us to print and read data for debugging
Serial.begin(9600);
//turn on the LCD
//this tells the arduino where to supply power
lcd.begin(16, 2);
// print these words to the LCD to ensure it boots properly:
lcd.print("HELP IM AN LCD!");
lcd.clear();
//define inputs/outputs
//this tells the arduino whether to send or recieve data/power
pinMode (rPin, OUTPUT);
pinMode (bPin, OUTPUT);
pinMode (gPin, OUTPUT);
pinMode (sensorPin, INPUT);
pinMode (potPin, INPUT);
}
void loop()
{
//read the potentiometer to determine the brightness of the LEDs
potReading = analogRead(potPin);
//divide by 1024 to allow for easy maths later on
//potReading variable must be a float to allow for decimals
potReading /= 1024;
Voltage = analogRead(sensorPin);
Kelvin = analogRead(sensorPin) * (0.489); // Read analog voltage and convert it to Kelvin (0.489 = 500/1023)
tempC = Kelvin - 273;
//print the temp to the LCD
lcd.setCursor(0, 0);
lcd.print(tempC);
lcd.print(" degrees");
//print to serial for debugging
Serial.print(tempC); Serial.println(" degrees C");
debug();
//then constrain the temp to be within 0-90 to easily split the gradient
tempC = constrain(tempC, 0, 90);
//map the values to bytes usable for PWM and asign colours
//PWM does not allow for numbers outside of 0-255
if (tempC < 60) {
if (tempC < 30) {
//fade between blue and green
blueGreen();
}
else {
//fade between green and yellow
greenYellow();
}
}
else {
//fade between yellow and red
yellowRed();
}
//write these values as PWM to the transistors
ledWrite();
}
//GRADIENT FUNCTIONS
void blueGreen() {
rValue = 0;
gValue = 255;
bValue = map (tempC, 0, 30, 255, 0);
}
void greenYellow() {
rValue = map(tempC, 30, 60, 0, 255);
gValue = 255;
bValue = 0;
}
void yellowRed() {
rValue = 255;
gValue = map(tempC, 30, 60, 255, 0);
bValue = 0;
}
void ledWrite() {
analogWrite (rPin, rValue * potReading);
analogWrite (gPin, gValue * potReading);
analogWrite (bPin, bValue * potReading);
}
void debug() {
if (tempC > 100) {
lcd.clear();
lcd.print("SENSOR ERROR");
}
}
You're right, I uploaded the wrong code.
This is the correct sketch.
/*
TEMPERATURE SENSITIVE PC CASE
The aim of this project is to make
a PC case with RGB LEDs that change
colour based on the temperature of
the case. This code was designed on
an arduino UNO/atmega328p using a
TMP36 as the temperature sensor, a
16x2 LCD and NPN transistors to use
for PWM to control the LEDs.
The circuit is designed for 5v.
*/
//import Liquid Crystal library
//this supplies the arduino with the code needed to run the LCD display2
#include <LiquidCrystal.h>
//initialise the LCD
//this tells the arduino which pins to use for sending data to the display
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
//define the sensor pins
//this tells the arduino which pins the inputs are tied to
//sensorPin leads to the TMP36
const int sensorPin = 0;
//potPin leads to the 250k pot
const int potPin = 1;
//define the variables
//this will tell the arduino where to save the sensor data
byte rValue, gValue, bValue;
int switchState, tempReading, potDisplay;
float tempC, Voltage, Kelvin, Celsius, potReading;
//allocate the LED transistors to pins
//these pins must be able to do PWM
const int rPin = 10;
const int bPin = 6;
const int gPin = 9;
void setup()
{
//start the serial monitor
//this allows us to print and read data for debugging
Serial.begin(9600);
//turn on the LCD
//this tells the arduino where to supply power
lcd.begin(16, 2);
// print these words to the LCD to ensure it boots properly:
lcd.print("HELP IM AN LCD!");
lcd.clear();
//define inputs/outputs
//this tells the arduino whether to send or recieve data/power
pinMode (rPin, OUTPUT);
pinMode (bPin, OUTPUT);
pinMode (gPin, OUTPUT);
pinMode (sensorPin, INPUT);
pinMode (potPin, INPUT);
}
void loop()
{
//read the potentiometer to determine the brightness of the LEDs
potReading = analogRead(potPin);
//divide by 1024 to allow for easy maths later on
//potReading variable must be a float to allow for decimals
potReading /= 1024;
Voltage = analogRead(sensorPin);
Kelvin = analogRead(sensorPin) * (0.489); // Read analog voltage and convert it to Kelvin (0.489 = 500/1023)
tempC = Kelvin - 273;
//print the temp to the LCD
lcd.setCursor(0, 0);
lcd.print(tempC);
lcd.print(" degrees");
//print to serial for debugging
Serial.print(tempC); Serial.println(" degrees C");
debug();
//then constrain the temp to be within 0-90 to easily split the gradient
tempC = constrain(tempC, 0, 90);
//map the values to bytes usable for PWM and asign colours
//PWM does not allow for numbers outside of 0-255
if (tempC < 60) {
if (tempC < 30) {
//fade between blue and green
blueGreen();
}
else {
//fade between green and yellow
greenYellow();
}
}
else {
//fade between yellow and red
yellowRed();
}
//write these values as PWM to the transistors
ledWrite();
}
//GRADIENT FUNCTIONS
void blueGreen() {
rValue = 0;
gValue = 255;
bValue = map (tempC, 0, 30, 255, 0);
}
void greenYellow() {
rValue = map(tempC, 30, 60, 0, 255);
gValue = 255;
bValue = 0;
}
void yellowRed() {
rValue = 255;
gValue = map(tempC, 30, 60, 255, 0);
bValue = 0;
}
void ledWrite() {
analogWrite (rPin, rValue * potReading);
analogWrite (gPin, gValue * potReading);
analogWrite (bPin, bValue * potReading);
}
void debug() {
if (tempC > 100) {
lcd.clear();
lcd.print("SENSOR ERROR");
}
}
This is an integer calculation, which amplifies small differences in temperature into large differences in intensity. You specify that a 30 degree range in temperature is mapped into 255 levels of intensity.
Thus, a one degree change in temperature results in a change of 8 to 9 in LED intensity.
Furthermore, since human vision responds nonlinearly to intensity, the effect is further amplified for low levels of illumination.
I suggest to rethink how the temperature is mapped to colors and intensity. It is far more difficult that most people realize to find an effective mapping. Search for "heat map table".
Do you mean the LM335Z, and why that sensor.
It's from the analogue times (50+ years ago), and a poor match for 5volt processors.
The LM35 or TMP36 would have been much better, because you could have used the more stable internal reference from the Uno. Best solution would be a digital DS18B20.
Leo..