设备管理
更新时间:2026-08-20 17:15:59
包括设备绑定,设备解绑,设备列表
// 导入头文件
import 'package:airtc_engine/src/device_center/rtcx_add_device.dart';
import 'package:airtc_engine/src/device_center/rtcx_add_device_controller.dart';
import 'package:airtc_engine/src/device_center/rtcx_device.dart';
设备绑定
设备绑定方式提供二维码、蓝牙配网绑定、4G绑定、AP配网绑定方式
总体介绍参考设备绑定开发指南。
- 设备绑定流程
- App调用prepareAddDevice方法后,当监听到RTCXFluDeviceAddStatus_Prepared状态时可获取bindToken (有效时长30分钟)。
- 将bindToken传递给设备(二维码、蓝牙等),设备保证网络连通情况下,通过DeviceSDK进行设备绑定
- 在RTCXFluDeviceAddStatus_Prepared状态下,App只需要调用startAddDevice方法实时监听绑定状态回调即可(超时自行控制,最大超时依赖bindToken的有效时长)。
class RTCXFluAddDeviceApi {
/// 添加设备
/// 准备添加设备,成功才可以进行下一步
void prepareAddDevice(RTCXFluDeviceAddType deviceAddType);
/// 添加事件回调
void onDeviceAddListener();
/// 开始添加设备,成功才可以进行下一步
void startAddDevice(RTCXFluDeviceAddReq req);
/// 开始添加设备, 有线方式
void startAddWRDevice(RTCXFluDeviceAddWRReq req);
/// 开始添加设备, 二维码方式
void startAddQRDevice(RTCXFluDeviceAddQRReq req);
/// 开始添加设备, 4G方式
void startAdd4GDevice(RTCXFluDeviceAdd4GReq req);
/// 开始添加设备, 蓝牙绑定方式
void startAddBTDevice(RTCXFluDeviceAddBTReq req);
/// 开始添加设备, AP绑定方式
void startAddAPDevice(RTCXFluDeviceAddAPReq req);
/// 停止添加设备
void stopAddDevice();
/// 获取二维码内容
@async
List<String> getQRCodeData(RTCXFluDeviceAddQRReq req);
/// 获取蓝牙授权权限
@async
RTCXFluBTAuthorizeStatus getBluetoothAuthorizeStatus();
/// 开始扫描蓝牙设备
@async
List<RTCXFluBTLinkDevInfoRsp> startScanBTDevices(RTCXFluBTLinkScanReq req);
/// 停止扫描蓝牙设备
void stopScanBTDevices();
/// 连接蓝牙设备
@async
RTCXFluBTLinkResult connectLinkBTDevice(RTCXFluBTLinkNetworkingReq req);
/// AP开始连接
@async
RTCXFluAPLinkResult startAPLinkConnect(RTCXFluAPLinkConnectReq req);
/// AP发送配网信息
@async
RTCXFluAPLinkResult sendAPLinkNetworking(RTCXFluAPLinkNetworkingReq req);
}
注意
- 需要prepareAddDevice:方法之前注册监听
二维码绑定
调用示例如下:
- 注册监听,并准备绑定
final addDeviceApi = RTCXFluAddDeviceController();
@override
void initState() {
super.initState();
addDeviceApi.onDeviceAddListener();
addDeviceApi.onDeviceAdd.listen((data) {
if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Success) {
Fluttertoast.showToast(msg: "绑定成功");
} else if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Prepared) {
Fluttertoast.showToast(msg: "已准备好添加设备");
debugPrint("error : ${data.error.code} -- ${data.error.message}");
} else {
Fluttertoast.showToast(
msg: "绑定结果:${data.status.name} + error:$data.error",
);
}
});
// 准备二维码绑定
addDeviceApi.prepareAddDevice(RTCXFluDeviceAddType.RTCXFluDeviceAddType_QR);
}
- 通过二维码绑定方式,生成带有 WiFi 名和密码的二维码内容
// 需要传递productKey、deviceName、ssid、wifiPwd
void getQRCodeData() async {
try {
final String productKey = "";
final String deviceName = "";
RTCXFluDeviceAddQRReq req = RTCXFluDeviceAddQRReq(productKey: productKey, deviceName: deviceName, ssid: "", wifiPwd: "");
addDeviceApi.getQRCodeData(req).then((List<String>? qrCodeStrings) {
if (qrCodeStrings!.isNotEmpty) {
setState(() {
qrcodeString = qrCodeStrings.first;
});
Fluttertoast.showToast(msg: 'qrcodeString:${qrcodeString}');
}
});
} catch (e) {
Fluttertoast.showToast(msg: '解析二维码失败: $e');
}
}
- 开始二维码绑定
void _startQRAddDevice() {
// 开始添加设备
addDeviceApi.startAddQRDevice(
RTCXFluDeviceAddQRReq(
productKey: "productKey",
deviceName: "deviceName",
),
);
}
- 结束绑定
// 在diapose中调用stopAddDevice与destroy方法
@override
void dispose() {
super.dispose();
addDeviceApi.stopAddDevice();
addDeviceApi.destroy();
}
4G绑定
设备已配有4G网,通过4G绑定方式进行绑定。 调用示例如下:
- 注册监听,并准备绑定
final addDeviceApi = RTCXFluAddDeviceController();
@override
void initState() {
super.initState();
addDeviceApi.onDeviceAddListener();
addDeviceApi.onDeviceAdd.listen((data) {
if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Success) {
Fluttertoast.showToast(msg: "绑定成功");
} else if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Prepared) {
Fluttertoast.showToast(msg: "已准备好添加设备");
debugPrint("error : ${data.error.code} -- ${data.error.message}");
} else {
Fluttertoast.showToast(
msg: "绑定结果:${data.status.name} + error:$data.error",
);
}
});
// 准备4G绑定
addDeviceApi.prepareAddDevice(RTCXFluDeviceAddType.RTCXFluDeviceAddType_4G);
_addDeviceBy4G();
}
- 开始4G绑定
// 调用startAdd4GDevice,等待绑定结果状态监听回调
void _addDeviceBy4G() {
RTCXFluDeviceAdd4GReq req = RTCXFluDeviceAdd4GReq(productKey: '填写设备的productKey', deviceName: '填写设备的deviceName');
//请不要更改req的deviceAddType类型。
addDeviceApi.startAdd4GDevice(req);
}
- 结束绑定
// 在diapose中调用stopAddDevice与destroy方法
@override
void dispose() {
super.dispose();
addDeviceApi.stopAddDevice();
addDeviceApi.destroy();
}
蓝牙配网绑定
通过蓝牙配网方式,将WI-FI及WI-FI密码发给设备,进行绑定设备方式。 蓝牙绑定前需要配置权限,详细配置权限请见配置权限
调用示例如下:
- 注册监听,并准备绑定
var addDeviceApi = RTCXFluAddDeviceController();
@override
void initState() {
super.initState();
addDeviceApi.onDeviceAddListener();
addDeviceApi.onDeviceAdd.listen((data) {
print("绑定结果:data: ${data.toString()}");
if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Success) {
Fluttertoast.showToast(msg: "绑定成功");
} else if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Prepared) {
Fluttertoast.showToast(msg: "已准备好添加设备");
debugPrint("error : ${data.error.code} -- ${data.error.message}");
} else {
Fluttertoast.showToast(
msg: "绑定结果:${data.status.name} + error:$data.error",
);
}
});
_prepare();
}
void _prepare() {
addDeviceApi.prepareAddDevice(RTCXFluDeviceAddType.RTCXFluDeviceAddType_BT);
}
- 获取蓝牙权限
void _getBluetoothAuthorizeStatus() {
addDeviceApi.getBluetoothAuthorizeStatus().then((RTCXFluBTAuthorizeStatus status) {
if (RTCXFluBTAuthorizeStatus.RTCXFluBTAuthorizeStatus_PoweredOn == status) {
_startScanDevices();
} else {
Fluttertoast.showToast(msg: '获取蓝牙权限status: $status');
}
}).catchError((error) {
Fluttertoast.showToast(msg: '获取蓝牙权限失败: $error');
});
}
- 获取蓝牙权限后,开始扫描设备
void _startScanDevices() {
RTCXFluBTLinkScanReq req = RTCXFluBTLinkScanReq(namePrefixs: [
"XSDEV_","XS_"
]);
addDeviceApi.startScanBTDevices(req).then((result){
if (result.isNotEmpty) {
// 扫描出的蓝牙设备
List<RTCXFluBTLinkDevInfoRsp> deviceList = result;
} else {
Fluttertoast.showToast(msg: '未搜索到设备');
}
}).catchError((error) {
Fluttertoast.showToast(msg: '扫描设备失败: $error');
_stopScanBTDevices();
});
}
// 停止扫描设备
void _stopScanBTDevices() {
addDeviceApi.stopScanBTDevices();
}
- 连接蓝牙设备
连接选择要绑定的设备,将WI-FI的名称及WI-FI密码发给设备。并进行绑定。
// 选择要绑定的设备后,连接蓝牙设备,
// 连接蓝牙设备,需要先调用获取到二维码字符串后,调用connectLinkBTDevice
void _connectLinkBTDevice(RTCXFluBTLinkDevInfoRsp info) {
// 这里productKey,deviceName没有就 传空字符串。
RTCXFluDeviceAddBTReq btReq = RTCXFluDeviceAddBTReq(productKey: '', deviceName: '');
// 调用startAddBTDevice
addDeviceApi.startAddBTDevice(btReq);
// 获取WI-FI、WI-FI密码content,发送给蓝牙设备
RTCXFluDeviceAddQRReq req = RTCXFluDeviceAddQRReq(productKey: "", deviceName: "", ssid: "WI-FI的名称", wifiPwd: "WI-FI的密码");
addDeviceApi.getQRCodeData(req).then((List<String>? qrCodeStrings) {
if (qrCodeStrings!.isNotEmpty) {
String qrcodeString = qrCodeStrings.first;
RTCXFluBTLinkNetworkingReq req = RTCXFluBTLinkNetworkingReq(sn: info.sn, content: qrcodeString);
addDeviceApi.connectLinkBTDevice(req).then((RTCXFluBTLinkResult result){
if (true == result.success) {
// 连接成功,等待addDeviceApi.onDeviceAdd.listen绑定结果
// 可以设置定时器如2分钟,超时则认为绑定失败。addDeviceApi.onDeviceAdd.listen返回后关闭定时器。
} else {
Fluttertoast.showToast(msg: '连接设备失败');
}
}).catchError((error) {
Fluttertoast.showToast(msg: '连接设备失败: $error');
});
} else {
Fluttertoast.showToast(msg: '获取content失败');
}
}).catchError((error) {
Fluttertoast.showToast(msg: '获取content失败: $error');
});
}
- 结束绑定
// 在diapose中调用stopAddDevice与destroy方法
@override
void dispose() {
super.dispose();
addDeviceApi.stopAddDevice();
addDeviceApi.destroy();
}
AP配网绑定
设备AP配网时,待设备重置后,等待设备待连接状态,连接设备的热点,通过App传输Wi-Fi的SSID和密码,使设备加入目标网络。
调用示例如下:
- 注册监听,并准备绑定
var addDeviceApi = RTCXFluAddDeviceController();
@override
void initState() {
super.initState();
addDeviceApi.onDeviceAddListener();
addDeviceApi.onDeviceAdd.listen((data) {
print("绑定结果:data: ${data.toString()}");
if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Success) {
Fluttertoast.showToast(msg: "绑定成功");
} else if (data.status ==
RTCXFluDeviceAddStatus.RTCXFluDeviceAddStatus_Prepared) {
Fluttertoast.showToast(msg: "已准备好添加设备");
debugPrint("error : ${data.error.code} -- ${data.error.message}");
} else {
Fluttertoast.showToast(
msg: "绑定结果:${data.status.name} + error:$data.error",
);
}
});
_prepare();
}
void _prepare() {
// 先添加代理 在调用
addDeviceApi.prepareAddDevice(RTCXFluDeviceAddType.RTCXFluDeviceAddType_AP);
}
- AP连接与发送配网信息
手机连接设备的热点后,调用startAPLinkConnect接口
// 调用AP连接
Future<void> _startAPLinkConnect() async {
try {
RTCXFluAPLinkConnectReq req = RTCXFluAPLinkConnectReq();
RTCXFluAPLinkResult result = await addDeviceApi.startAPLinkConnect(req);
if (true == result.success) {
// 连接成功
} else {
Fluttertoast.showToast(msg: 'AP连接失败: $e');
}
} catch(e) {
Fluttertoast.showToast(msg: 'AP连接失败: $e');
}
}
// 发送WI-FI、WI-FI密码给设备
Future<void> _sendNetworking() async {
try {
RTCXFluAPLinkNetworkingReq req = RTCXFluAPLinkNetworkingReq(ssid: 'wifi名', pwd: 'wifi密码');
RTCXFluAPLinkResult result = await addDeviceApi.sendAPLinkNetworking(req);
if (true == result.success) {
// 连接成功
} else {
Fluttertoast.showToast(msg: 'AP配网信息失败');
}
} catch(e) {
Fluttertoast.showToast(msg: 'AP配网信息失败: $e');
}
注意
发送WiFi名称、WiFi密码后,设备连接上WIFI后,设备会主动断开热点。 设备主动断开热点后,APP会断开网络后重新连接其他网络。
- 绑定设备
APP会断开网络后重新连接其他网络后进行绑定
Future<void> addAPDevice() async {
try {
RTCXFluDeviceAddAPReq req = RTCXFluDeviceAddAPReq(productKey: '设备的productKey', deviceName: '设备的deviceName');
await addDeviceApi.startAddAPDevice(req);
} catch(e) {
Fluttertoast.showToast(msg: 'AP配网信息失败: $e');
}
}
- 结束绑定
// 在diapose中调用stopAddDevice与destroy方法
@override
void dispose() {
super.dispose();
addDeviceApi.stopAddDevice();
addDeviceApi.destroy();
}
设备解绑
final deviceApi = RTCXFluDeviceApi();
// 解绑设备
try {
final result = await deviceApi.deviceUnbind('iotId');
if (result.success == true) {
Fluttertoast.showToast(msg: '解绑成功');
} else {
Fluttertoast.showToast(msg: '解绑失败');
}
} catch (e) {
Fluttertoast.showToast(msg: '解绑失败: $e');
}
设备列表
class RTCXFluDeviceApi {
/// 获取设备列表信息
@async
RTCXFluDeviceInfoList getDeviceList(RTCXFluQueryDeviceListReq req);
/// 获取子设备列表
@async
RTCXFluDeviceInfoList getSubDeviceList(RTCXFluQuerySubDeviceListReq req);
}
获取设备列表调用示例
try {
final req = RTCXFluQueryDeviceListReq(pageNo: 1, pageSize: 10);
RTCXFluDeviceInfoList result = await deviceApi.getDeviceList(req);
setState(() {
dataList = result.data;
// 判断是否还有更多
bool hasMore = (result.data?.length ?? 0) < (result.total ?? 0);
});
} catch (e) {
Fluttertoast.showToast(msg: "获取设备列表失败: $e");
}
获取设备的子设备列表调用示例
try {
final req = RTCXFluQuerySubDeviceListReq(
iotId: "iotId",
productKey: "productKey",
deviceName: "deviceName",
pageNo: 1,
pageSize: 10,
);
RTCXFluDeviceInfoList result = await deviceApi.getSubDeviceList(req);
setState(() {
dataList = result.data;
// 判断是否还有更多
bool hasMore = (result.data?.length ?? 0) < (result.total ?? 0);
});
} catch (e) {
Fluttertoast.showToast(msg: "获取子设备列表失败: $e");
}
设备详细信息
class RTCXFluDeviceApi {
/// 获取设备列表信息
@async
RTCXFluDeviceInfoList getDeviceDetail(RTCXFluQueryDeviceDetailListReq req);
}
void _getDeviceDetail() {
RTCXFluQueryDeviceDetailReq req = RTCXFluQueryDeviceDetailReq(
iotId: widget.iotId,
productKey: widget.productKey,
deviceName: widget.deviceName,
);
List<RTCXFluQueryDeviceDetailReq> iotIds = [];
iotIds.add(req);
RTCXFluQueryDeviceDetailListReq listReq = RTCXFluQueryDeviceDetailListReq(
list: iotIds,
);
deviceApi.getDeviceDetail(listReq).then((RTCXFluDeviceInfoList data) {
print('查询设备详情成功:\n\n${data.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
设备排序
class RTCXFluDeviceApi {
/// 设备排序
@async
RTCXFluDeviceResult deviceSort(RTCXFluDeviceSortReq req);
}
Future<void> _saveDeviceSort() async {
try {
List<int> sortIdList = [];
for (int i = 0; i < deviceList.length; i++) {
final info = deviceList[i];
if (info.sortId != null) {
sortIdList.add(info.sortId!);
}
}
final req = RTCXFluDeviceSortReq(sortedIdList: sortIdList);
final result = await deviceApi.deviceSort(req);
if (result.success) {
Fluttertoast.showToast(msg: "排序成功");
} else {
Fluttertoast.showToast(msg: "排序失败");
}
} catch (e) {
Fluttertoast.showToast(msg: "排序失败: $e");
}
}
修改设备昵称
class RTCXFluDeviceApi {
/// 设置设备昵称
@async
RTCXFluDeviceResult setDeviceNickName(RTCXFluDeviceNickdNameSetReq req);
}
修改设备昵称调用示例
try {
RTCXFluDeviceNickdNameSetReq req = RTCXFluDeviceNickdNameSetReq(iotId: '', nickName: '');
final result = await deviceApi.setDeviceNickName(req);
if (result.success == true) {
Fluttertoast.showToast(msg: '修改成功');
} else {
Fluttertoast.showToast(msg: '修改失败');
}
} catch (e) {
Fluttertoast.showToast(msg: '修改失败: $e');
}
设备配置
class RTCXFluDeviceApi {
/// 获取设备配置
@async
RTCXFluDeviceConfigRsp getDeviceConfig(RTCXFluGetDeviceConfigReq req);
/// 保存设备配置
@async
RTCXFluDeviceResult setDeviceConfig(RTCXFluSetDeviceConfigReq req);
}
获取设备配置
void _getDeviceConfig() {
RTCXFluGetDeviceConfigReq configReq = RTCXFluGetDeviceConfigReq(iotId: widget.iotId, attributeIdList: [1004]);
deviceApi.getDeviceConfig(configReq).then((RTCXFluDeviceConfigRsp configRsp) {
final buffer = StringBuffer();
buffer.writeln('获取设备配置');
buffer.writeln('maxUpdateTimeValue: ${configRsp.maxUpdateTimeValue}');
buffer.writeln('attributeMap: ${configRsp.attributeMap}');
if (configRsp.attributeMap != null) {
Map map = configRsp.attributeMap!["1004"] as Map;
configValue = map["value"];
}
buffer.writeln('configValue: ${configValue}');
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
保存设备配置
void _setDeviceConfig() {
if (configValue == null) {
return;
}
Map<String, Object> attribute = {
"id": "1004",
"value":configValue!,
};
RTCXFluSetDeviceConfigReq configReq = RTCXFluSetDeviceConfigReq(iotId: widget.iotId, attributeList: [attribute]);
deviceApi.setDeviceConfig(configReq).then((RTCXFluDeviceResult result) {
final buffer = StringBuffer();
buffer.writeln('保存设备配置');
buffer.writeln('result: ${result.success}');
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
云台预置位
class RTCXFluDeviceApi {
/// 保存预置位
@async
RTCXFluDeviceResult savePtzPresetPosition(
RTCXFluSavePtzPresetPositionReq req,
);
/// 获取预置位列表
@async
RTCXFluGetPtzPresetPositionListRsp getPtzPresetPositionList(
RTCXFluGetPtzPresetPositionListReq req,
);
/// 删除预置位
@async
RTCXFluDeviceResult deletePtzPresetPosition(
RTCXFluDeletePtzPresetPositionReq req,
);
/// 更新预置位名称
@async
RTCXFluDeviceResult updatePtzPresetPosition(
RTCXFluUpdatePtzPresetPositionReq req,
);
}
新增预置位
Future<void> _savePtzPresetPosition() async {
// ptz位置信息, 格式{"X":1054,"Y":2500}
String ptz = '';
// 图片的Uint8List
Uint8List data = await getAssetAsUint8List("assets/avatar1.png");
RTCXFluSavePtzPresetPositionReq positionReq = RTCXFluSavePtzPresetPositionReq(iotId: widget.iotId, ptz: ptz, name: "新预置名称", imageData: data);
deviceApi.savePtzPresetPosition(positionReq).then((RTCXFluDeviceResult result) {
final buffer = StringBuffer();
buffer.writeln('保存预置位');
buffer.writeln('result: ${result.success}');
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
删除预置位
void _deletePtzPresetPosition() {
// 预置位的picId
String picId = '';
RTCXFluDeletePtzPresetPositionReq positionReq = RTCXFluDeletePtzPresetPositionReq(iotId: widget.iotId, picId: picId);
deviceApi.deletePtzPresetPosition(positionReq).then((RTCXFluDeviceResult result) {
final buffer = StringBuffer();
buffer.writeln('删除预置位');
buffer.writeln('result: ${result.success}');
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
修改预置位名称
void _updatePtzPresetPosition() {
// 预置位的picId
String picId = '';
RTCXFluUpdatePtzPresetPositionReq positionReq = RTCXFluUpdatePtzPresetPositionReq(iotId: widget.iotId, picId: picId, name: '预置位新名称');
deviceApi.updatePtzPresetPosition(positionReq).then((RTCXFluDeviceResult result) {
final buffer = StringBuffer();
buffer.writeln('更新预置位');
buffer.writeln('result: ${result.success}');
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
获取预置位列表
void _getPtzPresetPositionList() {
RTCXFluGetPtzPresetPositionListReq listReq = RTCXFluGetPtzPresetPositionListReq(iotId: widget.iotId);
deviceApi.getPtzPresetPositionList(listReq).then((RTCXFluGetPtzPresetPositionListRsp listRsp) {
final buffer = StringBuffer();
buffer.writeln('获取预置位列表');
buffer.writeln('');
if (listRsp.presetPositionList != null) {
presetPositionList = listRsp.presetPositionList!;
for (int i = 0; i < listRsp.presetPositionList!.length; i++) {
final item = listRsp.presetPositionList![i];
buffer.writeln('[$i]');
buffer.writeln('name: ${item.name}');
buffer.writeln('picId: ${item.picId}');
buffer.writeln('ptz: ${item.ptz}');
buffer.writeln('url: ${item.url}');
buffer.writeln('');
}
}
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
获取设备电量信息
class RTCXFluDeviceApi {
/// 获取电池电量列表
@async
RTCXFluBatteryPowerListRsp getBatteryPowerList(
RTCXFluBatteryPowerListReq req,
);
}
void _getBatteryPowerList() {
final now = DateTime.now();
final yesterday = now.subtract(const Duration(hours: 24));
RTCXFluBatteryPowerListReq req = RTCXFluBatteryPowerListReq(iotId: widget.iotId, startTime: yesterday.millisecondsSinceEpoch, endTime: now.millisecondsSinceEpoch, limit: 100);
deviceApi.getBatteryPowerList(req).then((RTCXFluBatteryPowerListRsp listRsp) {
final buffer = StringBuffer();
buffer.writeln('获取电池电量列表');
buffer.writeln('');
if (listRsp.electricQuantityList != null) {
for (int i = 0; i < listRsp.electricQuantityList!.length; i++) {
final item = listRsp.electricQuantityList![i];
buffer.writeln('[$i]');
buffer.writeln('timestamp: ${item.timestamp}--value: ${item.value}');
buffer.writeln('');
}
}
print('Result:\n\n${buffer.toString()}');
}).catchError((error) {
print('调用异常:${error.toString()}');
});
}
设备缩略图
- 获取设备缩略图
void getDeviceThumb(RTCXFluDeviceInfoModel info) {
RTCXFluGetDeviceThumbnailReq req = RTCXFluGetDeviceThumbnailReq(
productKey: '${info.productKey}',
deviceName: '${info.deviceName}',
definition: 1,
picType: 'jpg',
isPrivatized: false);
String iotId = "${info.iotId}";
deviceApi.getDeviceThumbnail(req).then((RTCXFluGetDeviceThumbnailRsp thumbRsp) {
StringBuffer buffer = StringBuffer();
buffer.writeln('RTCXFluGetDeviceThumbnailRsp thumbRsp');
buffer.writeln('productKey: ${thumbRsp.productKey}');
buffer.writeln('deviceName: ${thumbRsp.productKey}');
buffer.writeln('设备缩略图地址 downloadUrl: ${thumbRsp.downloadUrl}');
buffer.writeln('设备缩略图过期时间: ${thumbRsp.expiredTime}');
buffer.writeln('');
print("getDeviceThumb thumbRsp :${buffer.toString()}");
if(thumbRsp.productKey != null && thumbRsp.deviceName != null) {
setState(() {
thumbData[iotId] = thumbRsp;
});
}
}).catchError((error){
print("getDeviceThumb catchError:$error");
});
}
- 通过物模型服务获取设备缩略图
// 导入物模型头文件
import 'package:airtc_engine/src/thing/rtcx_thing.dart';
import 'package:airtc_engine/src/thing/rtcx_thing_controller.dart';
late RTCXFluThingController _thingApi;
@override
void initState() {
super.initState();
// 物模型
RTCXFluThingReq req = RTCXFluThingReq(
productKey: widget.productKey,
deviceName: widget.deviceName,
iotId: widget.iotId,
deviceType: widget.deviceType,
);
_thingApi = RTCXFluThingController();
_thingApi.buildThing(req);
_thingApi.registerThingObserver();
_thingApi.onStatusChange.listen((data) {
print("onStatusChange:"+data.toString());
});
_thingApi.onDeviceTransferMessage.listen((RTCXFluThingObserver observer) {
print("onDeviceTransferMessage:"+observer.toString());
});
}
Future<void> getDeviceThumb() async {
try {
final result = await _thingApi.invokeService(
RTCXFluThingCommand(
command: "GetDevPicture",
params: {
"definition": 1,
"picType": "jpg",
},
),
);
if(result.success && result.dataObject != null) {
Map<String, dynamic> dataObjectMap = jsonDecode(result.dataObject!);
// 获取的设备缩略图
String? picUrl = dataObjectMap["downloadUrl"];
}
Fluttertoast.showToast(msg: "获取缩略图${result == true ? "成功" : "失败"}, ${result.dataObject}");
} catch(e) {
Fluttertoast.showToast(msg: "获取缩略图失败:${e.toString()}");
}
}
// 不需要的时候需要做destroy释放操作
@override
void dispose() {
super.dispose();
_thingApi.destroy();
}
低功耗设备唤醒
class RTCXFluDeviceApi {
/// 休眠设备唤醒,可以通过定时器循环调用唤醒设备,唤醒成功后关闭定时器,并且进行播放
@async
RTCXFluDeviceResult wakeupDevice(String iotId);
}
低功耗设备唤醒调用示例
Future<void> _wakeupDevice(String iotId) async {
try {
final result = await deviceApi.wakeupDevice(iotId);
if (result.success == true) {
Fluttertoast.showToast(msg: '调用成功');
} else {
Fluttertoast.showToast(msg: '调用失败');
}
} catch (e) {
Fluttertoast.showToast(msg: '调用失败: $e');
}
}
注意
- 调用该接口只代表触发了低功耗设备唤醒,其返回成功结果并不代表设备已经唤醒上线(因为唤醒需要一定的时间)
- 针对低功耗设备的播放,APP需要按如下逻辑实现:
- 调用唤醒接口触发设备唤醒
- 监听设备上线,监听方式有两种:a. 定时器轮询物模型的RTCXFluThingResult getStatus()接口 b. 或者代理协议监听物对象的void onStatusChange(RTCXFluThingObserver value)协议方法
- 设备上线后再调用播放器进行播放
- 为了防止低功耗设备在播放过程中休眠(比如从播放页进入设置页去设置一些参数,此时如果设备休眠,是无法成功设置参数的),App需要在播放界面使用定时器调用物模型,向设备发送物服务WakeupHeartbeat心跳(间隔可控制10秒一次),保持低功耗设备不休眠,播放界面销毁时,停止定时器