Wednesday, November 15, 2017

The energy monitor: Collecting the data?

Now that summer is over, it's time to get started on projects again. In particular, the Energy monitor has been something I've been toying with for a while. I've gone through a few iterations on this, mostly on how to collect the data from the monitored devices. I'm still planning on using a custom-built AC to DC conversion board for the current loops, but collecting the data has been problematic.

Originally, I thought I'd go with a specialty board that was capable of reading the sensors and peripherals directly, but that was difficult to get data out of. For some reason, it lacked SNMP facilities. Second thought was a Raspberry Pi. While quite a capable machine, the device needs to be really robust. In comes Arduino. While the Arduino doesn't have (for the most part) native network capabilities, it's easy enough to connect it to just about anything that can read serial, so it's still going to require a computer to collect and process the data. But it also gives the ability to have a device that simply turns on and works, and can have it's own display and simple alerts in case the monitoring computer fails.

Right now, I'm using an Arduino Uno. The speed is fine for collecting data, but the memory space is limiting me on how many things I can do with this unit. I'll probably end up moving to a larger device, like a Mega, but this is working for now.

First thing to do was to install the IDE and actually learn some code. I'm not really the best at C code, but there are enough examples of what to do (and plenty of pre-written libraries) that I'm able to walk through building some useful code. In this case, display libraries from Adafruit and the BMP180 library from Sparkfun were loaded into the IDE. From there, it was a simple matter of taking portions of the examples to get a usable program.

#include <Wire.h>
#include <SFE_BMP180.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define OLED_RESET 4
Adafruit_SSD1306 display(OLED_RESET);

SFE_BMP180 pressure;
#define ALTITUDE 274.93

  // set up the analog reads
  
  int furcur = 0;
  int furval = 0;
  float famp = 0;
  float fmul = 102.4;
  float inhg = 0;
  int i = 0;
  
void setup() {

  // clear the display and set the size/color (white is visible)

  display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  display.clearDisplay();
  display.display();
  display.setTextColor(WHITE);
    
  // serial? why not?
  
  Serial.begin(9600);

  // check to see if the bmp180 is ok

  if (pressure.begin())
  {
    display.setCursor(0,0);
    display.setTextSize(2);
    display.print("BMP180 OK!");
    display.setCursor(0,16);
    display.print("FMON WAIT!");
    display.display();
    display.setTextSize(1);
  }
    else
  {
    Serial.println("BMP180 init fail\n\n");
    // while(1); // Pause forever.
  }

}

  char status;
  double T,P,p0,a;

void loop() {

  // get the analog value(s)

  furval = analogRead(furcur);
  famp=furval/fmul;

  Serial.print("r");
  Serial.print(furval);
  Serial.print(" a");
  Serial.print(famp);
  
  // get the pressure and temperature
  
  status = pressure.startTemperature();
  if (status != 0)
  {
    delay(status);
    status = pressure.getTemperature(T);
    if (status != 0)
    {
      Serial.print(" t");
      Serial.print(T,2);
      status = pressure.startPressure(3);
      if (status != 0)
      {
        delay(status);
        status = pressure.getPressure(P,T);
        if (status != 0)
        {
          Serial.print(" p");
          Serial.print(P);
        }
        else Serial.println("error retrieving pressure measurement\n");
      }
      else Serial.println("error starting pressure measurement\n");
    }
    else Serial.println("error retrieving temperature measurement\n");
  }
  else Serial.println("error starting temperature measurement\n");

  Serial.println(" OK");

  // only update disp every x seconds
  
  i=i+1;
  if (i>30)
  {
    i=0;
    display.clearDisplay();
    display.display();
    display.setCursor(0,0);
    display.println("Furnace Room Monitor");
    display.setCursor(0,8);
    display.print("Furnace ");
    display.print(furval);
    display.print(" / ");
    display.print(famp);
    display.print("A");
    display.setCursor(0,24);
    display.print("T ");
    display.print((9.0/5.0)*T+32.0,2);
    display.print("F ");
    display.print("P ");
    display.print(P*0.0295333727,2);
    display.print("inHg");
    display.display(); 
  }


  delay(250);
}


This portion of code does almost everything that the energy monitor is going to be doing, save reading one-wire devices. I don't really have enough memory for that at the moment, so I'll probably get another Uno and try to run them side by side. In particular, this code reads an analog pin which will be the current input from the current loop/amplifier assembly, and converts it to an actual current value (1024 = 10 Amps.) The Uno then reads a BMP180 Pressure/Temperature sensor, converts it to specified units, and throws the whole mess out on the serial line (raw) and display (user-friendly units.)

The display itself is a simple I2C 128x32 from a well-known auction site. This display requires that you fill the display buffer then flush it with a display.display();. This in itself is somewhat problematic, since the display has to consume a block of RAM. In addition, you can't easily write over top of what's there without re-writing the whole display, so to minimize flicker the code only refreshes the display every 30 iterations. The unit is still throwing out values every 250ms, but the display is slower. I could format things a little better and overwrite the changed values with spaces before writing new ones, but this works for now. Working first, optimize later.

What I ended up with, which seems to be pretty decent for not knowing diddly this morning, looks like this as far as data output is concerned:



This is the raw current read, the actual amps, the temperature in DegC, and the pressure in mb. I'll probably remove the actual amps from the finished product and let the processing computer handle that.

The working, and unimpressive hardware looks something like this:



Next step is to try and get the 1-wire library working as desired, then put both portions of code together.

Tuesday, November 7, 2017

Time to get started again.

Summer's over, so it's time to get busy on all these projects again!

Sunday, February 26, 2017

Boards, boards, boards...but everything sure does look nice!

Things are moving along nicely for the energy monitor, and I've had a lot of fun designing boards for everything. As soon as I can get everything stuffed, I'll probably pull the old wireless sensors off the wall and put the new boxes in. 

The multivolt expansion boards came back from the manufacturer, and are ready to be stuffed. I have the jacks onboard, but nothing else - the LEDs, power conditioning, and input connectors will have to wait until I have more time.


Here's the family, in various states of assembly...

A couple of things to note, I decided to use some TO-92 heatsinks I'd collected over the years as a heat collector. That is, the DS18x20 in the upper left (sorry, black on black is hard to see...) now has a heatsink on it. Instead of getting rid of heat, it should get more surface area exposed to the air and hopefully provide a more accurate temperature measurement.

Second, and this is entirely my fault, the parts I ordered were not DS18S20, as claimed by the vendor, but DS18B20, which won't work at all if your device is expecting an older part. I ordered them, was told they were correct, and set them aside (without checking) until far too late. While some of the special-purpose embedded devices I use can't see them, I'm lucky that my chosen control board for this system has no problem with them. I learned my lesson: Always check your parts on arrival!

Last, but not least, as the loop expansion boards seem to work, I'm going to beef up the V+ tracks and send them off to have a production run made. I've seen a lot of board houses that can run 100 units for about $120, and use special color and masks to boot. Probably should order a  sample run first, though...

Tuesday, February 7, 2017

The one-wire-loop expansion board.

Yesterday evening, I received my generic expansion board (The One-Wire-Loop) back from OSHPark, and everything looks good. While I had originally planned this as a one-wire board, I figure it can work equally as well for any low-speed data, like serial or I2C.

The first example built up, sans the DS18X20 in the lower right corner, is ready to test in a live system.


With this board and the precision rectifier, I should be ready to start hooking up devices in their final configuration. Now, to just find the time...

Wednesday, January 25, 2017

Accessories and peripherals time!

Part of any good system is the amount of expansion that it offers. As I'm building my own components, I can build in as much expansion as I want.

As most of my components are going to run on 1-wire or powered I2C, I chose to go with the venerable modular jack for an expansion interface - in this case, the "5222" 6P6C style connector. They're common enough that you can buy them bulk for a few dollars on the web.

Since boards are so cheap, I've laid out my own board. 6 "5222" connectors, with the capability to add both power and a DS1820 sensor (if using 1-wire systems.) Otherwise, the DS1820 can be omitted. There's some minor power filtering on the board, and the 1-oz copper should handle 800mA or so with no issues. Anything more than that would be cabled direct anyway.



The top of the board offers the I/O connectors, an LED for any power that may be supplied, and a spot for a DS1820 sensor. Currently, I'm using AVTech Room Alert devices, and this board's DS1820 sensor is wired to follow their color code. That's completely optional for other devices. There's also a pullup resistor wired into the Data/VCC lines. There's a lot of discussion on the necessity of this, but it's there. Just in case...


The bottom has the filtering for the power and the resistors for the LED and pullup. A IPC-7351\Chip-CaseC capacitor for ripple smoothing and a single 0805 for high-frequency noise reduction. All mount holes are ground plane.

The boards are shared on OSHPark, feel free to use them.

There's not a whole lot going on, but I can make these by the dozen and drop them in where needed.


5222 "6P4C" connectors. Just remember the pin numbers are different than a 6P6C!

Wednesday, January 18, 2017

Testing the precision rectifier circuit...are those parts marked right?

My boards came back from OSHPark late yesterday afternoon, so I went ahead and built one up this morning. Most of the parts came from new stock or the shop's parts inventory, but the diodes did not - germanium diodes are easy to get if you buy packs of surplus Soviet parts on eBay, but buyer beware!

As with the other boards I've purchased from OSHPark, all the text was nice and clear, holes were clear, and the solderability of the board was excellent. It went together quickly and easily.

(In retrospect, I should have noticed the diodes weren't right, but I haven't worked with Ge diodes for so long...)

Some quick checks on the board revealed that I had made a stupid wiring error. The input voltage was reversed. I have no idea why, other than I just didn't run the traces correctly. That was a simple fix, cut a track and run a couple of jumpers. After that, it came right up, all LEDs lit and no smoke!

Second issue was the LEDs are drawing way too much current. While 20mA isn't much, I want to keep the total draw down as much as possible, so I'm going to increase the current limiting resistors to 4.7k. I need them lit, not lighting up the inside of the box.

So, those problems are taken care of, and I've got it hooked into the electrical system here at the shop for testing, but it's not acting like I think it should. Everything is floating around way too much, and the outputs are going negative...

That shouldn't happen. I immediately suspect the diodes.

Off to the bench, a quick meter check reveals that the bands on the diodes are actually on the anode! Looking closer, I can see the point contact to the Ge is under the bands. Go figure! (Someone mentioned that it was marked like a selenium device...)

Here's a closeup, and you can see the cup with the wire coming out, and just make out the semiconductor material under the bands. What I find odd about this whole thing is I've seen other examples of this diode, and they were marked correctly. Oh well, now I know.


(The Russian D9E, or so the package says!)

With the diodes in correctly, it goes back to the test rig. Now, everything is working just as it should!


Perfect. The output jumps when my device activates!

The current transformers are just clipped on to the input to the box. I'm not worried about how much, just the absence or presence of current in this case. Calibration will come when the devices are secured and can't move around.


This test is successful. Time to button up the panel and get ready to build one for myself, and think about where things are going to be installed.

Wednesday, January 4, 2017

The energy monitor begins to take shape.

One of the interesting things the CAI board offers is some analog 10V inputs - DC of course, but this is perfect for getting some sort of data back into the system. It just so happens the clips I purchased for the energy monitor work in this range, so...we're back on!

First thing is to wrap up the board necessary to get the voltage off the current clip and into the system. Since I'm also designing a similar project for my employer, that was easy enough, and an order from OSHPark later, I have a board getting ready to be spun up (and partially paid for by said employer!)


This is the same precision rectifier circuit that I was working with last month, except the board is now laid out, a power converter chosen ( the EC3SA-12D05N from mouser.com ) and other parts ordered.

Other than the power converter, it's pretty old-school. TL084 op-amps and germanium diodes, chosen for their low voltage drop. If you want to order a set of boards for yourself, the project is shared on OSHPark's website, but I would suggest waiting until I can verify I didn't do something stupid, and can get a parts list together.

I should have them in about 2 weeks. Until then...