123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250 |
- import * as tools from "./tools"
- import {inArray, isObject, logs, sleep} from "../util";
- import {showToast} from "../app";
- import {checkBleAuth} from "../uniFunction";
- import {ab2hex, stringToArrayBuffer} from "./hex";
- import {isH5} from "@/utils/platform";
- import Vue from "vue";
- /**
- * 蓝牙工具类
- * 封装小程序蓝牙流程方法
- * 处理事件通信
- */
- export class bleBase {
- constructor(topClass) {
- this.topClass = topClass
- this.typeKey = ''
- this.option = {}
- this.deviceId = null
- this.serviceId = null
- this.writeId = null // 写入id
- this.characteristicId = null// 接收id
- }
- /**
- * 搜索蓝牙设备
- * @param data
- * @param op
- * @param showLoad
- * @returns {Promise<unknown>}
- */
- getList(data = {}, op = {}, showLoad = true) {
- let option = {
- second: 5000,
- type: 1,
- fun: null,
- }
- option = Object.assign(option, op)
- return new Promise(async (resolve, reject) => {
- logs('进入 searchBle')
- try {
- await this.topClass.init()
- if (isH5) throw 'H5不支持蓝牙功能'
- await checkBleAuth() // 检查用户蓝牙授权是否通过
- if (showLoad) uni.showLoading({title: '搜索设备中。。。'})
- await tools._startSearch(Object.assign({
- allowDuplicatesKey: true
- }, data))
- let list = await this.bluetoothDeviceFound(option.second, option.type, option.fun)
- if (showLoad) uni.hideLoading()
- resolve(Object.values(list))
- } catch (msg) {
- if (showLoad) uni.hideLoading()
- showToast(msg, 4000)
- resolve(new Object())
- }
- })
- }
- /**
- * 过滤并转换附加参数 ok 表示 是否通过过滤
- * @param item
- * @returns item
- */
- filter(item) {
- item.ok = false
- if (this.option.top) {
- let index = item.manufacturerData.search(this.option.top)
- if (this.option.indexJudge) item.ok = this.option.indexJudge(index)
- } else {
- item.ok = true
- }
- if (item.ok && this.option.macSlice) item.mac = item.manufacturerData.slice(...this.option.macSlice)
- if (this.option.search && !inArray(item.mac, this.option.machine)) item.ok = !1
- return item
- }
- /**
- * 过滤设备信息
- * @param second
- * @param type 1 普通模式(只过滤是否符合);
- * 2 指定模式(只有找到一个就会结束,但因为搜索未完全结束可能会返回多个的情况)
- * 3 无限模式
- * @param fun
- * @returns {Promise<unknown>}
- */
- bluetoothDeviceFound(second = 5000, type = 1, fun = null) {
- let list = {}
- return new Promise(async (resolve, reject) => {
- try {
- this.topClass.bleDeviceFound((res) => {
- res.devices.forEach((item) => {
- item.manufacturerData = ab2hex(item.advertisData)
- item = this.filter(item)
- if (item.ok) {
- list[item.deviceId] = item
- if (type == 2) {
- tools._stopSearchBluetooth();
- throw '已找到设备'
- } else if (type == 3 && fun) {
- fun({
- run: true,
- data: item,
- })
- }
- }
- })
- })
- if (second > 0) {
- await sleep(second)
- throw '搜索结束'
- }
- } catch (error) {
- if (type != 3) {
- await tools._stopSearchBluetooth();
- } else if (type == 3 && fun) {
- fun({
- run: false,
- })
- }
- this.topClass.bleDeviceFound(null)
- return resolve(Object.values(list))
- }
- })
- }
- async startSearch(data) {
- await tools._startSearch(Object.assign({
- allowDuplicatesKey: true
- }, data))
- }
- stopSearch() {
- /* #ifndef H5 */
- tools._stopSearchBluetooth();
- /* #endif */
- }
- // 二、 蓝牙连接 根据某一id连接设备,4.0
- async connectionBle(deviceId) {
- try {
- if (isH5) throw 'H5无法运行'
- if (this.deviceId && this.deviceId == deviceId) {
- logs('同一台设备,跳出')
- return Promise.resolve() // 已连接设备与当前为同一台
- }
- if (this.deviceId && this.deviceId != deviceId) {
- logs('有旧设备,关闭旧设备中')
- await this.closeConnection() // 结束前一台
- await sleep(500)
- }
- this.topClass.addConnect(deviceId, this.typeKey)
- this.deviceId = deviceId
- logs('connectBle --- ' + this.deviceId)
- await tools._connectBlue(this.deviceId)
- await sleep(2000);
- await this.getBLEServices(this.option.serviceKey)
- await this.getCharacteristics(this.option.channelKey)
- await tools._notifyBLECharacteristicValueChange(this.deviceId, this.serviceId, this.characteristicId)
- return Promise.resolve()
- } catch (e) {
- await this.closeConnection()
- console.log('connectionBle catch', e)
- return Promise.reject('连接失败')
- }
- }
- async getBLEServices(serviceKey) {
- logs('开始蓝牙获取服务')
- let servicesList = await tools._getBLEServices(this.deviceId)
- if (!servicesList) throw '链接失败,蓝牙未找到服务号'
- logs('开始蓝牙获取服务', servicesList)
- for (let i = 0; i < servicesList.services.length; i++) {
- if (servicesList.services[i].isPrimary && (servicesList.services[i].uuid.indexOf(serviceKey) != -1)) {
- this.serviceId = servicesList.services[i].uuid
- return;
- }
- }
- }
- async getCharacteristics(channelKey = '') {
- logs('开始蓝牙通道信息')
- // 获取通道信息(读、写、监听)
- let writeKey = ''
- let notifyKey = ''
- if (isObject(channelKey)) {
- writeKey = channelKey.writeKey
- notifyKey = channelKey.notifyKey
- } else {
- writeKey = notifyKey = channelKey
- }
- let {characteristics} = await tools._getCharacteristics(this.deviceId, this.serviceId)
- logs(`开始蓝牙通道信息 writeKey:${writeKey} notifyKey:${notifyKey} characteristics:${characteristics}`)
- for (let i = 0; i < characteristics.length; i++) {
- let item = characteristics[i];
- if (item.uuid.search(writeKey) != -1) {
- this.writeId = item.uuid // 写入id
- }
- if (item.uuid.search(notifyKey) != -1) {
- this.characteristicId = item.uuid // 写入id
- }
- }
- logs(`开始蓝牙通道信息 writeId:${this.writeId} characteristicId:${this.characteristicId}`)
- }
- /**
- * 关闭设备连接
- * @param deviceId
- * @returns {Promise<void>}
- */
- async closeConnection(deviceId = '') {
- if (!deviceId) deviceId = this.deviceId
- // 断开已连接的连接
- try {
- if (this.deviceId) await tools._closeBLEConnection(deviceId);
- } catch (e) {
- }
- this.deviceId = null
- this.serviceId = null
- this.writeId = null
- this.characteristicId = null
- this.topClass.delConnect(deviceId)
- }
- async sentOrder(str, type = 1) {
- let buffer = type != 0 ? stringToArrayBuffer(str, type) : str
- logs("-- 发送数据: ", ab2hex(buffer, ' '))
- try {
- /* #ifndef H5 */
- if (this.deviceId) await tools._writeBLECharacteristicValue(this.deviceId, this.serviceId, this.writeId, buffer)
- /* #endif */
- return true
- } catch (error) {
- if (error.errCode == 10006) {
- this.topClass.delConnect(this.deviceId, this.typeKey)
- }
- console.error(error)
- logs(`发送出错 基本信息 deviceId:${this.deviceId}, serviceId:${this.serviceId}, writeId:${this.writeId}`)
- logs(error)
- }
- }
- }
|