Make Your Own Power Meter/Logger
Intro: Make Your Own Power Meter/Logger
In this project I will show you how I combined an Arduino, an INA219 power monitor IC, an OLED LCD and a Micro SD Card PCB in order to create a power meter/logger that has more functions than the popular USB Power Meter. Let's get started!
STEP 1: Watch the Video!
The video gives you a good overview on how to create your own power meter. In the next steps though I will present you some additional information to make this project even simpler.
STEP 2: Order Your Parts!
Here you can find a parts list with example seller for the portable version of this project (affiliate links).
Aliexpress:
1x LiPo Battery: https://s.click.aliexpress.com/e/_dZhZsnd
1x TP4056 Board: https://s.click.aliexpress.com/e/_dX8n0hp
1x Arduino Pro Mini: https://s.click.aliexpress.com/e/_d62ALdV
1x INA219 Board: https://s.click.aliexpress.com/e/_dUZvYoX
1x OLED LCD: https://s.click.aliexpress.com/e/_dWfFi0n
1x SD Card PCB: https://s.click.aliexpress.com/e/_dUy68bd
1x Switch: http://amzn.to/2gz9ZtW
Ebay:
1x TP4056 Board: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
1x Arduino Pro Mini: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
1x INA219 Board: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
1x OLED LCD: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
1x SD Card PCB: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
1x Switch: http://rover.ebay.com/rover/1/711-53200-19255-0/1?...
Amazon.de:
1x LiPo Battery: http://amzn.to/2gM2vXB
1x TP4056 Board: http://amzn.to/2eUvMNO
1x Arduino Pro Mini: http://amzn.to/2g6Ujjr
1x INA219 Board: http://amzn.to/2gM5M9v
1x OLED LCD: http://amzn.to/2g6Q3Rd
1x SD Card PCB: http://amzn.to/2gM9Zdf
STEP 3: Create the Circuit!
Here you can find the schematic for the Arduino Nano version and the portable version of this project. You can also find those schematic on the EasyEDA website:
https://easyeda.com/GreatScott/PowerMeter-b6051723...
https://easyeda.com/GreatScott/PortablePowerMeter-...
You can also use the pictures of my finished board as a reference for your own.
STEP 4: Upload the Code!
Now that your circuit is complete, it is time to upload the code. You can download it here. But don't forget to download and include the following libraries before uploading:
https://github.com/adafruit/Adafruit_INA219
https://github.com/adafruit/Adafruit_SSD1306
https://github.com/greiman/SdFat
You can find an improved version of my code here: https://github.com/gilleshenrard/datalogger
STEP 5: Success!
You did it! You just created your own Power Meter/Logger
Feel free to check out my YouTube channel for more awesome projects:
http://www.youtube.com/user/greatscottlab
You can also follow me on Facebook, Twitter and Google+ for news about upcoming projects and behind the scenes information:
75 Comments
meatwad010 3 months ago
I can make up from the video that the + of the device I want to check the power of is connected to the V- of the Ina219 sensor. And the - of the device I want to check the power of is connected to Ground. But what is connected to the V+ on the Ina219? Is that the + of the powersupply of the device I want to check the power of?
danishfernandes5 2 years ago
Geekineer 2 years ago
markvictoreid 2 years ago
FlorinA8 3 years ago
#include <Wire.h>
#include <Adafruit_INA219.h>
#include <Adafruit_SSD1306.h>
#include <Adafruit_GFX.h>
#include <SPI.h>
#include "SdFat.h"
#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 32 // OLED display height, in pixels
#define OLED_RESET -1
#define ROTATION 0
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
Adafruit_INA219 ina219;
unsigned long previousMillis = 0;
unsigned long interval = 100;
const int chipSelect = 10;
float shuntvoltage = 0;
float busvoltage = 0;
float current_mA = 0;
float loadvoltage = 0;
float power_mW = 0;
float energy = 0;
SdFat SD;
File TimeFile;
File VoltFile;
File CurFile;
void setup() {
display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
display.clearDisplay(); // Clear the display
display.display();
display.setRotation(ROTATION); // Set Rotation
display.setTextSize(1); // Set text size
display.setTextColor(WHITE);
delay(2000);
ina219.begin();
SD.begin(chipSelect);
}
void loop() {
unsigned long currentMillis = millis();
if (currentMillis - previousMillis >= interval)
{
previousMillis = currentMillis;
ina219values();
displaydata(); //subroutines display
TimeFile = SD.open("TIME.txt", FILE_WRITE);
if (TimeFile) {
TimeFile.println(currentMillis);
TimeFile.close();
}
VoltFile = SD.open("VOLT.txt", FILE_WRITE);
if (VoltFile) {
VoltFile.println(loadvoltage);
VoltFile.close();
}
CurFile = SD.open("CUR.txt", FILE_WRITE);
if (CurFile) {
CurFile.println(current_mA);
CurFile.close();
}
}
}
void displaydata() {
display.clearDisplay();
display.setTextColor(WHITE);
display.setTextSize(1);
display.setCursor(0, 0);
display.println(loadvoltage);
display.setCursor(35, 0);
display.println("V");
display.setCursor(50, 0);
display.println(current_mA);
display.setCursor(95, 0);
display.println("mA");
display.setCursor(0, 10);
display.println(loadvoltage * current_mA);
display.setCursor(65, 10);
display.println("mW");
display.setCursor(0, 20);
display.println(energy);
display.setCursor(65, 20);
display.println("mWh");
display.display();
}
void ina219values() {
shuntvoltage = ina219.getShuntVoltage_mV();
busvoltage = ina219.getBusVoltage_V();
current_mA = ina219.getCurrent_mA();
loadvoltage = busvoltage + (shuntvoltage / 1000);
power_mW = ina219.getPower_mW();
energy = energy + loadvoltage * current_mA / 3600;
}
2016n2552 3 years ago
utamadonny10 4 years ago
shuntvoltage = ina219.getShuntVoltage_mV();
busvoltage = ina219.getBusVoltage_V();
current_mA = ina219.getCurrent_mA();
loadvoltage = busvoltage + (shuntvoltage / 1000);
energy = energy + loadvoltage * current_mA / 3600;
why shuntvoltage divide by 1000 dan curren_mA is divided by 3600??
waltsfo 4 years ago
Dividing seconds by 3600 (60x60) gives hours.
hm010120 4 years ago
this is a great project! I just reviewed it and I have a quick question about the calculation for the energy. In my understanding, the calculation of the energy is not 100% correct as the time interval is missing. I would propose for the calculation of the energy --> energy = energy + loadvoltage * interval * current_mA / 3600.
What is your opinion about that?
Regards
JohnT184 3 years ago
This was my formula which can be rearranged but I found it easier to follow in it's current format.
energy = energy + (power / (3600 * (1000/interval)));
gulshanmishra02 3 years ago
kevinbeninca 4 years ago
hajerjr4 3 years ago
AlrickH 6 years ago
hi, congrats and thanks for a great video. I want to make a similar project but i need to monitor more current like upto 24 volts and 21 Apms.......what you suggest i do, or replace in the your given circuit? Hope to get a quick reply.
DerekB103 4 years ago
SÅ‚awomirS 3 years ago
mlhanes 5 years ago
bassbindevil 3 years ago
aoti100 4 years ago
Adafruit GFX Library 1.7.5
Adafruit INA219 1.0.6
Adafruit SSD1306 2.2.0
SdFat - Adafruit Fork 1.2.3
Thanks for help Regards Alex
===========================================================
#include // Serial Peripheral Interface comunication SD reader writer module
#include // Wire bus comunication I2C on SCL SDA display SD1306 and Ina219
#include // Display SSD1306 library
#include // Display shape library
#include // INA219 board library current voltage reader
#include //SD comunication library
#define SCREEN_WIDTH 128 // OLED display width in pixels
#define SCREEN_HEIGHT 64 // OLED display height in pixels
#define OLED_RESET 4 // Reset pin # (or -1 if sharing Arduino reset pin)
#define ROTATION 0
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
Adafruit_INA219 ina219;
unsigned long previousMillis = 0;
unsigned long interval = 100;
const int chipSelect = 10;
float shuntvoltage = 0;
float busvoltage = 0;
float current_mA = 0;
float loadvoltage = 0;
float power_mW = 0;
float energy = 0;
SdFat SD;
File TimeFile;
File VoltFile;
File CurrentFile;
void setup() {
display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
display.clearDisplay(); // Clear the display
display.display(); // Flushes all changes to the display hardware
display.setRotation(ROTATION); // Set Rotation
display.setTextSize(1); // Set text size
display.setTextColor(WHITE);
delay(2000);
ina219.begin();
SD.begin(chipSelect);
}
void loop() {
unsigned long currentMillis = millis();
if (currentMillis - previousMillis >= interval)
{ previousMillis = currentMillis;
ina219values(); //subroutines reading
displaydata(); //subroutines display
// Write on files - Time - Volt - Current
TimeFile = SD.open("Time.txt", FILE_WRITE);
if (TimeFile) {
TimeFile.println(currentMillis);
TimeFile.close();
}
VoltFile = SD.open("Volt.txt", FILE_WRITE);
if (VoltFile) {
VoltFile.println(loadvoltage);
VoltFile.close();
}
CurrentFile = SD.open("Current.txt", FILE_WRITE);
if (CurrentFile) {
CurrentFile.println(current_mA);
CurrentFile.close();
}
}
}
void ina219values()
{
shuntvoltage = ina219.getShuntVoltage_mV(); // V across shunt V+ and V-
busvoltage = ina219.getBusVoltage_V(); // V across V- and Gnd
current_mA = ina219.getCurrent_mA(); // I across the shunt
loadvoltage = busvoltage + (shuntvoltage / 1000);
power_mW = ina219.getPower_mW();
energy = energy + loadvoltage * current_mA / 3600;
}
void displaydata() {
display.clearDisplay();
display.setCursor(0, 0);
display.println("Voltage:");
display.setCursor(60, 0);
display.println(loadvoltage);
display.setCursor(100, 0);
display.println("V");
display.setCursor(0, 10);
display.println("Current:");
display.setCursor(60, 10);
display.println(current_mA);
display.setCursor(100, 10);
display.println("mA");
display.setCursor(0, 20);
display.println("Power:");
display.setCursor(60, 20);
display.println(loadvoltage * current_mA);
display.setCursor(100, 20);
display.println("mW");
display.setCursor(0, 30);
display.println("Energy:");
display.setCursor(60, 30);
display.println(energy);
display.setCursor(100, 30);
display.println("mWh");
display.display();
}
Craig12345 4 years ago