Controlling High Power Circuits With Arduino and Darlington ULN2803
by RU4Realz in Circuits > Arduino
46329 Views, 63 Favorites, 0 Comments
Controlling High Power Circuits With Arduino and Darlington ULN2803
Each of the digital i/o pins on the Arduino can only source or sink 40mA, and pushing the Arduino past these limits may damage it. If you need to get a little more power out of your outputs, try using a Darlington ULN2803.
The Darlington chip can source up to 500mA of current out each pin, and operates at up to 50V, so it's beefy enough to drive motors, incandescent bulbs, relays, solenoids and more. You can find the datasheet here. The
Darlington output pins can even be connected in parallel for higher current capability.
Get this IC at Digikey 296-19046-5-ND or at Sparkfun COM-00312
The Darlington chip can source up to 500mA of current out each pin, and operates at up to 50V, so it's beefy enough to drive motors, incandescent bulbs, relays, solenoids and more. You can find the datasheet here. The
Darlington output pins can even be connected in parallel for higher current capability.
Get this IC at Digikey 296-19046-5-ND or at Sparkfun COM-00312
Example: Driving a Large 7 Segment Display
I used a Darlington ULN2803 with an Arduino to control a giant common anode 7-segment display from Evil Mad Scientist.
Normal sized 7-segment displays consist of 7 rectangular leds arranged so that they can display the numbers 0-9. Lighting up one segment of a normal 7-segment display is equivalent to lighting up an LED, it requires about 3V and 20mA; this is easily accomplished by the Arduino alone. This giant seven segment is a little different because each of the segments consists of 4 parallel sets of 15 red LEDs wires in series (fig 2). To turn on the LEDs, the voltage across the segment should be 15*(forward voltage of each LED) and the current through each segment is 4*(typical operating current of each LED). This comes out to about 31.5V(15*2.1V) and 80mA(4*20mA) per segment, clearly the Arduino will not be able to handle this on its own.
To control this display I hooked up the common anode to 36V and then selectively grounded the segments of the display that I wanted to light up.
The code below counts through the numbers 0-9 on the 7-segment display, ticking from one number to the next once a second. It uses a for loop to increment the variable "i" from 0-9, and then uses switch/case statements to turn the appropriate segments on (by setting their corresponding Arduino pin high.
Normal sized 7-segment displays consist of 7 rectangular leds arranged so that they can display the numbers 0-9. Lighting up one segment of a normal 7-segment display is equivalent to lighting up an LED, it requires about 3V and 20mA; this is easily accomplished by the Arduino alone. This giant seven segment is a little different because each of the segments consists of 4 parallel sets of 15 red LEDs wires in series (fig 2). To turn on the LEDs, the voltage across the segment should be 15*(forward voltage of each LED) and the current through each segment is 4*(typical operating current of each LED). This comes out to about 31.5V(15*2.1V) and 80mA(4*20mA) per segment, clearly the Arduino will not be able to handle this on its own.
To control this display I hooked up the common anode to 36V and then selectively grounded the segments of the display that I wanted to light up.
The code below counts through the numbers 0-9 on the 7-segment display, ticking from one number to the next once a second. It uses a for loop to increment the variable "i" from 0-9, and then uses switch/case statements to turn the appropriate segments on (by setting their corresponding Arduino pin high.
/*7 seg display with ULN2803 by RU4Realz July 2012 arduino pin connections (via ULN2803): arduino (digital) pin 0 7 seg pin f 1 g 2 a 3 b 4 c 5 d 6 e */ void setup() { for (byte a=0;a<8;a++){ pinMode(a,OUTPUT);//set digital pins 0 - 6 as outputs } } void loop() { for (byte i = 0; i < 10; i++){//for 0 -9 switch(i){ case 0://if i == 0, turn on appropriate leds PORTD&=128;//turn digital 0-6 off digitalWrite(0,HIGH); digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); digitalWrite(5,HIGH); digitalWrite(6,HIGH); break; case 1://if i == 1 PORTD&=128;//turn digital 0-6 off digitalWrite(3,HIGH); digitalWrite(4,HIGH); break; case 2://if i == 2 PORTD&=128;//turn digital 0-6 off digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(5,HIGH); digitalWrite(6,HIGH); break; case 3: PORTD&=128; digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); digitalWrite(5,HIGH); break; case 4: PORTD&=128;//turn digital 0-7 off digitalWrite(0,HIGH); digitalWrite(1,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); break; case 5: PORTD&=128;//turn digital 0-7 off digitalWrite(0,HIGH); digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(4,HIGH); digitalWrite(5,HIGH); break; case 6: PORTD&=128;//turn digital 0-7 off digitalWrite(0,HIGH); digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(4,HIGH); digitalWrite(5,HIGH); digitalWrite(6,HIGH); break; case 7: PORTD&=128;//turn digital 0-7 off digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); break; case 8: PORTD&=128;//turn digital 0-7 off digitalWrite(0,HIGH); digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); digitalWrite(5,HIGH); digitalWrite(6,HIGH); break; case 9: PORTD&=128;//turn digital 0-7 off digitalWrite(0,HIGH); digitalWrite(1,HIGH); digitalWrite(2,HIGH); digitalWrite(3,HIGH); digitalWrite(4,HIGH); break; } delay (1000);//wait 1 sec } }