My ELEC2645 sensor project Bader Alathri 200826344

Dependencies:   FXOS8700Q N5110 SRF02 mbed

Files at this revision

API Documentation at this revision

Comitter:
fy13ba
Date:
Thu May 05 14:59:50 2016 +0000
Commit message:
final version

Changed in this revision

FXOS8700Q.lib Show annotated file Show diff for this revision Revisions of this file
N5110.lib Show annotated file Show diff for this revision Revisions of this file
SRF02.lib Show annotated file Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
main.h Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/FXOS8700Q.lib	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,1 @@
+https://developer.mbed.org/teams/ELEC2645-201516/code/FXOS8700Q/#8b9c3245ad61
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/N5110.lib	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/eencae/code/N5110/#ba8addc061ea
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/SRF02.lib	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/eencae/code/SRF02/#8e6587d88773
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,400 @@
+/*
+
+Bader Alathri
+ELEC2645_project
+
+*/
+
+
+#include "main.h"
+
+BusIn input(PTC5,PTC7); /// external button inputs (toggle,select)
+
+
+struct State { /// struct to group state information
+    int output;  /// output value
+    float time;    /// time in state
+    int nextState[4];  /// array of next states
+};
+
+typedef const struct State STyp;
+
+
+STyp fsm[9] = { /// finite state machine (FSM) transition table
+    {0,0.15,{0,1,3,0}},
+    {1,0.15,{1,2,7,1}},
+    {2,0.15,{2,0,8,2}},
+    {3,0.15,{3,4,5,3}},
+    {4,0.15,{4,3,6,4}},
+    {5,0.15,{5,0,5,5}},
+    {6,0.15,{6,0,6,6}},
+    {7,0.15,{7,0,7,7}},
+    {8,0.15,{8,0,8,8}}
+
+};
+
+
+int main()
+{
+
+    init_K64F();   /// initialise the board and serial port
+    init_serial(); /// initialise serial port
+    lcd.init(); /// initialise display
+    brightness = 0.4; /// setting initial brightness value to 0.4
+    lcd.setBrightness(brightness); /// sets lcd brightness to match 'brightness' variable
+    toggle.rise(&toggle_isr); /// rising edge for interrupt input set to trigger ISR (toggle button)
+    select.rise(&select_isr); /// rising edge for interrupt interrupt set to trigger ISR (select button)
+
+    toggle.mode(PullDown); /// interrupt input pin set to pulldown mode (toggle button)
+    select.mode(PullDown); /// interrupt input pin set to pulldown mode (select button)
+    /// as both buttons are connected to 3V3
+
+    int state = 0; /// intitial FSM state set to 0
+
+    while(1) {
+
+        int output; // /stores value of state output
+        output = fsm[state].output;  /// set ouput depending on current state
+        wait(fsm[state].time);       /// wait in that state for desired time
+        state = fsm[state].nextState[input];  /// read input (BusIn) and update curent state
+
+        if ( output == 0) { /// first state
+
+            acc.disable(); /// disable accelerometer, from FXOS8700Q library
+            ticker1.detach(); /// stops ticker from triggering timer1 ISR
+            g_toggle_flag = 0; /// resets toggle flag to 0
+            r_led = 0; /// turns off external red LED
+            g_led = 0; /// turns off external green LED
+
+            lcd.clear(); /// clears lcd
+            lcd.drawCircle(3,12,1,1); /// displays small circle next to selected option
+            /// display options on lcd
+            lcd.printString("get distance",7,1);
+            lcd.printString("spirit level",7,3);
+            lcd.printString("brightness",7,5);
+
+
+
+        } else if ( output == 1 ) { /// second state
+
+            g_toggle_flag = 0; /// resets toggle flag to 0
+            lcd.clear(); /// clears lcd
+            lcd.drawCircle(3,28,1,1); /// displays small circle next to selected option
+            /// display options on lcd
+            lcd.printString("get distance",7,1);
+            lcd.printString("spirit level",7,3);
+            lcd.printString("brightness",7,5);
+
+
+
+        } else if ( output == 2 ) { /// third state
+
+            g_toggle_flag = 0; /// resets toggle flag to 0
+            lcd.clear(); /// clears lcd
+            lcd.drawCircle(3,44,1,1); /// displays small circle next to selected option
+            /// display options on lcd
+            lcd.printString("get distance",7,1);
+            lcd.printString("spirit level",7,3);
+            lcd.printString("brightness",7,5);
+
+
+
+
+        } else if ( output == 3 ) { /// fourth state
+
+            g_select_flag = 0; /// resets select flag to 0
+            lcd.clear(); /// clears lcd
+            lcd.drawCircle(3,12,1,1); /// displays small circle next to selected option
+            /// display unit options on lcd
+            lcd.printString("centimetres",7,1);
+            lcd.printString("inches",7,3);
+
+        } else if ( output == 4 ) { /// fifth state
+
+            g_toggle_flag = 0; /// resets toggle flag to 0
+            lcd.clear(); /// clears lcd
+            lcd.drawCircle(3,28,1,1); /// displays small circle next to selected option
+            /// display unit options on lcd
+            lcd.printString("centimetres",7,1);
+            lcd.printString("inches",7,3);
+
+        } else if ( output == 5 && g_select_flag == 1 ) { /// sixth state, two conditions so that state triggers only once
+
+            g_select_flag = 0; /// resets select flag to 0
+            lcd.clear(); /// clears lcd
+            measuring_transition(); /// displays transition while measurement is taking place
+            get_average_distance_cm(); /// calculates average distance in cm from readings
+            lcd.clear(); /// clears lcd
+
+
+
+            if (g_error_flag) { /// checks if error flag is triggered
+                g_error_flag = 0; /// resets error flag to 0
+                measurement_error(); /// displays error message
+
+            }
+
+
+            else { /// if error flag was not triggered
+                display_distance_cm(); /// displays distance in cm
+                g_led = 1; /// turns on green external LED
+            }
+            lcd.refresh(); ///refreshes lcd
+            sleep(); /// puts K64F into sleep mode
+        }
+
+
+        else if ( output == 6 && g_select_flag == 1 ) { /// seventh state, two conditions so that state triggers only once
+
+            g_select_flag = 0; /// resets select flag to 0
+            lcd.clear(); /// clears lcd
+            measuring_transition(); /// displays transition while measurement is taking place
+            get_average_distance_in(); ///c alculates average distance in inches from readings
+            lcd.clear(); /// clears lcd
+
+
+            if (g_error_flag) { /// checks if error flag is triggered
+                g_error_flag = 0; /// resets error flag to 0
+                measurement_error(); /// displays error message
+            }
+
+
+            else { /// if error flag was not triggered
+                display_distance_in(); /// displays distance in inches
+                g_led = 1; /// turns on green external LED
+            }
+            lcd.refresh(); /// refreshes lcd
+            sleep(); /// puts K64F into sleep mode
+        }
+
+        else if ( output == 7 ) { /// eighth state
+
+            acc.enable(); /// enabling FXOS8700 accelerometer, credit: https://developer.mbed.org/teams/Freescale/code/Hello_FXOS8700Q/
+            ticker1.attach(&timer1_isr,0.125); /// attaching ticker1 to timer1 ISR
+            /// ISR triggered every 0.125 seconds
+
+            if (g_timer1_flag) { /// checks if ISR is triggered
+
+                g_timer1_flag = 0; /// resets timer flag to 0
+
+                get_z_axis_value(); ///calculates average z-axis reading
+                lcd.clear(); /// clears lcd
+                display_flatness(); /// displays whether surface is found to be flat
+                lcd.refresh(); /// refreshes lcd
+                sleep(); /// puts K64F into sleep mode
+            }
+
+
+        } else if ( output == 8 && g_select_flag == 1 ) { /// ninth state
+            g_select_flag = 0; /// resets select flag to 0
+            lcd.clear(); /// clears lcd
+            adjust_brightness(); /// adjusts brightness according to current value of 'brightness' variable
+            display_brightness(); /// displays brightness as a percentage on lcd
+            lcd.refresh(); /// refreshes lcd
+            sleep(); /// puts K64F into sleep mode
+
+        }
+
+    }
+}
+
+
+void init_serial()
+{
+
+    pc.baud(115200); /// set to highest baud - ensure terminal software matches
+}
+
+void init_K64F()
+{
+    /// on-board LEDs are active-low, so set pin high to turn them off.
+    red_led = 1;
+    green_led = 1;
+    blue_led = 1;
+
+}
+
+void timer1_isr()
+{
+    g_timer1_flag = 1;  /// set timer1 flag in ISR
+}
+
+void select_isr()
+{
+    g_select_flag = 1; /// set select flag in ISR
+}
+
+void toggle_isr()
+{
+    g_toggle_flag = 1; /// set toggle flag in ISR
+}
+
+void measurement_error()
+{
+    lcd.printString("error",25,2); /// displays 'error' on lcd
+    r_led = 1; /// turns on external red LED
+
+}
+
+void measuring_transition()
+{
+    /// turns off external LEDs
+    r_led = 0;
+    g_led = 0;
+    lcd.printString("measuring...",10,2); /// displays measuring message on lcd
+}
+
+void get_average_distance_cm()
+{
+    total_distance = 0.0; /// resets value for total distance
+    average_distance_cm = 0.0; /// resets value for average distance (cm)
+    for ( int i=0; i<10; i++) { /// 10 iterations
+
+        float distance = sensor.getDistanceCm(); /// gets 1 distance reading from sensor in cm
+        total_distance = total_distance + distance; /// stores sum of readings
+
+        if ( distance >= 249 ) { /// if a single measurement is above the range of the sensor
+
+            g_error_flag = 1; /// trigger error flag
+
+
+        }
+
+        else if ( distance <= 15 ) { /// if a single measurement is below the range of the sensor
+
+            g_error_flag = 1; /// trigger error flag
+
+        }
+        pc.printf("Distance = %.2f cm\n",distance); /// prints distance measurements to pc in cm
+    }
+
+    average_distance_cm = total_distance/10; /// calculates average distance in cm
+}
+
+void get_average_distance_in()
+{
+    total_distance = 0.0; /// resets value for total distance
+    average_distance_in = 0.0; /// resets value for average distance (inches)
+    for ( int i=0; i<10; i++) { /// 10 iterations
+
+        float distance = sensor.getDistanceCm(); /// gets 1 distance reading from sensor in cm
+        total_distance = total_distance + distance; /// stores sum of readings
+
+        if ( distance >= 249 ) { /// if a single measurement is above the range of the sensor
+
+            g_error_flag = 1; /// trigger error flag
+
+
+        }
+
+        else if ( distance <= 15 ) { /// if a single measurement is below the range of the sensor
+
+            g_error_flag = 1; /// trigger error flag
+
+        }
+        pc.printf("Distance = %.2f cm\n",distance); /// prints distance measurements to pc in cm
+    }
+
+    average_distance_in = (total_distance/10) * 0.394; /// calculates average distance in cm then converts it to inches
+}
+
+void display_distance_cm()
+{
+    /// prints value of distance and units
+    lcd.printString("Distance:",15,1);
+    char buffer[14];
+    float length = sprintf(buffer,"%.2f cm",average_distance_cm); /// print formatted data to buffer
+    lcd.printString(buffer,17,3); /// display on lcd
+
+}
+
+void display_distance_in()
+{
+    lcd.printString("Distance:",15,1);
+    char buffer[14];
+    float length = sprintf(buffer,"%.2f inches",average_distance_in); /// print formatted data to buffer
+    lcd.printString(buffer,9,3); /// display on lcd
+
+}
+
+
+void get_z_axis_value()
+{
+
+    int16_t raZ; /// variable for storing z-axis reading taken from FXOS8700Q library
+    /// from FXOS8700Q library
+
+    acc.getAxis(acc_data); /// gets data from accelerometer, from FXOS8700Q library
+
+
+
+    acc.getZ(&raZ); /// get z-axis reading, from FXOS8700Q library
+
+
+
+    int total_z = 0; /// variable to store sum of z-axis values
+
+    for ( int i=0; i<10; i++) { /// 10 iterations
+
+        int z = raZ; /// variable to store single z-axis reading, from FXOS8700Q library
+        total_z = total_z + z; /// summing z-axis readings
+
+        wait (0.01); /// delay of 0.01 seconds between loop iterations
+    }
+
+    average_z = total_z / 10 ; /// calculates average z-axis value
+
+    pc.printf("Z=%.2f\n  ", average_z); /// prints average z-axis value to pc
+}
+
+void display_flatness()
+{
+    if ((average_z <= 280) && (average_z >= 80)) { ///if average z-axis value within specified range (vertically flat)
+        r_led = 0; /// turns off external red LED
+        g_led = 1; /// turns on external green LED
+        lcd.printString("vertically",7,1); /// displays 'vertically flat' message on lcd
+        lcd.printString("flat",30,3);
+    }
+
+    else if ((average_z <= 4160) && (average_z >= 4147)) { ///if average z-axis value within specified range (horizontaly flat)
+        r_led = 0; /// turns off external red LED
+        g_led = 1; /// turns on external green LED
+        lcd.printString("horizontally",7,1); /// displays 'horizontaly flat' message on lcd
+        lcd.printString("flat",30,3);
+    }
+
+    else if ((average_z <= -3860) && (average_z >= -3880)) { ///if average z-axis value within specified range (horizontaly flat)
+        r_led = 0; /// turns off external red LED
+        g_led = 1; /// turns on external green LED
+        lcd.printString("horizontally",7,1);  /// displays 'horizontaly flat' message on lcd
+        lcd.printString("flat",30,3);
+    }
+
+    else { /// otherwise if average z-axis value within specified ranges (not flat)
+        r_led = 1; /// turns on external red LED
+        g_led = 0; /// turns off external green LED
+        lcd.printString("not flat",18,2); /// displays 'not flat' message on lcd
+
+    }
+        
+}
+
+void adjust_brightness()
+{
+    if ( brightness == 1.0 ) { /// if the brightness value is at 1.0
+        brightness = 0.0; /// set brightness back to 0
+    } else { /// if the brightness value is not 1.0
+        brightness = brightness + 0.2; /// increase its value by 0.2
+    }
+
+    lcd.setBrightness(brightness); /// sets lcd brightness to valeu of 'brightness' variable
+}
+
+void display_brightness()
+{
+    lcd.printString("brightness:",7,1);
+    int brightness_percentage = brightness * 100; /// calculates brightness percentage
+    char buffer[14];
+    float length = sprintf(buffer,"%d%%",brightness_percentage); /// print formatted data to buffer
+    lcd.printString(buffer,31,3); /// display on lcd
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.h	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,213 @@
+/**
+@file main.h
+@brief Header file containing functions prototypes, defines and global variables.
+@brief Leeds University ELEC2645 sensor project
+@author Bader Alathri
+@date   May 2016
+*/
+
+#ifndef MAIN_H
+#define MAIN_H
+
+
+#include "mbed.h"
+#include "N5110.h"
+#include "SRF02.h"
+#include "FXOS8700Q.h"  /**
+@see https://developer.mbed.org/teams/Freescale/code/Hello_FXOS8700Q/
+*/
+
+
+
+/**
+@namespace lcd
+@brief output pins for N5110 LCD
+@brief (PWR,SCE,RST,D/C,MOSI,SCLK,LED)****
+*/
+N5110 lcd(PTA1,PTA0,PTC4,PTD0,PTD2,PTD1,PTC3);
+  
+
+/**
+@namespace sensor
+@brief output pins for SRF02 sensor
+*/
+SRF02 sensor(PTE25,PTE24);
+
+/**
+@namespace acc
+@brief output pins for FXOS8700
+@brief onboard accelerometer
+*/
+FXOS8700Q_acc acc( PTE25, PTE24, FXOS8700CQ_SLAVE_ADDR1);
+
+/**
+@namespace pc
+@brief UART connection for PC
+*/
+Serial pc(USBTX,USBRX);
+
+/**
+@see https://developer.mbed.org/teams/Freescale/code/Hello_FXOS8700Q/
+@brief retrieves data from accelerometer
+@brief taken from FXOS8700Q library
+*/
+MotionSensorDataUnits acc_data; 
+
+
+/**
+@namespace r_led
+@brief GPIO output for external red LED
+*/
+DigitalOut r_led(PTC8);
+
+/**
+@namespace g_led
+@brief GPIO output for external green LED
+*/
+DigitalOut g_led(PTC1);
+
+/**
+@namespace red_led
+@brief output for onboard red LED
+*/
+DigitalOut red_led(LED_RED);
+
+/**
+@namespace green_led
+@brief output for onboard green LED
+*/
+DigitalOut green_led(LED_GREEN);
+
+/**
+@namespace blue_led
+@brief output for onboard blue LED
+*/
+DigitalOut blue_led(LED_BLUE); 
+
+/**
+@namespace toggle
+@brief GPIO interrupt input for external toggle button
+*/
+InterruptIn toggle(PTC5);
+
+/**
+@namespace select
+@brief GPIO interrupt input for external select button
+*/
+InterruptIn select(PTC7);
+
+/**
+@namespace ticker1
+@brief periodically calls timer1_isr
+*/
+Ticker ticker1;
+
+
+volatile int g_select_flag = 0; /*!< flag to be set in ISR when select button is pressed*/
+volatile int g_toggle_flag = 0; /*!< flag to be set in ISR when toggle button is pressed*/
+volatile int g_timer1_flag =0; /*!< flag to be set in ISR when periodically by ticker1 is pressed*/
+volatile int g_error_flag = 0; /*!< flag to be set when measurement error is detected*/
+
+float total_distance; /*!< stores the sum of the 10 SRF02 readings */
+float average_distance_cm; /*!< stores the average distance calculated in cm*/
+float average_distance_in; /*!< stores the average distance calculated in inches */
+float average_z; /*!< stores the calculated average z-axis value */
+float brightness; /*!< stores the brightness value*/
+
+
+/**
+Interrupt service routine for select button
+sets select button flag
+*/
+void select_isr();
+
+/**
+Interrupt service routine for toggle button
+sets toggle button flag
+*/
+void toggle_isr();
+
+/**
+Interrupt service routine for ticker1
+sets timer1 flag
+*/
+void timer1_isr();
+
+/**
+lights up external red LED and displays error message on LCD
+*/
+void measurement_error();
+
+/**
+displays measurement transition screen and turns off external LEDs
+*/
+void measuring_transition();
+
+/**
+calculates average distance in cm from 10 SRF02 readings
+and saves it in average_distance_cm variable;
+*/
+void get_average_distance_cm();
+
+/**
+calculates average distance in inches from 10 SRF02 readings
+and saves it in average_distance_in variable;
+*/
+void get_average_distance_in();
+
+/**
+displays calculated average distance in cm on lcd
+including the units
+*/
+void display_distance_cm();
+
+/**
+displays calculated average distance in inches on lcd
+including the units
+*/
+void display_distance_in();
+
+/**
+gets average z-axis value from 10 readings in 0.1 seconds
+of the onboard FXOS8700 accelerometer
+and saves it in the average_z variable
+*/
+void get_z_axis_value();
+
+/**
+according to the calculated average_z value, 
+displays on lcd whether surface is flat or not
+specifying whether it is flat horizontally or vertically
+*/
+void display_flatness();
+
+/**
+increases brightness value by 0.2 if it is less than 1.0,
+and changes brightness to 0 if it is already at 1.0
+*/
+void adjust_brightness();
+
+/**
+displays brightness as a percentage on lcd
+*/
+void display_brightness();
+
+/**
+error function hangs flashing onboard LED
+*/
+void error();
+
+/**
+setup serial port
+*/
+void init_serial();
+
+/**
+set-up the on-board LEDs
+*/
+void init_K64F();
+
+
+
+
+#endif
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Thu May 05 14:59:50 2016 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/mbed_official/code/mbed/builds/87f2f5183dfb
\ No newline at end of file