UNIAPP框架中使用BLE蓝牙连接

概述

  1. 蓝牙连接包括搜索蓝牙设备,选择蓝牙设备,监听设备特征值,发送命令,断开蓝牙连接5种基础方法。
  2. Uni-App BLE 文档地址
  3. 搜索设备时

搜索蓝牙设备

javascript 复制代码
function discoveryDevices(pushDevice){
	console.log('enter search ble bluetooth func');
	// 初始化蓝牙模块
	uni.openBluetoothAdapter({
	  success(res) {
	    // console.log("uni.openBluetoothAdapter success:", res);
		if (res && res.errMsg && res.errMsg === 'openBluetoothAdapter:ok') {
			startScanDevice();
			startListenDeviceFound(pushDevice);
		}
	  },
	  fail(res) {
		console.log("uni.openBluetoothAdapter fail:", res);
		switch (res.errCode) {
			case 10001:
				console.log("uni.openBluetoothAdapter faile:当前蓝牙适配器不可用");break;
			default:
		}
	  }
	})
}

function startScanDevice() {
	uni.startBluetoothDevicesDiscovery({
	  success(res) {
	    // console.log("uni.startBluetoothDevicesDiscovery success:", res);
	  },
	  fail(res) {
		console.log("uni.startBluetoothDevicesDiscovery fail:", res);
	  }
	})
}

function startListenDeviceFound(pushDevice) {
	uni.onBluetoothDeviceFound(function (res) {
	  // console.log('new device list has founded', res);
	  let devices = res.devices.map(item => {
		  return {
			  name: item.localName || item.name,
			  value: item.deviceId
		  }
	  }).filter(item => {return item.name});
	  devices.forEach(item => {
		  let vaildArray = deviceListXianXY.filter(item2 => {
			  return item2.value === item.value;
		  })
		  if (vaildArray.length === 0) {
			  deviceListXianXY.push(item);
			  pushDevice(item);
		  }
	  });
	})
}

选择蓝牙设备

javascript 复制代码
function connDevice(deviceId){
	console.log("choosed deviceId: ", deviceId);

	uni.createBLEConnection({
	  // 这里的 deviceId 需要已经通过 createBLEConnection 与对应设备建立链接
	  deviceId,
	  success(res) {
		// console.log("uni.createBLEConnection success:", res);
		setTimeout(() => {
			getDeviceService(deviceId, () => {
				startNotify(deviceId);
			})
		}, 1000) // 这里设置延时是因为连接完成后立即获取不到服务信息
		stopScanDevice();
	  },
	  fail(res) {
		console.log("uni.createBLEConnection fail:", res);
	  }
	})
}

// 关闭扫描
function stopScanDevice(){
	uni.stopBluetoothDevicesDiscovery({
		success(res) {
		  console.log("uni.stopBluetoothDevicesDiscovery success:", res);
		}
	})
}

function getDeviceService(deviceId, callback) {
	uni.getBLEDeviceServices({
	  // 这里的 deviceId 需要已经通过 createBLEConnection 与对应设备建立链接
	  deviceId,
	  success(res) {
	    // console.log("uni.getBLEDeviceServices success:", res);
		setTimeout(() => {
			getDeviceServcieCharacteristics(deviceId, callback);
		}, 20);
	  },
	  fail(res) {
		console.log("uni.getBLEDeviceServices fail:", res);
	  }
	})
}

function getDeviceServcieCharacteristics(deviceId, callback) {
	uni.getBLEDeviceCharacteristics({
	  // 这里的 deviceId 需要已经通过 createBLEConnection 与对应设备建立链接
	  deviceId,
	  // 这里的 serviceId 需要在 getBLEDeviceServices 接口中获取
	  serviceId,
	  success(res) {
	    // console.log("uni.getDeviceServcieCharacteristics success:", res);
		if (callback) {
			callback();
		}
	  },
	  fail(res) {
		console.log("uni.getDeviceServcieCharacteristics fail:", res);
	  }
	})
}

function startNotify(deviceId) {
	console.log("enter startNotify");
	uni.notifyBLECharacteristicValueChange({
	  state: true, // 启用 notify 功能
	  // 这里的 deviceId 需要已经通过 createBLEConnection 与对应设备建立链接
	  deviceId,
	  // 这里的 serviceId 需要在 getBLEDeviceServices 接口中获取
	  serviceId,
	  // 这里的 characteristicId 需要在 getBLEDeviceCharacteristics 接口中获取
	  characteristicId: characteristicIdNotify,
	  success(res) {
		// console.log("uni.notifyBLECharacteristicValueChange success:", res);
	  },
	  fail(res) {
		console.log("uni.notifyBLECharacteristicValueChange fail:", res);
	  }
	})
}

发送命令

javascript 复制代码
function writeCommand(deviceId,command,ck,failfun){
	//监听
	startListenble(function (buf) {
		ck(buf)
	});
	console.log("command===",command,"长度",command.length);
	const subCommandArray = splitArr(command, 20); //安卓系统中默认每包最大字节数为20,现在版本已经支持设置mtu,但有些框架不支持,所以还是使用这种方式。
	sendCommand(deviceId, serviceId, characteristicId2, subCommandArray, 0);
}

function sendCommand(deviceId, serviceId, characteristicId2, commands, index, callback) {
	uni.writeBLECharacteristicValue({
	  // 这里的 deviceId 需要在 getBluetoothDevices 或 onBluetoothDeviceFound 接口中获取
	  deviceId,
	  // 这里的 serviceId 需要在 getBLEDeviceServices 接口中获取
	  serviceId,
	  // 这里的 characteristicId 需要在 getBLEDeviceCharacteristics 接口中获取
	  characteristicId: characteristicId2,
	  // 这里的value是ArrayBuffer类型
	  value: commands[index],
	  success(res) {
	    // console.log('uni.writeBLECharacteristicValue success', res.errMsg);
		if (index >= commands.length - 1) {
			if (callback) {
				callback();
			}
		} else {
			// 这里使用递归是因为使用循环可能出现发送数据错误的情况
			sendCommand(deviceId, serviceId, characteristicId2, commands, ++index, callback);
		}
	  },
	  fail(res) {
		console.log('uni.writeBLECharacteristicValue fail', res.errMsg);
	  }
	})
}

function startListenble(callback){
	let resultBuf = "";
	uni.onBLECharacteristicValueChange(function (res) {
	  // console.log(`characteristic ${res.characteristicId} has changed, now is ${res.value}`)
	  const buf = buf2hex(res.value)
	  console.log("buf", buf);
	  resultBuf += buf;
	  if (resultBuf.endsWith('e9')) { // 帧结束标志位E9
		console.log("响应帧",resultBuf);
		callback(resultBuf);
	  }
	})
}

function splitArr(ar, size = 1) {
	let index = 0;
	let res = [];
	while (index < ar.length) {
		res.push(ar.slice(index, (index+size)));
		index += size;
	}
	return res;
}

function buf2hex(buffer) {// buffer is an ArrayBuffer
	return Array.prototype.map.call(new Uint8Array(buffer), x => ('00' + x.toString(16)).slice(-2)).join('');
}

关闭连接

javascript 复制代码
function closeConn(deviceId){
	uni.closeBLEConnection({
	  deviceId,
	  success(res) {
	    console.log('uni.closeBLEConnection success', res);
	  },
	  fail(res) {
		console.log('uni.closeBLEConnection fail', res);
	  }
	})
}
相关推荐
2501_916007471 小时前
iOS和macOS应用程序性能分析和优化工具使用综合指南
android·macos·ios·小程序·uni-app·iphone·webview
2501_916007471 天前
深入理解HTTPS对称与非对称加密机制及Charles抓包实践
网络协议·http·ios·小程序·https·uni-app·iphone
小徐_23331 天前
AI 写 wot-ui 总在猜 API?我们把 Skills、MCP 和 CLI 都配好了
前端·uni-app·ai编程
Liu.7741 天前
uni-app 组件 uni-easyinput 常见 Bug 及解决方案
uni-app·bug
小徐_23332 天前
uni-app 项目别再从零搭了!3 个 Wot UI 起手模板怎么选?
前端·uni-app
蜡台2 天前
uniapp pdf文件预览组件
pdf·uni-app·合同·pdfh5
凡泰AI2 天前
如何借助MCP打通企业APP内部服务:从统一调用到小程序承接
小程序·uni-app·app·mpaas·mcp·小程序容器
华玥作者2 天前
uniapp 万条数据不卡顿:我写了个虚拟列表组件 hy-list,原生支持瀑布流
数据结构·uni-app·list·vue3
这是个栗子2 天前
uni-app 微信小程序开发:常用函数总结(一)
微信小程序·小程序·uni-app·getcurrentpages
宠友信息4 天前
消息序号如何保证即时通讯源码聊天记录稳定加载
java·spring boot·redis·python·mysql·uni-app