蓝牙单点

更新时间:2023-05-22 06:38:24下载pdf

本文主要介绍了蓝牙设备与手机一对一相连的 蓝牙单点 技术。

准备工作

  • 系统要求:蓝牙使用需要安卓 4.3 以及以上版本,智能生活 App SDK 从安卓 4.4 开始支持。
  • Manifest 权限
    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    <uses-permission android:name="android.permission.BLUETOOTH" />
    <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
    
  • 蓝牙权限检测:每次扫描和连接前,都要进行检测,否则 App 无法正常使用蓝牙。
    • App 在使用蓝牙连接或者扫描操作前,需要检查 App 定位权限是否被允许。
    • 检查蓝牙状态是否为开启。

      该部分检查逻辑,智能生活 SDK 未提供 API,您可自行检测。

扫描设备

开始扫描

待配网的蓝牙设备会向周围发送蓝牙广播包,SDK 会根据协议对广播包进行解析发现周围的涂鸦蓝牙单点设备和双模设备等。

蓝牙设备扫描前需要进行权限检测,只有具备权限才能正常扫描

  • 蓝牙是否打开。
  • 应用是否具有定位权限。

接口说明

void startLeScan(LeScanSetting setting, TyBleScanResponse response);

参数说明

参数 类型 说明
setting LeScanSetting 扫描的设置
response TyBleScanResponse 扫描结果的回调,不能为空

构建类说明

LeScanSetting.Builder 用于构建需要扫描设备的设置。

方法名 参数 说明 是否必需
setTimeout() long 设置超时时间
默认:40000;单位:毫秒
可选
addScanType() ScanType
  • SINGLE:点对点蓝牙设备
  • MESH:涂鸦自研协议的 Mesh 设备
  • SIG_MESH:标准蓝牙 Mesh 设备
  • SINGLE_QR:扫码配网设备。
必需
setRepeatFilter() boolean 重复过滤,默认:true 可选

示例代码

LeScanSetting scanSetting = new LeScanSetting.Builder()
		.setTimeout(60000) // 扫描的超时时间:ms
		.addScanType(ScanType.SINGLE) // 若需要扫描蓝牙设备,则只需要添加 ScanType.SINGLE
		// .addScanType(ScanType.SIG_MESH) 可同时添加其他类型设备
		.build();

// 开始扫描
TuyaHomeSdk.getBleOperator().startLeScan(scanSetting, new TyBleScanResponse() {
	@Override
	public void onResult(ScanDeviceBean bean) {
		// 回调扫描的结果 TODO
	}
});

回调说明

ScanDeviceBean 说明

属性 类型 说明
id String 扫描 ID 通常由 UUID 组成,可以唯一区别设备
name String 扫描到的蓝牙名称,一般为空
providerName String 取值为 SingleBleProvider 则表示只开发单点设备,您无需关注该字段
data byte[] 原始数据
configType String
  • config_type_single:单点设备
  • config_type_wifi:双模设备
productId String 产品 ID
uuid String 设备 UUID,设备唯一码
mac String 设备 Mac,不可作为唯一码
isbind boolean 设备是否被绑定,能回调的均为未配网的设备
flag int
  • bit0:是否⽀支持 5G,表明双模设备是否支持 5G Wi-Fi
  • bit2:是否分享设备
  • bit3:是否⽀持蓝牙兜底配网设备
  • bit4:是否是扫码配网设备
address String 设备地址
deviceType int 设备类型,用于区分不同协议的设备,您无需关注该字段

deviceType 表示待配网设备类型,若带有 Wi-Fi 的双模设备见 双模配网,蓝牙设备见 蓝牙配网

deviceType 值 configType 设备类型
200 config_type_single 蓝牙设备
300 config_type_single 蓝牙设备
301 config_type_wifi Wi-Fi + 蓝牙双模设备
304 config_type_wifi Wi-Fi + 蓝牙双模设备(支持蓝牙兜底配网)
400 config_type_single 蓝牙设备
401 config_type_wifi Wi-Fi + 蓝牙双模设备
404 config_type_wifi Wi-Fi + 蓝牙双模设备(支持蓝牙兜底配网)

查询设备名称

扫描到目标设备以后,可以通过查询显示产品配置的名称和图标。

接口说明

void getActivatorDeviceInfo(String productId, String uuid, String mac, ITuyaDataCallback<ConfigProductInfoBean> callback);

参数说明

参数 类型 说明
productId String ScanDeviceBean.getProductId
uuid String ScanDeviceBean.getUuid
mac String ScanDeviceBean.getMac 该值一般设备为 null,只有某些品类有值

示例代码

TuyaHomeSdk.getActivatorInstance().getActivatorDeviceInfo(
	scanDeviceBean.getProductId(),
	scanDeviceBean.getUuid(),
	scanDeviceBean.getMac(),
	new ITuyaDataCallback<ConfigProductInfoBean>() {
		@Override
		public void onSuccess(ConfigProductInfoBean result) {

		}

		@Override
		public void onError(String errorCode, String errorMessage) {

		}
});

回调说明

ConfigProductInfoBean 说明

属性 类型 说明
name String 产品名称,云端配置,一般是用户首次创建产品时的名称
icon String 产品图标

停止扫描

当退出配网页面或者在执行设备入网时,建议停止设备扫描,以防止扫描影响到配网过程。

接口说明

void stopLeScan();

代码示例

TuyaHomeSdk.getBleOperator().stopLeScan();

单点设备配网

开始单点设备入网

扫描到的设备的 configType 属性取值为 config_type_single 表示单点蓝牙设备,config_type_wifi 为双模设备。

接口说明

void startActivator(BleActivatorBean bleActivatorBean, IBleActivatorListener listener);

参数说明

参数 类型 说明
bleActivatorBean BleActivatorBean 需要连接的设备的参数集合
listener IBleActivatorListener 配网结果的回调

BleActivatorBean 用于存放需要配网设备的参数以及设置。

属性 类型 说明 是否必需
homeId long 当前家庭 ID 必需
uuid String 设备 UUID,通过扫描可以查询 必需
address String 设备地址,通过扫描可以查询 可选
productId String 产品 ID,通过扫描可以查询 可选
deviceType Integer 设备类型,通过扫描可以查询 必需
isShare boolean 是否为共享设备,通过扫描可以查询,默认为 false 可选
timeout long 配网总超时,配网超时失败以该参数为准。
单位:毫秒,默认:60000
可选

代码示例

BleActivatorBean bleActivatorBean = new BleActivatorBean();

// mScanDeviceBean 来自于扫描回调的 ScanDeviceBean
bleActivatorBean.homeId = 123456; // homeId
bleActivatorBean.address = mScanDeviceBean.getAddress(); // 设备地址
bleActivatorBean.deviceType = mScanDeviceBean.getDeviceType(); // 设备类型
bleActivatorBean.uuid = mScanDeviceBean.getUuid(); // UUID
bleActivatorBean.productId = mScanDeviceBean.getProductId(); // 产品 ID
bleActivatorBean.isShare = (mScanDeviceBean.getFlag() >> 2) & 0x01 == 1; // 设备是否为共享类型的标志

// 开始配网
TuyaHomeSdk.getActivator().newBleActivator().startActivator(bleActivatorBean, new IBleActivatorListener() {
	@Override
	public void onSuccess(DeviceBean deviceBean) {
		// 配网成功
	}

	@Override
	public void onFailure(int code, String msg, Object handle) {
		// 配网失败
	}
});

取消单点设备入网

配网过程中终止配网。

接口说明

void stopActivator(String uuid);

参数说明

参数 类型 说明
uuid String 扫描到的设备的 UUID,即 ScanDeviceBean.uuid

示例代码

TuyaHomeSdk.getBleManager().stopBleConfig("uuid");

双模设备配网

双模设备入网

双模设备扫描到后,可以进行入网激活扫描到的设备。configType 属性取值为 config_type_single 表示单点蓝牙设备,config_type_wifi 为双模设备。

接口说明

void startActivator(MultiModeActivatorBean multiModeActivatorBean, IMultiModeActivatorListener listener);

参数说明

参数 类型 说明
multiModeActivatorBean MultiModeActivatorBean 需要配网的双模设备参数集合
listener IMultiModeActivatorListener 配网结果回调

MultiModeActivatorBean 说明

属性 类型 说明
deviceType Integer 设备类型,通过扫描可以查询
uuid String 设备 UUID,通过扫描可以查询
address String 设备地址,通过扫描可以查询
mac String 设备 Mac,通过扫描可以查询
ssid String Wi-Fi SSID
pwd String Wi-Fi 密码
token String 配网 Token,获取 Token 的方式与 Wi-Fi 设备配网一致,请参考 获取 Token
homeId long 当前家庭的 ID
timeout long 配网总超时,配网超时失败以该参数为准,单位为毫秒

若未说明,一般设备只支持 2.4G 频段 Wi-Fi 配网,部分设备支持 5G。您可以根据 ScanDeviceBean.flag 进行判定。

代码示例

MultiModeActivatorBean multiModeActivatorBean = new MultiModeActivatorBean();

// mScanDeviceBean 来自于扫描回调的 ScanDeviceBean
multiModeActivatorBean.deviceType = mScanDeviceBean.getDeviceType(); // 设备类型
multiModeActivatorBean.uuid = mScanDeviceBean.getUuid(); // 设备 uuid
multiModeActivatorBean.address = mScanDeviceBean.getAddress(); // 设备地址
multiModeActivatorBean.mac = mScanDeviceBean.getMac(); // 设备 mac
multiModeActivatorBean.ssid = "WIFI_2.4G"; // Wi-Fi SSID
multiModeActivatorBean.pwd = "WIFI_PASSWORD"; // Wi-Fi 密码
multiModeActivatorBean.token = "abcd1234"; // 获取的 Token
multiModeActivatorBean.homeId = ; // 当前家庭 homeId
multiModeActivatorBean.timeout = 120000; // 超时时间

// 开始配网
TuyaHomeSdk.getActivator().newMultiModeActivator().startActivator(multiModeActivatorBean, new IMultiModeActivatorListener() {
	@Override
	public void onSuccess(DeviceBean deviceBean) {
		// 配网成功
	}

	@Override
	public void onFailure(int code, String msg, Object handle) {
		// 配网失败
	}
});

回调说明

  • DeviceBean:表示设备信息数据类型,请参考 DeviceBean 数据模型

  • Object handle:handle 返回类型是实体对象 ConfigErrorBean,参数说明如下:

    参数 类型 说明
    name String 设备名称
    errorCode String 错误码
    devId String 设备 ID
    iconUrl String 设备图标
    errorMsg String 错误信息

取消双模设备配网

如果在配网过程中终止了配网,若设备已经进行到云端激活阶段,虽取消设备配网,但可能会配网成功。

接口说明

TuyaHomeSdk.getActivator().newMultiModeActivator().stopActivator(uuid);

参数说明

参数 类型 说明
devUuid String 扫描到的设备的 UUID

示例代码

TuyaHomeSdk.getActivator().newMultiModeActivator().stopActivator("uuidxxxx");

双模设备蓝牙兜底配网

部分双模设备拥有蓝牙兜底配网能力。用户使用 App 通过手机蓝牙,将设备连云所需信息传输给待配网设备,设备会尝试连接 Wi-Fi。若激活云端链路失败,会启动本地连接模式,使用手机蓝牙直接与设备通信。

判断扫描到的设备是否拥有蓝牙兜底配网能力,可以通过 ScanDeviceBeangetDeviceType() 方法查询。返回值为 404304,则表示该设备拥有蓝牙兜底配网能力。其它结果则表示没有该能力。

蓝牙单点

接口说明

void startActivator(MultiModeActivatorBean multiModeActivatorBean, IMultiModeActivatorListener listener);

MultiModeActivatorBean 说明

参数 类型 说明
homeId long 将设备添加到指定 ID 的家庭中
uuid String 需要配网的设备 UUID
deviceType int 设备类型
address String 设备地址
timeout long 设备配网超时总时长,单位为 ms
phase1Timeout long 设备连云激活配网超时时长,默认:60000,单位:ms
ssid String 需要连接的 Wi-Fi SSID
pwd String 需要连接的 Wi-Fi 密码,若无密码则传空字符串
token String 从云端查询的账号身份认证信息,获取 Token 的方式与 Wi-Fi 设备配网一致,请参考 获取 Token
mac String 设备 Mac 地址

若未说明,一般设备只支持 2.4G 频段 Wi-Fi 配网,部分设备支持 5G。可以根据 ScanDeviceBean.flag 进行判定。

代码示例

// scanDeviceBean 为蓝牙扫描到的设备信息回调
MultiModeActivatorBean multiModeActivatorBean = new MultiModeActivatorBean();
// 设置 Wi-Fi 的 SSID
multiModeActivatorBean.ssid = "SSID_xxx";
// 设置 Wi-Fi 的密码
multiModeActivatorBean.pwd = "pwd_xxx";
// 设置设备 UUID
multiModeActivatorBean.uuid = scanDeviceBean.getUuid();
// 设置设备类型
multiModeActivatorBean.deviceType = scanDeviceBean.getDeviceType();
// 设置设备 Mac 地址
multiModeActivatorBean.mac = scanDeviceBean.getMac();
// 设置设备地址
multiModeActivatorBean.address = scanDeviceBean.getAddress();
// 设置 HomeID
multiModeActivatorBean.homeId = "homeId_xxx";
// 设置获取到的 Token
multiModeActivatorBean.token = "token_xxx";
// 设置配网总超时,单位:ms
multiModeActivatorBean.timeout = 120 * 1000L;
// 设置仅 Wi-Fi 连接的超时,单位:ms
multiModeActivatorBean.phase1Timeout = 60 * 1000L;

// 配网结果回调
IMultiModeActivatorListener listener = new IMultiModeActivatorListener() {
    @Override
    public void onSuccess(DeviceBean deviceBean) {
        // 配网成功
    }
    @Override
    public void onFailure(int code, String error, Object handle) {
        // 配网失败
    }
};

// 开始配网
TuyaHomeSdk.getActivator().newMultiModeActivator().startActivator(multiModeActivatorBean, listener);
  • 开启连云激活需要确保设备当前处于蓝牙链路激活状态,即通过蓝牙将连云激活的信息传输给设备。调用 DeviceBean 实例的 getCommunicationOnline(CommunicationEnum.BLE) 方法,可以查询当前设备蓝牙连接状态。只有返回值为 true 时,才能调用开启连云激活的方法。

  • 如果需要判断云端链路是否激活,可以通过 deviceBean.getMeta().get("wifiEnable") 方法,查询设备是否连接 Wi-Fi。结果为 true,则表示云端链路已激活。

蓝牙兜底双模设备连云

上述蓝牙兜底配网设备如果 Wi-Fi 激活失败,会进入蓝牙本地连接进行操作。此时,若想重新尝试让设备连接 Wi-Fi 进行云端激活,可以调用如下接口,调用时需要确保设备处于本地蓝牙连接状态且云端链路未激活:

  1. 通过 DeviceBeangetCommunicationOnline(CommunicationEnum.BLE) 方法,查询本地蓝牙链路是否激活。

  2. 使用 deviceBean.getMeta().get("wifiEnable") 查询设备是否激活云端链路。

    蓝牙单点

接口说明

void startWifiEnable(MultiModeActivatorBean multiModeActivatorBean, IMultiModeActivatorListener listener);

参数说明

参数 类型 说明
multiModeActivatorBean MultiModeActivatorBean 需要重连 Wi-Fi 的设备参数集合
listener IMultiModeActivatorListener 重连 Wi-Fi 结果的回调

MultiModeActivatorBean 说明

参数 类型 说明
timeout long 设备重连 Wi-Fi 云端激活超时时长,单位为 ms
ssid String 需要连接的 Wi-Fi SSID
pwd String 需要连接的 Wi-Fi 密码,若无密码则传空字符串
devId Long 需要开启 Wi-Fi 使能的设备 ID

代码示例

MultiModeActivatorBean multiModeActivatorBean = new MultiModeActivatorBean();
multiModeActivatorBean.devId = "devId_xxx"; // 设备 devId
multiModeActivatorBean.ssid = "ssid_xxx"; // 需要连接的 Wi-Fi ssid
multiModeActivatorBean.pwd = "pwd_xxx"; // 需要连接的 Wi-Fi 密码
multiModeActivatorBean.timeout = 120 * 1000L; // 超时时长,单位:ms

// Wi-Fi 重新配网结果回调
IMultiModeActivatorListener listener = new IMultiModeActivatorListener() {
    @Override
    public void onSuccess(DeviceBean deviceBean) {
        // 激活 Wi-Fi ,连接云端成功
    }
    @Override
    public void onFailure(int code, String msg, Object handle) {
        // 激活 Wi-Fi ,连接云端失败
    }
};

// 开始重新连接 Wi-Fi 并云端激活
TuyaHomeSdk.getActivator().newMultiModeActivator().startWifiEnable(multiModeActivatorBean, listener);

设备操作

本章节介绍了已配网的单点设备,如何进行状态检测、连接、解绑等。

判断设备在线状态

  • 方式一:通过通用方式查询。方法与 Wi-Fi 设备一致。查询的结果是综合状态,若蓝牙设备添加到网关下面,则蓝牙设备可云端在线。

    TuyaHomeSdk.getDataInstance().getDeviceBean(devId).getIsOnline();
    
  • 方式二:查询设备蓝牙是否本地连接。通常情况下蓝牙只需要考虑本地状态即可。只有加入蓝牙网关下的蓝牙设备才需要考虑是否云端在线。

    TuyaHomeSdk.getBleManager().isBleLocalOnline(devId);
    

连接离线设备

连接方法需要在主线程中调用。

接口说明

void connectBleDevice(List<BleConnectBuilder> builderList);

参数说明

参数 类型 说明
builderList List BleConnectBuilder 集合,用于构建需要连接设备的设置

BleConnectBuilder 说明

方法名 参数 说明
setDirectConnect() boolean
  • true:使用缓存连接,使用缓存普通情况下会增快连接速度
  • false:不使用缓存连接
setDevId() String 需要连接的设备 ID
setScanTimeout() Integer 扫描超时时长,单位为毫秒
setLevel() BleConnectBuilder.Level
  • NORMAL:如果连接资源已满,则将忽略该连接
  • FORCE:如果连接资源已满,将释放其它资源以连接到当前设备
默认值:NORMAL

示例代码

List<BleConnectBuilder> builderList = new ArrayList<>();

BleConnectBuilder bleConnectBuilder1 = new BleConnectBuilder();
BleConnectBuilder bleConnectBuilder2 = new BleConnectBuilder();

bleConnectBuilder1.setDevId(devId1); // 设备 1 的 devId
bleConnectBuilder2.setDevId(devId2); // 设备 2 的 devId

builderList.add(bleConnectBuilder1); // 添加设备 1
builderList.add(bleConnectBuilder2); // 添加设备 2

TuyaHomeSdk.getBleManager().connectBleDevice(builderList); // 开始连接

断开连接设备

需要在主线程中调用。

接口说明

void disconnectBleDevice(List<BleConnectBuilder> builderList);

参数说明

参数 类型 说明
builderList List BleConnectBuilder 集合,用于构建需要断开设备的设置

BleConnectBuilder 说明

方法名 参数 说明
setDevId() String 需要断开的设备 ID

示例代码

List<BleConnectBuilder> builderList = new ArrayList<>();

builderList.add(new BleConnectBuilder().setDevId(devId1)); // 设备 1 的 devId
builderList.add(new BleConnectBuilder().setDevId(devId2)); // 设备 2 的 devId

TuyaHomeSdk.getBleManager().disconnectBleDevice(builderList); // 断开连接

设备管理操作

您可以通过设备的操作类进行监听设备状态。该部分与 Wi-Fi 逻辑类似,可参考 设备管理 了解更多逻辑信息。以下操作均与 Wi-Fi 设备的指令下发一致:

  • 设备信息查询

  • 初始化设备控制

  • 注册设备监听

  • 取消设备监听

  • 设备功能说明

  • 设备重命名

  • 移除设备

    蓝牙设备的解绑与 Wi-Fi 使用方式一致,都是调用 TuyaHomeSdk.newDeviceInstance("devId").removeDevice() 或者 resetFactory()。但是,有以下区别:

    • 蓝牙设备除了进行云端移除之外,若设备此时本地连接状态,则会自动移除设备。若此时设备离线,则只会云端移除,设备会仍处于绑定状态。
    • 下次想要继续重新绑定设备,用户需要将设备手动置为配网状态。
    • SDK 在扫描时,若发现设备处于绑定状态但是云端已解绑,也会进行自动重置。
  • 回收设备资源

固件升级

固件 OTA 升级前,需要先检查固件信息,然后进行升级。

检查固件信息

接口说明

void requestUpgradeInfo(String devId, IRequestUpgradeInfoCallback callback);

参数说明

参数 类型 说明
devId String 需要升级的设备 ID
callback IRequestUpgradeInfoCallback 检查回调

示例代码

TuyaHomeSdk.getMeshInstance().requestUpgradeInfo(mDevID, new IRequestUpgradeInfoCallback() {
	@Override
	public void onSuccess(ArrayList<BLEUpgradeBean> bleUpgradeBeans) {

	}

	@Override
	public void onError(String errorCode, String errorMsg) {
	}
});

BLEUpgradeBean 返回固件升级的信息,提供以下信息:

字段 类型 描述
upgradeStatus Integer 升级状态:
  • 0:无新版本
  • 1:有新版本
  • 2:在升级中
version String 最新版本
currentVersion String 当前版本
timeout Integer 超时时间,单位:秒
upgradeType Integer
  • 0:App 提醒升级
  • 2:App 强制升级
  • 3: 检测升级
type Integer 固件来源:
  • 0:Wi-Fi 模组
  • 1:蓝牙模组
  • 2:GPRS 模组
  • 3:Zigbee 模组
  • 9:MCU 设备
typeDesc String 来源描述
lastUpgradeTime long 上次升级时间,单位:毫秒
url String 新固件下载地址,type 取值为 19 时有值
fileSize long 新固件大小
md5 String 新固件 MD5 值

OTA 升级

将检查到的新固件下载到本地后,进行 OTA 升级。

接口说明

void startBleOta(String uuid, int type, String version, String binPackagePath, OnBleUpgradeListener listener);

参数说明

参数 类型 说明
uuid String 需要升级的设备 UUID,可通过 deviceBean.getUuid() 查询
type int
  • 0:蓝牙固件升级,此时 BLEUpgradeBean.type = 1
  • 1:MCU 升级,此时 BLEUpgradeBean.type = 9
version String 新固件版本号
binPackagePath String 下载到本地的固件的路径
listener OnBleUpgradeListener 升级进度回调
TuyaHomeSdk.getBleManager().startBleOta(uuid, type, version, binPackagePath, new  OnBleUpgradeListener() {
	@Override
	public void onUpgrade(int percent) {
		// 升级进度,单位为百分比
	}

	@Override
	public void onSuccess() {
		// 升级成功
	}

	@Override
	public void onFail(String errorCode, String errorMsg) {
		// 升级失败
	}
});

错误码

错误码 说明
1 设备接收的数据包格式错误
2 设备找不到路由器
3 Wi-Fi 密码错误
4 设备连不上路由器
5 设备 DHCP 失败
6 设备连云失败
100 用户取消配网
101 蓝牙连接错误
102 发现蓝牙服务错误
103 打开蓝牙通讯通道失败
104 蓝牙查询设备信息失败
105 蓝牙配对失败
106 配网超时
107 Wi-Fi 信息发送失败
108 Token 失效
109 查询蓝牙加密密钥失败
110 设备不存在
111 设备云端注册失败
112 设备云端激活失败
113 云端设备已被绑定
114 主动断开
115 云端查询设备信息失败
116 设备此时正被其他方式配网
117 OTA 升级失败
118 OTA 升级超时
119 Wi-Fi 配网传参校验失败