Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed VL53L3ExpansionBoard
Main.cpp@2:75271310def9, 2020-10-19 (annotated)
- Committer:
- charlesmn
- Date:
- Mon Oct 19 07:30:36 2020 +0000
- Revision:
- 2:75271310def9
- Parent:
- 0:34269810c435
Some name changes. No functional change.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
charlesmn | 0:34269810c435 | 1 | /* |
charlesmn | 0:34269810c435 | 2 | * my_no_shield_interrupt.h |
charlesmn | 0:34269810c435 | 3 | * This pogram is a simple sample program which demonstrates the VL53L3 being used without |
charlesmn | 0:34269810c435 | 4 | * a nucleo sheild using interrupts to alert the program that a measurement is ready. |
charlesmn | 0:34269810c435 | 5 | * The shutdown pins are directly connected to the MCU pins D9,D4 and D3 |
charlesmn | 0:34269810c435 | 6 | * as defined by this line: |
charlesmn | 0:34269810c435 | 7 | * status = board->init_board(D9,D4,D3); |
charlesmn | 0:34269810c435 | 8 | * the interrupt pins are defined in |
charlesmn | 0:34269810c435 | 9 | * board = NoShield53L3::instance(dev_I2C, A2, D8, D2); |
charlesmn | 0:34269810c435 | 10 | * |
charlesmn | 0:34269810c435 | 11 | * This program only uses one sensor but can easily be adapted to run 3. |
charlesmn | 0:34269810c435 | 12 | * |
charlesmn | 0:34269810c435 | 13 | * Measured ranges are ouput on the Serial Port, running at 115200 baud. |
charlesmn | 0:34269810c435 | 14 | * |
charlesmn | 0:34269810c435 | 15 | * The Reset button can be used to restart the program. |
charlesmn | 0:34269810c435 | 16 | */ |
charlesmn | 0:34269810c435 | 17 | |
charlesmn | 0:34269810c435 | 18 | |
charlesmn | 0:34269810c435 | 19 | |
charlesmn | 0:34269810c435 | 20 | #include <stdio.h> |
charlesmn | 0:34269810c435 | 21 | |
charlesmn | 0:34269810c435 | 22 | #include "mbed.h" |
charlesmn | 0:34269810c435 | 23 | #include "NoShield53L3.h" |
charlesmn | 2:75271310def9 | 24 | #include "vl53L3_I2c.h" |
charlesmn | 0:34269810c435 | 25 | #include <time.h> |
charlesmn | 0:34269810c435 | 26 | |
charlesmn | 0:34269810c435 | 27 | // define I2C pins |
charlesmn | 0:34269810c435 | 28 | #define VL53L1_I2C_SDA D14 |
charlesmn | 0:34269810c435 | 29 | #define VL53L1_I2C_SCL D15 |
charlesmn | 0:34269810c435 | 30 | |
charlesmn | 0:34269810c435 | 31 | #define TIMINGBUDGET 50 |
charlesmn | 0:34269810c435 | 32 | |
charlesmn | 0:34269810c435 | 33 | static NoShield53L3 *board=NULL; |
charlesmn | 0:34269810c435 | 34 | Serial pc(SERIAL_TX, SERIAL_RX); |
charlesmn | 0:34269810c435 | 35 | |
charlesmn | 0:34269810c435 | 36 | static int int_centre_dropped = 0; |
charlesmn | 0:34269810c435 | 37 | static int int_left_dropped = 0; |
charlesmn | 0:34269810c435 | 38 | static int int_right_dropped = 0; |
charlesmn | 0:34269810c435 | 39 | |
charlesmn | 0:34269810c435 | 40 | |
charlesmn | 0:34269810c435 | 41 | |
charlesmn | 0:34269810c435 | 42 | class WaitForMeasurement { |
charlesmn | 0:34269810c435 | 43 | public: |
charlesmn | 0:34269810c435 | 44 | |
charlesmn | 0:34269810c435 | 45 | |
charlesmn | 0:34269810c435 | 46 | // this class services the interrupts from the ToF sensors. |
charlesmn | 0:34269810c435 | 47 | // There is a limited amount you can do in an interrupt routine; printfs,mutexes break them among other things. |
charlesmn | 0:34269810c435 | 48 | // We keep things simple by only raising a flag so all the real work is done outside the interrupt. |
charlesmn | 0:34269810c435 | 49 | // This is designed around MBED V2 which doesn't have the RTOS features that would make this work nicely e.g. semaphores/queues. |
charlesmn | 0:34269810c435 | 50 | WaitForMeasurement(): _interrupt(A1) |
charlesmn | 0:34269810c435 | 51 | { |
charlesmn | 0:34269810c435 | 52 | } |
charlesmn | 0:34269810c435 | 53 | |
charlesmn | 0:34269810c435 | 54 | |
charlesmn | 0:34269810c435 | 55 | // constructor - Sensor is not used and can be removed |
charlesmn | 0:34269810c435 | 56 | WaitForMeasurement(PinName pin,VL53LX_DEV Dev) : _interrupt(pin) // create the InterruptIn on the pin specified to Counter |
charlesmn | 0:34269810c435 | 57 | { |
charlesmn | 0:34269810c435 | 58 | Devlocal = Dev; |
charlesmn | 0:34269810c435 | 59 | _interrupt.fall(callback(this, &WaitForMeasurement::lost_interrupt)); // attach increment function of this counter instance |
charlesmn | 0:34269810c435 | 60 | |
charlesmn | 0:34269810c435 | 61 | } |
charlesmn | 0:34269810c435 | 62 | |
charlesmn | 0:34269810c435 | 63 | |
charlesmn | 0:34269810c435 | 64 | // function is called every time an interupt is seen. A flag is raised which allows the main routine to service the interupt. |
charlesmn | 0:34269810c435 | 65 | |
charlesmn | 0:34269810c435 | 66 | void lost_interrupt() |
charlesmn | 0:34269810c435 | 67 | { |
charlesmn | 0:34269810c435 | 68 | if (Devlocal->I2cDevAddr == NEW_SENSOR_CENTRE_ADDRESS) |
charlesmn | 0:34269810c435 | 69 | int_centre_dropped = 1; //flag to main that interrupt happened |
charlesmn | 0:34269810c435 | 70 | if (Devlocal->I2cDevAddr == NEW_SENSOR_LEFT_ADDRESS) |
charlesmn | 0:34269810c435 | 71 | int_left_dropped = 1; //flag to main that interrupt happened |
charlesmn | 0:34269810c435 | 72 | if (Devlocal->I2cDevAddr == NEW_SENSOR_RIGHT_ADDRESS) |
charlesmn | 0:34269810c435 | 73 | int_right_dropped = 1; //flag to main that interrupt happened |
charlesmn | 0:34269810c435 | 74 | } |
charlesmn | 0:34269810c435 | 75 | |
charlesmn | 0:34269810c435 | 76 | |
charlesmn | 0:34269810c435 | 77 | //destructor |
charlesmn | 0:34269810c435 | 78 | ~WaitForMeasurement() |
charlesmn | 0:34269810c435 | 79 | { |
charlesmn | 0:34269810c435 | 80 | printf("destruction \n"); |
charlesmn | 0:34269810c435 | 81 | } |
charlesmn | 0:34269810c435 | 82 | |
charlesmn | 0:34269810c435 | 83 | private: |
charlesmn | 0:34269810c435 | 84 | InterruptIn _interrupt; |
charlesmn | 0:34269810c435 | 85 | VL53LX_DEV Devlocal; //store the device for this instance of the class |
charlesmn | 0:34269810c435 | 86 | int status; |
charlesmn | 0:34269810c435 | 87 | |
charlesmn | 0:34269810c435 | 88 | }; |
charlesmn | 0:34269810c435 | 89 | |
charlesmn | 0:34269810c435 | 90 | |
charlesmn | 0:34269810c435 | 91 | // sensor classes. We don't use left and right in this program as we only have one sensor |
charlesmn | 0:34269810c435 | 92 | VL53LX_Dev_t devCentre; |
charlesmn | 0:34269810c435 | 93 | VL53LX_Dev_t devLeft; |
charlesmn | 0:34269810c435 | 94 | VL53LX_Dev_t devRight; |
charlesmn | 0:34269810c435 | 95 | //VL53LX_DEV Dev = &devCentre; |
charlesmn | 0:34269810c435 | 96 | |
charlesmn | 0:34269810c435 | 97 | |
charlesmn | 0:34269810c435 | 98 | |
charlesmn | 0:34269810c435 | 99 | |
charlesmn | 0:34269810c435 | 100 | |
charlesmn | 0:34269810c435 | 101 | /*=================================== Main ================================== |
charlesmn | 0:34269810c435 | 102 | =============================================================================*/ |
charlesmn | 0:34269810c435 | 103 | int main() |
charlesmn | 0:34269810c435 | 104 | { |
charlesmn | 0:34269810c435 | 105 | int status; |
charlesmn | 0:34269810c435 | 106 | // VL53LX * Sensor; |
charlesmn | 0:34269810c435 | 107 | uint16_t wordData; |
charlesmn | 0:34269810c435 | 108 | uint8_t ToFSensor = 1; // 0=Left, 1=Center(default), 2=Right |
charlesmn | 0:34269810c435 | 109 | |
charlesmn | 0:34269810c435 | 110 | // interupt classes for the sensors . we only use int1 |
charlesmn | 0:34269810c435 | 111 | WaitForMeasurement* int2; |
charlesmn | 0:34269810c435 | 112 | WaitForMeasurement* int1; |
charlesmn | 0:34269810c435 | 113 | WaitForMeasurement* int3; |
charlesmn | 0:34269810c435 | 114 | |
charlesmn | 0:34269810c435 | 115 | pc.baud(115200); // baud rate is important as printf statements take a lot of time |
charlesmn | 0:34269810c435 | 116 | |
charlesmn | 0:34269810c435 | 117 | printf("Hello world!\r\n"); |
charlesmn | 0:34269810c435 | 118 | |
charlesmn | 0:34269810c435 | 119 | // start the I2C interface |
charlesmn | 2:75271310def9 | 120 | vl53L3_DevI2C *dev_I2C = new vl53L3_DevI2C(VL53L1_I2C_SDA, VL53L1_I2C_SCL); |
charlesmn | 0:34269810c435 | 121 | |
charlesmn | 0:34269810c435 | 122 | |
charlesmn | 0:34269810c435 | 123 | /* no expansion board so don't use stmpe1600. Define interupt pins, only A2 used with one sensor */ |
charlesmn | 0:34269810c435 | 124 | board = NoShield53L3::instance(dev_I2C, A2, D8, D2); |
charlesmn | 0:34269810c435 | 125 | printf("board created!\r\n"); |
charlesmn | 0:34269810c435 | 126 | |
charlesmn | 0:34269810c435 | 127 | /* define the shutdown pins. D4 and D3 aren't used with one sensor */ |
charlesmn | 0:34269810c435 | 128 | status = board->init_board(D9,D4,D3); |
charlesmn | 0:34269810c435 | 129 | if (status) { |
charlesmn | 0:34269810c435 | 130 | printf("Failed to init board!\r\n"); |
charlesmn | 0:34269810c435 | 131 | return 0; |
charlesmn | 0:34269810c435 | 132 | } |
charlesmn | 0:34269810c435 | 133 | |
charlesmn | 0:34269810c435 | 134 | |
charlesmn | 0:34269810c435 | 135 | printf("board initiated! - %d\r\n", status); |
charlesmn | 0:34269810c435 | 136 | |
charlesmn | 0:34269810c435 | 137 | |
charlesmn | 0:34269810c435 | 138 | wait_ms(15); |
charlesmn | 0:34269810c435 | 139 | |
charlesmn | 0:34269810c435 | 140 | if (board->sensor_centre== NULL ) { |
charlesmn | 0:34269810c435 | 141 | printf("Failed to init sensor!\r\n"); |
charlesmn | 0:34269810c435 | 142 | return 0; |
charlesmn | 0:34269810c435 | 143 | } |
charlesmn | 0:34269810c435 | 144 | printf("configuring centre channel \n"); |
charlesmn | 0:34269810c435 | 145 | |
charlesmn | 0:34269810c435 | 146 | |
charlesmn | 0:34269810c435 | 147 | |
charlesmn | 0:34269810c435 | 148 | // configure the I2C interface |
charlesmn | 0:34269810c435 | 149 | |
charlesmn | 0:34269810c435 | 150 | devCentre.I2cDevAddr = NEW_SENSOR_CENTRE_ADDRESS; |
charlesmn | 0:34269810c435 | 151 | devCentre.comms_speed_khz = 400; |
charlesmn | 0:34269810c435 | 152 | devCentre.comms_type = 1; |
charlesmn | 0:34269810c435 | 153 | |
charlesmn | 0:34269810c435 | 154 | /* Device Initialization and setting */ |
charlesmn | 0:34269810c435 | 155 | |
charlesmn | 0:34269810c435 | 156 | status = board->sensor_centre->VL53LX_DataInit(); |
charlesmn | 0:34269810c435 | 157 | status = board->sensor_centre->VL53LX_SetDistanceMode(VL53LX_DISTANCEMODE_LONG); |
charlesmn | 0:34269810c435 | 158 | status = board->sensor_centre->VL53LX_SetMeasurementTimingBudgetMicroSeconds( TIMINGBUDGET * 1000); |
charlesmn | 0:34269810c435 | 159 | status = board->sensor_centre->VL53LX_SmudgeCorrectionEnable(VL53LX_SMUDGE_CORRECTION_SINGLE); |
charlesmn | 0:34269810c435 | 160 | status = board->sensor_centre->VL53LX_SetXTalkCompensationEnable(1); |
charlesmn | 0:34269810c435 | 161 | |
charlesmn | 0:34269810c435 | 162 | printf("starting interrupt centre\n"); |
charlesmn | 0:34269810c435 | 163 | |
charlesmn | 0:34269810c435 | 164 | int1 = new WaitForMeasurement(A2,&devCentre); // initialise interrupt for the sensor |
charlesmn | 0:34269810c435 | 165 | status = board->sensor_centre->VL53LX_StartMeasurement(); |
charlesmn | 0:34269810c435 | 166 | status = board->sensor_centre->VL53LX_ClearInterruptAndStartMeasurement(); |
charlesmn | 0:34269810c435 | 167 | |
charlesmn | 0:34269810c435 | 168 | |
charlesmn | 0:34269810c435 | 169 | |
charlesmn | 0:34269810c435 | 170 | // loop waiting for interrupts to happen. This is signaled by int_centre_dropped |
charlesmn | 0:34269810c435 | 171 | // being non zero. It is set back to zero when processing is completed |
charlesmn | 0:34269810c435 | 172 | while (1) |
charlesmn | 0:34269810c435 | 173 | { |
charlesmn | 0:34269810c435 | 174 | |
charlesmn | 0:34269810c435 | 175 | VL53LX_MultiRangingData_t MultiRangingData; |
charlesmn | 0:34269810c435 | 176 | VL53LX_MultiRangingData_t *pMultiRangingData = &MultiRangingData; |
charlesmn | 0:34269810c435 | 177 | |
charlesmn | 0:34269810c435 | 178 | wait_ms( 1 * 10); |
charlesmn | 0:34269810c435 | 179 | |
charlesmn | 0:34269810c435 | 180 | if (int_centre_dropped != 0) |
charlesmn | 0:34269810c435 | 181 | { |
charlesmn | 0:34269810c435 | 182 | int_centre_dropped = 0; |
charlesmn | 0:34269810c435 | 183 | // interrupt has occurred so a measurement is waiting |
charlesmn | 0:34269810c435 | 184 | status = board->sensor_centre->VL53LX_GetMultiRangingData( pMultiRangingData); |
charlesmn | 0:34269810c435 | 185 | int no_of_object_found=pMultiRangingData->NumberOfObjectsFound; |
charlesmn | 0:34269810c435 | 186 | if (( no_of_object_found < 10 ) && ( no_of_object_found != 0 )) |
charlesmn | 0:34269810c435 | 187 | { |
charlesmn | 0:34269810c435 | 188 | for(int j=0;j<no_of_object_found;j++){ |
charlesmn | 0:34269810c435 | 189 | if ((pMultiRangingData->RangeData[j].RangeStatus == VL53LX_RANGESTATUS_RANGE_VALID) || |
charlesmn | 0:34269810c435 | 190 | (pMultiRangingData->RangeData[j].RangeStatus == VL53LX_RANGESTATUS_RANGE_VALID_NO_WRAP_CHECK_FAIL)) |
charlesmn | 0:34269810c435 | 191 | { |
charlesmn | 0:34269810c435 | 192 | printf("centre\t status=%d, \t D=%5dmm, \t Signal=%2.2f Mcps, \t Ambient=%2.2f Mcps \n", |
charlesmn | 0:34269810c435 | 193 | pMultiRangingData->RangeData[j].RangeStatus, |
charlesmn | 0:34269810c435 | 194 | pMultiRangingData->RangeData[j].RangeMilliMeter, |
charlesmn | 0:34269810c435 | 195 | pMultiRangingData->RangeData[j].SignalRateRtnMegaCps/65536.0, |
charlesmn | 0:34269810c435 | 196 | pMultiRangingData->RangeData[j].AmbientRateRtnMegaCps/65536.0); |
charlesmn | 0:34269810c435 | 197 | } |
charlesmn | 0:34269810c435 | 198 | } |
charlesmn | 0:34269810c435 | 199 | } |
charlesmn | 0:34269810c435 | 200 | |
charlesmn | 0:34269810c435 | 201 | wait_ms( TIMINGBUDGET); |
charlesmn | 0:34269810c435 | 202 | status = board->sensor_centre->VL53LX_ClearInterruptAndStartMeasurement(); |
charlesmn | 0:34269810c435 | 203 | } |
charlesmn | 0:34269810c435 | 204 | |
charlesmn | 0:34269810c435 | 205 | } |
charlesmn | 0:34269810c435 | 206 | printf("terminated"); |
charlesmn | 0:34269810c435 | 207 | } |
charlesmn | 0:34269810c435 | 208 |