St-connect

Dependencies:   HP206C mbed WakeUp QMC5883L DHT22 DS1820

  1. ST Conect Project Look how we did it : [Hackster](https://www.hackster.io/monginjulien/st-connect-dike-monitoring-534a32)

main.cpp

Committer:
raminou
Date:
2019-01-08
Revision:
13:8cbc053fdca1
Parent:
12:41fa5a145a22

File content as of revision 13:8cbc053fdca1:

#include "mbed.h"
#include "WakeUp.h"
#include "DHT22.h"
#include "HP20x_dev.h"
#include "DS1820.h"
#include "QMC5883L.h"

// Time during the deepsleep in ms
#define DEEPSLEEP_TIME (1*60000)

// Enabling components
#define ENABLE_BAROMETER 1
#define ENABLE_MAGNETOMETER 1
#define ENABLE_GROUND_TEMPERATURE 1
#define ENABLE_GROUND_HUMIDITY 1
#define ENABLE_DHT22 1

// Sigfox constants
#define MESSAGE_SIZE 32
#define TRAME_SIZE 25

// Enable the debug
#define DEBUG

// Enable the sending over Sigfox
#define SEND_SIGFOX 1

// Object initializations
#ifdef DEBUG
    Serial pc(USBTX, USBRX);
    DigitalOut myled(LED1);
#endif

#ifdef ENABLE_BAROMETER
    HP20x_dev capt_barometer(D4, D5);
#endif

#ifdef ENABLE_MAGNETOMETER
    QMC5883L capt_magnetometer(D4, D5);
#endif

#ifdef ENABLE_GROUND_TEMPERATURE
    DS1820 capt_ground_temperature(A1);
#endif

#ifdef ENABLE_GROUND_HUMIDITY
    DigitalOut transistor_humidity(D12);
    AnalogIn capt_ground_humidity(A0);      // SEN0
#endif

#ifdef ENABLE_DHT22
    DHT22 capt_thermo_air_humidity(D3);     // DHT22
#endif

// Pin to disable deepsleep
DigitalIn disable_deep(D6);

Serial sigfox(D1, D0);

// Pin to control the transistor
DigitalInOut reset_sigfox(D9);


char message[MESSAGE_SIZE] = "AT$SF=";

// Default values at the init
long pressure = 10000;
float air_temperature = 20.0;
float air_humidity = 50.0;
float ground_temperature = 20.0;
float ground_humidity = 0.5;
int16_t magnetic_field[3] = {}; // x, y, z

/*
 * Empty callback of the deepsleep because in this version of mbed, the wakeup
 * does not work without it. 
 * But the code inside it is not executed !
 */
void mycallback()
{
}

/*
 * Round the float f
 */
int16_t round(float f)
{
    int16_t res = (int16_t)f;
    if (f - res > 1/2) 
        res++;
        
    return res;
}

/*
 * Format the trame to send over Sigfox
 * Put the trame in *v_trame
 */
void format(float v_ground_temperature, float v_air_temperature, float v_ground_humidity, float v_air_humidity, long v_pressure, int16_t* v_magnetic_field, char* v_trame)
{
    // Converting our data to use as few bits as possible
    int16_t i_ground_temperature = (int16_t) round(v_ground_temperature * 10);
    int16_t i_air_temperature = (int16_t) round(v_air_temperature * 10);
    int16_t i_ground_humidity = (int16_t) round(v_ground_humidity);
    int16_t i_air_humidity = (int16_t) round(v_air_humidity);
    int32_t i_pressure = (int32_t) v_pressure;
    bool err[3] = {false, false, false};    // magnetic field error x,y,z
    
    // Checking if the values are in the range
    if(!(i_ground_temperature >= -512 && i_ground_temperature < 511))
        i_ground_temperature = -512;
        
    if(!(i_air_temperature >= -512 && i_air_temperature < 511))
        i_air_temperature = -512;
    
    if(!(i_ground_humidity <= 100))
        i_ground_humidity = 127;
    
    if(!(i_air_humidity <= 100))
        i_air_humidity = 127;
    
    if(!(i_pressure <= 131071))
        i_pressure = 0;
    
    unsigned int i;
    for(i = 0; i < 3; i++)
    {
        if(!(v_magnetic_field[i] > -65536 && v_magnetic_field[i] < 65535))
            err[i] = true;
    }
    
    // Putting them in the trame
    snprintf(v_trame, TRAME_SIZE, "%02x", (char)(i_ground_temperature >> 2));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((i_ground_temperature << 6) | ((i_air_temperature >> 4) & 0x3f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((i_air_temperature << 4) | ((i_ground_humidity >> 3) & 0x0f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((i_ground_humidity << 5) | ((i_air_humidity >> 2) & 0x1f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((i_air_humidity << 6) | ((i_pressure >> 11) & 0x3f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)(i_pressure >> 3));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((i_pressure << 5) | ((v_magnetic_field[0] >> 9) & 0x1f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)(v_magnetic_field[0] >> 1));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((v_magnetic_field[0] << 7) | ((v_magnetic_field[1] >> 7) & 0x7f)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((v_magnetic_field[1] << 1) | ((v_magnetic_field[2] >> 13) & 0x01)));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)(v_magnetic_field[2] >> 5));
    snprintf(v_trame, TRAME_SIZE, "%s%02x", v_trame, (char)((v_magnetic_field[2] << 3) | (err[0] << 2) | (err[1] << 1) | (err[2])));
}

int main()
{
    #ifdef DEBUG
        pc.printf("\r\n\r\n\r\nInit...\r\n");
    #endif
    
    sigfox.printf("\r\n");
    
    #ifdef ENABLE_BAROMETER
    if(capt_barometer.isAvailable())
        pressure = capt_barometer.ReadPressure();
    #endif
    
    #ifdef ENABLE_MAGNETOMETER
        capt_magnetometer.init();
    #endif
    
    wait(5);
    
    // Main loop
    while(1) {
        #ifdef DEBUG
            myled = 1;
            wait(5);
            myled = 0;
        #endif
        
        #ifdef ENABLE_GROUND_HUMIDITY
            // Plug the ground humidity
            transistor_humidity = 1;
        #endif
        
        // Wake Up sigfox
        reset_sigfox.output();
        reset_sigfox = 0;
        wait(5);
        
        // Set high impendance the sigfox reset pin
        reset_sigfox.input();
        
        #ifdef ENABLE_GROUND_TEMPERATURE
            // Ground Temperature
            capt_ground_temperature.convertTemperature(true, DS1820::all_devices);
            ground_temperature = capt_ground_temperature.temperature();
        #endif
        
        #ifdef ENABLE_GROUND_HUMIDITY
            // Ground Humidity
            ground_humidity = capt_ground_humidity.read() * 100;
            transistor_humidity = 0;
        #endif
        
        #ifdef ENABLE_DHT22
            // Air temperature and humidity
            if(capt_thermo_air_humidity.sample())
            {
                air_temperature = capt_thermo_air_humidity.getTemperature() / 10.0;
                air_humidity = capt_thermo_air_humidity.getHumidity() / 10.0;
            }
        #endif
        
        #ifdef ENABLE_BAROMETER
            // Pressure
            if(capt_barometer.isAvailable())
                pressure = capt_barometer.ReadPressure();
        #endif
        
        #ifdef ENABLE_MAGNETOMETER
            // Magnetometer
            capt_magnetometer.init();
            magnetic_field[0] = capt_magnetometer.getMagXvalue();
            magnetic_field[1] = capt_magnetometer.getMagYvalue();
            magnetic_field[2] = capt_magnetometer.getMagZvalue();
            capt_magnetometer.standby();
        #endif
        
        #ifdef DEBUG
            // Display to check your values
            pc.printf("\r\n");
            pc.printf("Pressure: %f hPa\r\n", pressure/100.0);
            pc.printf("Ground Temperature: %f\t|\t", ground_temperature);
            pc.printf("Ground Humidity: %.1f\r\n", ground_humidity);
            pc.printf("Air Temperature: %.1f\t|\tAir Humidity: %.1f\r\n", air_temperature, air_humidity);
            pc.printf("Magnetic field: x: %hd, y: %hd, z: %hd\r\n", magnetic_field[0], magnetic_field[1], magnetic_field[2]);
        #endif
        
        // Creating your sigfox trame
        format(ground_temperature, air_temperature, ground_humidity, air_humidity, pressure, magnetic_field, &(message[6]));
        message[MESSAGE_SIZE-2] = '\r';
        message[MESSAGE_SIZE-1] = '\n';
        #ifdef DEBUG
            pc.printf("msg=%s", message);
        #endif
        
        // Sending over sigfox
        #ifdef SEND_SIGFOX
            sigfox.printf("%s", message);
            wait(8);    // Time during the sigfox module is sending, do not stop the sigfox before !
        #endif
        
        // Sleep Sigfox
        sigfox.printf("AT$P=1\r\n");
        
        #ifdef DEBUG
            // Detect that the system is going in sleep mode
            pc.printf("Sleep");
            myled = 1;
            wait(0.3);
            myled = 0;
            wait(0.3);
            myled = 1;
            wait(0.3);
            myled = 0;
            wait(0.3);
            myled = 1;
            wait(0.3);
            myled = 0;
        #endif
                
        // Deepsleep
        if(disable_deep == 0)
        {
            WakeUp::set_ms(DEEPSLEEP_TIME);
            WakeUp::attach(&mycallback);
            deepsleep();
        }
    }
}