Self-Powered Arduino Voltmeter (12-90v DC)

by CanadianWinters in Circuits > Arduino

1128 Views, 1 Favorites, 0 Comments

Self-Powered Arduino Voltmeter (12-90v DC)

Arduino self-powered Volt Meter (12-90v DC)

In this instructable, I've built a voltmeter to measure high voltages DC (12-100v) with relative precision and accuracy using an Arduino Nano, an ADS 1115 ADC, a dc/dc converter, and an Oled Display.

This is very similar to one of my previous instructable: here, but in this case, the voltmeter does not need any external power supply.

Supplies

For the actual board I used:

1 x Arduino Nano - Link

1 x Oled Display (SSD 1306) - Link

1 x ADS 1115 - 16 bit ADC - Link

1 x 1/4W (I suggest using 1W resistors though) 1% Resistors - 690k ohm - Link

1 x 1/4W (I suggest using 1W resistors though) 1% Resistors - 10k ohm - Link

I had my own PCB produced, but you can use Breadboard and wires for testing - Link

Digital DMM - Link

DC/DC converter ( XH-M298) - Link

To test the voltmeter you can use: 9V Batteries - Link, or an electric bicycle charger - Link, or a lab power supply - Link


For the project box:

I used a 3D printer to print the box. I created the.STL file in Openscad and then imported it into Tinkercad to create the holes for the OIed display and wiring.

Design file - Link

Filament - Link

3D Printer - Link


CanadianWinters is a participant in the Amazon Services LLC Associates Program, an affiliate advertising program designed to provide a means for sites to earn fees by linking to Amazon.com and affiliated sites. By using these links, as an Amazon Associate, I earn from qualifying purchases, even if you buy something else--and it won't cost you anything.

The Circuit

ArduinoselfpowVolt_fritzing.png
ArduinoselfpowVolt_schem.png

I connected the Dc-Dc converter first and tested it with my ebike battery charger (Vout at ~54v), to make sure the Dc-Dc output was 12v.

Once I verified this detail, I connected all the other parts as per the schematics above.

I tied the ADDR pin of the ADC1115 to ground. This sets the address of the ADC to 0x48.

The Code and Resistor Calculations

Arduino_code_precise.png

As in the previous Instructables, the idea of the circuit is that the DC voltage to be measured goes through a voltage divider. The scaled voltage and then gets into the analog pin of the ADC converter to be read, then passed to the Arduino via I2C, and then re-scaled and displayed on the OLed display.


I made a spreadsheet that automates the calculations in case you want to use different resistor values in the voltage divider: Link to Google Sheet . Please note that you won't be able to modify the sheet. You can simply download it on your PC and you will then be able to edit it.

Here is the code I used for this project:

#include <Arduino.h>
#include <U8g2lib.h>
#include <Adafruit_ADS1015.h>
#include <Wire.h>
Adafruit_ADS1115 ads(0x48); //Adress of the ADC

U8G2_SSD1306_128X64_NONAME_F_HW_I2C u8g2(U8G2_R0);// (rotation, [reset])
int calib = 7; // Value of calibration of ADS1115 to reduce error
float voltage =0; // used to store voltage value
float Radjust = 0.01430684; // (for 690K resistior) Voltage divider factor ( R2 / R1+R2 )
float vbat =0; //final voltage after calcs- voltage of the battery

//variables for refreshing the screen without using delay
unsigned long previousMillis = 0;        // will store last time the screen was refreshed

// constants won't change:
const long interval = 250;           // interval at which to refresh the screen (milliseconds)


void setup(void) {
  Serial.begin(9600);
  u8g2.begin();
  ads.begin();
   
}


void loop(void) {


int16_t adc0; // 16 bits ADC read of input A0
adc0 = ads.readADC_SingleEnded(0);
voltage = ((adc0 + calib) * 0.1875)/1000;


unsigned long currentMillis = millis();

vbat = voltage/Radjust;

//Prevent displaying negative voltage when battery/power is disconnected  
 if (vbat < 0.1) {
        vbat = 0.01;
 }  
// Setting the delay for the screen refresh using Millis 
   
  if (currentMillis - previousMillis >= interval) {
       previousMillis = currentMillis;


  u8g2.clearBuffer();          // clear the internal menory
 
//Pack Voltage display - Fonts at this page: https://github.com/olikraus/u8g2/wiki/fntlistall
  //u8g2.setFont(u8g2_font_fub20_tr);  // 20px font 
  u8g2.setFont(u8g2_font_fub35_tr);  // 35px font 
  u8g2.setCursor (1, 42);
  u8g2.print(vbat,2);
  u8g2.setFont(u8g2_font_8x13B_mr);  // 10 px font
  u8g2.setCursor (1, 60);
  u8g2.print("Volts");
   
 }
  u8g2.sendBuffer();          // transfer internal memory to the display
  delay(1);
}


Test!

ArduinoselfpowVolt_Test..png

To test this voltmeter I used my electric bicycle charger and the battery pack that comes with the bike. The charger is set to 54.4/54.5v.

I tested the voltage against my digital multi-meter and everything checks out!

I really like that the voltmeter is self-powered and nicely packaged in the 3D-printed enclosure.

I hope you enjoyed this Instructable and let me know your thoughts!