Python3环境,树莓派使用bluepy与BLE设备通信
扫描设备
创建一个ScanDelegate
1 class ScanDelegate(DefaultDelegate): 2 def __init__(self): 3 DefaultDelegate.__init__(self) 4 5 def handleDiscovery(self, dev, isNewDev, isNewData): 6 if isNewDev: 7 print("Discovered device", dev.addr) 8 elif isNewData: 9 print("Received new data from", dev.addr)
扫描设备并打印
1 scanner = Scanner().withDelegate(ScanDelegate()) 2 devices = scanner.scan(10.0) 3 creyond_devices = [] 4 for dev in devices: 5 print("Device %s (%s), RSSI=%d dB" % (dev.addr, dev.addrType, dev.rssi)) 6 for (adtype, desc, value) in dev.getScanData(): 7 if value == "CreYond": 8 creyond_devices.append(dev) 9 print(" %s = %s" % (desc, value)) 10 11 print(creyond_devices)
获取Services与Characteristics
通过Peripheral来获取Services
1 c_device = creyond_devices[0] 2 p_device = Peripheral(c_device) 3 p_device.withDelegate(NotifyDelegate(p_device)) 4 services = p_device.getServices() 5 6 # displays all services 7 for service in services: 8 print(service)
通过UUID获取指定Service
1 service_uuid = UUID("00000010-3354-4d64-6e6f-XXXXXXX3534a") 2 c_service = p_device.getServiceByUUID(service_uuid) 3 print(c_service)
获取Service下的Characteristics
1 characteristics = c_service.getCharacteristics() 2 # displays all characteristics 3 for char in characteristics: 4 print(char)
订阅与通知
创建一个NotifyDelegate
1 class NotifyDelegate(DefaultDelegate): 2 # Constructor (run once on startup) 3 def __init__(self, params): 4 DefaultDelegate.__init__(self) 5 6 # func is caled on notifications 7 def handleNotification(self, cHandle, data): 8 print("Notification from Handle: 0x" + format(cHandle,'02X') ) 9 print(hexlify(data))
在创建Peripheral时,指定
1 p_device.withDelegate(NotifyDelegate(p_device))
查找descriptor,并设定其值为1.设定值时注意大小端 bytes([1, 0])。注意,直接写characteristic是错误的,一定要找到characteristic下的UUID为0x2902的descriptor。部分蓝牙设备的UUID可能不规范,通过UUID查找可能存在重复,建议getDescriptors筛选好对应范围。
1 hEcg=notify_char.getHandle() 2 for descriptor in p_device.getDescriptors(hEcg,c_service.hndEnd): 3 if (descriptor.uuid==0x2902): 4 print(f'Client Characteristic Configuration found at handle 0x{format(descriptor.handle,"02X")}') 5 hEcgCCC=descriptor.handle 6 7 p_device.writeCharacteristic(hEcgCCC,bytes([1, 0]))
等待显示:
1 while True: 2 if p_device.waitForNotifications(1.0): 3 # handleNotification() was called 4 continue 5 6 print("Waiting... Waited more than one sec for notification")
完整代码:
1 # %% 2 from bluepy.btle import Scanner, DefaultDelegate,UUID, Peripheral 3 from binascii import hexlify 4 import struct 5 # %% 6 class ScanDelegate(DefaultDelegate): 7 def __init__(self): 8 DefaultDelegate.__init__(self) 9 10 def handleDiscovery(self, dev, isNewDev, isNewData): 11 if isNewDev: 12 print("Discovered device", dev.addr) 13 elif isNewData: 14 print("Received new data from", dev.addr) 15 16 17 class NotifyDelegate(DefaultDelegate): 18 # Constructor (run once on startup) 19 def __init__(self, params): 20 DefaultDelegate.__init__(self) 21 22 # func is caled on notifications 23 def handleNotification(self, cHandle, data): 24 print("Notification from Handle: 0x" + format(cHandle,'02X') ) 25 print(hexlify(data)) 26 27 28 # %% 29 scanner = Scanner().withDelegate(ScanDelegate()) 30 devices = scanner.scan(10.0) 31 creyond_devices = [] 32 for dev in devices: 33 print("Device %s (%s), RSSI=%d dB" % (dev.addr, dev.addrType, dev.rssi)) 34 for (adtype, desc, value) in dev.getScanData(): 35 if value == "CreYond": 36 creyond_devices.append(dev) 37 print(" %s = %s" % (desc, value)) 38 39 print(creyond_devices) 40 # %% get services 41 # the first device name CreYond 42 c_device = creyond_devices[0] 43 p_device = Peripheral(c_device) 44 p_device.withDelegate(NotifyDelegate(p_device)) 45 services = p_device.getServices() 46 47 # displays all services 48 for service in services: 49 print(service) 50 # %% get specified service 51 service_uuid = UUID("00000010-3354-4d64-6e6f-xxxxxxxxx534a") 52 c_service = p_device.getServiceByUUID(service_uuid) 53 print(c_service) 54 55 # %% 56 characteristics = c_service.getCharacteristics() 57 # displays all characteristics 58 for char in characteristics: 59 print(char) 60 # %% 61 notify_char = characteristics[0] 62 63 #%% 64 hEcg=notify_char.getHandle() 65 for descriptor in p_device.getDescriptors(hEcg,c_service.hndEnd): 66 if (descriptor.uuid==0x2902): 67 print(f'Client Characteristic Configuration found at handle 0x{format(descriptor.handle,"02X")}') 68 hEcgCCC=descriptor.handle 69 70 p_device.writeCharacteristic(hEcgCCC,bytes([1, 0])) 71 72 #%% 73 tmp_data=p_device.readCharacteristic(0x11) 74 print(tmp_data) 75 # %% 76 while True: 77 if p_device.waitForNotifications(1.0): 78 # handleNotification() was called 79 continue 80 81 print("Waiting... Waited more than one sec for notification") 82 83 # %% 84 p_device.disconnect() 85 86 # %%
参考链接: