iBreathe Breathalyzer can now talk thanks to the Text to Speech Click Board

Dependencies:   Hexi_KW40Z Hexi_OLED_SSD1351 text_to_speak_mbed

Fork of iBreathe_Breathalyzer by Dave Clarke

Committer:
daveyclk
Date:
Wed Sep 28 10:47:30 2016 +0000
Revision:
7:5d272a0e250b
Parent:
6:7f4ba36b025f
Child:
9:fe5114551ec3
Added iBreathe compatibility with custom Hexiware iOS app, kept backards compatibility with existing iOS app

Who changed what in which revision?

UserRevisionLine numberNew contents of line
daveyclk 5:a27fdb811237 1 /****************************************************************************
daveyclk 5:a27fdb811237 2 * Title : iBreathe Breathalyzer
daveyclk 5:a27fdb811237 3 * Filename : breathalyzer
daveyclk 5:a27fdb811237 4 * Author : Dave Clarke
daveyclk 5:a27fdb811237 5 * Origin Date : 27/09/2016
daveyclk 5:a27fdb811237 6 * Notes : Breathalyzer utilizing Hexiware, Alcohol click and Wolksense
daveyclk 5:a27fdb811237 7 *****************************************************************************/
daveyclk 5:a27fdb811237 8 /**************************CHANGE LIST **************************************
daveyclk 5:a27fdb811237 9 *
daveyclk 5:a27fdb811237 10 * Date Software Version Initials Description
daveyclk 5:a27fdb811237 11 * 27/09/16 1.0.0 DC Interface Created.
daveyclk 5:a27fdb811237 12 *
daveyclk 5:a27fdb811237 13 *****************************************************************************/
daveyclk 5:a27fdb811237 14
daveyclk 5:a27fdb811237 15 /**
daveyclk 5:a27fdb811237 16 * @page TEST_CFG Test Configurations
daveyclk 5:a27fdb811237 17 * <h3> Test configuration : </h3>
daveyclk 5:a27fdb811237 18 * @par
daveyclk 5:a27fdb811237 19 * <ul>
daveyclk 5:a27fdb811237 20 * <li><b> MCU </b> : MK64FN1M0XXX12 </li>
daveyclk 5:a27fdb811237 21 * <li><b> Dev. Board </b> : HEXIWEAR </li>
daveyclk 5:a27fdb811237 22 * <li><b> Oscillator </b> : 12 MHz external </li>
daveyclk 5:a27fdb811237 23 * <li><b> Ext. Modules </b> : Alcohol Click on mikroBUS 1 </li>
daveyclk 5:a27fdb811237 24 * <li><b> SW </b> : mBed OS5 </li>
daveyclk 5:a27fdb811237 25 * </ul>
daveyclk 5:a27fdb811237 26 */
daveyclk 5:a27fdb811237 27
daveyclk 5:a27fdb811237 28 /**
daveyclk 5:a27fdb811237 29 * @mainpage
daveyclk 5:a27fdb811237 30 * <h3> Breathalyser created with HEXIWEAR and mBed OS 5 </h3>
daveyclk 5:a27fdb811237 31 * @par This will show you how much you've drunk and tell you with an Emoticon if
daveyclk 5:a27fdb811237 32 * you're too hammered to even consider driving. Using the Hexiware app the readings
daveyclk 5:a27fdb811237 33 * are transmitted to the cloud via bluetooth. Is it time to give up drinking yet?!
daveyclk 5:a27fdb811237 34
daveyclk 5:a27fdb811237 35 * <h3> Alcohol Features </h3>
daveyclk 5:a27fdb811237 36 * @par Alcohol click, Hexiwear docking station, Hexiware
daveyclk 5:a27fdb811237 37 */
daveyclk 5:a27fdb811237 38
daveyclk 5:a27fdb811237 39 /******************************************************************************
daveyclk 5:a27fdb811237 40 * Includes
daveyclk 5:a27fdb811237 41 *******************************************************************************/
daveyclk 5:a27fdb811237 42
khuang 0:a1af4ae04b06 43 #include "mbed.h"
daveyclk 5:a27fdb811237 44 #include "Hexi_KW40Z.h"
khuang 0:a1af4ae04b06 45 #include "Hexi_OLED_SSD1351.h"
daveyclk 5:a27fdb811237 46 #include "OLED_types.h"
daveyclk 5:a27fdb811237 47 #include "OpenSans_Font.h"
khuang 0:a1af4ae04b06 48 #include "string.h"
daveyclk 5:a27fdb811237 49 #include "iBreatheImages.h"
daveyclk 5:a27fdb811237 50
daveyclk 5:a27fdb811237 51 /******************************************************************************
daveyclk 5:a27fdb811237 52 * Module Variable Definitions
daveyclk 5:a27fdb811237 53 *******************************************************************************/
daveyclk 5:a27fdb811237 54
daveyclk 5:a27fdb811237 55 #define LED_ON 0
daveyclk 5:a27fdb811237 56 #define LED_OFF 1
daveyclk 5:a27fdb811237 57
daveyclk 5:a27fdb811237 58 // Pointers to:
daveyclk 5:a27fdb811237 59 const uint8_t *welcome, // Welcome screen image
daveyclk 5:a27fdb811237 60 *blank, // blank image
daveyclk 5:a27fdb811237 61 *blow, // Start Blowing Image
daveyclk 5:a27fdb811237 62 *drink, // You've been drinking image
daveyclk 5:a27fdb811237 63 *drive, // Don't drive image
daveyclk 5:a27fdb811237 64 *hang, // You'll have a hangover image
daveyclk 5:a27fdb811237 65 *ini, // Initialising image
daveyclk 5:a27fdb811237 66 *sober; // Sober as a judge image
daveyclk 5:a27fdb811237 67
daveyclk 5:a27fdb811237 68 const float Vadc_3V3 = 0.00005035; // 16-Bit ADC step 3V3/65535 = 0.05035 mV
daveyclk 5:a27fdb811237 69
daveyclk 5:a27fdb811237 70 float Vrl = 0, // Output voltage
daveyclk 5:a27fdb811237 71 ambientAlc = 0, // Abmient Output voltage from sensor
daveyclk 5:a27fdb811237 72 SensorRes = 0, // SensorRes (Ohm) - Sensor resistance
daveyclk 5:a27fdb811237 73 SensorRes1 = 0, // SensorRes (Ohm) - Sensor resistance
daveyclk 5:a27fdb811237 74 ppm = 0, // ppm
daveyclk 5:a27fdb811237 75 ppm_1 = 0, // Ambient ppm variable
daveyclk 5:a27fdb811237 76 ratio = 0; // SensorRes/LoadRes ratio
daveyclk 5:a27fdb811237 77
daveyclk 5:a27fdb811237 78 unsigned short adc_rd = 0; //Initialise anologue read variable
daveyclk 5:a27fdb811237 79
daveyclk 5:a27fdb811237 80 const uint8_t ppmText[] = "ppm:"; // text for PPM label
daveyclk 5:a27fdb811237 81
daveyclk 5:a27fdb811237 82 char text[20], // Text array variables
daveyclk 5:a27fdb811237 83 text2[20],
daveyclk 5:a27fdb811237 84 text3[20];
daveyclk 5:a27fdb811237 85
daveyclk 5:a27fdb811237 86 float value[20], // initial sensor set up values
daveyclk 6:7f4ba36b025f 87 value1[20]; // initial sensor set up values
daveyclk 6:7f4ba36b025f 88
daveyclk 6:7f4ba36b025f 89 bool isFirstBoot = true;
daveyclk 5:a27fdb811237 90
daveyclk 5:a27fdb811237 91
daveyclk 5:a27fdb811237 92 /******************************************************************************
daveyclk 5:a27fdb811237 93 * Function Prototypes
daveyclk 5:a27fdb811237 94 *******************************************************************************/
daveyclk 5:a27fdb811237 95
daveyclk 5:a27fdb811237 96 void sysinit(void);
daveyclk 5:a27fdb811237 97 void ReadSensor();
daveyclk 5:a27fdb811237 98 void CalculatePPM(int times, bool amb);
daveyclk 5:a27fdb811237 99 void ambient(int times);
daveyclk 5:a27fdb811237 100 void StartHaptic(void);
daveyclk 5:a27fdb811237 101 void StopHaptic(void const *n);
daveyclk 5:a27fdb811237 102 void ButtonUp(void);
daveyclk 5:a27fdb811237 103 void txTask(void);
daveyclk 5:a27fdb811237 104
daveyclk 5:a27fdb811237 105 /******************************************************************************
daveyclk 5:a27fdb811237 106 * Instance setups
daveyclk 5:a27fdb811237 107 *******************************************************************************/
daveyclk 6:7f4ba36b025f 108 /* Define timer for haptic feedback */
daveyclk 6:7f4ba36b025f 109 RtosTimer hapticTimer(StopHaptic, osTimerOnce);
daveyclk 6:7f4ba36b025f 110
daveyclk 6:7f4ba36b025f 111 //set up Analog read pin for alcohol sensor
daveyclk 6:7f4ba36b025f 112 AnalogIn Alcohol(PTB2);
khuang 0:a1af4ae04b06 113
daveyclk 5:a27fdb811237 114 /* Instantiate the SSD1351 OLED Driver */
daveyclk 5:a27fdb811237 115 SSD1351 oled(PTB22,PTB21,PTC13,PTB20,PTE6, PTD15); /* (MOSI,SCLK,POWER,CS,RST,DC) */
daveyclk 5:a27fdb811237 116
daveyclk 5:a27fdb811237 117 /* Get OLED Class Default Text Properties */
daveyclk 5:a27fdb811237 118 oled_text_properties_t textProperties = {0};
daveyclk 5:a27fdb811237 119
daveyclk 5:a27fdb811237 120 /* Instantiate the Hexi KW40Z Driver (UART TX, UART RX) */
daveyclk 5:a27fdb811237 121 KW40Z kw40z_device(PTE24, PTE25);
daveyclk 5:a27fdb811237 122
daveyclk 5:a27fdb811237 123 /* LED and Haptic Set ups */
daveyclk 5:a27fdb811237 124 DigitalOut redLed(LED1);
daveyclk 5:a27fdb811237 125 DigitalOut greenLed(LED2);
daveyclk 5:a27fdb811237 126 DigitalOut blueLed(LED3);
daveyclk 5:a27fdb811237 127 DigitalOut haptic(PTB9);
daveyclk 5:a27fdb811237 128
daveyclk 5:a27fdb811237 129 /******************************************************************************
daveyclk 5:a27fdb811237 130 * Bluetooth button functions and passkey function
daveyclk 5:a27fdb811237 131 *******************************************************************************/
daveyclk 5:a27fdb811237 132
daveyclk 5:a27fdb811237 133 void ButtonRight(void)
daveyclk 5:a27fdb811237 134 {
daveyclk 5:a27fdb811237 135 StartHaptic();
daveyclk 5:a27fdb811237 136 kw40z_device.ToggleAdvertisementMode();
daveyclk 5:a27fdb811237 137 blueLed = kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 138 redLed = !kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 139 greenLed = !kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 140 }
daveyclk 5:a27fdb811237 141
daveyclk 5:a27fdb811237 142 void ButtonLeft(void)
daveyclk 5:a27fdb811237 143 {
daveyclk 5:a27fdb811237 144 StartHaptic();
daveyclk 5:a27fdb811237 145 kw40z_device.ToggleAdvertisementMode();
daveyclk 5:a27fdb811237 146 blueLed = kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 147 redLed = !kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 148 greenLed = !kw40z_device.GetAdvertisementMode(); /*Indicate BLE Advertisment Mode*/
daveyclk 5:a27fdb811237 149 }
daveyclk 5:a27fdb811237 150
daveyclk 5:a27fdb811237 151 void PassKey(void)
daveyclk 5:a27fdb811237 152 {
daveyclk 5:a27fdb811237 153 StartHaptic();
daveyclk 5:a27fdb811237 154 strcpy((char *) text,"PAIR CODE");
daveyclk 5:a27fdb811237 155 oled.TextBox((uint8_t *)text,0,25,95,18);
daveyclk 5:a27fdb811237 156
daveyclk 5:a27fdb811237 157 /* Display Bond Pass Key in a 95px by 18px textbox at x=0,y=40 */
daveyclk 5:a27fdb811237 158 sprintf(text3,"%d", kw40z_device.GetPassKey());
daveyclk 5:a27fdb811237 159 oled.TextBox((uint8_t *)text3,0,40,95,18);
daveyclk 5:a27fdb811237 160 }
daveyclk 5:a27fdb811237 161
daveyclk 5:a27fdb811237 162 /******************************************************************************
daveyclk 5:a27fdb811237 163 * Main
daveyclk 5:a27fdb811237 164 *******************************************************************************/
daveyclk 5:a27fdb811237 165 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 166 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 167 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 168 int main()
daveyclk 5:a27fdb811237 169 {
daveyclk 5:a27fdb811237 170 /* Set pointers to the BMPs stored in iBreatheImages.c */
daveyclk 5:a27fdb811237 171 welcome = iBreatheWS_bmp; // Welcome screen image
daveyclk 5:a27fdb811237 172 blank = iBreatheBlank_bmp; // blank image
daveyclk 5:a27fdb811237 173 blow = iBreatheBlow_bmp; // Start Blowing Image
daveyclk 5:a27fdb811237 174 drink = iBreatheDrink_bmp; // You've been drinking image
daveyclk 5:a27fdb811237 175 drive = iBreatheDrive_bmp; // Don't drive image
daveyclk 5:a27fdb811237 176 hang = iBreatheHang_bmp; // You'll have a hangover image
daveyclk 5:a27fdb811237 177 ini = iBreatheini_bmp; // Initialising image
daveyclk 5:a27fdb811237 178 sober = iBreatheSober_bmp; // Sober as a judge image
daveyclk 6:7f4ba36b025f 179
daveyclk 5:a27fdb811237 180 /* Set initial Values */
daveyclk 5:a27fdb811237 181 sysinit();
daveyclk 5:a27fdb811237 182 }
daveyclk 5:a27fdb811237 183
daveyclk 5:a27fdb811237 184 /******************************************************************************
daveyclk 5:a27fdb811237 185 * Public Function Definitions
daveyclk 5:a27fdb811237 186 *******************************************************************************/
daveyclk 5:a27fdb811237 187 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 188 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 189 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 190 /**************************************************************************************************
daveyclk 5:a27fdb811237 191 * Function readSensor(void)
daveyclk 5:a27fdb811237 192 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 193 * Overview: Read sensor
daveyclk 5:a27fdb811237 194 * Input: None
daveyclk 5:a27fdb811237 195 * Output: None
daveyclk 5:a27fdb811237 196 **************************************************************************************************/
daveyclk 5:a27fdb811237 197
daveyclk 5:a27fdb811237 198 void ReadSensor()
daveyclk 5:a27fdb811237 199 {
daveyclk 5:a27fdb811237 200 /* Read 16 Bit Analog value */
daveyclk 5:a27fdb811237 201 adc_rd = Alcohol.read_u16();
daveyclk 5:a27fdb811237 202
daveyclk 5:a27fdb811237 203 // pause 200ms
daveyclk 5:a27fdb811237 204 Thread::wait(200);
daveyclk 5:a27fdb811237 205 }
daveyclk 5:a27fdb811237 206
daveyclk 5:a27fdb811237 207 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 208 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 209 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 210 /**************************************************************************************************
daveyclk 5:a27fdb811237 211 * Function CalculatePPM(Int times, bool amb)
daveyclk 5:a27fdb811237 212 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 213 * Overview: Calculation of PPM
daveyclk 5:a27fdb811237 214 * Input: times = Number of samples to take, amb sets either ambient reading or test reading (true for test)
daveyclk 5:a27fdb811237 215 * Output: None
daveyclk 5:a27fdb811237 216 **************************************************************************************************/
khuang 0:a1af4ae04b06 217
daveyclk 5:a27fdb811237 218 void CalculatePPM(int times, bool amb)
daveyclk 5:a27fdb811237 219 {
daveyclk 5:a27fdb811237 220 float lgPPM;
daveyclk 5:a27fdb811237 221
daveyclk 5:a27fdb811237 222 /* Read values x times */
daveyclk 5:a27fdb811237 223 for(int x = 0; x < times; x++)
daveyclk 5:a27fdb811237 224 {
daveyclk 5:a27fdb811237 225 ReadSensor();
daveyclk 5:a27fdb811237 226 value[x] = ((float)adc_rd * Vadc_3V3);
daveyclk 5:a27fdb811237 227 StartHaptic();
daveyclk 5:a27fdb811237 228 Thread::wait(50);
daveyclk 5:a27fdb811237 229 }
daveyclk 5:a27fdb811237 230
daveyclk 5:a27fdb811237 231 /* Calculate the average value for accuratcy */
daveyclk 5:a27fdb811237 232 for(int y = 0; y < times; y++)
daveyclk 5:a27fdb811237 233 {
daveyclk 5:a27fdb811237 234 Vrl += value[y];
daveyclk 5:a27fdb811237 235 }
daveyclk 5:a27fdb811237 236 Vrl = Vrl / times;
daveyclk 5:a27fdb811237 237
daveyclk 5:a27fdb811237 238 /* Set SensorRes reference value */
daveyclk 5:a27fdb811237 239 SensorRes = (Vrl / 3.3);
daveyclk 5:a27fdb811237 240
daveyclk 5:a27fdb811237 241 /* Set ratio */
daveyclk 5:a27fdb811237 242 ratio = SensorRes1 / SensorRes;
daveyclk 5:a27fdb811237 243
daveyclk 5:a27fdb811237 244 /* Convert to PPM */
daveyclk 5:a27fdb811237 245 lgPPM = ( log10( ratio ) * -1.5512 ) + 2.5911;
daveyclk 5:a27fdb811237 246
daveyclk 5:a27fdb811237 247 /* If true create test result, flase creates reference result */
daveyclk 5:a27fdb811237 248 if (amb == true)
daveyclk 5:a27fdb811237 249 {
daveyclk 5:a27fdb811237 250 ppm = pow( 10, lgPPM );
daveyclk 5:a27fdb811237 251 }
daveyclk 5:a27fdb811237 252 else
daveyclk 5:a27fdb811237 253 {
daveyclk 5:a27fdb811237 254 ppm_1 = pow( 10, lgPPM );
daveyclk 5:a27fdb811237 255 }
daveyclk 5:a27fdb811237 256 }
daveyclk 5:a27fdb811237 257
daveyclk 5:a27fdb811237 258 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 259 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 260 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 261 /**************************************************************************************************
daveyclk 5:a27fdb811237 262 * Function void ambient(int times)
daveyclk 5:a27fdb811237 263 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 264 * Overview: Reading of the Ambient Voltgage of the sensor for reference
daveyclk 5:a27fdb811237 265 * Input: times = Number of samples to take
daveyclk 5:a27fdb811237 266 * Output: None
daveyclk 5:a27fdb811237 267 **************************************************************************************************/
daveyclk 5:a27fdb811237 268
daveyclk 5:a27fdb811237 269 void ambient(int times)
daveyclk 5:a27fdb811237 270 {
daveyclk 5:a27fdb811237 271 /* Read ambient values x times flashing green led*/
daveyclk 5:a27fdb811237 272 for(int x = 0; x < times; x++)
daveyclk 5:a27fdb811237 273 {
daveyclk 5:a27fdb811237 274 redLed = LED_OFF;
daveyclk 5:a27fdb811237 275 greenLed = LED_OFF;
daveyclk 5:a27fdb811237 276 blueLed = LED_OFF;
daveyclk 5:a27fdb811237 277
daveyclk 5:a27fdb811237 278 ReadSensor();
daveyclk 5:a27fdb811237 279 value1[x] = (float)adc_rd * Vadc_3V3;
daveyclk 5:a27fdb811237 280
daveyclk 5:a27fdb811237 281 redLed = LED_OFF;
daveyclk 5:a27fdb811237 282 greenLed = LED_ON;
daveyclk 5:a27fdb811237 283 blueLed = LED_OFF;
daveyclk 5:a27fdb811237 284 Thread::wait(48);
daveyclk 5:a27fdb811237 285 }
khuang 0:a1af4ae04b06 286
daveyclk 5:a27fdb811237 287 /* Calculate the average value for accuratcy */
daveyclk 5:a27fdb811237 288 for(int y = 0; y < times; y++)
daveyclk 5:a27fdb811237 289 {
daveyclk 5:a27fdb811237 290 ambientAlc+=value1[y];
daveyclk 5:a27fdb811237 291 }
daveyclk 5:a27fdb811237 292 ambientAlc = ambientAlc / times;
daveyclk 5:a27fdb811237 293
daveyclk 5:a27fdb811237 294 /* Set SensorRes1 reference value */
daveyclk 5:a27fdb811237 295 SensorRes1 = (ambientAlc / 3.3);
daveyclk 5:a27fdb811237 296 }
daveyclk 5:a27fdb811237 297
daveyclk 5:a27fdb811237 298 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 299 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 300 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 301 /**************************************************************************************************
daveyclk 5:a27fdb811237 302 * Function void StartHaptic(void)
daveyclk 5:a27fdb811237 303 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 304 * Overview: Start Buzzing haptic motor
daveyclk 5:a27fdb811237 305 * Input: None
daveyclk 5:a27fdb811237 306 * Output: None
daveyclk 5:a27fdb811237 307 **************************************************************************************************/
daveyclk 5:a27fdb811237 308
daveyclk 5:a27fdb811237 309 void StartHaptic(void)
daveyclk 5:a27fdb811237 310 {
daveyclk 5:a27fdb811237 311 hapticTimer.start(50);
daveyclk 5:a27fdb811237 312 haptic = 1;
daveyclk 5:a27fdb811237 313 }
daveyclk 5:a27fdb811237 314
daveyclk 5:a27fdb811237 315 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 316 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 317 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 318 /**************************************************************************************************
daveyclk 5:a27fdb811237 319 * Function void StopHaptic(void)
daveyclk 5:a27fdb811237 320 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 321 * Overview: Stop Buzzing haptic motor
daveyclk 5:a27fdb811237 322 * Input: None
daveyclk 5:a27fdb811237 323 * Output: None
daveyclk 5:a27fdb811237 324 **************************************************************************************************/
daveyclk 5:a27fdb811237 325
daveyclk 5:a27fdb811237 326 void StopHaptic(void const *n) {
daveyclk 5:a27fdb811237 327 haptic = 0;
daveyclk 5:a27fdb811237 328 hapticTimer.stop();
daveyclk 5:a27fdb811237 329 }
daveyclk 5:a27fdb811237 330
daveyclk 5:a27fdb811237 331 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 332 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 333 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 334 /**************************************************************************************************
daveyclk 5:a27fdb811237 335 * Function void ButtonUp(void)
daveyclk 5:a27fdb811237 336 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 337 * Overview: Function called whe up button pressed, Begins Breathilyzer testing procedure
daveyclk 5:a27fdb811237 338 * Input: None
daveyclk 5:a27fdb811237 339 * Output: None
daveyclk 5:a27fdb811237 340 **************************************************************************************************/
khuang 0:a1af4ae04b06 341
daveyclk 5:a27fdb811237 342 void ButtonUp(void)
daveyclk 5:a27fdb811237 343 {
daveyclk 5:a27fdb811237 344 StartHaptic();
daveyclk 6:7f4ba36b025f 345
daveyclk 6:7f4ba36b025f 346 bool Ref = false;
daveyclk 6:7f4ba36b025f 347 bool Test = true;
daveyclk 5:a27fdb811237 348
daveyclk 5:a27fdb811237 349 /* LED set to green for test beginning*/
daveyclk 5:a27fdb811237 350 redLed = LED_OFF;
daveyclk 5:a27fdb811237 351 greenLed = LED_ON;
daveyclk 5:a27fdb811237 352 blueLed = LED_OFF;
daveyclk 5:a27fdb811237 353
daveyclk 5:a27fdb811237 354 /* Fill 96px by 96px Screen with 96px by 96px Initialising Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 355 oled.DrawImage(ini,0,0);
daveyclk 5:a27fdb811237 356
daveyclk 6:7f4ba36b025f 357 /* first boot bug work around to stop junk values */
daveyclk 6:7f4ba36b025f 358 if (isFirstBoot == true)
daveyclk 6:7f4ba36b025f 359 {
daveyclk 6:7f4ba36b025f 360 /*read ambient atmosphere levels with 10 samples and set flag to show it's ambient basline figure*/
daveyclk 6:7f4ba36b025f 361 ambient(1);
daveyclk 6:7f4ba36b025f 362 CalculatePPM(1,Ref);
daveyclk 6:7f4ba36b025f 363 isFirstBoot = false;
daveyclk 6:7f4ba36b025f 364 }
daveyclk 6:7f4ba36b025f 365
daveyclk 5:a27fdb811237 366 /*read ambient atmosphere levels with 10 samples and set flag to show it's ambient basline figure*/
daveyclk 5:a27fdb811237 367 ambient(10);
daveyclk 6:7f4ba36b025f 368 CalculatePPM(10,Ref);
daveyclk 6:7f4ba36b025f 369
daveyclk 5:a27fdb811237 370
daveyclk 5:a27fdb811237 371 /* Fill 96px by 96px Screen with 96px by 96px Blowing Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 372 oled.DrawImage(blow,0,0);
daveyclk 5:a27fdb811237 373
daveyclk 5:a27fdb811237 374 /*read breathe alcohol levels with 10 samples and set flag to show it's breathilyzer test figure*/
daveyclk 6:7f4ba36b025f 375 CalculatePPM(10,Test);
daveyclk 5:a27fdb811237 376
daveyclk 5:a27fdb811237 377 /*Calculate the difference in Alcohol level based on Ambient and test sample*/
daveyclk 5:a27fdb811237 378 ppm = ppm - ppm_1;
daveyclk 5:a27fdb811237 379
daveyclk 5:a27fdb811237 380 /*Throw away any values less than 0*/
daveyclk 5:a27fdb811237 381 if (ppm < 0)
daveyclk 5:a27fdb811237 382 {
daveyclk 5:a27fdb811237 383 ppm = 0;
daveyclk 5:a27fdb811237 384 }
daveyclk 5:a27fdb811237 385
daveyclk 5:a27fdb811237 386 /* Fill 96px by 96px Screen with 96px by 96px Blank Background Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 387 oled.DrawImage(blank,0,0);
daveyclk 5:a27fdb811237 388
daveyclk 5:a27fdb811237 389 /* Show Calculated alcohol level in PPM and send data via bluetooth to the cloud */
daveyclk 5:a27fdb811237 390 oled.SetTextProperties(&textProperties);
daveyclk 5:a27fdb811237 391 oled.Label(ppmText,20,36);
daveyclk 5:a27fdb811237 392 sprintf(text,"%.2f",ppm);
daveyclk 5:a27fdb811237 393 oled.Label((uint8_t *)text,50,36);
daveyclk 5:a27fdb811237 394 Thread::wait(1000);
daveyclk 5:a27fdb811237 395
daveyclk 5:a27fdb811237 396 /* Currently sending to the Pressure variable as a temp place holder */
daveyclk 7:5d272a0e250b 397 kw40z_device.SendiBreathe(ppm); // this is used for custom Hexiware app
daveyclk 7:5d272a0e250b 398 kw40z_device.SendPressure(ppm * 10); // using this to record on Wolksense Cloud
daveyclk 7:5d272a0e250b 399
daveyclk 5:a27fdb811237 400
daveyclk 5:a27fdb811237 401 /* You've got a Hangover coming!*/
daveyclk 5:a27fdb811237 402 if ( ppm > 200)
daveyclk 5:a27fdb811237 403 {
daveyclk 5:a27fdb811237 404 redLed = LED_ON;
daveyclk 5:a27fdb811237 405 greenLed = LED_OFF;
daveyclk 5:a27fdb811237 406 blueLed = LED_OFF;
daveyclk 5:a27fdb811237 407
daveyclk 5:a27fdb811237 408 StartHaptic();
daveyclk 5:a27fdb811237 409
daveyclk 5:a27fdb811237 410 /* Fill 96px by 96px Screen with 96px by 96px Hangover Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 411 oled.DrawImage(hang,0,0);
daveyclk 5:a27fdb811237 412 }
daveyclk 5:a27fdb811237 413
daveyclk 5:a27fdb811237 414 /* You Shouldn't drive */
daveyclk 5:a27fdb811237 415 else if (ppm < 200 && ppm > 150)
daveyclk 5:a27fdb811237 416 {
daveyclk 5:a27fdb811237 417 redLed = LED_ON;
daveyclk 5:a27fdb811237 418 greenLed = LED_OFF;
daveyclk 5:a27fdb811237 419 blueLed = LED_ON;
daveyclk 5:a27fdb811237 420
daveyclk 5:a27fdb811237 421 StartHaptic();
daveyclk 5:a27fdb811237 422
daveyclk 5:a27fdb811237 423 /* Fill 96px by 96px Screen with 96px by 96px Don't Drive Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 424 oled.DrawImage(drive,0,0);
daveyclk 5:a27fdb811237 425 }
daveyclk 5:a27fdb811237 426
daveyclk 5:a27fdb811237 427 /* You've had a drink */
daveyclk 5:a27fdb811237 428 else if (ppm < 150 && ppm > 50)
daveyclk 5:a27fdb811237 429 {
daveyclk 5:a27fdb811237 430 redLed = LED_OFF;
daveyclk 5:a27fdb811237 431 greenLed = LED_ON;
daveyclk 5:a27fdb811237 432 blueLed = LED_ON;
daveyclk 5:a27fdb811237 433
daveyclk 5:a27fdb811237 434 StartHaptic();
daveyclk 5:a27fdb811237 435
daveyclk 5:a27fdb811237 436 /* Fill 96px by 96px Screen with 96px by 96px Had a drink Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 437 oled.DrawImage(drink,0,0);
daveyclk 5:a27fdb811237 438 }
daveyclk 5:a27fdb811237 439
daveyclk 5:a27fdb811237 440 /* Sober as a judge*/
daveyclk 5:a27fdb811237 441 else
daveyclk 5:a27fdb811237 442 {
daveyclk 5:a27fdb811237 443 redLed = LED_OFF;
daveyclk 5:a27fdb811237 444 greenLed = LED_ON;
daveyclk 5:a27fdb811237 445 blueLed = LED_OFF;
daveyclk 5:a27fdb811237 446
daveyclk 5:a27fdb811237 447 StartHaptic();
daveyclk 5:a27fdb811237 448 oled.DrawImage(sober,0,0);
daveyclk 5:a27fdb811237 449 }
daveyclk 5:a27fdb811237 450 Thread::wait(5000);
daveyclk 5:a27fdb811237 451
daveyclk 5:a27fdb811237 452 /* Go back to start screen */
daveyclk 5:a27fdb811237 453 sysinit();
daveyclk 5:a27fdb811237 454 }
daveyclk 5:a27fdb811237 455
daveyclk 5:a27fdb811237 456 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 457 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 458 /////////////////////////////////////////////////////////////////////////////////////////////////////////////
daveyclk 5:a27fdb811237 459 /**************************************************************************************************
daveyclk 5:a27fdb811237 460 * Function void sysint(void)
daveyclk 5:a27fdb811237 461 * -------------------------------------------------------------------------------------------------
daveyclk 5:a27fdb811237 462 * Overview: System Initial Values Set up
daveyclk 5:a27fdb811237 463 * Input: None
daveyclk 5:a27fdb811237 464 * Output: None
daveyclk 5:a27fdb811237 465 **************************************************************************************************/
daveyclk 5:a27fdb811237 466 void sysinit(void)
daveyclk 5:a27fdb811237 467 {
daveyclk 5:a27fdb811237 468 /* Set LED to Blue by default*/
daveyclk 5:a27fdb811237 469 redLed = LED_OFF;
daveyclk 5:a27fdb811237 470 greenLed = LED_OFF;
daveyclk 5:a27fdb811237 471 blueLed = LED_ON;
daveyclk 5:a27fdb811237 472
khuang 1:42e8e50ae4ac 473 /* Turn on the backlight of the OLED Display */
khuang 1:42e8e50ae4ac 474 oled.DimScreenON();
khuang 1:42e8e50ae4ac 475
daveyclk 5:a27fdb811237 476 /* Fill 96px by 96px Screen with 96px by 96px Welcome Image starting at x=0,y=0 */
daveyclk 5:a27fdb811237 477 oled.DrawImage(welcome,0,0);
daveyclk 5:a27fdb811237 478
daveyclk 5:a27fdb811237 479 /* Register callbacks to application functions */
daveyclk 5:a27fdb811237 480 kw40z_device.attach_buttonUp(&ButtonUp);
daveyclk 5:a27fdb811237 481 kw40z_device.attach_buttonLeft(&ButtonLeft);
daveyclk 5:a27fdb811237 482 kw40z_device.attach_buttonRight(&ButtonRight);
daveyclk 5:a27fdb811237 483 kw40z_device.attach_passkey(&PassKey);
daveyclk 5:a27fdb811237 484
daveyclk 5:a27fdb811237 485 /* Send sensor data to bluetooth */
daveyclk 5:a27fdb811237 486 kw40z_device.SendSetApplicationMode(GUI_CURRENT_APP_SENSOR_TAG);
daveyclk 5:a27fdb811237 487
daveyclk 5:a27fdb811237 488 /* Change font color to White */
daveyclk 5:a27fdb811237 489 oled.GetTextProperties(&textProperties);
daveyclk 5:a27fdb811237 490 textProperties.fontColor = COLOR_WHITE;
khuang 0:a1af4ae04b06 491 oled.SetTextProperties(&textProperties);
daveyclk 5:a27fdb811237 492 }