
鸿蒙5蓝牙互联:智能家居设备控制实战指南
一、鸿蒙5蓝牙能力概述
鸿蒙5在ArkCompiler的支持下,提供了全新的蓝牙互联框架,主要特性包括:
多协议支持:BLE/BR/EDR/LE Audio
低功耗优化:专为IoT设备设计
安全连接:支持多种加密方式
设备组网:轻松构建设备Mesh网络
二、开发环境配置
- 权限配置
在config.json中添加蓝牙权限:
{
“module”: {
“reqPermissions”: [
{
“name”: “ohos.permission.USE_BLUETOOTH”
},
{
“name”: “ohos.permission.DISCOVER_BLUETOOTH”
},
{
“name”: “ohos.permission.MANAGE_BLUETOOTH”
},
{
“name”: “ohos.permission.LOCATION”
}
]
}
}
2. 蓝牙适配器初始化
import ble from ‘@ohos.bluetooth’;
// 获取蓝牙适配器实例
let adapter: ble.BluetoothAdapter;
try {
adapter = ble.getBluetoothAdapter();
console.log(‘蓝牙适配器获取成功’);
} catch (err) {
console.error(蓝牙适配器获取失败: ${err}
);
}
// 检查蓝牙状态
let isEnable = await adapter.isEnable();
if (!isEnable) {
// 启用蓝牙
await adapter.enableBluetooth();
}
三、设备扫描与发现
- 扫描设备
// 定义设备发现回调
let deviceMap = new Map<string, ble.BluetoothDevice>();
class MyBluetoothScanObserver implements ble.BluetoothScanObserver {
onScanResult(device: ble.BluetoothDevice) {
console.log(发现设备: ${device.deviceName}, MAC: ${device.deviceId}
);
deviceMap.set(device.deviceId, device);
}
}
// 注册扫描观察者
let scanObserver = new MyBluetoothScanObserver();
adapter.registerScanObserver(scanObserver);
// 开始扫描
try {
await adapter.startBluetoothDiscovery();
console.log(‘开始扫描蓝牙设备’);
// 10秒后停止扫描
setTimeout(async () => {
await adapter.stopBluetoothDiscovery();
console.log(‘停止扫描蓝牙设备’);
adapter.unregisterScanObserver(scanObserver);
}, 10000);
} catch (err) {
console.error(扫描失败: ${err}
);
}
2. 设备过滤
// 只扫描智能家居设备
let scanFilter: ble.ScanFilter = {
deviceName: ‘SmartHome_’, // 名称前缀
serviceUuid: ‘0000180A-0000-1000-8000-00805F9B34FB’ // 特定服务UUID
};
await adapter.startBluetoothDiscovery(scanFilter);
四、设备连接与通信
- 设备配对与连接
// 选择要连接的设备
let targetDevice = deviceMap.get(‘XX:XX:XX:XX:XX:XX’);
// 配对设备
try {
let isPaired = await adapter.isPaired(targetDevice.deviceId);
if (!isPaired) {
await adapter.pairDevice(targetDevice.deviceId);
console.log(‘设备配对成功’);
}
// 建立连接
let gattClient = await targetDevice.createGattClient();
await gattClient.connect();
console.log(‘设备连接成功’);
} catch (err) {
console.error(连接失败: ${err}
);
}
2. 服务与特征值发现
// 发现服务
let services = await gattClient.getServices();
console.log(‘发现服务数量:’, services.length);
// 查找特定服务
let smartHomeService = services.find(service =>
service.uuid === ‘0000180A-0000-1000-8000-00805F9B34FB’);
if (smartHomeService) {
// 发现特征值
let characteristics = await smartHomeService.getCharacteristics();
let controlChar = characteristics.find(char =>
char.uuid === ‘00002A00-0000-1000-8000-00805F9B34FB’);
if (controlChar) {
console.log(‘找到控制特征值’);
}
}
五、智能家居设备控制
- 发送控制指令
// 定义控制指令
enum SmartHomeCommand {
TURN_ON = 0x01,
TURN_OFF = 0x02,
SET_BRIGHTNESS = 0x03,
SET_COLOR = 0x04
}
// 发送指令函数
async function sendCommand(gattClient: ble.GattClientDevice,
char: ble.GattCharacteristic,
command: SmartHomeCommand,
value?: number) {
let buffer = new ArrayBuffer(2);
let dataView = new DataView(buffer);
dataView.setUint8(0, command);
if (value !== undefined) {
dataView.setUint8(1, value);
}
try {
await gattClient.writeCharacteristic(char, buffer);
console.log(‘指令发送成功’);
} catch (err) {
console.error(‘指令发送失败:’, err);
}
}
// 示例:开灯
await sendCommand(gattClient, controlChar, SmartHomeCommand.TURN_ON);
// 示例:设置亮度50%
await sendCommand(gattClient, controlChar, SmartHomeCommand.SET_BRIGHTNESS, 50);
2. 接收设备状态
// 注册特征值变化通知
class MyNotifyObserver implements ble.NotifyObserver {
onCharacteristicChanged(device: ble.GattClientDevice,
char: ble.GattCharacteristic) {
let value = char.value;
if (value) {
let dataView = new DataView(value.buffer);
let status = dataView.getUint8(0);
console.log(‘设备状态更新:’, status);
}
}
}
let notifyObserver = new MyNotifyObserver();
gattClient.registerNotifyObserver(notifyObserver);
// 启用通知
await gattClient.setCharacteristicNotification(controlChar, true);
六、设备组网与控制中心
- 多设备管理
class SmartHomeManager {
private devices: Map<string, ble.GattClientDevice> = new Map();
async connectDevice(deviceId: string) {
if (this.devices.has(deviceId)) {
return this.devices.get(deviceId);
}
let device = deviceMap.get(deviceId);
if (!device) {
throw new Error('设备未找到');
}
let gattClient = await device.createGattClient();
await gattClient.connect();
this.devices.set(deviceId, gattClient);
return gattClient;
}
async controlDevice(deviceId: string, command: SmartHomeCommand, value?: number) {
let gattClient = this.devices.get(deviceId);
if (!gattClient) {
gattClient = await this.connectDevice(deviceId);
}
let services = await gattClient.getServices();
let service = services.find(s => s.uuid === SMART_HOME_SERVICE_UUID);
let char = service?.getCharacteristics().find(c => c.uuid === CONTROL_CHAR_UUID);
if (char) {
await sendCommand(gattClient, char, command, value);
}
}
async disconnectAll() {
for (let [_, gattClient] of this.devices) {
await gattClient.disconnect();
}
this.devices.clear();
}
}
2. 场景联动
async function activateScene(sceneName: string) {
const sceneConfig = {
‘回家模式’: [
{ device: ‘LIVING_ROOM_LIGHT’, command: SmartHomeCommand.TURN_ON, value: 80 },
{ device: ‘AIR_CONDITIONER’, command: SmartHomeCommand.TURN_ON, value: 26 }
],
‘睡眠模式’: [
{ device: ‘ALL_LIGHTS’, command: SmartHomeCommand.TURN_OFF },
{ device: ‘AIR_CONDITIONER’, command: SmartHomeCommand.TURN_ON, value: 28 }
]
};
const actions = sceneConfig[sceneName];
if (!actions) return;
let manager = new SmartHomeManager();
try {
await Promise.all(actions.map(action =>
manager.controlDevice(action.device, action.command, action.value)));
console.log(场景[${sceneName}]激活成功
);
} catch (err) {
console.error(场景激活失败: ${err}
);
} finally {
await manager.disconnectAll();
}
}
七、安全与优化
- 安全连接
// 使用加密连接
let secureParams: ble.GattConnectParams = {
isAutoConnect: false,
isEncrypted: true,
strategy: ble.BLE_CONNECTION_PRIORITY_HIGH
};
await gattClient.connect(secureParams);
2. 连接优化
// 连接参数优化
let connectionParams: ble.ConnectionParameters = {
interval: 24, // 1.25ms单位
latency: 0, // 无延迟
timeout: 500 // 超时时间(10ms单位)
};
await gattClient.setConnectionParameters(connectionParams);
3. 错误处理与重连
class ReliableDeviceConnection {
private retryCount = 0;
private maxRetries = 3;
constructor(private deviceId: string) {}
async executeCommand(command: SmartHomeCommand, value?: number) {
let gattClient: ble.GattClientDevice | null = null;
try {
gattClient = await this.connectWithRetry();
let char = await this.getControlCharacteristic(gattClient);
await sendCommand(gattClient, char, command, value);
this.retryCount = 0; // 重置重试计数
} catch (err) {
console.error('执行命令失败:', err);
throw err;
} finally {
if (gattClient) {
await gattClient.disconnect();
}
}
}
private async connectWithRetry(): Promise<ble.GattClientDevice> {
while (this.retryCount < this.maxRetries) {
try {
let device = deviceMap.get(this.deviceId);
if (!device) throw new Error(‘设备未找到’);
let gattClient = await device.createGattClient();
await gattClient.connect();
return gattClient;
} catch (err) {
this.retryCount++;
if (this.retryCount >= this.maxRetries) {
throw err;
}
await new Promise(resolve => setTimeout(resolve, 1000)); // 1秒后重试
}
}
throw new Error('达到最大重试次数');
}
private async getControlCharacteristic(gattClient: ble.GattClientDevice) {
// 实现特征值获取逻辑
}
}
八、实战案例:智能灯泡控制
- 灯泡控制组件
@Component
struct SmartBulbController {
@State brightness: number = 0;
@State isOn: boolean = false;
@State color: string = ‘#ffffff’;
private deviceId: string = ‘BULB_DEVICE_ID’;
async turnOn() {
let controller = new ReliableDeviceConnection(this.deviceId);
await controller.executeCommand(SmartHomeCommand.TURN_ON);
this.isOn = true;
}
async turnOff() {
let controller = new ReliableDeviceConnection(this.deviceId);
await controller.executeCommand(SmartHomeCommand.TURN_OFF);
this.isOn = false;
}
async setBrightness(value: number) {
let controller = new ReliableDeviceConnection(this.deviceId);
await controller.executeCommand(SmartHomeCommand.SET_BRIGHTNESS, value);
this.brightness = value;
}
build() {
Column() {
Toggle({ type: ToggleType.Switch, isOn: this.isOn })
.onChange((isOn) => {
isOn ? this.turnOn() : this.turnOff();
})
Slider({ value: this.brightness, min: 0, max: 100, style: SliderStyle.OutSet })
.onChange((value: number) => {
this.setBrightness(value);
})
ColorPicker({ color: this.color })
.onChange((color: Color) => {
// 转换颜色并发送指令
let rgb = colorToRgb(color);
let controller = new ReliableDeviceConnection(this.deviceId);
controller.executeCommand(SmartHomeCommand.SET_COLOR, rgb);
})
}
}
}
2. 灯泡状态同步
class BulbStatusMonitor {
private observer: ble.NotifyObserver;
private gattClient: ble.GattClientDevice | null = null;
constructor(private deviceId: string,
private updateCallback: (status: BulbStatus) => void) {
this.observer = {
onCharacteristicChanged: (device, char) => {
if (char.uuid === STATUS_CHAR_UUID && char.value) {
let view = new DataView(char.value.buffer);
let status: BulbStatus = {
isOn: view.getUint8(0) === 1,
brightness: view.getUint8(1),
color: rgb(${view.getUint8(2)}, ${view.getUint8(3)}, ${view.getUint8(4)})
};
this.updateCallback(status);
}
}
};
}
async start() {
let device = deviceMap.get(this.deviceId);
if (!device) throw new Error(‘设备未找到’);
this.gattClient = await device.createGattClient();
await this.gattClient.connect();
let services = await this.gattClient.getServices();
let service = services.find(s => s.uuid === SMART_HOME_SERVICE_UUID);
let char = service?.getCharacteristics().find(c => c.uuid === STATUS_CHAR_UUID);
if (char) {
this.gattClient.registerNotifyObserver(this.observer);
await this.gattClient.setCharacteristicNotification(char, true);
}
}
async stop() {
if (this.gattClient) {
this.gattClient.unregisterNotifyObserver(this.observer);
await this.gattClient.disconnect();
this.gattClient = null;
}
}
}
九、总结与最佳实践
- 开发流程建议
权限检查:确保获取了所有必要的蓝牙权限
状态监听:监听蓝牙适配器状态变化
设备过滤:使用扫描过滤器提高效率
连接管理:实现健壮的重连机制
资源释放:及时断开连接和注销观察者 - 性能优化
限制扫描时间,避免不必要的电量消耗
使用适当的连接参数平衡功耗和响应速度
批量发送指令,减少通信次数 - 安全建议
使用加密连接传输敏感数据
实现设备认证机制
定期更新设备配对密钥
鸿蒙5的蓝牙框架结合ArkCompiler的优化,为智能家居设备控制提供了强大的支持。通过本文介绍的技术方案,开发者可以构建出高效、稳定、安全的智能家居控制应用。随着鸿蒙生态的扩展,这套蓝牙互联方案将支持更多样化的智能设备接入场景。
