As usual, the build of this project started with the electronics. The PCBs arrived looking quite good, and you can clearly see that the board design was based around the EPD, with how much space is dedicated to it in the front.
I started by soldering the boost-passthrough voltage converter components, testing them in isolation to make sure the converter works, before assembling the rest of the power supply section and testing it as a whole.
Once I confirmed that the power supply seemed to work fine, there was no reason to subdivide the rest of the circuit into more small sections, as I didn’t really have a way to test them individually anyway – so I soldered all remaining components into place. The EPD was still not attached to the board at this point, for easier testing, and the SCD30 module would be mounted on the 7-pin header in the bottom left later.
At this point, I could power the board up and start working on the firmware for the controller.
Most of the smaller features, like the real-time clock and USB serial communication, were easily handled using Microchip’s official driver libraries. They also provided an EEPROM emulation library, which allowed me to efficiently use some of the controller’s built-in flash memory to store persistent values even if the device lost power, for example, setting values and the time and date.
Communicating with the SCD30 module was also not a problem, as the I2C protocol is supported by the controller’s hardware, and the module-specific data transfer protocol was very simple and easy to use.
Driving the EPD was a different story: On one hand, the display and its driver are designed to be powered down between screen updates, to save power, as EPDs don’t require any power to keep their existing image. To update the image, it was necessary to follow a very specific sequence of power-up, sending data, starting the update, waiting for it to finish, before powering it down again – with certain timing requirements specified by the manufacturer.
With some trial and error, I was able to get the display to update, but it behaved quite weird, taking much longer for the update than it should. However, thanks to some very helpful tips from the Pervasive Displays support team, I finally got it to work as expected and display a test image.
Next, I created some very simple bitmap font files, mostly containing numbers and a few special characters for displaying all the required information. I wrote a small program in C# that allowed me to convert these fonts into C header files, containing the corresponding pixel data in array form, for easy inclusion into the firmware.
Adding a function to process this raw font data and send it to the display, I could now print numbers to the EPD.
With that, the display logic was almost done – I just created a static base design, positioned various number printouts to display all of the relevant information, created a battery charge level icon, and finished it off with a dynamic “status bar” at the bottom, displaying a message for the user if necessary.
After that, only a few pieces of logic were left – like debouncing and handling user button inputs, and giving status indications using the red/green LED at the front.
I assigned the two buttons to be “power/standby” and “measure/calibrate”: The former would switch in/out of “standby” mode on a short press (sensor disabled, low power consumption), and completely switch the system off (blank display) on a long press, while the latter would perform an immediate update of the EPD using the latest sensor data on a short press, and initiate the SCD30’s self-calibration procedure on a long press.
The status LED would glow red while charging, turn green once charging is finished, blink red when the battery is low, and blink green when sensor calibration is recommended.
The remaining settings would be configured over the USB serial interface – date/time, calibration values, measurement and display update intervals, etc.
The device could also be configured to automatically go into standby mode between certain times – for example, to reduce power consumption at night, when the sensor is not needed.
Finally, after attaching the EPD to the circuit board using double-sided tape, the functional part of the project was complete.
The electronics design files and firmware source code are available on GitHub here.
Now I was just missing the enclosure, so it was time to build it!