3magku
Created July 30, 2017 © CC BY

Be(e) Sensitive!

A sensor equipped solitary bee observation nest box.

IntermediateWork in progress7 hours181

Things used in this project

Hardware components

Arduino 101
Arduino 101
×1
SparkFun Humidity and Temperature Sensor Breakout - HTU21D
×1
Capacitive Touch Sensor Breakout - MPR121
Adafruit Capacitive Touch Sensor Breakout - MPR121
×1
GY-30 (BH1750FVI) Digital Light Intensity Sensor Module
×1
Jumper wires (generic)
Jumper wires (generic)
×1
Miscellaneous: Cigar box, acrylic plate, wood, screws, aluminium foil, glue
×1
Breadboard (generic)
Breadboard (generic)
×1

Software apps and online services

Arduino IDE
Arduino IDE
Adafruit Library: HTU21D-F Humidity + Temp sensor
SparkFun Library: MPR121 Capacitive Touch Sensor Breakout Board
Library: Digital light sensor breakout boards containing the BH1750FVI IC
Microsoft Bluetooth LE Explorer

Hand tools and fabrication machines

Miscellaneous: Electric drill/screwdriver, wood drill bits, ...

Story

Read more

Custom parts and enclosures

Solitary Bee Observation Nest Box (01)

Solitary Bee Observation Nest Box (02)

Aluminium foil patches and wires to be placed on near the entry holes and to be connected to the MPR121.

Solitary Bee Observation Nest Box (03)

Sensors, breadboard, wiring ...

Solitary Bee Observation Nest Box (04)

Sensors, breadboard, wiring ...

Solitary Bee Observation Nest Box (05)

Solitary Bee Observation Nest Box (06)

Solitary Bee Observation Nest Box (07)

Arduino 101 and battery ...

Solitary Bee Observation Nest Box (08)

Schematics

BeeSensitive - Fritzing

BeeSensitive - Wiring

Code

BeeSensitive.ino

Arduino
/* Be(e) Sensitve
*/

/*
   Imports
*/

// Curie BLE support
#include <CurieBLE.h>

// I2C support
#include <Wire.h>

// Each I2C is connected like
// 3,3V/VIN/VCC to 3,3V
// GND to ground
// SCL to I2C clock pin = A5
// SDA to I2C data pin  = A4

// HTU21D
#include "Adafruit_HTU21DF.h"

// MPR121 support
#include "mpr121.h"

// BHT1750 support
#include <BH1750.h>


/*
   BLE Peripheral
*/

BLEPeripheral blePeripheral; // BLE peripheral device
BLEService beeNestBoxService("273335a0-7576-11e7-b5a5-be2e44b06b34"); // BLE service
// BLE characteristics
BLEIntCharacteristic  beeNestBoxTemperature("27333cb2-7576-11e7-b5a5-be2e44b06b34",BLERead | BLENotify);
BLEIntCharacteristic  beeNestBoxHumidity("27333e06-7576-11e7-b5a5-be2e44b06b34", BLERead | BLENotify);
BLEUnsignedIntCharacteristic  beeNestBoxLightIntensity("27333eec-7576-11e7-b5a5-be2e44b06b34", BLERead | BLENotify);
BLEUnsignedIntCharacteristic  beeNestBoxCapacitySensorReading("27334054-7576-11e7-b5a5-be2e44b06b34", BLERead | BLENotify);

/*
   HTU21D
*/

Adafruit_HTU21DF htu21d;;
int htu21d_temperature = 0;
int htu21d_humidity = 0;

/*
   MPR121
*/

int mpr121_irqpin = 2;  // D2
uint16_t mpr121_pins = 0;

/*
   BH1750
*/

BH1750 bh1750;
uint16_t bh1750_lux = 0;

/*
   misc.
*/

int updateDelay = 30000;
long previousMillis = 0;  // last time the heart rate was checked, in ms

/*
   setup() & loop ()
*/

void setup() {
  Serial.begin(115200); // Initialize serial communication
  pinMode(13, OUTPUT);  // Initialize the LED on pin 13 to indicate when a BLE central is connected
  setup_HTU21D();
  delay(100);
  setup_MPR121();
  delay(100);
  setup_BH1750();
  delay(100);
  setup_BLE();
}

void loop() {
  // Listen for BLE centrals to connect:
  BLECentral central = blePeripheral.central();
  // If a central is connected to peripheral:
  if (central) {
    Serial.print("*** BLE: connected to central: ");
    // Print the central's MAC address:
    Serial.println(central.address());
    // Turn on the LED to indicate the connection:
    digitalWrite(13, HIGH);
    // Read the sensor values every 30s
    // as long as the central is still connected:
    while (central.connected()) {
      long currentMillis = millis();
      // If 30000 ms have passed, check the heart rate measurement:
      if (currentMillis - previousMillis >= updateDelay) {
        previousMillis = currentMillis;
        Serial.println("*** BLE: updating attributes ... ");
        updateAttributes();
      }
    }
    // When the central disconnects, turn off the LED:
    digitalWrite(13, LOW);
    Serial.print("*** BLED: disconnected from central: ");
    Serial.println(central.address());
  }

}

/*
   BLE
*/

void setup_BLE() {
  /* Set a local name for the BLE device
     This name will appear in advertising packets
     and can be used by remote devices to identify this BLE device
     The name can be changed but maybe be truncated based on space left in advertisement packet */
  blePeripheral.setLocalName("BeeNestBox");
  blePeripheral.setAdvertisedServiceUuid(beeNestBoxService.uuid());  // Add the service UUID
  blePeripheral.addAttribute(beeNestBoxService);   // Add the BLE service
  // Add characteristics
  blePeripheral.addAttribute(beeNestBoxTemperature);
  blePeripheral.addAttribute(beeNestBoxHumidity);
  blePeripheral.addAttribute(beeNestBoxLightIntensity);
  blePeripheral.addAttribute(beeNestBoxCapacitySensorReading);
  /* Now activate the BLE device.  It will start continuously transmitting BLE
     advertising packets and will be visible to remote BLE central devices
     until it receives a new connection */
  Serial.println("*** BLE: initializing peripheral ...");
  blePeripheral.begin();
  Serial.println("*** BLE: peripheral active & waiting for connections.");
}

void updateAttributes() {
  read_HTU21D();
  delay(100);
  read_MPR121();
  delay(100);
  read_BH1750();
  delay(100);
  beeNestBoxTemperature.setValue(htu21d_temperature);
  beeNestBoxHumidity.setValue(htu21d_humidity);
  beeNestBoxCapacitySensorReading.setValue(mpr121_pins);
  beeNestBoxLightIntensity.setValue(bh1750_lux);
}

/*
   BH1750 setup & reading
*/

void setup_HTU21D() {
  Serial.println("*** HTU21D - temperature & humidity sensor: initializing ...");
  htu21d = Adafruit_HTU21DF();
  if (!htu21d.begin()) {
    Serial.println("*** HTU21D: sensor not found!");
    while (1);
  }
  Serial.println("*** HTU21D: initialized.");
}

void read_HTU21D() {
  float temperature = htu21d.readTemperature();;
  float humidity = htu21d.readHumidity();
  Serial.println("*** HTU21D: reading ...");
  htu21d_temperature = (int) (temperature * 100);
  htu21d_humidity = (int) (humidity * 100);
  Serial.print("*** HTU21D: temperature (*C) = ");
  Serial.println(temperature);
  Serial.print("*** HTU21D: humidity (%) = ");
  Serial.println(humidity);
}

/*
   BH1750 setup & reading
*/

void setup_BH1750() {
  Serial.println("*** BH1750 - light intensity sensor: initializing ...");
  bh1750.begin();
  Serial.println("*** BH1750: initialized.");
}

void read_BH1750() {
  Serial.println("*** BH1750: reading ...");
  bh1750_lux = bh1750.readLightLevel();
  Serial.print("*** BH1750: light (lx) = ");
  Serial.println(bh1750_lux);
}

/*
   MPR121 setup & reading
*/

void setup_MPR121() {
  Serial.println("*** MPR121 - capacitive touch sensor: initializing ...");
  pinMode(mpr121_irqpin, INPUT);
  digitalWrite(mpr121_irqpin, HIGH); //enable pullup resistor
  Wire.begin();
  mpr121_setup();
  Serial.println("*** MPR121: initialized.");
}

void read_MPR121() {
  Serial.println("*** MPR121: reading ...");
  if (!mpr121_checkInterrupt()) {
    Serial.println("*** MPR121: triggered ...");
    //read the pin states from the MPR121
    Wire.requestFrom(0x5A, 2);
    byte LSB = Wire.read();
    byte MSB = Wire.read();
    uint16_t pins = ((MSB << 8) | LSB); // 16 bits that represent the pin states
    mpr121_pins = pins;
    Serial.print("*** MPR121: pins (X=touched) = ");
    for (int i = 0; i <= 11; i++) {
      Serial.print(i);
      if (pins & (1 << i)) {
        Serial.print(":(X) ");
      } else {
        Serial.print(":( ) ");
      }
    }
     Serial.println(" .");
  }
}

/*
   MPR121 support
   excerpt from
   https://github.com/sparkfun/MPR121_Capacitive_Touch_Breakout/blob/master/Firmware/MPR121Q/Arduino%20Sketch/mpr121.ino
*/

void mpr121_setup(void) {
  set_register(0x5A, ELE_CFG, 0x00);
  // Section A - Controls filtering when data is > baseline.
  set_register(0x5A, MHD_R, 0x01);
  set_register(0x5A, NHD_R, 0x01);
  set_register(0x5A, NCL_R, 0x00);
  set_register(0x5A, FDL_R, 0x00);
  // Section B - Controls filtering when data is < baseline.
  set_register(0x5A, MHD_F, 0x01);
  set_register(0x5A, NHD_F, 0x01);
  set_register(0x5A, NCL_F, 0xFF);
  set_register(0x5A, FDL_F, 0x02);
  // Section C - Sets touch and release thresholds for each electrode
  set_register(0x5A, ELE0_T, TOU_THRESH);
  set_register(0x5A, ELE0_R, REL_THRESH);
  set_register(0x5A, ELE1_T, TOU_THRESH);
  set_register(0x5A, ELE1_R, REL_THRESH);
  set_register(0x5A, ELE2_T, TOU_THRESH);
  set_register(0x5A, ELE2_R, REL_THRESH);
  set_register(0x5A, ELE3_T, TOU_THRESH);
  set_register(0x5A, ELE3_R, REL_THRESH);
  set_register(0x5A, ELE4_T, TOU_THRESH);
  set_register(0x5A, ELE4_R, REL_THRESH);
  set_register(0x5A, ELE5_T, TOU_THRESH);
  set_register(0x5A, ELE5_R, REL_THRESH);
  set_register(0x5A, ELE6_T, TOU_THRESH);
  set_register(0x5A, ELE6_R, REL_THRESH);
  set_register(0x5A, ELE7_T, TOU_THRESH);
  set_register(0x5A, ELE7_R, REL_THRESH);
  set_register(0x5A, ELE8_T, TOU_THRESH);
  set_register(0x5A, ELE8_R, REL_THRESH);
  set_register(0x5A, ELE9_T, TOU_THRESH);
  set_register(0x5A, ELE9_R, REL_THRESH);
  set_register(0x5A, ELE10_T, TOU_THRESH);
  set_register(0x5A, ELE10_R, REL_THRESH);
  set_register(0x5A, ELE11_T, TOU_THRESH);
  set_register(0x5A, ELE11_R, REL_THRESH);
  // Section D
  // Set the Filter Configuration
  // Set ESI2
  set_register(0x5A, FIL_CFG, 0x04);
  // Section E
  // Electrode Configuration
  // Set ELE_CFG to 0x00 to return to standby mode
  set_register(0x5A, ELE_CFG, 0x0C);  // Enables all 12 Electrodes
  // Section F
  // Enable Auto Config and auto Reconfig
  /*set_register(0x5A, ATO_CFG0, 0x0B);
    set_register(0x5A, ATO_CFGU, 0xC9);  // USL = (Vdd-0.7)/vdd*256 = 0xC9 @3.3V   set_register(0x5A, ATO_CFGL, 0x82);  // LSL = 0.65*USL = 0x82 @3.3V
    set_register(0x5A, ATO_CFGT, 0xB5);*/  // Target = 0.9*USL = 0xB5 @3.3V
  set_register(0x5A, ELE_CFG, 0x0C);
}

boolean mpr121_checkInterrupt(void) {
  return digitalRead(mpr121_irqpin);
}

void set_register(int address, unsigned char r, unsigned char v) {
  Wire.beginTransmission(address);
  Wire.write(r);
  Wire.write(v);
  Wire.endTransmission();
}

Credits

3magku

3magku

4 projects • 10 followers

Comments