Display sensor values

nRF52 bluefruit adafruit LiPo uv temperature humidity veml6075 si7021

Pre-requisites

Display UV and temperature / humidity sensor values with a LiPo.

Hardware used:

  1. Adafruit Bluefruit nRF52 breakout board
  2. Adafruit SHARP Memory Monochrome Display Breakout 168x144 pixels
  3. Adafruit UV sensor VEML 6075 breakout board
  4. Adafruit Temperature/Humidity sensor Si7021 breakout board
  5. LiPo 1200mAh 3.7V

Code

Download code
#include <Adafruit_GFX.h>
#include <Adafruit_SharpMem.h>
#include <Wire.h>
#include "Adafruit_VEML6075.h"
#include "Adafruit_Si7021.h"

Adafruit_VEML6075 uv = Adafruit_VEML6075();
Adafruit_Si7021 sensor = Adafruit_Si7021();

#define SHARP_SCK  12
#define SHARP_MOSI 13
#define SHARP_SS   7

#define VBAT_PIN          (A7)
#define VBAT_MV_PER_LSB   (0.73242188F)   // 3.0V ADC range and 12-bit ADC resolution = 3000mV/4096
#define VBAT_DIVIDER      (0.71275837F)   // 2M + 0.806M voltage divider on VBAT = (2M / (0.806M + 2M))
#define VBAT_DIVIDER_COMP (1.403F)        // Compensation factor for the VBAT divider

Adafruit_SharpMem display(SHARP_SCK, SHARP_MOSI, SHARP_SS, 144, 168);

#define BLACK 0
#define WHITE 1

bool debug = false; // toggle true or false to enable serial console debug messages

struct SensorValues {
  int vbat_raw;
  uint8_t vbat_per;
  float vbat_mv;

  float uvindex;
  float uva;
  float uvb;

  float humidity;
  float temperature;
};

void setup(void) {
  if (debug) {
      Serial.begin(115200);
  }

  initDisplay();
  initUVSensor();
  initTempHumiditySensor();
  initBatt();
}

void loop(void) {
  SensorValues v = getSensorValues();

  display.clearDisplay();

  displayBatt(v.vbat_raw, v.vbat_per, v.vbat_mv);
  displayUV(v.uvindex, v.uva, v.uvb);
  displayTempHumidity(v.temperature, v.humidity);

  display.refresh();
  delay(4000);
}

void initDisplay(void) {
  display.begin();

  display.setRotation(0);
  display.setTextSize(2);
  display.setTextColor(BLACK);

  display.clearDisplay();
}

void initUVSensor(void) {
  if (! uv.begin() && debug) {
    Serial.println("Failed to communicate with VEML6075 sensor, check wiring?");
  }
  if (debug) {
    Serial.println("Found VEML6075 sensor");
  }
}

void initTempHumiditySensor(void) {
  if (!sensor.begin() && debug) {
    Serial.println("Failed to communicate with Si7021 sensor, check wiring?");
  }
  if (debug) {
    Serial.println("Found Si7021 sensor");
  }
}

void initBatt(void) {
  analogReference(AR_INTERNAL_3_0);
  analogReadResolution(12); // Can be 8, 10, 12 or 14
  delay(1);
}

uint8_t mvToPercent(float mvolts) {
    uint8_t battery_level;

    if (mvolts >= 3000) {
        battery_level = 100;
    }
    else if (mvolts > 2900) {
        battery_level = 100 - ((3000 - mvolts) * 58) / 100;
    }
    else if (mvolts > 2740) {
        battery_level = 42 - ((2900 - mvolts) * 24) / 160;
    }
    else if (mvolts > 2440) {
        battery_level = 18 - ((2740 - mvolts) * 12) / 300;
    }
    else if (mvolts > 2100) {
        battery_level = 6 - ((2440 - mvolts) * 6) / 340;
    }
    else {
        battery_level = 0;
    }

    return battery_level;
}

void displayBatt(int vbat_raw, uint8_t vbat_per, float vbat_mv) {
  if (debug) {
    Serial.print("ADC = ");
    Serial.print(vbat_raw * VBAT_MV_PER_LSB);
    Serial.print(" mV (");
    Serial.print(vbat_raw);
    Serial.print(") ");
    Serial.print("LIPO = ");
    Serial.print(vbat_mv);
    Serial.print(" mV (");
    Serial.print(vbat_per);
    Serial.print("%)");
  }
}

void displayUV(float uvindex, float uva, float uvb) {
  if (debug) {
    Serial.print(", UV Index: ");
    Serial.print(uvindex, 2);
    Serial.print(", UVA: ");
    Serial.print(uva, 2);
    Serial.print(", UVB: ");
    Serial.print(uvb, 2);
  }

  display.setCursor(10,10);
  display.println("UV index");
  display.setCursor(10,30);
  display.println(uvindex, 0);

  display.setCursor(10,65);
  display.print("UVA ");
  display.println(uva, 0);

  display.setCursor(10,85);
  display.print("UVB ");
  display.println(uvb, 0);
}

void displayTempHumidity(float temperature, float humidity) {
  if (debug) {
    Serial.print(" Temperature: ");
    Serial.print(temperature, 2);
    Serial.print("°C, Humidity: ");
    Serial.print(humidity, 2);
    Serial.println(" RH%");
  }

  display.setCursor(10,120);
  display.print("Temp ");
  display.print(temperature, 0);
  display.println(" C");

  display.setCursor(10,140);
  display.print("Hum ");
  display.print(humidity, 0);
  display.println(" RH%");
}

SensorValues getSensorValues(void) {
  int vbat_raw = analogRead(VBAT_PIN);

  SensorValues v = {
    vbat_raw,
    mvToPercent(vbat_raw * VBAT_MV_PER_LSB),
    (float)vbat_raw * VBAT_MV_PER_LSB * VBAT_DIVIDER_COMP,

    uv.readUVI(),
    uv.readUVA(),
    uv.readUVB(),

    sensor.readHumidity(),
    sensor.readTemperature()
  };

  return v;
}

Serial console

Serial output from the firmware.

Display sensor values serial console

Prototype

A photo of the actual setup.

Display sensor values prototype

Schematic

Wire up the hardware accordingly

Display sensor values schematic

References