- WeDo 2.0 – reverse engineering
- WeDo 2.0 Battery Service
- WeDo 2.0 LED Button Service
- LEGO WeDo 2.0 – playing sound
- WeDo 2.0 colors with python (again)
- WeDo 2.0 Tilt Sensor
After some head aches with the WeDo 2.0 SDK I found out that the WeDo 2.0 Hub has 2 modes for the RGB LED device:
- Indexed
- Absolute
“Indexed” is the one I used before – only 10 colors are available. This the mode used in the WeDo 2.0 App, and when in this mode the command used to write to the RGB LED accepts only one byte as argument, which works as an “index” to 10 predefined colors. Why only 10 if the same byte can address up to 255 colors? Internal memory limitations?
The same command accepts also 3 one-byte arguments (Red, Green and Blue) but only when the RGB LED mode is “Absolute”. This is clear in the SDK… what is not so clear is how to change from default (power on) Indexed mode to Absolute?
After reading many Java files I found out how: we use the “Input Command” characteristic (handle 0x3a) and send it this command:
0102061701010000000201
I’ll explain the format of the “Input Command” in another post, but for now this is the meaning:
- first two bytes (0102) is the header used to set definitions
- the third is the port of the device (06 is the RGB LED)
- the fourth is the type of the device (17h a RGB LED)
- the fifth is the mode (01 is Absolute, 00 is Indexed)
- the sixth to nineth bytes is the delta for notifications to be noticed (so 01 00 00 00 = 1d is the minimum)
- the tenth byte is the unit format to be used (02 is “SI”, internation standard)
- the eleventh and last byte is to disable or enable notifications (01)
So we can now use any of the 16777216 color tones available:
The pyhton script used for the video above (the video just shows a small part)
#!/usr/bin/python # run with sudo from gattlib import GATTRequester from time import sleep BTdevice = "hci0" # BlueTooth 4.0 BLE capable device WeDo2HubAddress = "A0:E6:F8:1E:58:57" InputCommand_hnd = 0x3a OutputCommand_hnd = 0x3d RGBAbsoluteMode_cmd = str(bytearray([01,02,06,17,01,01,00,00,00,02,01])) RGBAbsoluteOutput_cmd = str(bytearray([06,04,03])) DELAY = 0.3 req = GATTRequester(WeDo2HubAddress,True,BTdevice) sleep(DELAY) # configure RBG LED to Absolute Mode req.write_by_handle(InputCommand_hnd,RGBAbsoluteMode_cmd) # loop all colors while True: for blue in range (0,256,16): for green in range (0,256,16): for red in range (0,256,16): req.write_by_handle(OutputCommand_hnd, RGBAbsoluteOutput_cmd+chr(red)+chr(green)+chr(blue))