蓝牙连接demo
This commit is contained in:
parent
dfc0ce357a
commit
4af6b033d1
Binary file not shown.
Binary file not shown.
|
|
@ -0,0 +1,8 @@
|
||||||
|
# #参考使用设备类型
|
||||||
|
```
|
||||||
|
F01PRO
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
##
|
||||||
|
|
||||||
|
|
@ -0,0 +1,5 @@
|
||||||
|
//app.js
|
||||||
|
App({
|
||||||
|
onLaunch: function () {
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
"pages": [
|
||||||
|
"pages/index/index"
|
||||||
|
],
|
||||||
|
"window": {
|
||||||
|
"navigationBarBackgroundColor": "#0082FE",
|
||||||
|
"navigationBarTextStyle": "white",
|
||||||
|
"navigationBarTitleText": "蓝牙连接Demo",
|
||||||
|
"backgroundColor": "#eeeeee",
|
||||||
|
"backgroundTextStyle": "light"
|
||||||
|
},
|
||||||
|
"plugins": {
|
||||||
|
"sdkPlugin": {
|
||||||
|
"version": "2.1.0",
|
||||||
|
"provider": "wx17e93aad47cdae1a"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"style": "v2",
|
||||||
|
"sitemapLocation": "sitemap.json"
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,55 @@
|
||||||
|
/**app.wxss**/
|
||||||
|
view,
|
||||||
|
cover-view,
|
||||||
|
scroll-view,
|
||||||
|
swiper,
|
||||||
|
swiper-item,
|
||||||
|
movable-area,
|
||||||
|
movable-view,
|
||||||
|
button,
|
||||||
|
input,
|
||||||
|
textarea,
|
||||||
|
label,
|
||||||
|
navigator {
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
page {
|
||||||
|
--safe-bottom: env(safe-area-inset-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container {
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
width: 100vw;
|
||||||
|
height: 100vh;
|
||||||
|
padding-bottom: var(--safe-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header button {
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 40px;
|
||||||
|
width: 100% !important;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.device_item {
|
||||||
|
padding: 15px;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.weight {
|
||||||
|
width: 100%;
|
||||||
|
margin: 15px;
|
||||||
|
padding-bottom: 15px;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: 700;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,322 @@
|
||||||
|
const util = require("../../utils/util");
|
||||||
|
const {
|
||||||
|
inArray,
|
||||||
|
ab2hex
|
||||||
|
} = util
|
||||||
|
const plugin = requirePlugin("sdkPlugin").AiLink;
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
devices: [],
|
||||||
|
connected: false,
|
||||||
|
cmd: '',
|
||||||
|
name: '',
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
text: "",
|
||||||
|
imp: "",
|
||||||
|
uuid1: "",
|
||||||
|
uuid2: "",
|
||||||
|
uuid3: "",
|
||||||
|
deviceId: null,
|
||||||
|
},
|
||||||
|
onLoad: function() {},
|
||||||
|
// 初始化蓝牙模块
|
||||||
|
openBluetoothAdapter() {
|
||||||
|
wx.openBluetoothAdapter({
|
||||||
|
success: (res) => {
|
||||||
|
console.log('openBluetoothAdapter success', res)
|
||||||
|
wx.showToast({
|
||||||
|
title: '蓝牙连接中',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
fail: (res) => {
|
||||||
|
if (res.errCode === 10001) {
|
||||||
|
wx.showToast({
|
||||||
|
title: '请打开蓝牙',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
// 监听本机蓝牙状态变化的事件
|
||||||
|
wx.onBluetoothAdapterStateChange((res) => {
|
||||||
|
console.log('onBluetoothAdapterStateChange', res)
|
||||||
|
if (res.available) {
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 开始搜寻附近的蓝牙外围设备
|
||||||
|
startBluetoothDevicesDiscovery() {
|
||||||
|
if (this._discoveryStarted) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
this._discoveryStarted = true
|
||||||
|
wx.startBluetoothDevicesDiscovery({
|
||||||
|
allowDuplicatesKey: true,
|
||||||
|
interval: 1000, //上报设备的间隔
|
||||||
|
services: [
|
||||||
|
"FFE0",
|
||||||
|
],
|
||||||
|
success: (res) => {
|
||||||
|
console.log('startBluetoothDevicesDiscovery success', res)
|
||||||
|
this.onBluetoothDeviceFound()
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 停止搜寻附近的蓝牙外围设备
|
||||||
|
stopBluetoothDevicesDiscovery() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
|
||||||
|
// 找到新设备的事件
|
||||||
|
onBluetoothDeviceFound() {
|
||||||
|
wx.onBluetoothDeviceFound((res) => {
|
||||||
|
res.devices.forEach(device => {
|
||||||
|
if (!device.name && !device.localName) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if (device.name.indexOf('AiLink_') != -1) {
|
||||||
|
wx.stopBluetoothDevicesDiscovery() //搜索到名称为“AiLink_”的蓝牙后,停止搜寻附近的蓝牙
|
||||||
|
const foundDevices = this.data.devices
|
||||||
|
const idx = inArray(foundDevices, 'deviceId', device.deviceId)
|
||||||
|
const data = {}
|
||||||
|
let buff = device.advertisData.slice(-6)
|
||||||
|
device.mac = new Uint8Array(buff) // 保存广播数据中的mac地址,这是由于iOS不直接返回mac地址
|
||||||
|
let tempMac = Array.from(device.mac)
|
||||||
|
tempMac.reverse()
|
||||||
|
device.macAddr = ab2hex(tempMac, ':').toUpperCase()
|
||||||
|
if (idx === -1) {
|
||||||
|
data[`devices[${foundDevices.length}]`] = device
|
||||||
|
} else {
|
||||||
|
data[`devices[${idx}]`] = device
|
||||||
|
}
|
||||||
|
this.setData(data)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 连接低功耗蓝牙设备
|
||||||
|
createBLEConnection(e) {
|
||||||
|
wx.showLoading({
|
||||||
|
title: '连接中',
|
||||||
|
})
|
||||||
|
const ds = e.currentTarget.dataset
|
||||||
|
const index = ds.index
|
||||||
|
this._device = this.data.devices[index]
|
||||||
|
const deviceId = ds.deviceId
|
||||||
|
const name = ds.name
|
||||||
|
this.mac = ds.mac
|
||||||
|
wx.createBLEConnection({
|
||||||
|
deviceId,
|
||||||
|
success: (res) => {
|
||||||
|
this.setData({
|
||||||
|
connected: true,
|
||||||
|
name,
|
||||||
|
deviceId,
|
||||||
|
})
|
||||||
|
console.log("createBLEConnection:success")
|
||||||
|
this.onBLEConnectionStateChange()
|
||||||
|
this.getBLEDeviceServices(deviceId)
|
||||||
|
},
|
||||||
|
fail: res => {
|
||||||
|
wx.hideLoading()
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接失败',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
//监听蓝牙连接状态
|
||||||
|
onBLEConnectionStateChange() {
|
||||||
|
wx.onBLEConnectionStateChange((res) => {
|
||||||
|
if (!res.connected) {
|
||||||
|
setTimeout(() => {
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接已断开',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}, 500)
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
text: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 获取蓝牙设备的 serviceId
|
||||||
|
getBLEDeviceServices(deviceId) {
|
||||||
|
wx.getBLEDeviceServices({
|
||||||
|
deviceId,
|
||||||
|
success: (res) => {
|
||||||
|
for (let i = 0; i < res.services.length; i++) {
|
||||||
|
if (res.services[i].isPrimary && res.services[i].uuid.indexOf('FFE0') > -1) {
|
||||||
|
wx.showLoading({
|
||||||
|
title: '获取设备的UUID成功',
|
||||||
|
})
|
||||||
|
this.getBLEDeviceCharacteristics(deviceId, res.services[i].uuid)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 获取蓝牙设备某个服务中所有特征值(characteristic)
|
||||||
|
/**
|
||||||
|
* read: true读,write: true写,notify: true广播
|
||||||
|
*/
|
||||||
|
getBLEDeviceCharacteristics(deviceId, serviceId) {
|
||||||
|
let that = this
|
||||||
|
that._deviceId = deviceId
|
||||||
|
that._serviceId = serviceId
|
||||||
|
that._device.serviceId = serviceId
|
||||||
|
wx.hideLoading()
|
||||||
|
wx.getBLEDeviceCharacteristics({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
success: (res) => {
|
||||||
|
console.log('getBLEDeviceCharacteristics success', res.characteristics)
|
||||||
|
for (let i = 0; i < res.characteristics.length; i++) {
|
||||||
|
let item = res.characteristics[i];
|
||||||
|
if (item.uuid.indexOf('0000FFE1') != -1) {
|
||||||
|
that.data.uuid1 = item.uuid //下发数据
|
||||||
|
} else if (item.uuid.indexOf('0000FFE2') != -1) {
|
||||||
|
that.data.uuid2 = item.uuid //监听数据
|
||||||
|
} else if (item.uuid.indexOf('0000FFE3') != -1) {
|
||||||
|
that.data.uuid3 = item.uuid //写入设置
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 打开监听
|
||||||
|
wx.notifyBLECharacteristicValueChange({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
characteristicId: that.data.uuid2,
|
||||||
|
state: true,
|
||||||
|
})
|
||||||
|
wx.notifyBLECharacteristicValueChange({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
characteristicId: that.data.uuid3,
|
||||||
|
state: true,
|
||||||
|
})
|
||||||
|
// 初始化插件
|
||||||
|
plugin.initPlugin(res.characteristics, that._device)
|
||||||
|
|
||||||
|
wx.onBLECharacteristicValueChange((characteristic) => {
|
||||||
|
let bleData = plugin.parseBleData(characteristic.value)
|
||||||
|
let dw1 = "kg"
|
||||||
|
if (bleData.status == 0) {
|
||||||
|
// 发送 男,22岁,185
|
||||||
|
let A = 22
|
||||||
|
let H = 185
|
||||||
|
let sex = "0x01"
|
||||||
|
let age = "0x" + A.toString(16)
|
||||||
|
let height = "0x" + H.toString(16)
|
||||||
|
let arr = [0x01, parseInt(sex), parseInt(age), parseInt(height),0x00]
|
||||||
|
plugin.sendDataOfA7(arr)
|
||||||
|
console.log("握手成功", arr)
|
||||||
|
} else if (bleData.status == 1) {
|
||||||
|
let payload = ab2hex(bleData.data, '')
|
||||||
|
let type = payload.substring(0, 2)
|
||||||
|
let typeInfo = payload.substring(4, 6)
|
||||||
|
console.log("payload", payload)
|
||||||
|
if (type == "10" || type == "40") { //体脂模式
|
||||||
|
let data = parseInt(payload.substring(6, 12), 16)
|
||||||
|
let num = payload.substring(12, 13)
|
||||||
|
let dw = payload.substring(13, 14)
|
||||||
|
if (dw == "1") {
|
||||||
|
dw1 = "斤"
|
||||||
|
}
|
||||||
|
if (num == "1") {
|
||||||
|
data = data / 10
|
||||||
|
}
|
||||||
|
if (num == "2") {
|
||||||
|
data = data / 100
|
||||||
|
}
|
||||||
|
if (num == "3") {
|
||||||
|
data = data / 1000
|
||||||
|
}
|
||||||
|
if (typeInfo == "01") {
|
||||||
|
that.setData({
|
||||||
|
weight: "实时体重是:" + data + dw1
|
||||||
|
})
|
||||||
|
}
|
||||||
|
if (typeInfo == "02") {
|
||||||
|
that.setData({
|
||||||
|
weight: "稳定体重是:" + data + dw1
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (type == "14" || type == "41") { //身高模式
|
||||||
|
let height = parseInt(payload.substring(4, 8), 16)
|
||||||
|
that.setData({
|
||||||
|
height: "身高是:" + height
|
||||||
|
})
|
||||||
|
}
|
||||||
|
if (type == "11") { //阻抗模式
|
||||||
|
if (typeInfo == "03" || typeInfo == "04") {
|
||||||
|
let imp = parseInt(payload.substring(8, 12), 16)
|
||||||
|
console.log("imp", payload, imp)
|
||||||
|
that.setData({
|
||||||
|
imp: "阻抗值:" + imp
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
fail(res) {
|
||||||
|
console.error('getBLEDeviceCharacteristics', res)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 断开蓝牙模块
|
||||||
|
*/
|
||||||
|
closeBluetoothAdapter() {
|
||||||
|
wx.closeBluetoothAdapter()
|
||||||
|
this._discoveryStarted = false
|
||||||
|
wx.showToast({
|
||||||
|
title: '断开蓝牙模块',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
text: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 断开与低功耗蓝牙设备的连接
|
||||||
|
closeBLEConnection() {
|
||||||
|
wx.closeBLEConnection({
|
||||||
|
deviceId: this._deviceId
|
||||||
|
})
|
||||||
|
wx.showToast({
|
||||||
|
title: '断开蓝牙连接',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
text: "",
|
||||||
|
height: "",
|
||||||
|
weight: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
});
|
||||||
|
|
@ -0,0 +1,4 @@
|
||||||
|
{
|
||||||
|
"usingComponents": {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,37 @@
|
||||||
|
<wxs module="utils">
|
||||||
|
module.exports.max = function(n1, n2) {
|
||||||
|
return Math.max(n1, n2)
|
||||||
|
}
|
||||||
|
module.exports.len = function(arr) {
|
||||||
|
arr = arr || []
|
||||||
|
return arr.length
|
||||||
|
}
|
||||||
|
</wxs>
|
||||||
|
|
||||||
|
<view class="container">
|
||||||
|
<view class="header">
|
||||||
|
<button bindtap="openBluetoothAdapter">开始扫描</button>
|
||||||
|
<button bindtap="stopBluetoothDevicesDiscovery">停止扫描</button>
|
||||||
|
<button bindtap="closeBluetoothAdapter">结束流程</button>
|
||||||
|
</view>
|
||||||
|
<view class="weight">
|
||||||
|
<view>{{weight}}</view>
|
||||||
|
<view>{{height}}</view>
|
||||||
|
<view>{{imp}}</view>
|
||||||
|
<view>{{text}}</view>
|
||||||
|
</view>
|
||||||
|
<view class="devices_summary">已发现 {{devices.length}} 个外围设备:</view>
|
||||||
|
<scroll-view class="device_list" scroll-y scroll-with-animation>
|
||||||
|
<view wx:for="{{devices}}" wx:key="index" data-device-id="{{item.deviceId}}"
|
||||||
|
data-name="{{item.name || item.localName}}" data-mac="{{item.mac}}" data-index="{{index}}"
|
||||||
|
bindtap="createBLEConnection" class="device_item" hover-class="device_item_hover">
|
||||||
|
<view style="font-size: 32rpx;">
|
||||||
|
<text style="color:#000;font-weight:bold">{{item.name}}</text>
|
||||||
|
<text style="font-size:26rpx">(信号强度: {{item.RSSI}}dBm)</text>
|
||||||
|
</view>
|
||||||
|
<view style="font-size: 26rpx">mac地址: {{item.macAddr || item.deviceId}}</view>
|
||||||
|
<!-- <view style="font-size: 26rpx">广播数据:{{item.analyzeDataText}}</view> -->
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
</view>
|
||||||
|
|
@ -0,0 +1,52 @@
|
||||||
|
{
|
||||||
|
"description": "项目配置文件,详见文档:https://developers.weixin.qq.com/miniprogram/dev/devtools/projectconfig.html",
|
||||||
|
"setting": {
|
||||||
|
"urlCheck": true,
|
||||||
|
"es6": false,
|
||||||
|
"enhance": true,
|
||||||
|
"postcss": true,
|
||||||
|
"preloadBackgroundData": false,
|
||||||
|
"minified": true,
|
||||||
|
"newFeature": false,
|
||||||
|
"coverView": true,
|
||||||
|
"nodeModules": false,
|
||||||
|
"autoAudits": false,
|
||||||
|
"showShadowRootInWxmlPanel": true,
|
||||||
|
"scopeDataCheck": false,
|
||||||
|
"uglifyFileName": false,
|
||||||
|
"checkInvalidKey": true,
|
||||||
|
"checkSiteMap": true,
|
||||||
|
"uploadWithSourceMap": true,
|
||||||
|
"compileHotReLoad": false,
|
||||||
|
"lazyloadPlaceholderEnable": false,
|
||||||
|
"useMultiFrameRuntime": true,
|
||||||
|
"useApiHook": true,
|
||||||
|
"useApiHostProcess": true,
|
||||||
|
"babelSetting": {
|
||||||
|
"ignore": [],
|
||||||
|
"disablePlugins": [],
|
||||||
|
"outputPath": ""
|
||||||
|
},
|
||||||
|
"useIsolateContext": true,
|
||||||
|
"userConfirmedBundleSwitch": false,
|
||||||
|
"packNpmManually": false,
|
||||||
|
"packNpmRelationList": [],
|
||||||
|
"minifyWXSS": true,
|
||||||
|
"disableUseStrict": false,
|
||||||
|
"minifyWXML": true,
|
||||||
|
"showES6CompileOption": false,
|
||||||
|
"useCompilerPlugins": false,
|
||||||
|
"ignoreUploadUnusedFiles": true
|
||||||
|
},
|
||||||
|
"compileType": "miniprogram",
|
||||||
|
"simulatorType": "wechat",
|
||||||
|
"simulatorPluginLibVersion": {},
|
||||||
|
"projectname": "bluetooth_demo_F01",
|
||||||
|
"libVersion": "2.23.2",
|
||||||
|
"appid": "wx39cf431caa22b5c8",
|
||||||
|
"editorSetting": {
|
||||||
|
"tabIndent": "insertSpaces",
|
||||||
|
"tabSize": 2
|
||||||
|
},
|
||||||
|
"condition": {}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
{
|
||||||
|
"desc": "关于本文件的更多信息,请参考文档 https://developers.weixin.qq.com/miniprogram/dev/framework/sitemap.html",
|
||||||
|
"rules": [{
|
||||||
|
"action": "allow",
|
||||||
|
"page": "*"
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
function inArray(arr, key, val) {
|
||||||
|
if (!arr || !arr.length || typeof arr != 'object' || !Array.isArray(arr)) {
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
for (let i = 0; i < arr.length; i++) {
|
||||||
|
if (!key) {
|
||||||
|
if (arr[i] == val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
} else if (arr[i][key] === val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ArrayBuffer转16进度字符串示例
|
||||||
|
function ab2hex(buffer, split) {
|
||||||
|
var hexArr = Array.prototype.map.call(
|
||||||
|
new Uint8Array(buffer),
|
||||||
|
function(bit) {
|
||||||
|
return ('00' + bit.toString(16)).slice(-2)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
return hexArr.join(split);
|
||||||
|
}
|
||||||
|
module.exports = {
|
||||||
|
inArray,
|
||||||
|
ab2hex,
|
||||||
|
}
|
||||||
Binary file not shown.
|
|
@ -0,0 +1,8 @@
|
||||||
|
# #参考使用设备类型
|
||||||
|
```
|
||||||
|
H01PRO
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
##
|
||||||
|
|
||||||
|
|
@ -0,0 +1,5 @@
|
||||||
|
//app.js
|
||||||
|
App({
|
||||||
|
onLaunch: function () {
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
"pages": [
|
||||||
|
"pages/index/index"
|
||||||
|
],
|
||||||
|
"window": {
|
||||||
|
"navigationBarBackgroundColor": "#0082FE",
|
||||||
|
"navigationBarTextStyle": "white",
|
||||||
|
"navigationBarTitleText": "蓝牙连接Demo",
|
||||||
|
"backgroundColor": "#eeeeee",
|
||||||
|
"backgroundTextStyle": "light"
|
||||||
|
},
|
||||||
|
"plugins": {
|
||||||
|
"sdkPlugin": {
|
||||||
|
"version": "2.1.0",
|
||||||
|
"provider": "wx17e93aad47cdae1a"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"style": "v2",
|
||||||
|
"sitemapLocation": "sitemap.json"
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,55 @@
|
||||||
|
/**app.wxss**/
|
||||||
|
view,
|
||||||
|
cover-view,
|
||||||
|
scroll-view,
|
||||||
|
swiper,
|
||||||
|
swiper-item,
|
||||||
|
movable-area,
|
||||||
|
movable-view,
|
||||||
|
button,
|
||||||
|
input,
|
||||||
|
textarea,
|
||||||
|
label,
|
||||||
|
navigator {
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
page {
|
||||||
|
--safe-bottom: env(safe-area-inset-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container {
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
width: 100vw;
|
||||||
|
height: 100vh;
|
||||||
|
padding-bottom: var(--safe-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header button {
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 40px;
|
||||||
|
width: 100% !important;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.device_item {
|
||||||
|
padding: 15px;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.weight {
|
||||||
|
width: 100%;
|
||||||
|
margin: 15px;
|
||||||
|
padding-bottom: 15px;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: 700;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,275 @@
|
||||||
|
const util = require("../../utils/util");
|
||||||
|
const {
|
||||||
|
inArray,
|
||||||
|
ab2hex
|
||||||
|
} = util
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
devices: [],
|
||||||
|
connected: false,
|
||||||
|
text: '',
|
||||||
|
name: '',
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
imp: "",
|
||||||
|
readId: "",
|
||||||
|
writeId: "",
|
||||||
|
notifyId: "",
|
||||||
|
deviceId: null,
|
||||||
|
},
|
||||||
|
onLoad: function() {},
|
||||||
|
// 初始化蓝牙模块
|
||||||
|
openBluetoothAdapter() {
|
||||||
|
wx.openBluetoothAdapter({
|
||||||
|
success: (res) => {
|
||||||
|
console.log('openBluetoothAdapter success', res)
|
||||||
|
wx.showToast({
|
||||||
|
title: '蓝牙连接中',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
fail: (res) => {
|
||||||
|
if (res.errCode === 10001) {
|
||||||
|
wx.showToast({
|
||||||
|
title: '请打开蓝牙',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
// 监听本机蓝牙状态变化的事件
|
||||||
|
wx.onBluetoothAdapterStateChange((res) => {
|
||||||
|
console.log('onBluetoothAdapterStateChange', res)
|
||||||
|
if (res.available) {
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 开始搜寻附近的蓝牙外围设备
|
||||||
|
startBluetoothDevicesDiscovery() {
|
||||||
|
if (this._discoveryStarted) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
this._discoveryStarted = true
|
||||||
|
wx.startBluetoothDevicesDiscovery({
|
||||||
|
allowDuplicatesKey: true,
|
||||||
|
interval: 500, //上报设备的间隔
|
||||||
|
success: (res) => {
|
||||||
|
console.log('startBluetoothDevicesDiscovery success', res)
|
||||||
|
this.onBluetoothDeviceFound()
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 停止搜寻附近的蓝牙外围设备
|
||||||
|
stopBluetoothDevicesDiscovery() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
|
||||||
|
// 找到新设备的事件
|
||||||
|
onBluetoothDeviceFound() {
|
||||||
|
wx.onBluetoothDeviceFound((res) => {
|
||||||
|
res.devices.forEach(device => {
|
||||||
|
if (!device.name && !device.localName) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if (device.name.indexOf('My') != -1) {
|
||||||
|
wx.stopBluetoothDevicesDiscovery() //搜索到名称为“AiLink_”的蓝牙后,停止搜寻附近的蓝牙
|
||||||
|
const foundDevices = this.data.devices
|
||||||
|
const idx = inArray(foundDevices, 'deviceId', device.deviceId)
|
||||||
|
const data = {}
|
||||||
|
let buff = device.advertisData.slice(-6)
|
||||||
|
device.mac = new Uint8Array(buff) // 保存广播数据中的mac地址,这是由于iOS不直接返回mac地址
|
||||||
|
let tempMac = Array.from(device.mac)
|
||||||
|
device.macAddr = ab2hex(tempMac, ':').toUpperCase()
|
||||||
|
if (idx === -1) {
|
||||||
|
data[`devices[${foundDevices.length}]`] = device
|
||||||
|
} else {
|
||||||
|
data[`devices[${idx}]`] = device
|
||||||
|
}
|
||||||
|
this.setData(data)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 连接低功耗蓝牙设备
|
||||||
|
createBLEConnection(e) {
|
||||||
|
wx.showLoading({
|
||||||
|
title: '连接中',
|
||||||
|
})
|
||||||
|
const ds = e.currentTarget.dataset
|
||||||
|
const index = ds.index
|
||||||
|
this._device = this.data.devices[index]
|
||||||
|
const deviceId = ds.deviceId
|
||||||
|
const name = ds.name
|
||||||
|
this.mac = ds.mac
|
||||||
|
wx.createBLEConnection({
|
||||||
|
deviceId,
|
||||||
|
success: (res) => {
|
||||||
|
this.setData({
|
||||||
|
connected: true,
|
||||||
|
name,
|
||||||
|
deviceId,
|
||||||
|
})
|
||||||
|
console.log("createBLEConnection:success")
|
||||||
|
this.onBLEConnectionStateChange()
|
||||||
|
this.getBLEDeviceServices(deviceId)
|
||||||
|
},
|
||||||
|
fail: res => {
|
||||||
|
wx.hideLoading()
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接失败',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
//监听蓝牙连接状态
|
||||||
|
onBLEConnectionStateChange() {
|
||||||
|
wx.onBLEConnectionStateChange((res) => {
|
||||||
|
if (!res.connected) {
|
||||||
|
setTimeout(() => {
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接已断开',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}, 500)
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
text: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 获取蓝牙设备的 serviceId
|
||||||
|
getBLEDeviceServices(deviceId) {
|
||||||
|
wx.getBLEDeviceServices({
|
||||||
|
deviceId,
|
||||||
|
success: (res) => {
|
||||||
|
for (let i = 0; i < res.services.length; i++) {
|
||||||
|
if (res.services[i].uuid.indexOf('FFE0') > -1) {
|
||||||
|
wx.showLoading({
|
||||||
|
title: '获取设备的UUID成功',
|
||||||
|
})
|
||||||
|
this.getBLEDeviceCharacteristics(deviceId, res.services[i].uuid)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 获取蓝牙设备某个服务中所有特征值(characteristic)
|
||||||
|
/**
|
||||||
|
* read: true读,write: true写,notify: true广播
|
||||||
|
*/
|
||||||
|
getBLEDeviceCharacteristics(deviceId, serviceId) {
|
||||||
|
let that = this
|
||||||
|
that._deviceId = deviceId
|
||||||
|
that._serviceId = serviceId
|
||||||
|
that._device.serviceId = serviceId
|
||||||
|
wx.hideLoading()
|
||||||
|
wx.getBLEDeviceCharacteristics({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
success: (res) => {
|
||||||
|
console.log('getBLEDeviceCharacteristics success', res.characteristics)
|
||||||
|
that.setData({
|
||||||
|
text: "请站在秤上,开始测量"
|
||||||
|
})
|
||||||
|
for (let i = 0; i < res.characteristics.length; i++) {
|
||||||
|
let item = res.characteristics[i];
|
||||||
|
if (item.uuid.indexOf("FFE1") != -1) {
|
||||||
|
if (item.properties.notify == true) {
|
||||||
|
that.data.notifyId = item.uuid
|
||||||
|
}
|
||||||
|
if (item.properties.read) {
|
||||||
|
that.data.readId = item.uuid
|
||||||
|
}
|
||||||
|
if (item.properties.write == true) {
|
||||||
|
that.data.writeId = item.uuid
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 打开监听
|
||||||
|
wx.notifyBLECharacteristicValueChange({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
characteristicId: that.data.notifyId,
|
||||||
|
state: true,
|
||||||
|
})
|
||||||
|
wx.notifyBLECharacteristicValueChange({
|
||||||
|
deviceId,
|
||||||
|
serviceId,
|
||||||
|
characteristicId: that.data.writeId,
|
||||||
|
state: true,
|
||||||
|
})
|
||||||
|
|
||||||
|
wx.onBLECharacteristicValueChange((res) => {
|
||||||
|
let value = ab2hex(res.value, '');
|
||||||
|
let weight = parseInt(value.substring(4, 8), 16) / 100
|
||||||
|
let height = parseInt(value.substring(30, 34), 16) / 10
|
||||||
|
let imp0 = value.substring(28, 30) + value.substring(34, 36)
|
||||||
|
that.setData({
|
||||||
|
weight: "您的体重是:" + weight + 'kg'
|
||||||
|
})
|
||||||
|
that.setData({
|
||||||
|
height: "您的身高是:" + height + 'kg'
|
||||||
|
})
|
||||||
|
that.setData({
|
||||||
|
imp: "阻抗:" + parseInt(imp0, 16)
|
||||||
|
})
|
||||||
|
that.setData({
|
||||||
|
text: "测量结束"
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
fail(res) {
|
||||||
|
console.error('getBLEDeviceCharacteristics', res)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 断开蓝牙模块
|
||||||
|
*/
|
||||||
|
closeBluetoothAdapter() {
|
||||||
|
wx.closeBluetoothAdapter()
|
||||||
|
this._discoveryStarted = false
|
||||||
|
wx.showToast({
|
||||||
|
title: '断开蓝牙模块',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
height: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 断开与低功耗蓝牙设备的连接
|
||||||
|
closeBLEConnection() {
|
||||||
|
wx.closeBLEConnection({
|
||||||
|
deviceId: this._deviceId
|
||||||
|
})
|
||||||
|
wx.showToast({
|
||||||
|
title: '断开蓝牙连接',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
height: "",
|
||||||
|
weight: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
});
|
||||||
|
|
@ -0,0 +1,4 @@
|
||||||
|
{
|
||||||
|
"usingComponents": {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,37 @@
|
||||||
|
<wxs module="utils">
|
||||||
|
module.exports.max = function(n1, n2) {
|
||||||
|
return Math.max(n1, n2)
|
||||||
|
}
|
||||||
|
module.exports.len = function(arr) {
|
||||||
|
arr = arr || []
|
||||||
|
return arr.length
|
||||||
|
}
|
||||||
|
</wxs>
|
||||||
|
|
||||||
|
<view class="container">
|
||||||
|
<view class="header">
|
||||||
|
<button bindtap="openBluetoothAdapter">开始扫描</button>
|
||||||
|
<button bindtap="stopBluetoothDevicesDiscovery">停止扫描</button>
|
||||||
|
<button bindtap="closeBluetoothAdapter">结束流程</button>
|
||||||
|
</view>
|
||||||
|
<view class="weight">
|
||||||
|
<view>{{weight}}</view>
|
||||||
|
<view>{{height}}</view>
|
||||||
|
<view>{{imp}}</view>
|
||||||
|
<view>{{text}}</view>
|
||||||
|
</view>
|
||||||
|
<view class="devices_summary">已发现 {{devices.length}} 个外围设备:</view>
|
||||||
|
<scroll-view class="device_list" scroll-y scroll-with-animation>
|
||||||
|
<view wx:for="{{devices}}" wx:key="index" data-device-id="{{item.deviceId}}"
|
||||||
|
data-name="{{item.name || item.localName}}" data-mac="{{item.mac}}" data-index="{{index}}"
|
||||||
|
bindtap="createBLEConnection" class="device_item" hover-class="device_item_hover">
|
||||||
|
<view style="font-size: 32rpx;">
|
||||||
|
<text style="color:#000;font-weight:bold">{{item.name}}</text>
|
||||||
|
<text style="font-size:26rpx">(信号强度: {{item.RSSI}}dBm)</text>
|
||||||
|
</view>
|
||||||
|
<view style="font-size: 26rpx">mac地址: {{item.macAddr || item.deviceId}}</view>
|
||||||
|
<!-- <view style="font-size: 26rpx">广播数据:{{item.analyzeDataText}}</view> -->
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
</view>
|
||||||
|
|
@ -0,0 +1,52 @@
|
||||||
|
{
|
||||||
|
"description": "项目配置文件,详见文档:https://developers.weixin.qq.com/miniprogram/dev/devtools/projectconfig.html",
|
||||||
|
"setting": {
|
||||||
|
"urlCheck": true,
|
||||||
|
"es6": false,
|
||||||
|
"enhance": true,
|
||||||
|
"postcss": true,
|
||||||
|
"preloadBackgroundData": false,
|
||||||
|
"minified": true,
|
||||||
|
"newFeature": false,
|
||||||
|
"coverView": true,
|
||||||
|
"nodeModules": false,
|
||||||
|
"autoAudits": false,
|
||||||
|
"showShadowRootInWxmlPanel": true,
|
||||||
|
"scopeDataCheck": false,
|
||||||
|
"uglifyFileName": false,
|
||||||
|
"checkInvalidKey": true,
|
||||||
|
"checkSiteMap": true,
|
||||||
|
"uploadWithSourceMap": true,
|
||||||
|
"compileHotReLoad": false,
|
||||||
|
"lazyloadPlaceholderEnable": false,
|
||||||
|
"useMultiFrameRuntime": true,
|
||||||
|
"useApiHook": true,
|
||||||
|
"useApiHostProcess": true,
|
||||||
|
"babelSetting": {
|
||||||
|
"ignore": [],
|
||||||
|
"disablePlugins": [],
|
||||||
|
"outputPath": ""
|
||||||
|
},
|
||||||
|
"useIsolateContext": true,
|
||||||
|
"userConfirmedBundleSwitch": false,
|
||||||
|
"packNpmManually": false,
|
||||||
|
"packNpmRelationList": [],
|
||||||
|
"minifyWXSS": true,
|
||||||
|
"disableUseStrict": false,
|
||||||
|
"minifyWXML": true,
|
||||||
|
"showES6CompileOption": false,
|
||||||
|
"useCompilerPlugins": false,
|
||||||
|
"ignoreUploadUnusedFiles": true
|
||||||
|
},
|
||||||
|
"compileType": "miniprogram",
|
||||||
|
"simulatorType": "wechat",
|
||||||
|
"simulatorPluginLibVersion": {},
|
||||||
|
"projectname": "bluetooth_demo_F01",
|
||||||
|
"libVersion": "2.23.2",
|
||||||
|
"appid": "wx39cf431caa22b5c8",
|
||||||
|
"editorSetting": {
|
||||||
|
"tabIndent": "insertSpaces",
|
||||||
|
"tabSize": 2
|
||||||
|
},
|
||||||
|
"condition": {}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
{
|
||||||
|
"desc": "关于本文件的更多信息,请参考文档 https://developers.weixin.qq.com/miniprogram/dev/framework/sitemap.html",
|
||||||
|
"rules": [{
|
||||||
|
"action": "allow",
|
||||||
|
"page": "*"
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
function inArray(arr, key, val) {
|
||||||
|
if (!arr || !arr.length || typeof arr != 'object' || !Array.isArray(arr)) {
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
for (let i = 0; i < arr.length; i++) {
|
||||||
|
if (!key) {
|
||||||
|
if (arr[i] == val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
} else if (arr[i][key] === val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ArrayBuffer转16进度字符串示例
|
||||||
|
function ab2hex(buffer, split) {
|
||||||
|
var hexArr = Array.prototype.map.call(
|
||||||
|
new Uint8Array(buffer),
|
||||||
|
function(bit) {
|
||||||
|
return ('00' + bit.toString(16)).slice(-2)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
return hexArr.join(split);
|
||||||
|
}
|
||||||
|
module.exports = {
|
||||||
|
inArray,
|
||||||
|
ab2hex,
|
||||||
|
}
|
||||||
Binary file not shown.
|
|
@ -0,0 +1,10 @@
|
||||||
|
# #参考使用设备类型
|
||||||
|
```
|
||||||
|
J02/J02B
|
||||||
|
L01/02/03/05
|
||||||
|
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
##
|
||||||
|
|
||||||
|
|
@ -0,0 +1,5 @@
|
||||||
|
//app.js
|
||||||
|
App({
|
||||||
|
onLaunch: function () {
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
"pages": [
|
||||||
|
"pages/index/index"
|
||||||
|
],
|
||||||
|
"window": {
|
||||||
|
"navigationBarBackgroundColor": "#0082FE",
|
||||||
|
"navigationBarTextStyle": "white",
|
||||||
|
"navigationBarTitleText": "蓝牙连接Demo",
|
||||||
|
"backgroundColor": "#eeeeee",
|
||||||
|
"backgroundTextStyle": "light"
|
||||||
|
},
|
||||||
|
"plugins": {
|
||||||
|
"sdkPlugin": {
|
||||||
|
"version": "2.1.0",
|
||||||
|
"provider": "wx17e93aad47cdae1a"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"style": "v2",
|
||||||
|
"sitemapLocation": "sitemap.json"
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,55 @@
|
||||||
|
/**app.wxss**/
|
||||||
|
view,
|
||||||
|
cover-view,
|
||||||
|
scroll-view,
|
||||||
|
swiper,
|
||||||
|
swiper-item,
|
||||||
|
movable-area,
|
||||||
|
movable-view,
|
||||||
|
button,
|
||||||
|
input,
|
||||||
|
textarea,
|
||||||
|
label,
|
||||||
|
navigator {
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
page {
|
||||||
|
--safe-bottom: env(safe-area-inset-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container {
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
width: 100vw;
|
||||||
|
height: 100vh;
|
||||||
|
padding-bottom: var(--safe-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header button {
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 40px;
|
||||||
|
width: 100% !important;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.device_item {
|
||||||
|
padding: 15px;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.weight {
|
||||||
|
width: 100%;
|
||||||
|
margin: 15px;
|
||||||
|
padding-bottom: 15px;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: 700;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,164 @@
|
||||||
|
const util = require("../../utils/util");
|
||||||
|
const {
|
||||||
|
inArray,
|
||||||
|
ab2hex
|
||||||
|
} = util
|
||||||
|
const plugin = requirePlugin("sdkPlugin").AiLink;
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
devices: [],
|
||||||
|
connected: false,
|
||||||
|
weight: "",
|
||||||
|
imp: "",
|
||||||
|
deviceId: null,
|
||||||
|
},
|
||||||
|
onLoad: function() {},
|
||||||
|
// 初始化蓝牙模块
|
||||||
|
openBluetoothAdapter() {
|
||||||
|
wx.openBluetoothAdapter({
|
||||||
|
success: (res) => {
|
||||||
|
console.log('openBluetoothAdapter success', res)
|
||||||
|
wx.showToast({
|
||||||
|
title: '蓝牙连接中',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
fail: (res) => {
|
||||||
|
if (res.errCode === 10001) {
|
||||||
|
wx.showToast({
|
||||||
|
title: '请打开蓝牙',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
// 监听本机蓝牙状态变化的事件
|
||||||
|
wx.onBluetoothAdapterStateChange((res) => {
|
||||||
|
console.log('onBluetoothAdapterStateChange', res)
|
||||||
|
if (res.available) {
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 开始搜寻附近的蓝牙外围设备
|
||||||
|
startBluetoothDevicesDiscovery() {
|
||||||
|
if (this._discoveryStarted) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
this._discoveryStarted = true
|
||||||
|
wx.startBluetoothDevicesDiscovery({
|
||||||
|
allowDuplicatesKey: true, //是否允许重复上报同一设备
|
||||||
|
services: [ //要搜索蓝牙设备主 service 的 uuid 列表
|
||||||
|
"F0A0",
|
||||||
|
],
|
||||||
|
success: (res) => {
|
||||||
|
console.log('startBluetoothDevicesDiscovery success', res)
|
||||||
|
this.onBluetoothDeviceFound()
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 停止搜寻附近的蓝牙外围设备
|
||||||
|
stopBluetoothDevicesDiscovery() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
|
||||||
|
// 找到新设备的事件
|
||||||
|
onBluetoothDeviceFound() {
|
||||||
|
let that = this
|
||||||
|
wx.onBluetoothDeviceFound((res) => {
|
||||||
|
res.devices.forEach(device => {
|
||||||
|
if (!device.name && !device.localName) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if (device.advertisServiceUUIDs[0].indexOf("F0A0") !== -1) {
|
||||||
|
let value = ab2hex(device.advertisData)
|
||||||
|
let parseDataRes = plugin.parseBroadcastData(device.advertisData)
|
||||||
|
let analyzeData = plugin.analyzeBroadcastScaleData(parseDataRes)
|
||||||
|
let analyzeDataText = analyzeData.text
|
||||||
|
let data = analyzeData.data
|
||||||
|
const dataT = {}
|
||||||
|
const foundDevices = this.data.devices
|
||||||
|
const idx = inArray(foundDevices, 'deviceId', device.deviceId)
|
||||||
|
let buffer = device.advertisData.slice(0, 8)
|
||||||
|
device.mac = new Uint8Array(buffer)
|
||||||
|
let tempMac = Array.from(device.mac)
|
||||||
|
tempMac.reverse()
|
||||||
|
device.macAddr = ab2hex(tempMac, ':').toUpperCase()
|
||||||
|
|
||||||
|
if (idx === -1) {
|
||||||
|
dataT[`devices[${foundDevices.length}]`] = device
|
||||||
|
} else {
|
||||||
|
dataT[`devices[${idx}]`] = device
|
||||||
|
}
|
||||||
|
this.setData(dataT)
|
||||||
|
if (parseDataRes.status == 1) {
|
||||||
|
let dw1 = "kg"
|
||||||
|
if (data.weightUnit == "1") {
|
||||||
|
dw1 = "斤"
|
||||||
|
}
|
||||||
|
if (data.weightUnit == "4") {
|
||||||
|
dw1 = "st:lb"
|
||||||
|
data = 1 * data + 5
|
||||||
|
}
|
||||||
|
if (data.weightUnit == "6") {
|
||||||
|
dw1 = "lb"
|
||||||
|
}
|
||||||
|
if (data.weightDecimal == "1") {
|
||||||
|
data.weight = data.weight / 10
|
||||||
|
}
|
||||||
|
if (data.weightDecimal == "2") {
|
||||||
|
data.weight = data.weight / 100
|
||||||
|
}
|
||||||
|
if (data.weightDecimal == "3") {
|
||||||
|
data.weight = data.weight / 1000
|
||||||
|
}
|
||||||
|
that.setData({
|
||||||
|
weight: analyzeData.text
|
||||||
|
})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
//监听蓝牙连接状态
|
||||||
|
onBLEConnectionStateChange() {
|
||||||
|
wx.onBLEConnectionStateChange((res) => {
|
||||||
|
if (!res.connected) {
|
||||||
|
wx.stopBluetoothDevicesDiscovery();
|
||||||
|
setTimeout(() => {
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接已断开',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}, 500)
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 断开蓝牙模块
|
||||||
|
*/
|
||||||
|
closeBluetoothAdapter() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery();
|
||||||
|
wx.closeBluetoothAdapter()
|
||||||
|
this._discoveryStarted = false
|
||||||
|
wx.showToast({
|
||||||
|
title: '结束流程',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
imp: ""
|
||||||
|
})
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
@ -0,0 +1,4 @@
|
||||||
|
{
|
||||||
|
"usingComponents": {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,42 @@
|
||||||
|
<wxs module="utils">
|
||||||
|
module.exports.max = function(n1, n2) {
|
||||||
|
return Math.max(n1, n2)
|
||||||
|
}
|
||||||
|
module.exports.len = function(arr) {
|
||||||
|
arr = arr || []
|
||||||
|
return arr.length
|
||||||
|
}
|
||||||
|
</wxs>
|
||||||
|
|
||||||
|
<view class="container">
|
||||||
|
<view class="header">
|
||||||
|
<button bindtap="openBluetoothAdapter">开始扫描</button>
|
||||||
|
<!-- <button bindtap="stopBluetoothDevicesDiscovery">停止扫描</button> -->
|
||||||
|
<button bindtap="closeBluetoothAdapter">结束流程</button>
|
||||||
|
</view>
|
||||||
|
<view class="weight">
|
||||||
|
<view>{{weight}}</view>
|
||||||
|
<!-- <view>{{imp}}</view> -->
|
||||||
|
<!-- <view>{{text}}</view> -->
|
||||||
|
</view>
|
||||||
|
<view class="devices_summary">已发现 {{devices.length}} 个外围设备:</view>
|
||||||
|
<scroll-view class="device_list" scroll-y scroll-with-animation>
|
||||||
|
<view wx:for="{{devices}}" wx:key="index"
|
||||||
|
data-device-id="{{item.deviceId}}"
|
||||||
|
data-name="{{item.name || item.localName}}"
|
||||||
|
data-mac="{{item.mac}}"
|
||||||
|
data-index="{{index}}"
|
||||||
|
bindtap="createBLEConnection"
|
||||||
|
class="device_item"
|
||||||
|
hover-class="device_item_hover">
|
||||||
|
<view style="font-size: 32rpx;">
|
||||||
|
<text style="color:#000;font-weight:bold">{{item.name}}</text>
|
||||||
|
<text style="font-size:26rpx">(信号强度: {{item.RSSI}}dBm)</text>
|
||||||
|
</view>
|
||||||
|
<view style="font-size: 26rpx">mac地址: {{item.macAddr || item.deviceId}}</view>
|
||||||
|
<!-- <view style="font-size: 26rpx">广播数据:{{item.analyzeDataText}}</view> -->
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
</view>
|
||||||
|
|
||||||
|
|
@ -0,0 +1,56 @@
|
||||||
|
{
|
||||||
|
"description": "项目配置文件,详见文档:https://developers.weixin.qq.com/miniprogram/dev/devtools/projectconfig.html",
|
||||||
|
"setting": {
|
||||||
|
"urlCheck": true,
|
||||||
|
"es6": false,
|
||||||
|
"enhance": true,
|
||||||
|
"postcss": true,
|
||||||
|
"preloadBackgroundData": false,
|
||||||
|
"minified": true,
|
||||||
|
"newFeature": false,
|
||||||
|
"coverView": true,
|
||||||
|
"nodeModules": false,
|
||||||
|
"autoAudits": false,
|
||||||
|
"showShadowRootInWxmlPanel": true,
|
||||||
|
"scopeDataCheck": false,
|
||||||
|
"uglifyFileName": false,
|
||||||
|
"checkInvalidKey": true,
|
||||||
|
"checkSiteMap": true,
|
||||||
|
"uploadWithSourceMap": true,
|
||||||
|
"compileHotReLoad": false,
|
||||||
|
"lazyloadPlaceholderEnable": false,
|
||||||
|
"useMultiFrameRuntime": true,
|
||||||
|
"useApiHook": true,
|
||||||
|
"useApiHostProcess": true,
|
||||||
|
"babelSetting": {
|
||||||
|
"ignore": [],
|
||||||
|
"disablePlugins": [],
|
||||||
|
"outputPath": ""
|
||||||
|
},
|
||||||
|
"useIsolateContext": true,
|
||||||
|
"userConfirmedBundleSwitch": false,
|
||||||
|
"packNpmManually": false,
|
||||||
|
"packNpmRelationList": [],
|
||||||
|
"minifyWXSS": true,
|
||||||
|
"disableUseStrict": false,
|
||||||
|
"minifyWXML": true,
|
||||||
|
"showES6CompileOption": false,
|
||||||
|
"useCompilerPlugins": false,
|
||||||
|
"ignoreUploadUnusedFiles": true
|
||||||
|
},
|
||||||
|
"compileType": "miniprogram",
|
||||||
|
"simulatorType": "wechat",
|
||||||
|
"simulatorPluginLibVersion": {},
|
||||||
|
"editorSetting": {
|
||||||
|
"tabIndent": "insertSpaces",
|
||||||
|
"tabSize": 2
|
||||||
|
},
|
||||||
|
"projectname": "bluetooth_demo_L01",
|
||||||
|
"libVersion": "2.23.2",
|
||||||
|
"appid": "wxcea3504a31518eb6",
|
||||||
|
"packOptions": {
|
||||||
|
"ignore": [],
|
||||||
|
"include": []
|
||||||
|
},
|
||||||
|
"condition": {}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
{
|
||||||
|
"desc": "关于本文件的更多信息,请参考文档 https://developers.weixin.qq.com/miniprogram/dev/framework/sitemap.html",
|
||||||
|
"rules": [{
|
||||||
|
"action": "allow",
|
||||||
|
"page": "*"
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
function inArray(arr, key, val) {
|
||||||
|
if (!arr || !arr.length || typeof arr != 'object' || !Array.isArray(arr)) {
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
for (let i = 0; i < arr.length; i++) {
|
||||||
|
if (!key) {
|
||||||
|
if (arr[i] == val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
} else if (arr[i][key] === val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ArrayBuffer转16进度字符串示例
|
||||||
|
function ab2hex(buffer, split) {
|
||||||
|
var hexArr = Array.prototype.map.call(
|
||||||
|
new Uint8Array(buffer),
|
||||||
|
function(bit) {
|
||||||
|
return ('00' + bit.toString(16)).slice(-2)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
return hexArr.join(split);
|
||||||
|
}
|
||||||
|
module.exports = {
|
||||||
|
inArray,
|
||||||
|
ab2hex,
|
||||||
|
}
|
||||||
Binary file not shown.
|
|
@ -0,0 +1,5 @@
|
||||||
|
//app.js
|
||||||
|
App({
|
||||||
|
onLaunch: function () {
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,14 @@
|
||||||
|
{
|
||||||
|
"pages": [
|
||||||
|
"pages/index/index"
|
||||||
|
],
|
||||||
|
"window": {
|
||||||
|
"navigationBarBackgroundColor": "#0082FE",
|
||||||
|
"navigationBarTextStyle": "white",
|
||||||
|
"navigationBarTitleText": "蓝牙连接Demo",
|
||||||
|
"backgroundColor": "#eeeeee",
|
||||||
|
"backgroundTextStyle": "light"
|
||||||
|
},
|
||||||
|
"style": "v2",
|
||||||
|
"sitemapLocation": "sitemap.json"
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,55 @@
|
||||||
|
/**app.wxss**/
|
||||||
|
view,
|
||||||
|
cover-view,
|
||||||
|
scroll-view,
|
||||||
|
swiper,
|
||||||
|
swiper-item,
|
||||||
|
movable-area,
|
||||||
|
movable-view,
|
||||||
|
button,
|
||||||
|
input,
|
||||||
|
textarea,
|
||||||
|
label,
|
||||||
|
navigator {
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
page {
|
||||||
|
--safe-bottom: env(safe-area-inset-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container {
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
width: 100vw;
|
||||||
|
height: 100vh;
|
||||||
|
padding-bottom: var(--safe-bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header button {
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 40px;
|
||||||
|
width: 100% !important;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.device_item {
|
||||||
|
padding: 15px;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
||||||
|
.weight {
|
||||||
|
width: 100%;
|
||||||
|
margin: 15px;
|
||||||
|
padding-bottom: 15px;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: 700;
|
||||||
|
border-bottom: 1px solid #dfdfdf;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,155 @@
|
||||||
|
const util = require("../../utils/util");
|
||||||
|
const {
|
||||||
|
inArray,
|
||||||
|
ab2hex
|
||||||
|
} = util
|
||||||
|
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
devices: [],
|
||||||
|
deviceId: null,
|
||||||
|
connected: false,
|
||||||
|
weight: "",
|
||||||
|
imp: "",
|
||||||
|
tetx: ''
|
||||||
|
},
|
||||||
|
onLoad: function() {},
|
||||||
|
// 初始化蓝牙模块
|
||||||
|
openBluetoothAdapter() {
|
||||||
|
wx.openBluetoothAdapter({
|
||||||
|
success: (res) => {
|
||||||
|
console.log('openBluetoothAdapter success', res)
|
||||||
|
wx.showToast({
|
||||||
|
title: '蓝牙连接中',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
fail: (res) => {
|
||||||
|
if (res.errCode === 10001) {
|
||||||
|
wx.showToast({
|
||||||
|
title: '请打开蓝牙',
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
// 监听本机蓝牙状态变化的事件
|
||||||
|
wx.onBluetoothAdapterStateChange((res) => {
|
||||||
|
console.log('onBluetoothAdapterStateChange', res)
|
||||||
|
if (res.available) {
|
||||||
|
this.startBluetoothDevicesDiscovery()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
// 开始搜寻附近的蓝牙外围设备
|
||||||
|
startBluetoothDevicesDiscovery() {
|
||||||
|
if (this._discoveryStarted) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
this._discoveryStarted = true
|
||||||
|
wx.startBluetoothDevicesDiscovery({
|
||||||
|
allowDuplicatesKey: true, //是否允许重复上报同一设备
|
||||||
|
success: (res) => {
|
||||||
|
console.log('startBluetoothDevicesDiscovery success', res)
|
||||||
|
this.onBluetoothDeviceFound()
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
// 停止搜寻附近的蓝牙外围设备
|
||||||
|
stopBluetoothDevicesDiscovery() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery()
|
||||||
|
},
|
||||||
|
|
||||||
|
// 找到新设备的事件
|
||||||
|
onBluetoothDeviceFound() {
|
||||||
|
let that = this
|
||||||
|
wx.onBluetoothDeviceFound((res) => {
|
||||||
|
res.devices.forEach(device => {
|
||||||
|
if (!device.name && !device.localName) {
|
||||||
|
let value = ab2hex(device.advertisData, "")
|
||||||
|
let id = value.substring(12, 16)
|
||||||
|
if (value.indexOf('c0') !== -1 && id == '0002') {
|
||||||
|
let buff = device.advertisData.slice(-6)
|
||||||
|
device.mac = new Uint8Array(buff) // 保存广播数据中的mac地址,这是由于iOS不直接返回mac地址
|
||||||
|
let tempMac = Array.from(device.mac)
|
||||||
|
device.macAddr = ab2hex(tempMac, ':').toUpperCase()
|
||||||
|
let msg = parseInt(value.substring(16, 18), 16).toString(2)
|
||||||
|
let weight = parseInt(value.substring(4, 8), 16)//体重
|
||||||
|
let type = msg.substring(5, 6) //0实时,1稳定
|
||||||
|
let num = msg.substring(3, 5) //小数点
|
||||||
|
let unit = msg.substring(1, 3) //单位
|
||||||
|
let dw1 = "kg"
|
||||||
|
if (unit == "10") {
|
||||||
|
dw1 = "lb"
|
||||||
|
}
|
||||||
|
if (num == "00") {
|
||||||
|
weight = parseInt(value.substring(4, 8), 16) / 10
|
||||||
|
}
|
||||||
|
if (num == "10") {
|
||||||
|
if (unit == "10") {
|
||||||
|
dw1 = "lb"
|
||||||
|
weight = parseInt(value.substring(4, 8), 16) / 10
|
||||||
|
} else {
|
||||||
|
weight = parseInt(value.substring(4, 8), 16) / 100
|
||||||
|
}
|
||||||
|
}
|
||||||
|
that.setData({
|
||||||
|
weight: "实时体重:" + weight + dw1,
|
||||||
|
})
|
||||||
|
if (type == '1') {
|
||||||
|
that.setData({
|
||||||
|
weight: "稳定体重:" + weight + dw1,
|
||||||
|
imp: "阻抗:" + parseInt(value.substring(8, 12), 16) / 10,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
//监听蓝牙连接状态
|
||||||
|
onBLEConnectionStateChange() {
|
||||||
|
wx.onBLEConnectionStateChange((res) => {
|
||||||
|
if (!res.connected) {
|
||||||
|
wx.stopBluetoothDevicesDiscovery();
|
||||||
|
setTimeout(() => {
|
||||||
|
wx.showToast({
|
||||||
|
title: '连接已断开',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
}, 500)
|
||||||
|
this.setData({
|
||||||
|
connected: false,
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
imp: "",
|
||||||
|
text: ''
|
||||||
|
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 断开蓝牙模块
|
||||||
|
*/
|
||||||
|
closeBluetoothAdapter() {
|
||||||
|
wx.stopBluetoothDevicesDiscovery();
|
||||||
|
wx.closeBluetoothAdapter()
|
||||||
|
this._discoveryStarted = false
|
||||||
|
wx.showToast({
|
||||||
|
title: '结束流程',
|
||||||
|
icon: 'none'
|
||||||
|
})
|
||||||
|
this.setData({
|
||||||
|
devices: [],
|
||||||
|
weight: "",
|
||||||
|
imp: "",
|
||||||
|
text: ''
|
||||||
|
})
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
@ -0,0 +1,4 @@
|
||||||
|
{
|
||||||
|
"usingComponents": {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,35 @@
|
||||||
|
<wxs module="utils">
|
||||||
|
module.exports.max = function(n1, n2) {
|
||||||
|
return Math.max(n1, n2)
|
||||||
|
}
|
||||||
|
module.exports.len = function(arr) {
|
||||||
|
arr = arr || []
|
||||||
|
return arr.length
|
||||||
|
}
|
||||||
|
</wxs>
|
||||||
|
|
||||||
|
<view class="container">
|
||||||
|
<view class="header">
|
||||||
|
<button bindtap="openBluetoothAdapter">开始扫描</button>
|
||||||
|
<!-- <button bindtap="stopBluetoothDevicesDiscovery">停止扫描</button> -->
|
||||||
|
<button bindtap="closeBluetoothAdapter">结束流程</button>
|
||||||
|
</view>
|
||||||
|
<view class="weight">
|
||||||
|
<view>{{weight}}</view>
|
||||||
|
<view>{{imp}}</view>
|
||||||
|
<view>{{text}}</view>
|
||||||
|
</view>
|
||||||
|
<view class="devices_summary">已发现 {{devices.length}} 个外围设备:</view>
|
||||||
|
<scroll-view class="device_list" scroll-y scroll-with-animation>
|
||||||
|
<view wx:for="{{devices}}" wx:key="index" data-device-id="{{item.deviceId}}"
|
||||||
|
data-name="{{item.name || item.localName}}" data-mac="{{item.mac}}" data-index="{{index}}"
|
||||||
|
bindtap="createBLEConnection" class="device_item" hover-class="device_item_hover">
|
||||||
|
<view style="font-size: 32rpx;">
|
||||||
|
<text style="color:#000;font-weight:bold">{{item.name}}</text>
|
||||||
|
<text style="font-size:26rpx">(信号强度: {{item.RSSI}}dBm)</text>
|
||||||
|
</view>
|
||||||
|
<view style="font-size: 26rpx">mac地址: {{item.macAddr || item.deviceId}}</view>
|
||||||
|
</view>
|
||||||
|
</scroll-view>
|
||||||
|
|
||||||
|
</view>
|
||||||
|
|
@ -0,0 +1,46 @@
|
||||||
|
{
|
||||||
|
"description": "项目配置文件,详见文档:https://developers.weixin.qq.com/miniprogram/dev/devtools/projectconfig.html",
|
||||||
|
"setting": {
|
||||||
|
"urlCheck": true,
|
||||||
|
"scopeDataCheck": false,
|
||||||
|
"coverView": true,
|
||||||
|
"es6": false,
|
||||||
|
"postcss": true,
|
||||||
|
"compileHotReLoad": false,
|
||||||
|
"lazyloadPlaceholderEnable": false,
|
||||||
|
"preloadBackgroundData": false,
|
||||||
|
"minified": true,
|
||||||
|
"autoAudits": false,
|
||||||
|
"newFeature": false,
|
||||||
|
"uglifyFileName": false,
|
||||||
|
"uploadWithSourceMap": true,
|
||||||
|
"useIsolateContext": false,
|
||||||
|
"nodeModules": false,
|
||||||
|
"enhance": true,
|
||||||
|
"useMultiFrameRuntime": true,
|
||||||
|
"useApiHook": true,
|
||||||
|
"useApiHostProcess": true,
|
||||||
|
"showShadowRootInWxmlPanel": true,
|
||||||
|
"packNpmManually": false,
|
||||||
|
"packNpmRelationList": [],
|
||||||
|
"minifyWXSS": true,
|
||||||
|
"disableUseStrict": false,
|
||||||
|
"ignoreUploadUnusedFiles": true,
|
||||||
|
"minifyWXML": true
|
||||||
|
},
|
||||||
|
"compileType": "miniprogram",
|
||||||
|
"simulatorType": "wechat",
|
||||||
|
"simulatorPluginLibVersion": {},
|
||||||
|
"editorSetting": {
|
||||||
|
"tabIndent": "insertSpaces",
|
||||||
|
"tabSize": 2
|
||||||
|
},
|
||||||
|
"projectname": "bluetooth_demo",
|
||||||
|
"libVersion": "2.23.2",
|
||||||
|
"appid": "wxcea3504a31518eb6",
|
||||||
|
"packOptions": {
|
||||||
|
"ignore": [],
|
||||||
|
"include": []
|
||||||
|
},
|
||||||
|
"condition": {}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
{
|
||||||
|
"desc": "关于本文件的更多信息,请参考文档 https://developers.weixin.qq.com/miniprogram/dev/framework/sitemap.html",
|
||||||
|
"rules": [{
|
||||||
|
"action": "allow",
|
||||||
|
"page": "*"
|
||||||
|
}]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
function inArray(arr, key, val) {
|
||||||
|
if (!arr || !arr.length || typeof arr != 'object' || !Array.isArray(arr)) {
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
for (let i = 0; i < arr.length; i++) {
|
||||||
|
if (!key) {
|
||||||
|
if (arr[i] == val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
} else if (arr[i][key] === val) {
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ArrayBuffer转16进度字符串示例
|
||||||
|
function ab2hex(buffer, split) {
|
||||||
|
var hexArr = Array.prototype.map.call(
|
||||||
|
new Uint8Array(buffer),
|
||||||
|
function(bit) {
|
||||||
|
return ('00' + bit.toString(16)).slice(-2)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
return hexArr.join(split);
|
||||||
|
}
|
||||||
|
module.exports = {
|
||||||
|
inArray,
|
||||||
|
ab2hex,
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue