Very advanced Click Air Quality example for Hexiwear featuring OLED Display, Bluetooth, Cloud and Touch

Dependencies:   Hexi_KW40Z Hexi_OLED_SSD1351

This project has been developed by mbed user daveyclk

This project demonstrates the use of the Mikroelektronika Click Air Quality module with hexiwear featuring the OLED display, the Bluetooth for Cloud connectivity and Touch buttons

Plug Hexiwear into the Docking Station and the Air Quality Click to the Click Socket 1
Connect the USB cable to your computer and to the micro-USB port of the Docking Station

Compile the project and copy the binary "Hexi_Click_AirQuality_Example_HEXIWEAR.bin" in the DAP-LINK drive from your computer file explorer
Press the K64F-RESET button on the docking station to start the program on your board

The OLED screen will display some graphics and the Air Quality measurement in ppm below
Blow gently on the sensor and see the value changing
Graphic displayed will move the Arrow from Green to Purple depending from the ppm value measured by the Air Quality sensor
Download the cell phone App Hexiwear from iOS or Android stores to connect your board to your phone
Type the pin displayed on the screen and give a name to your board to pair it via the App
Congratulation your data are now streamed directly to Wolkabout Cloud...
To visualize the data remotely (over cloud not bluetooth), you can go to Wolksense.com or download the Wolksense iOS/Android App and login with same account

Committer:
GregC
Date:
Thu Oct 20 01:24:41 2016 +0000
Revision:
0:4cf89612afab
Child:
1:7b9c19276087
in development

Who changed what in which revision?

UserRevisionLine numberNew contents of line
GregC 0:4cf89612afab 1 /******************************************************************************
GregC 0:4cf89612afab 2 * Includes
GregC 0:4cf89612afab 3 *******************************************************************************/
GregC 0:4cf89612afab 4
GregC 0:4cf89612afab 5 #include "mbed.h"
GregC 0:4cf89612afab 6 #include "Hexi_OLED_SSD1351.h"
GregC 0:4cf89612afab 7 #include "images.h"
GregC 0:4cf89612afab 8 #include "string.h"
GregC 0:4cf89612afab 9
GregC 0:4cf89612afab 10 /******************************************************************************
GregC 0:4cf89612afab 11 * Input and Output Pinout
GregC 0:4cf89612afab 12 *******************************************************************************/
GregC 0:4cf89612afab 13
GregC 0:4cf89612afab 14 AnalogIn ain(PTB2);
GregC 0:4cf89612afab 15 SSD1351 oled(PTB22,PTB21,PTC13,PTB20,PTE6, PTD15); // SSD1351 OLED Driver (MOSI,SCLK,POWER,CS,RST,DC)
GregC 0:4cf89612afab 16 DigitalOut led1(LED_GREEN);
GregC 0:4cf89612afab 17 Serial pc(USBTX, USBRX);
GregC 0:4cf89612afab 18
GregC 0:4cf89612afab 19 /******************************************************************************
GregC 0:4cf89612afab 20 * Module Variable Definitions
GregC 0:4cf89612afab 21 *******************************************************************************/
GregC 0:4cf89612afab 22
GregC 0:4cf89612afab 23 double ppm; // ppm
GregC 0:4cf89612afab 24
GregC 0:4cf89612afab 25 int value = 0;
GregC 0:4cf89612afab 26 int value_old = 0;
GregC 0:4cf89612afab 27 uint16_t adc_rd;
GregC 0:4cf89612afab 28
GregC 0:4cf89612afab 29 const uint8_t *image1; // Pointer for the image to be displayed
GregC 0:4cf89612afab 30 char text[20]; // Text Buffer for dynamic value displayed
GregC 0:4cf89612afab 31
GregC 0:4cf89612afab 32
GregC 0:4cf89612afab 33
GregC 0:4cf89612afab 34 /**************************************************************************************************
GregC 0:4cf89612afab 35 * Function InitModules()
GregC 0:4cf89612afab 36 * -------------------------------------------------------------------------------------------------
GregC 0:4cf89612afab 37 * Overview:
GregC 0:4cf89612afab 38 * Input: None
GregC 0:4cf89612afab 39 * Output: None
GregC 0:4cf89612afab 40 **************************************************************************************************/
GregC 0:4cf89612afab 41
GregC 0:4cf89612afab 42 void InitModules()
GregC 0:4cf89612afab 43 {
GregC 0:4cf89612afab 44 image1 = AirQuality; // Setting pointer location of the 96 by 96 pixel bitmap
GregC 0:4cf89612afab 45 oled.DrawImage(image1,0,0); // Fill 96px by 96px Screen with 96px by 96px NXP Image starting at x=0,y=0
GregC 0:4cf89612afab 46
GregC 0:4cf89612afab 47 oled_text_properties_t textProperties = {0}; // Get OLED Class Default Text Properties
GregC 0:4cf89612afab 48 oled.GetTextProperties(&textProperties);
GregC 0:4cf89612afab 49
GregC 0:4cf89612afab 50 textProperties.fontColor = COLOR_BLUE; // Set text properties to white and right aligned for the dynamic text
GregC 0:4cf89612afab 51 textProperties.alignParam = OLED_TEXT_ALIGN_LEFT;
GregC 0:4cf89612afab 52 oled.SetTextProperties(&textProperties);
GregC 0:4cf89612afab 53
GregC 0:4cf89612afab 54 strcpy((char *) text,"ppm:"); // Display Legends
GregC 0:4cf89612afab 55 oled.Label((uint8_t *)text,15,75);
GregC 0:4cf89612afab 56
GregC 0:4cf89612afab 57 textProperties.fontColor = COLOR_BLUE; // Set text properties to white and right aligned for the dynamic text
GregC 0:4cf89612afab 58 textProperties.alignParam = OLED_TEXT_ALIGN_RIGHT;
GregC 0:4cf89612afab 59 oled.SetTextProperties(&textProperties);
GregC 0:4cf89612afab 60
GregC 0:4cf89612afab 61 sprintf(text,"%i",value); // Format the value
GregC 0:4cf89612afab 62 oled.TextBox((uint8_t *)text,55,75,20,15); //Increase textbox for more digits
GregC 0:4cf89612afab 63
GregC 0:4cf89612afab 64 /** initialize ADC */
GregC 0:4cf89612afab 65 // ADC0_Init();
GregC 0:4cf89612afab 66
GregC 0:4cf89612afab 67 /** pause for 100ms for ADC module stabilization */
GregC 0:4cf89612afab 68 wait_ms(100);
GregC 0:4cf89612afab 69 }
GregC 0:4cf89612afab 70
GregC 0:4cf89612afab 71
GregC 0:4cf89612afab 72 /**************************************************************************************************
GregC 0:4cf89612afab 73 * Function ReadSensor()
GregC 0:4cf89612afab 74 * -------------------------------------------------------------------------------------------------
GregC 0:4cf89612afab 75 * Overview: Read sensor.
GregC 0:4cf89612afab 76 * Input: None
GregC 0:4cf89612afab 77 * Output: None
GregC 0:4cf89612afab 78 **************************************************************************************************/
GregC 0:4cf89612afab 79
GregC 0:4cf89612afab 80 void ReadSensor()
GregC 0:4cf89612afab 81 {
GregC 0:4cf89612afab 82 adc_rd = ain.read_u16();
GregC 0:4cf89612afab 83 wait_ms(10);
GregC 0:4cf89612afab 84 }
GregC 0:4cf89612afab 85
GregC 0:4cf89612afab 86
GregC 0:4cf89612afab 87 /**************************************************************************************************
GregC 0:4cf89612afab 88 * Function CalculatePPM()
GregC 0:4cf89612afab 89 * -------------------------------------------------------------------------------------------------
GregC 0:4cf89612afab 90 * Overview: Calculation of PPM.
GregC 0:4cf89612afab 91 * Input: None
GregC 0:4cf89612afab 92 * Output: None
GregC 0:4cf89612afab 93 **************************************************************************************************/
GregC 0:4cf89612afab 94
GregC 0:4cf89612afab 95 void CalculatePPM()
GregC 0:4cf89612afab 96 {
GregC 0:4cf89612afab 97 const double Rl = 5000.0; // Rl (Ohm) - Load resistance
GregC 0:4cf89612afab 98 const double Vadc_33 = 0.0032226562; // ADC step 3,3V/1024 3,22mV (10bit ADC)
GregC 0:4cf89612afab 99 double Vrl; // Output voltage
GregC 0:4cf89612afab 100 double Rs; // Rs (Ohm) - Sensor resistance
GregC 0:4cf89612afab 101 double ratio; // Rs/Rl ratio
GregC 0:4cf89612afab 102 double lgPPM;
GregC 0:4cf89612afab 103
GregC 0:4cf89612afab 104 Vrl = (double)adc_rd * Vadc_33; // For 3.3V Vcc use Vadc_33
GregC 0:4cf89612afab 105 Rs = Rl * (5 - Vrl)/Vrl; // Calculate sensor resistance
GregC 0:4cf89612afab 106 ratio = Rs/Rl; // Calculate ratio
GregC 0:4cf89612afab 107 lgPPM = (log10(ratio) * -0.8) + 0.9; // Calculate ppm
GregC 0:4cf89612afab 108 ppm = pow(10,lgPPM); // Calculate ppm
GregC 0:4cf89612afab 109 }
GregC 0:4cf89612afab 110
GregC 0:4cf89612afab 111
GregC 0:4cf89612afab 112
GregC 0:4cf89612afab 113 /**************************************************************************************************
GregC 0:4cf89612afab 114 * Function DisplayAirQValue()
GregC 0:4cf89612afab 115 * -------------------------------------------------------------------------------------------------
GregC 0:4cf89612afab 116 * Overview:
GregC 0:4cf89612afab 117 * Input: None
GregC 0:4cf89612afab 118 * Output: None
GregC 0:4cf89612afab 119 **************************************************************************************************/
GregC 0:4cf89612afab 120
GregC 0:4cf89612afab 121 void DisplayAirQValue( uint16_t value )
GregC 0:4cf89612afab 122 {
GregC 0:4cf89612afab 123 if (value_old != value)
GregC 0:4cf89612afab 124 {
GregC 0:4cf89612afab 125
GregC 0:4cf89612afab 126 oled_text_properties_t textProperties = {0}; // Get OLED Class Default Text Properties
GregC 0:4cf89612afab 127 oled.GetTextProperties(&textProperties);
GregC 0:4cf89612afab 128
GregC 0:4cf89612afab 129 // clear the previous value
GregC 0:4cf89612afab 130 textProperties.fontColor = COLOR_WHITE; // Set text properties to white and right aligned for the dynamic text
GregC 0:4cf89612afab 131 textProperties.alignParam = OLED_TEXT_ALIGN_RIGHT;
GregC 0:4cf89612afab 132 oled.SetTextProperties(&textProperties);
GregC 0:4cf89612afab 133
GregC 0:4cf89612afab 134 sprintf(text,"%i",value_old); // Format the value
GregC 0:4cf89612afab 135 oled.TextBox((uint8_t *)text,55,75,20,15); //Increase textbox for more digits
GregC 0:4cf89612afab 136
GregC 0:4cf89612afab 137 // display the new value
GregC 0:4cf89612afab 138 textProperties.fontColor = COLOR_WHITE; // Set text properties to white and right aligned for the dynamic text
GregC 0:4cf89612afab 139 textProperties.alignParam = OLED_TEXT_ALIGN_RIGHT;
GregC 0:4cf89612afab 140 oled.SetTextProperties(&textProperties);
GregC 0:4cf89612afab 141
GregC 0:4cf89612afab 142 sprintf(text,"%i",value); // Format the value
GregC 0:4cf89612afab 143 oled.TextBox((uint8_t *)text,55,75,20,15); //Increase textbox for more digits
GregC 0:4cf89612afab 144 }
GregC 0:4cf89612afab 145 value_old = value;
GregC 0:4cf89612afab 146 }
GregC 0:4cf89612afab 147
GregC 0:4cf89612afab 148
GregC 0:4cf89612afab 149 /**************************************************************************************************
GregC 0:4cf89612afab 150 * Function Main()
GregC 0:4cf89612afab 151 * -------------------------------------------------------------------------------------------------
GregC 0:4cf89612afab 152 * Overview:
GregC 0:4cf89612afab 153 * Input: None
GregC 0:4cf89612afab 154 * Output: None
GregC 0:4cf89612afab 155 **************************************************************************************************/
GregC 0:4cf89612afab 156
GregC 0:4cf89612afab 157 int main()
GregC 0:4cf89612afab 158 {
GregC 0:4cf89612afab 159
GregC 0:4cf89612afab 160 InitModules();
GregC 0:4cf89612afab 161
GregC 0:4cf89612afab 162 while (true)
GregC 0:4cf89612afab 163 {
GregC 0:4cf89612afab 164
GregC 0:4cf89612afab 165 ReadSensor();
GregC 0:4cf89612afab 166 pc.printf("Sensor Value 0x%04X\n\r",ain.read_u16());
GregC 0:4cf89612afab 167
GregC 0:4cf89612afab 168 CalculatePPM();
GregC 0:4cf89612afab 169
GregC 0:4cf89612afab 170 DisplayAirQValue(ppm);
GregC 0:4cf89612afab 171
GregC 0:4cf89612afab 172 led1 = !led1;
GregC 0:4cf89612afab 173 Thread::wait(500);
GregC 0:4cf89612afab 174
GregC 0:4cf89612afab 175 }
GregC 0:4cf89612afab 176 }