Skip to content

Instantly share code, notes, and snippets.

@ali1234
Created October 17, 2015 15:47
Show Gist options
  • Save ali1234/5e5758d9c591090291d6 to your computer and use it in GitHub Desktop.
Save ali1234/5e5758d9c591090291d6 to your computer and use it in GitHub Desktop.
Control Sphero BB-8 from Linux.
#!/usr/bin/env python
# BB-8 Python driver by Alistair Buxton <a.j.buxton@gmail.com>
from bluepy import btle
import time
class BB8(btle.DefaultDelegate):
def __init__(self, deviceAddress):
btle.DefaultDelegate.__init__(self)
# Address type must be "random" or it won't connect.
self.peripheral = btle.Peripheral(deviceAddress, btle.ADDR_TYPE_RANDOM)
self.peripheral.setDelegate(self)
self.seq = 0
# Attribute UUIDs are identical to Ollie.
self.antidos = self.getSpheroCharacteristic('2bbd')
self.wakecpu = self.getSpheroCharacteristic('2bbf')
self.txpower = self.getSpheroCharacteristic('2bb2')
self.roll = self.getSpheroCharacteristic('2ba1')
self.notify = self.getSpheroCharacteristic('2ba6')
# This startup sequence is also identical to the one for Ollie.
# It even uses the same unlock code.
print 'Sending antidos'
self.antidos.write('011i3', withResponse=True)
print 'Sending txpower'
self.txpower.write('\x0007', withResponse=True)
print 'Sending wakecpu'
self.wakecpu.write('\x01', withResponse=True)
def getSpheroCharacteristic(self, fragment):
return self.peripheral.getCharacteristics(uuid='22bb746f'+fragment+'75542d6f726568705327')[0]
def dumpCharacteristics(self):
for s in self.peripheral.getServices():
print s
for c in s.getCharacteristics():
print c, hex(c.handle)
def cmd(self, did, cid, data=[], answer=True, resetTimeout=True):
# Commands are as specified in Sphero API 1.50 PDF.
# https://github.com/orbotix/DeveloperResources/
seq = (self.seq&255)
self.seq += 1
sop2 = 0xfc
sop2 |= 1 if answer else 0
sop2 |= 2 if resetTimeout else 0
dlen = len(data)+1
chk = (sum(data)+did+cid+seq+dlen)&255
chk ^= 255
msg = [0xff, sop2, did, cid, seq, dlen] + data + [chk]
print 'cmd:', ' '.join([chr(c).encode('hex') for c in msg])
# Note: withResponse is very important. Most commands won't work without it.
self.roll.write(''.join([chr(c) for c in msg]), withResponse=True)
def handleNotification(self, cHandle, data):
print 'Notification:', cHandle, data.encode('hex')
def waitForNotifications(self, time):
self.peripheral.waitForNotifications(time)
def disconnect(self):
self.peripheral.disconnect()
if __name__ == '__main__':
# Connect by address. Use "sudo hcitool lescan" to find address.
bb = BB8('EE:D7:9A:A7:79:77')
# Dump all GATT stuff.
#bb.dumpCharacteristics()
# Request some sensor stream.
bb.cmd(0x02, 0x11, [0, 80, 0, 1, 0x80, 0, 0, 0, 0])
for i in range(255):
# Set RGB LED colour.
bb.cmd(0x02, 0x20, [254, i, 2, 0])
# Wait for streamed data.
bb.waitForNotifications(1.0)
# Must manually disconnect or you won't be able to reconnect.
bb.disconnect()
Copy link

ghost commented Oct 18, 2017

good evening,

Congratulations on the code, I need to get information from the BB8 as the data of your sensors, IMU, accelerometer, gyroscope, can you do something like this?

@harmitbadyal
Copy link

Hello,
Thank you so much for the code!
I have an issue whenever I run the BB8test.py. Here is the output that comes up on my terminal. Any help would be greatly appreciated!

"File "BB8test.py", line 8, in <module>
    bb8.connect()
  File "/home/pi/Projects/SpheroBB8-python/BB8_driver.py", line 259, in connect
    self.bt = BTInterface(self.deviceAddress)
  File "/home/pi/Projects/SpheroBB8-python/BB8_driver.py", line 138, in __init__
    self.peripheral = btle.Peripheral(deviceAddress, btle.ADDR_TYPE_RANDOM)
  File "/usr/local/lib/python2.7/dist-packages/bluepy/btle.py", line 391, in __init__
    self._connect(deviceAddr, addrType, iface)
  File "/usr/local/lib/python2.7/dist-packages/bluepy/btle.py", line 439, in _connect
    raise BTLEDisconnectError("Failed to connect to peripheral %s, addr type: %s" % (addr, addrType), rsp)
bluepy.btle.BTLEDisconnectError: Failed to connect to peripheral D7:74:05:73:09:55, addr type: random

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment