1+ #include < Wire.h>
2+
3+ #define ALVIK_I2C_ADDRESS 0x2B
4+
5+ // Command codes (from Alvik firmware)
6+ #define CMD_SET_RPM ' J' // Set wheel RPM (left, right)
7+ #define CMD_SET_DRIVE ' V' // Set linear/angular velocity
8+ #define CMD_SET_WHEEL ' W' // Set individual wheel control
9+ #define CMD_SET_POSITION ' A' // Set wheel positions
10+ #define CMD_SET_SERVO ' S' // Set servo angles
11+ #define CMD_SET_LEDS ' L' // Set LED colors
12+ #define CMD_SET_PID ' P' // Set PID parameters
13+ #define CMD_ROTATE ' R' // Rotate by angle
14+ #define CMD_MOVE ' G' // Move distance
15+ #define CMD_RESET_POSE ' Z' // Reset pose (x, y, theta)
16+ #define CMD_ACK_CONFIRM ' X' // ACK confirmation
17+ #define CMD_SET_BEHAVIOUR ' B' // Set behaviour
18+ #define CMD_REQUEST ' #' // Request data publication
19+
20+ // Request sub-commands
21+ #define REQ_VERSION ' v'
22+ #define REQ_BATTERY ' b'
23+ #define REQ_IMU ' i'
24+ #define REQ_MOTORS ' m'
25+ #define REQ_ACK ' k'
26+ #define REQ_SENSORS ' s'
27+
28+ uint8_t txBuffer[128 ];
29+
30+ // Statistics
31+ struct Statistics {
32+ uint32_t packetsSent = 0 ;
33+ uint32_t packetsReceived = 0 ;
34+ uint32_t i2cErrors = 0 ;
35+ uint32_t checksumErrors = 0 ;
36+ unsigned long lastResponseTime = 0 ;
37+ };
38+
39+ Statistics stats;
40+
41+ void setup () {
42+ Serial.begin (115200 );
43+ delay (2000 );
44+
45+ Serial.println (" \n\n ======================================" );
46+ Serial.println (" Alvik Protocol I2C Tester" );
47+ Serial.println (" ======================================\n " );
48+
49+ Wire1.begin ();
50+
51+ Serial.println (" I2C Master initialized" );
52+ Serial.print (" Alvik slave address: 0x" );
53+ Serial.println (ALVIK_I2C_ADDRESS, HEX);
54+
55+ // Scan for Alvik
56+ Serial.println (" \n Scanning for Alvik..." );
57+ if (scanForAlvik ()) {
58+ Serial.println (" ✅ Alvik found!" );
59+ } else {
60+ Serial.println (" ❌ Alvik not found!" );
61+ Serial.println (" Check I2C connections and address" );
62+ }
63+
64+ Serial.println (" \n ======================================" );
65+ Serial.println (" Test Menu:" );
66+ Serial.println (" 1 - Request Version" );
67+ Serial.println (" 2 - Request Battery" );
68+ Serial.println (" 3 - Request IMU" );
69+ Serial.println (" 4 - Request Line Sensor" );
70+ Serial.println (" 5 - Request Touch Sensor" );
71+ Serial.println (" 6 - Request Color Sensor" );
72+ Serial.println (" 7 - Request ToF Sensors" );
73+ Serial.println (" 8 - Set LEDs (cycle colors)" );
74+ Serial.println (" 9 - Set Motor RPM (test)" );
75+ Serial.println (" 0 - Stop Motors" );
76+ Serial.println (" s - Show statistics" );
77+ Serial.println (" r - Reset statistics" );
78+ Serial.println (" ======================================\n " );
79+
80+ }
81+
82+ void loop () {
83+ // Check for serial commands
84+ if (Serial.available ()) {
85+ char cmd = Serial.read ();
86+ handleCommand (cmd);
87+ receiveI2CData (8 );
88+ }
89+
90+ delay (10 );
91+ }
92+
93+ bool scanForAlvik () {
94+ Wire1.beginTransmission (ALVIK_I2C_ADDRESS);
95+ uint8_t error = Wire1.endTransmission ();
96+ return (error == 0 );
97+ }
98+
99+ void receiveI2CData (int size) {
100+
101+ for (int i = 0 ; i < size; i++) {
102+ Wire1.requestFrom (ALVIK_I2C_ADDRESS, 1 );
103+
104+ if (Wire1.available ()) {
105+ Serial.print (" 📥 Received " );
106+
107+ // while (Wire1.available()) {
108+ uint8_t b = Wire1.read ();
109+ Serial.print (" 0x" );
110+ Serial.print (b, HEX);
111+ Serial.print (" " );
112+
113+ // }
114+ Serial.println ();
115+
116+ stats.packetsReceived ++;
117+ stats.lastResponseTime = millis ();
118+ }
119+ }
120+
121+ }
122+
123+ bool sendI2CData (const uint8_t * data, uint8_t length) {
124+ Wire1.beginTransmission (ALVIK_I2C_ADDRESS);
125+ Wire1.write (data, length);
126+ uint8_t error = Wire1.endTransmission ();
127+
128+ if (error == 0 ) {
129+ stats.packetsSent ++;
130+ Serial.print (" 📤 Sent " );
131+ Serial.print (length);
132+ Serial.print (" bytes: " );
133+ printHex (data, length);
134+ return true ;
135+ } else {
136+ stats.i2cErrors ++;
137+ Serial.print (" ❌ I2C Error: " );
138+ Serial.println (error);
139+ return false ;
140+ }
141+ }
142+
143+ uint8_t createRequestPacket (uint8_t * buf, uint8_t cmd, uint8_t id = 0 ) {
144+ buf[0 ] = CMD_REQUEST;
145+ buf[1 ] = cmd;
146+ buf[2 ] = id;
147+ return 3 ;
148+ }
149+
150+ void handleCommand (char cmd) {
151+ uint8_t length = 0 ;
152+ static uint8_t ledColor = 0 ;
153+
154+ switch (cmd) {
155+ case ' 1' : // Request Version
156+ Serial.println (" \n >>> Requesting version..." );
157+ length = createRequestPacket (txBuffer, REQ_VERSION);
158+ sendI2CData (txBuffer, length);
159+ break ;
160+
161+ // case '2': // Request Battery
162+ // Serial.println("\n>>> Requesting battery...");
163+ // length = createRequestPacket(txBuffer, REQ_BATTERY);
164+ // sendI2CData(txBuffer, length);
165+ // break;
166+ //
167+ // case '3': // Request IMU
168+ // Serial.println("\n>>> Requesting IMU...");
169+ // length = createRequestPacket(txBuffer, REQ_IMU);
170+ // sendI2CData(txBuffer, length);
171+ // break;
172+ //
173+ // case '4': // Request Line Sensor
174+ // Serial.println("\n>>> Requesting line sensor...");
175+ // length = createRequestPacket(txBuffer, REQ_SENSORS, SENSOR_LINE);
176+ // sendI2CData(txBuffer, length);
177+ // break;
178+ //
179+ // case '5': // Request Touch Sensor
180+ // Serial.println("\n>>> Requesting touch sensor...");
181+ // length = createRequestPacket(txBuffer, REQ_SENSORS, SENSOR_TOUCH);
182+ // sendI2CData(txBuffer, length);
183+ // break;
184+ //
185+ // case '6': // Request Color Sensor
186+ // Serial.println("\n>>> Requesting color sensor...");
187+ // length = createRequestPacket(txBuffer, REQ_SENSORS, SENSOR_COLOR);
188+ // sendI2CData(txBuffer, length);
189+ // break;
190+ //
191+ // case '7': // Request ToF Sensors
192+ // Serial.println("\n>>> Requesting ToF sensors...");
193+ // length = createRequestPacket(txBuffer, REQ_SENSORS, SENSOR_TOF);
194+ // sendI2CData(txBuffer, length);
195+ // break;
196+ //
197+ // case '8': // Set LEDs (cycle colors)
198+ // Serial.println("\n>>> Setting LEDs...");
199+ // ledColor = (ledColor + 1) % 8;
200+ // length = createLEDPacket(txBuffer, ledColor);
201+ // sendI2CData(txBuffer, length);
202+ // Serial.print("LED color: ");
203+ // Serial.println(ledColor);
204+ // break;
205+ //
206+ // case '9': // Test motor RPM
207+ // Serial.println("\n>>> Setting motor RPM (50, 50)...");
208+ // length = createRPMPacket(txBuffer, 50.0f, 50.0f);
209+ // sendI2CData(txBuffer, length);
210+ // break;
211+ //
212+ // case '0': // Stop motors
213+ // Serial.println("\n>>> Stopping motors...");
214+ // length = createRPMPacket(txBuffer, 0.0f, 0.0f);
215+ // sendI2CData(txBuffer, length);
216+ // break;
217+
218+ case ' s' : // Show statistics
219+ case ' S' :
220+ printStatistics ();
221+ break ;
222+
223+ case ' r' : // Reset statistics
224+ case ' R' :
225+ resetStatistics ();
226+ break ;
227+
228+ default :
229+ break ;
230+ }
231+ }
232+
233+ void printHex (const uint8_t * data, uint8_t length) {
234+ for (uint8_t i = 0 ; i < length; i++) {
235+ Serial.print (" 0x" );
236+ if (data[i] < 16 ) Serial.print (" 0" );
237+ Serial.print (data[i], HEX);
238+ Serial.print (" " );
239+ }
240+ Serial.println ();
241+ }
242+
243+ void printStatistics () {
244+ Serial.println (" \n ======================================" );
245+ Serial.println (" STATISTICS" );
246+ Serial.println (" ======================================" );
247+ Serial.print (" Packets sent: " );
248+ Serial.println (stats.packetsSent );
249+ Serial.print (" Packets received: " );
250+ Serial.println (stats.packetsReceived );
251+ Serial.print (" I2C errors: " );
252+ Serial.println (stats.i2cErrors );
253+ Serial.print (" Checksum errors: " );
254+ Serial.println (stats.checksumErrors );
255+ Serial.print (" Last response: " );
256+ if (stats.lastResponseTime > 0 ) {
257+ Serial.print ((millis () - stats.lastResponseTime ) / 1000 );
258+ Serial.println (" seconds ago" );
259+ } else {
260+ Serial.println (" never" );
261+ }
262+ Serial.println (" ======================================\n " );
263+ }
264+
265+ void resetStatistics () {
266+ stats.packetsSent = 0 ;
267+ stats.packetsReceived = 0 ;
268+ stats.i2cErrors = 0 ;
269+ stats.checksumErrors = 0 ;
270+ Serial.println (" \n ✅ Statistics reset\n " );
271+ }
0 commit comments