文章来源地址https://www.toymoban.com/news/detail-530450.html
import {
SERVICEID,
NOTIFYID,
WRITEID,
BLUETOOTH_MESSAGE,
OPERATE_PROCESS
} from "./config.js"
import {
openBluetoothAdapterFailCallback,
onBluetoothAdapterStateChangeCallback,
onBluetoothDeviceFoundCallback,
getBluetoothAdapterStateSuccessCallback,
getBluetoothAdapterStateFailCallback,
createBLEConnectioSuccessCallback,
createBLEConnectioFailCallback,
onBLEConnectionStateChangeCallback,
onBLECharacteristicValueChangeCallback,
initStoreState,
notifyBLECharacteristicValueChangeFailCallback
} from "./tool.js"
import {
hexStringToArrayBuffer,
sleep,
getBufferArrayBy20,
arrayBufferToHexString,
setCommunicationListUtil,
getNowTime,
getMac,
filterDevices,
filterDevicesByRe,
unique,
showModalByMethod
} from "./utils.js"
let util = require('@/static/utils/utils.js');
import vm from "@/main.js"
//正常蓝牙流程开始
export let bluetoothStart = () => {
getBluetoothAdapterState();
}
export let onBluetoothAdapterStateChange = () => {
//如果蓝牙打开-关闭-再打开-监听不到?
uni.onBluetoothAdapterStateChange(async (res) => {
bluetoothExecByAdapterStatus(res);
})
}
//根据蓝牙适配器的状态、是否正在搜索设备执行不同的操作流程
export let bluetoothExecByAdapterStatus = (res) => {
console.log("蓝牙适配器状态", res);
if (!res.available) {
util.showModal("蓝牙适配器不可用,请打开蓝牙");
} else {
if (!res.discovering && !vm.isNormalDiscoveryStatus) { // 防止正常停止搜索的时候会触发这个条件
//如果前面已经搜索过蓝牙,则不需要再次搜索
vm.$u.vuex("isImmediateWhitePackage", false); //防止打开手机蓝牙后并连接成功后,直接让蓝牙发送指令
if (vm.isBluetoothDiscovery) {
getBluetoothDevices();
} else {
startAndStopbluetoothDevicesDiscovery();
}
}
}
}
//获取在蓝牙模块生效期间所有已发现的蓝牙设备。包括已经和本机处于连接状态的设备
export let getBluetoothDevices = () => {
uni.getBluetoothDevices({
success(res) {
let devices = res.devices;
let devicesList = filterDevices(res.devices, vm.currentBike);
if (devicesList.length > 0) {
vm.$u.vuex('bluetoothDevice', devicesList[0])
vm.$u.vuex('connectCount', 0)
createBLEConnection(devicesList[0])
} else {
startAndStopbluetoothDevicesDiscovery();
}
}
})
}
//打开蓝牙设备并监听蓝牙设备
export let openAndOnBluetoothAdapter = () => {
vm.$u.vuex("bluetoothContent", "正在初始化蓝牙");
uni.openBluetoothAdapter({
success(res) {
console.log("打开蓝牙适配器成功");
startAndStopbluetoothDevicesDiscovery();
},
fail(res) {
console.log("打开蓝牙设备器失败", res)
console.log(res.errMsg == "openBluetoothAdapter:fail already opened")
//蓝牙适配器已经打开
if (res.errMsg == "openBluetoothAdapter:fail already opened") {
startAndStopbluetoothDevicesDiscovery();
} else {
console.log("打开蓝牙适配器失败:", BLUETOOTH_MESSAGE[res.errCode]);
util.showModal("蓝牙适配器不可用,请打开蓝牙或微信APP开启蓝牙权限");
openBluetoothAdapterFailCallback();
}
},
complete() {
onBluetoothAdapterStateChange();
}
})
}
//开始和停止蓝牙搜索
export let startAndStopbluetoothDevicesDiscovery = () => {
//1、关闭蓝牙-杀掉进程,开启蓝牙不会重新连接,没有监听搜索到的设备
onBluetoothDeviceFound();
//2、接步骤1,再关闭,再开发蓝牙,连接成功,但是不会触发蓝牙连接
onBLEConnectionStateChange();
vm.$u.vuex('bluetoothContent', '正在搜索蓝牙设备');
vm.$u.vuex("isBluetoothDiscovery", true);
vm.$u.vuex("bluetoothDevice", {}); //清空
//如果60s都还未搜索到蓝牙,提示未搜索到,提示蓝牙不在可搜索范围内,
let timer = setTimeout(() => {
clearTimeout(timer);
//没有找到设备并且定时器还在
if (vm.validatenull(vm.bluetoothDevice)) {
util.showModal('蓝牙不在可搜索范围内');
stopBluetoothDevicesDiscovery();
}
}, 10000);
vm.$u.vuex('blueToothSearchTimer', timer);
uni.startBluetoothDevicesDiscovery({
services: [], //添加了SERVICEID搜索不到蓝牙
allowDuplicatesKey: true,
powerLevel: 'high',
success() {
console.log("开始蓝牙搜索成功");
},
fail(res) {
console.log(res);
util.showModal('开始蓝牙搜索失败');
console.log("开始蓝牙搜索失败:", BLUETOOTH_MESSAGE[res.errCode]);
}
})
}
export let stopBluetoothDevicesDiscovery = () => {
uni.stopBluetoothDevicesDiscovery({
success() {
console.log("停止蓝牙搜索成功");
},
fail(res) {
console.log("停止蓝牙搜索失败:", BLUETOOTH_MESSAGE[res.errCode]);
},
complete() {
vm.$u.vuex("isNormalDiscoveryStatus", true);
setTimeout(()=>{
vm.$u.vuex("isNormalDiscoveryStatus", false);
},1000)
}
})
}
//监听寻找到新设备的事件
export let onBluetoothDeviceFound = () => {
uni.onBluetoothDeviceFound((res) => {
//搜索到的蓝牙设备并唯一
let devices = filterDevices(res.devices, vm.currentBike);
if (devices.length) {
console.log("搜索到的目标设备", devices)
vm.$u.vuex('bluetoothDevice', devices[0])
clearTimeout(vm.blueToothSearchTimer);
vm.$u.vuex('connectCount', 0)
createBLEConnection(devices[0]);
stopBluetoothDevicesDiscovery();
}
})
}
export let getBluetoothAdapterState = () => {
uni.getBluetoothAdapterState({
success(res) {
bluetoothExecByAdapterStatus(res);
},
fail(res) {
console.log("获取蓝牙适配器状态失败:", BLUETOOTH_MESSAGE[res.errCode]);
openAndOnBluetoothAdapter();
util.showModal('蓝牙适配器不可用,请打开蓝牙');
}
})
}
//ios必须要执行
let getBLEDeviceServices = (device) => {
uni.getBLEDeviceServices({
deviceId: device.deviceId,
success(res) {
console.log(`获取${device.deviceId}服务成功`, res);
getBLEDeviceCharacteristics(device);
},
fail(res) {
console.log(`获取${device.deviceId}服务失败:`, BLUETOOTH_MESSAGE[res.errCode]);
getBLEDeviceCharacteristics(device);
}
})
}
export let createBLEConnection = (device) => {
console.log("正在连接蓝牙")
vm.$u.vuex('bluetoothContent', '正在连接蓝牙设备');
//如果当前状态没有连接,只去连接蓝牙
if (!vm.isConnected && !vm.validatenull(vm.bluetoothDevice)) {
uni.createBLEConnection({
deviceId: device.deviceId,
success(res) {
console.log(`与蓝牙设备${device.name}创建连接成功`, res);
getBLEDeviceServices(device);
createBLEConnectioSuccessCallback();
},
fail(res) {
console.log(res)
if(res.errCode == 10001) return;//如果是蓝牙设配器没有打开,则直接退出连接
if (vm.connectCount < 4) {
createBLEConnection(device);
let connectCount = vm.connectCount;
let newConnectCount = connectCount + 1;
vm.$u.vuex('connectCount', newConnectCount);
} else {
util.showModal('蓝牙连接失败');
}
}
})
}
}
//ios必须要执行
let getBLEDeviceCharacteristics = (device) => {
uni.getBLEDeviceCharacteristics({
deviceId: device.deviceId,
serviceId: SERVICEID,
success: function(res) {
console.log(`获取${device.deviceId}特征值成功`, res);
notifyAndOnBLECharacteristicValueChange(device);
},
fail: function(res) {
console.log(`获取${device.deviceId}特征值失败`, res);
},
})
}
export let onBLEConnectionStateChange = () => {
uni.onBLEConnectionStateChange((res) => {
console.log("监听蓝牙是否断开", res);
if(vm.lastConnectionStatus == res.connected){
let bluetoothDisconnectedCount = vm.bluetoothDisconnectedCount;
let newBluetoothDisconnectedCount = bluetoothDisconnectedCount+1;
vm.$u.vuex("bluetoothDisconnectedCount",newBluetoothDisconnectedCount);
}else{
vm.$u.vuex("bluetoothDisconnectedCount",0);
}
vm.$u.vuex("isConnected", res.connected);
if (!res.connected && !vm.isNormalBluetoothDisconnect && vm.bluetoothDisconnectedCount < 2) { //当前检测到时异常断开状态,则进行重连操作,连接不上,还是会触发这个监听
vm.$u.vuex('connectCount', 0);
createBLEConnection(vm.bluetoothDevice);
}
vm.$u.vuex("lastConnectionStatus", res.connected);
onBLEConnectionStateChangeCallback(res);
})
}
//开始并且监听特征值的变化
export let notifyAndOnBLECharacteristicValueChange = (device) => {
//防止没有更换状态
uni.notifyBLECharacteristicValueChange({
state: true,
deviceId: device.deviceId,
serviceId: SERVICEID,
characteristicId: NOTIFYID,
success(res) {
console.log("开启notify通知模式成功", res);
uni.onBLECharacteristicValueChange((res) => {
console.log("监听特征值", res);
clearTimeout(vm.notifyTimerId);
//关闭蓝牙连接
onBLECharacteristicValueChangeCallback(device, res);
})
},
fail(res) {
notifyBLECharacteristicValueChangeFailCallback(device, res);
console.log("开启notify通知模式失败:", BLUETOOTH_MESSAGE[res.errCode]);
}
})
}
let writeBLECharacteristicValue = (device, value) => {
console.log("写入数据", arrayBufferToHexString(value));
uni.writeBLECharacteristicValue({
deviceId: device.deviceId,
serviceId: SERVICEID,
characteristicId: WRITEID,
value,
success(res) {
console.log("写入数据成功", res);
//判断是否是最后一包,如果是最后一包,则开启通讯计时器
},
fail(res) {
console.log("写入数据失败", BLUETOOTH_MESSAGE[res.errCode]);
console.log("写入数据失败", res);
util.showModal("写入数据失败");
}
})
}
export let closeBLEConnection = (device, callback = () => {}) => {
vm.$u.vuex("isNormalBluetoothDisconnect", true);
uni.closeBLEConnection({
deviceId: device.deviceId,
success() {
console.log("关闭蓝牙连接成功");
},
fail(res) {
console.log("关闭蓝牙连接失败", res);
console.log("关闭蓝牙连接失败", BLUETOOTH_MESSAGE[res.errCode]);
},
complete() {
setTimeout(() => {
vm.$u.vuex("isNormalBluetoothDisconnect", false);
}, 1000)
callback();
}
})
}
export let closeBluetoothAdapter = (callback) => {
return new Promise((resolve, reject) => {
uni.closeBluetoothAdapter({
success() {
console.log("关闭蓝牙适配器成功");
},
fail(res) {
console.log("关闭蓝牙适配器失败:", BLUETOOTH_MESSAGE[res.errCode]);
},
complete() {
callback();
}
})
})
}
//不分包写数据
export let writeDataToDevice = (device, data) => {
console.log("发送数据", data);
vm.$u.vuex("bluetoothContent", "正在发送指令");
let allBuffer = hexStringToArrayBuffer(data);
writeBLECharacteristicValue(device, allBuffer);
}
//分包写数据
export let writeDataToDeviceBySubPackage = (data) => {
vm.$u.vuex("commandMessage", '');
vm.$u.vuex("bluetoothContent", `正在发送${vm.commandName}指令`);
let bufferArray = getBufferArrayBy20(data);
console.log('bufferArray.length', bufferArray.length);
for (let i = 0; i < bufferArray.length; i++) {
//sleep(1); //同步延迟1ms
writeBLECharacteristicValue(bufferArray[i], i == bufferArray.length - 1);
}
// let allBuffer = hexStringToArrayBuffer(data);
// writeBLECharacteristicValue(allBuffer);
}
export let getConnectedBluetoothDevices = (callback) => {
uni.getConnectedBluetoothDevices({
services: [SERVICEID],
success(res) {
console.log("获取连接的蓝牙设备成功", res);
callback(res.devices)
},
fail(res) {
console.log("获取连接的蓝牙设备失败", res);
callback([]);
},
complete() {
}
})
}
文章来源:https://www.toymoban.com/news/detail-530450.html
到了这里,关于微信小程序蓝牙流程及代码的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!