How to Play Any Game Using a Time of Flight
Learn to use your pc keyboard with your Arduino board and play a game using a Time of Flight and AI to send the inputs.
Components and supplies
1
Arduino® UNO R4 WiFi
1
X-NUCLEO-53L5A1
Apps and platforms
1
NanoEdge AI Studio
1
Arduino IDE 1.8.19
Project description
Code
data logger
c
code for data logging
1/* ============= 2Copyright (c) 2024, STMicroelectronics 3 4All rights reserved. 5 6Redistribution and use in source and binary forms, with or without modification, are permitted provided that 7the following conditions are met: 8 9* Redistributions of source code must retain the above copyright notice, this list of conditions and the 10 following disclaimer. 11 12* Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the 13 following disclaimer in the documentation and/or other materials provided with the distribution. 14 15* Neither the name of the copyright holders nor the names of its contributors may be used to endorse or promote 16 products derived from this software without specific prior written permission. 17 18*THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, 19INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 20DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER / OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 22SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 23WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 24USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.* 25*/ 26 27/* If you want to use NEAI functions please, include NEAI library 28 * in your Arduino libraries then, uncomment NEAI parts in the following code 29 */ 30 31/* Libraries part */ 32#include <Wire.h> 33#include <SparkFun_VL53L5CX_Library.h> 34// #include "NanoEdgeAI.h" 35// #include "knowledge.h" 36 37/* Macros definitions */ 38#define SERIAL_BAUD_RATE 115200 39 40/* Frame resolution: 4x4 or 8x8 */ 41#define SENSOR_FRAME_RESOLUTION 64 42 43/* Number of successive frames to be collected */ 44#define SENSOR_FRAMES 1 45 46/* Sensor data rate */ 47#define SENSOR_DATA_RATE 15 48 49/* NanoEdgeAI defines part 50 * NEAI_MODE = 1: NanoEdgeAI functions = AI Mode. 51 * NEAI_MODE = 0: Datalogging mode. 52 */ 53#define NEAI_MODE 0 54 55/* Depending on your target, you need to adapt 56 * the i2c connection. For example, you have to use 57 * "Wire" with Arduino Uno R4 Wifi but, "Wire1" with 58 * the Arduino Giga R1 board. Check your hardware ! 59 */ 60#define i2c_comm Wire 61 62/* In this example, we use I2C connection */ 63SparkFun_VL53L5CX myImager; 64VL53L5CX_ResultsData measurementData; 65 66/* Global variables definitions */ 67static uint16_t neai_ptr = 0; 68static float neai_buffer[SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES] = {0.0}; 69 70/* NEAI library variables */ 71// const char *id2class[CLASS_NUMBER + 1] = { 72// "unknown", 73// "nothing", 74// "scissors", 75// "paper", 76// "rock", 77// }; 78// static uint8_t neai_code = 0; 79// static uint16_t id_class = 0; 80// static float output_class_buffer[CLASS_NUMBER]; 81 82/* Initialization function: In this function, 83 * code runs only once at boot / reset. 84 */ 85void setup() { 86 /* Init serial at baud rate 115200 */ 87 Serial.begin(SERIAL_BAUD_RATE); 88 89 /* I2C workaround: Sometimes, on some boards, 90 * I2C get stuck after software reboot, reset so, 91 * to avoid this, we toggle I2C clock pin at boot. 92 */ 93 pinMode(SCL, OUTPUT); 94 for (uint8_t i = 0; i < 20; i++) { 95 digitalWrite(SCL, !digitalRead(SCL)); 96 delay(1); 97 } 98 delay(100); 99 100 /* Init I2C connection between board & sensor */ 101 i2c_comm.begin(); 102 i2c_comm.setClock(400000); 103 if (myImager.begin() == false) { 104 Serial.print("Sensor not found - check your wiring. Freezing.\n"); 105 while (1); 106 } 107 108 /* Init VL53L5CX sensor settings: resolution & data rate */ 109 myImager.setResolution(SENSOR_FRAME_RESOLUTION); 110 myImager.setRangingFrequency(SENSOR_DATA_RATE); 111 myImager.startRanging(); 112 113 /* Initialize NanoEdgeAI AI */ 114 // neai_code = neai_classification_init(knowledge); 115 // if(neai_code != NEAI_OK) { 116 // Serial.print("Not supported board.\n"); 117 // } 118} 119 120/* Main function: Code run indefinitely */ 121void loop() { 122 while(neai_ptr < SENSOR_FRAMES) { 123 /* Check if new data if available */ 124 if (myImager.isDataReady() == true) { 125 /* If new data is available we read it ! */ 126 myImager.getRangingData(&measurementData); 127 /* Get data in the neai buffer */ 128 for (uint16_t i = 0; i < SENSOR_FRAME_RESOLUTION; i++) { 129 neai_buffer[i + (SENSOR_FRAME_RESOLUTION * neai_ptr)] = (float) measurementData.distance_mm[i]; 130 } 131 neai_ptr++; 132 } 133 } 134 /* Reset pointer */ 135 neai_ptr = 0; 136 137 /* Depending on NEAI_MODE value, run NanoEdge AI functions 138 * or print accelerometer data to the serial (datalogging) 139 */ 140 // if(NEAI_MODE) { 141 // neai_classification(neai_buffer, output_class_buffer, &id_class); 142 // Serial.print((String)"Class: " + id2class[id_class] + ".\n"); 143 // } 144 // else { 145 /* Print the whole buffer to the serial */ 146 for (uint16_t i = 0; i < (uint16_t) (SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES); i++) { 147 Serial.print((String) neai_buffer[i] + " "); 148 } 149 Serial.print("\n"); 150 // } 151 152 /* Clean neai buffer */ 153 memset(neai_buffer, 0.0, (uint16_t) (SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES) * sizeof(float)); 154}
main
c
main code
1/* ============= 2 Copyright (c) 2024, STMicroelectronics 3 4 All rights reserved. 5 6 Redistribution and use in source and binary forms, with or without modification, are permitted provided that 7 the following conditions are met: 8 9 Redistributions of source code must retain the above copyright notice, this list of conditions and the 10 following disclaimer. 11 12 Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the 13 following disclaimer in the documentation and/or other materials provided with the distribution. 14 15 Neither the name of the copyright holders nor the names of its contributors may be used to endorse or promote 16 products derived from this software without specific prior written permission. 17 18 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, 19 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 20 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER / OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 22 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 23 WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 24 USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.* 25*/ 26 27/* If you want to use NEAI functions please, include NEAI library 28 in your Arduino libraries then, uncomment NEAI parts in the following code 29*/ 30 31/* Libraries part */ 32#include <Wire.h> 33#include <SparkFun_VL53L5CX_Library.h> 34#include "NanoEdgeAI.h" 35#include "knowledge.h" 36#include <Keyboard.h> 37 38/* Macros definitions */ 39#define SERIAL_BAUD_RATE 115200 40 41/* Frame resolution: 4x4 or 8x8 */ 42#define SENSOR_FRAME_RESOLUTION 64 43 44/* Number of successive frames to be collected */ 45#define SENSOR_FRAMES 1 46 47/* Sensor data rate */ 48#define SENSOR_DATA_RATE 15 49 50/* NanoEdgeAI defines part 51 NEAI_MODE = 1: NanoEdgeAI functions = AI Mode. 52 NEAI_MODE = 0: Datalogging mode. 53*/ 54#define NEAI_MODE 1 55 56/* Depending on your target, you need to adapt 57 the i2c connection. For example, you have to use 58 "Wire" with Arduino Uno R4 Wifi but, "Wire1" with 59 the Arduino Giga R1 board. Check your hardware ! 60*/ 61#define i2c_comm Wire 62 63/* In this example, we use I2C connection */ 64SparkFun_VL53L5CX myImager; 65VL53L5CX_ResultsData measurementData; 66 67/* Global variables definitions */ 68static uint8_t neai_code = 0; 69static uint16_t neai_ptr = 0; 70static float neai_buffer[SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES] = {0.0}; 71 72/* NEAI library variables */ 73uint16_t id_class = 0; // Point to id class (see argument of neai_classification fct) 74float input_user_buffer[DATA_INPUT_USER * AXIS_NUMBER]; // Buffer of input values 75float output_class_buffer[CLASS_NUMBER]; // Buffer of class probabilities 76const char *id2class[CLASS_NUMBER + 1] = { // Buffer for mapping class id to class name 77 "unknown", 78 "dm_jumpcenter", 79 "dm_jumpleft", 80 "dm_jumpright", 81 "dm_left", 82 "dm_right", 83 "dm_stand", 84}; 85/* Initialization function: In this function, 86 code runs only once at boot / reset. 87*/ 88void setup() { 89 /* Init serial at baud rate 115200 */ 90 Serial.begin(SERIAL_BAUD_RATE); 91 92 93 /* I2C workaround: Sometimes, on some boards, 94 I2C get stuck after software reboot, reset so, 95 to avoid this, we toggle I2C clock pin at boot. 96 */ 97 pinMode(SCL, OUTPUT); 98 for (uint8_t i = 0; i < 20; i++) { 99 digitalWrite(SCL, !digitalRead(SCL)); 100 delay(1); 101 } 102 delay(100); 103 104 /* Init I2C connection between board & sensor */ 105 i2c_comm.begin(); 106 i2c_comm.setClock(400000); 107 if (myImager.begin() == false) { 108 Serial.print("Sensor not found - check your wiring. Freezing.\n"); 109 while (1); 110 } 111 112 /* Init VL53L5CX sensor settings: resolution & data rate */ 113 myImager.setResolution(SENSOR_FRAME_RESOLUTION); 114 myImager.setRangingFrequency(SENSOR_DATA_RATE); 115 myImager.startRanging(); 116 117 Keyboard.begin(); 118 119 /* Initialize NanoEdgeAI AI */ 120 neai_code = neai_classification_init(knowledge); 121 if (neai_code != NEAI_OK) { 122 Serial.print("Not supported board.\n"); 123 } 124 125 delay(10000); 126} 127 128/* Main function: Code run indefinitely */ 129void loop() { 130 while (neai_ptr < SENSOR_FRAMES) { 131 /* Check if new data if available */ 132 if (myImager.isDataReady() == true) { 133 /* If new data is available we read it ! */ 134 myImager.getRangingData(&measurementData); 135 /* Get data in the neai buffer */ 136 for (uint16_t i = 0; i < SENSOR_FRAME_RESOLUTION; i++) { 137 neai_buffer[i + (SENSOR_FRAME_RESOLUTION * neai_ptr)] = (float) measurementData.distance_mm[i]; 138 } 139 neai_ptr++; 140 } 141 } 142 143 144 /* Depending on NEAI_MODE value, run NanoEdge AI functions 145 or print accelerometer data to the serial (datalogging) 146 */ 147 if (NEAI_MODE) { 148 neai_classification(neai_buffer, output_class_buffer, &id_class); 149 Serial.print((String)"Class: " + id2class[id_class] + ".\n"); 150 151 switch (id_class) { 152 case 6: 153 //stand 154 Keyboard.releaseAll(); 155 break; 156 case 4: 157 //move left 158 Keyboard.press('q'); 159 break; 160 case 5: 161 //move right 162 Keyboard.press('d'); 163 break; 164 case 1: 165 //jump 166 Keyboard.press(0x20); 167 break; 168 case 2: 169 //jump left 170 Keyboard.press(0x20); 171 Keyboard.press('q'); 172 break; 173 case 3: 174 //jump right 175 Keyboard.press(0x20); 176 Keyboard.press('d'); 177 break; 178 } 179 delay(500); 180 Keyboard.releaseAll(); 181 } 182 else { 183 /* Print the whole buffer to the serial */ 184 for (uint16_t i = 0; i < (uint16_t) (SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES); i++) { 185 Serial.print((String) neai_buffer[i] + " "); 186 } 187 Serial.print("\n"); 188 } 189 190 /* Clean neai buffer */ 191 memset(neai_buffer, 0.0, (uint16_t) (SENSOR_FRAME_RESOLUTION * SENSOR_FRAMES) * sizeof(float)); 192 /* Reset pointer */ 193 neai_ptr = 0; 194}
Downloadable files
data logger code
arduino-tof-mario-datalogger.ino
main code
arduino-tof-mario-main.ino
Comments
Only logged in users can leave comments