This instructable describes how to design an Arduino controlled power supply source.
A short video presenting its work can be seen in my Youtube channel
Step 1: Design Ideas, Used Approach...
The purpose of the project was to create a small power supply block with extended functions :
- To be able to communicate with computer, which could set the output voltage and to be able to control the device to produce output voltage with some specific performance (special ramp up forms, having different values at specific time periods..etc.)
- To be able to store the desired voltage value and at the consequent power up to settle on it
- To be able to change its output depending on the readings of different analog sensors
...Based on these requirements I decided to to use Arduino as main controller for the power supply block.
I wanted also to implement the device using as much as possible ready modules, instead designing my own PCB. Following this directive I found that the use of Arduino Nano should be the best choice. You can by it for ~ 2 USD at ebay. There I found also a nice DIY power supply kit based on LM317. ( LM317 may be is not the most suitable part for this design. Why, I shall explain further, but having this nice kit, I decided to use it :-) )To be able to control the output voltage I decided to use a digital potentiometer in its feedback loop. I have chosen to use the 8 bit Microchop I2C part MCP4562. (the datasheet is attached). It was 10K (Not really nice chose for LM317 - why? Will be explained later ).Of course another type of digital potentiometer can be used also - for example SPI controlled, or 7 bit....To mount the digital potentiometer chip I have used SOI8 to DIP8 adapter board.
Step 2: Design Step 1
As first step I have soldered the LM317 KIT. The mechanical potentiometr from the KIT was put in my parts collection for some future project.
Step 3: Design Step 2
I have soldered Female pin header to the Arduino board, which should serve as interface to the external world.
Step 4: Design Step 3
I have soldered the digital potentiometr chip on the SOI8 to DIP8 adapter board. There I have placed also two 20KOhm resistors between the SDA,SCL pins and Vcc needed for the I2C communication.
Step 5: Design Step 4
I have soldered the digipot board on the place of the mechanical one. To supply it temporary I have used additional 7805 regulator (After that disconnected). At start up the digital potentiometer sets its wiper at middle value. The output voltage is nice defined.
Step 6: Design Step 5
To control the output voltage I decided to use a rotary encoder connected to the arduino. It has also push button.
I have soldered the button ground pin together with the middle pin of the rotary encoder - the blue wire.
Step 7: Full Schemaitic of the Device
Here you can see the full schematic of the power supply block.
I would like to make here the following explanations:
- The digital potemtiometer is I2C type - it communicates with the arduino through it SDA,SCL pins (A4 and A5 arduino pins)
- The arduino is supplied by the rectified, but not regulated input voltage of the power supply kit. - This limits the input, also the output voltage to acceptable for arduino voltage of ~ 12V DC. If higher input voltage is needed, the arduino must be supplied by some intermediate regulator chip (for example 7808,7809,7812)
- The produced by the arduino board 5V is used as supply voltage for the digital potentiometer.
- The button is connected to the digital arduino pin 4. It uses the library "Button", attached here. Pressing the button forces the arduino to store the current voltage value.The LEd indicator blinks 5 times for conformation.
- The A0, A1 pins of the digipot are grounded. This determines its device address to 0101100 (44 DEC). For additional info see the datasheet.
- Here I will explain the problem with the LM317. Its output voltage is determined by the formula:
VO = VREF (1 + R2 / R1) + (IADJ × R2);
where R1 is 240 Ohm.
R2 is the value of the digital potentiometer,
Iadj ~ 50uA
There is limit of the maximum voltage over the digital potentiomer set to 5.5V. The voltage drop over R1 is 1.25V.
This limits the total output voltage at 6.75V and prevents using of the LM317 regulator chip for higher needed voltages.
If such are required - other regulator shall be used. There are different types, in which the reference voltage appears between the ground node and the adjustment pin and connecting there a digital potentiometer will be absolutely problem less. To keep my potentiometer safe, I limited also its value to less than 1 KOhm, connecting additional 1 KOhm resistor in parallel with it. Using the formula above it gives a maximum output voltage of ~ 6 V. Adding this parallel resistor changes the linearity of the output voltage dependence on the digital code. (see the graph). In some cases this could be useful - the resolution for higher voltages is better, then for lower, which are used rarely. But, if you want to use LM317, it is better to use 1 KOhm digipot and to omit the parallel resistor.
- At the arduino pin 5 I have connected a LED. In my version of the program its intensity depends on the output voltage - I use PWM signal controlled by the same digital word used for the digipot.
- The rotary encoder is connected to the arduino pins 2 and 3 - I use the hardware interrupts 0 and 1 to read the rotary encoder state.
In this schematic the pull-up resistors connected between SDA, SCL and the supply are not shown. I have soldered them on the small digipot adapter board.
Step 8: Design Step 6
I have extracted a transformer from old AC/DC adapter.
Step 9: Assembling....
To assemble the device, I have used a plastic box bought from a local store.
I drilled all the needed holes in it using dremel like tool and small piles.
The transformer I fixed by the use of epoxy glue.
Step 10: Assembling Continues...
The arduino board was fixed also with epoxy glue.
The regulator board was mounted on the bottom of the box by screws and spacers.
For the fixing of the LED voltmeter I used again epoxy glue.
Step 11: Additional Hardware Changes....
As described before, this device is able to store its current voltage and at next power up to settle on it.
My first idea was to use for that purpose the internal EEPROM of the digital potentiometer - its stored value is loaded very fast at power up and the voltage is set very quickly. But, unfortunately I was not able to write in the digipot EEPROM. The reasons are few :
- its WP (write protect bit) is set by default and requires high voltage writing. I lost a lot of time trying to reset it, but without success
- This digital potentiometer is 8 bit (257 steps). It requires 10 bit data to be sent. The "wire" library of the arduino normally works with whole bytes. I did not want to lose additional time changing the whole library to be able to communicate properly with the digital potentiometr. Now two resistor steps are missing, but this is not problem for me - I write in the digipot only one byte, which defines 255 steps instead the possible 257. Using 7 bit digipot could solve the problem. In all cases, I was not able to make the writing in the device EEPROM work.
I decided then to use the internal EEPROM of the arduino ATmega328 chip to store the voltage digital value.
Using the arduino for that purpose creates additional problem - the arduino needs a second~two to boot, to start the program and to communicate with the digital potentiometer. This delay causes that the output voltage is set at the start up by the internally stored in the digital potentiometer value (by default the middle pot value), and after some time, it settles to the programmed by the arduino value. This could be dangerous in some cases - a low voltage device supplied by this source could be damaged, until its proper voltage is set. To prevent this and make the things safer, I have added a small soft start block. It is based on the NMOS transistor BS123. When the rectified voltage appears, its gate is pulled up by the electrolytic capacitor.This closes the MOS transistor, which is connected in parallel with the digipot resistor, and shorts it to the ground, keeping the output voltage low for some time, until the arduino wakes up. The electrolytic capacitor is after some time charged throw the resistor to the ground and the MOS gate potential goes low, what opens the transistor and the output voltage returns to its default value.
On the pictures can be seen this small board soldered near the digipot board.
Step 12: Codding Time
The arduino code is attached.
It can be modified by you according your needs.
It is simple code. Can be understood easy.
May be the most complicated there is the reverse calculation - when you type the target voltage value in the serial monitor, and it calculates the digital word, which must be written in the digital potentiometer register. This calculation is based on the formula given before for the output voltage of the LM317 regulator. In my case it becomes more complicated because of the parallel connected 1 KOhm resistor. If you do not use it - the code will be simpler.
I would suggest you to measure precisely by DMM the exact values of R2, the parallel resistor (if used), the digipot resistor ( at power up it sets its half value - measure it and multiply by 2), the reference voltage - the voltage drop over R2. Having these correct values, the inverse calculation will be more precise. Have in mind that the voltage meter included in the kit is not very precise - especially for low voltages.
The functionality of this block can be further developed by adding Ethernet options, wifi modules...etc. The output voltage can be controlled through Internet, can be done dependent on different analog sensor measurements...
I leave these new ideas on your imagination and fantasy.