|
@@ -1,8 +1,7 @@
|
|
|
// components/map-sense.js
|
|
|
|
|
|
-let innerAudioContext = wx.createInnerAudioContext({
|
|
|
- useWebAudioImplement: true,
|
|
|
-});
|
|
|
+let innerAudioContext = wx.createInnerAudioContext();
|
|
|
+innerAudioContext.src = 'none'
|
|
|
import { promisify, BeaconUtils } from "../../utils/util";
|
|
|
|
|
|
|
|
@@ -17,7 +16,7 @@ import {
|
|
|
CONNECT_STATUS,
|
|
|
STATUS_TEXT,
|
|
|
API_BASE_URL,
|
|
|
- DISTRIBUTION,
|
|
|
+ DISTRIBUTION2,
|
|
|
AudioAddress,
|
|
|
} from "../../config/index";
|
|
|
|
|
@@ -42,6 +41,8 @@ let updateTO = null
|
|
|
|
|
|
let changeTO = null;
|
|
|
|
|
|
+let isalwaysNullTO = null
|
|
|
+
|
|
|
// 选择6档
|
|
|
const TXPOWER = -55;
|
|
|
var result = 0,
|
|
@@ -49,7 +50,7 @@ var result = 0,
|
|
|
// 距离经验值(调试所得)
|
|
|
const N = 3.3;
|
|
|
|
|
|
-const R = 3.4; //设定感应范围半径
|
|
|
+const R = 4; //设定感应范围半径
|
|
|
|
|
|
const RSSIVAL = 70; //rssi信号过滤临界点
|
|
|
|
|
@@ -69,8 +70,7 @@ let group = [
|
|
|
["10014"],
|
|
|
["10015"],
|
|
|
["10016"],
|
|
|
- ["10017"],
|
|
|
- ["10018"],
|
|
|
+ ["10017", "10018"],
|
|
|
["10019"],
|
|
|
["10020", "10021"],
|
|
|
["10022"],
|
|
@@ -162,222 +162,237 @@ Component({
|
|
|
}
|
|
|
let aveArr = [];
|
|
|
|
|
|
- this.openBluetooth(() => {
|
|
|
- wx.showLoading({
|
|
|
- title: "正在连接…",
|
|
|
- mask: true,
|
|
|
+ let fn = ()=>{
|
|
|
+ wx.hideLoading({ fail() {} });
|
|
|
+ this.setData({
|
|
|
+ status: "2",
|
|
|
});
|
|
|
- startBeaconDiscovery({
|
|
|
- uuids: ["FDA50693-A4E2-4FB1-AFCF-C6EB07647825"],
|
|
|
- })
|
|
|
- .then(() => {
|
|
|
- wx.hideLoading({ fail() {} });
|
|
|
- this.setData({
|
|
|
- status: "2",
|
|
|
- });
|
|
|
- isCollect = true;
|
|
|
- updateingBeacon = false
|
|
|
-
|
|
|
- if (this.data.isAndroid) {
|
|
|
- checkCollect && clearInterval(checkCollect)
|
|
|
- checkTimeout && clearTimeout(checkTimeout)
|
|
|
- checkTimeout = setTimeout(() => {
|
|
|
- checkCollect = setInterval(() => {
|
|
|
- if (!updateingBeacon) {
|
|
|
- if (!hadshowModal) {
|
|
|
- hadshowModal = true
|
|
|
- wx.showModal({
|
|
|
- title: "请检查手机定位服务、蓝牙和网络是否保持打开状态",
|
|
|
- showCancel: false,
|
|
|
- success:()=>{
|
|
|
- this.resetPage()
|
|
|
- checkCollect && clearInterval(checkCollect)
|
|
|
- checkTimeout && clearTimeout(checkTimeout)
|
|
|
- hadshowModal = false
|
|
|
- }
|
|
|
- });
|
|
|
- }
|
|
|
+ isCollect = true;
|
|
|
+ updateingBeacon = false
|
|
|
+
|
|
|
+ if (this.data.isAndroid) {
|
|
|
+ checkCollect && clearInterval(checkCollect)
|
|
|
+ checkTimeout && clearTimeout(checkTimeout)
|
|
|
+ checkTimeout = setTimeout(() => {
|
|
|
+ checkCollect = setInterval(() => {
|
|
|
+ if (!updateingBeacon) {
|
|
|
+ if (!hadshowModal) {
|
|
|
+ hadshowModal = true
|
|
|
+ wx.showModal({
|
|
|
+ title: "请检查手机定位服务、蓝牙和网络是否保持打开状态(注:部分鸿蒙系统不支持该功能)",
|
|
|
+ showCancel: false,
|
|
|
+ success:()=>{
|
|
|
+ this.resetPage()
|
|
|
+ checkCollect && clearInterval(checkCollect)
|
|
|
+ checkTimeout && clearTimeout(checkTimeout)
|
|
|
+ hadshowModal = false
|
|
|
+ }
|
|
|
+ });
|
|
|
}
|
|
|
- }, 1000)
|
|
|
- }, 2000);
|
|
|
- }
|
|
|
-
|
|
|
- wx.onBeaconUpdate((data) => {
|
|
|
- console.log(data, "onBeaconUpdate");
|
|
|
- if (!isCollect) {
|
|
|
- return;
|
|
|
- }
|
|
|
- if (this.data.isAndroid) {
|
|
|
- updateTO && clearTimeout(updateTO)
|
|
|
-
|
|
|
- updateTO = setTimeout(() => {
|
|
|
- console.log('重置updateingBeacon');
|
|
|
- updateingBeacon = false
|
|
|
- }, 3000);
|
|
|
-
|
|
|
- updateingBeacon = true
|
|
|
- }
|
|
|
-
|
|
|
- console.log("还在收集…………");
|
|
|
- // 需要收集十组数据,索引号最大的组是最旧的
|
|
|
- if (!aveArr.includes(data.beacons)) {
|
|
|
- if (aveArr.length >= AveLength) {
|
|
|
- //当超过十组时,应该将索引号大的组淘汰掉
|
|
|
- aveArr.pop();
|
|
|
}
|
|
|
- aveArr.unshift(BeaconUtils.clone(data.beacons)); //在队列前面插入
|
|
|
- }
|
|
|
+ }, 4000)
|
|
|
+ }, 3000);
|
|
|
+ }
|
|
|
|
|
|
- let all = []; //获取所有data.beacons数据
|
|
|
- for (let i = 0; i < aveArr.length; i++) {
|
|
|
- let ele = aveArr[i];
|
|
|
- for (let j = 0; j < ele.length; j++) {
|
|
|
- let item = ele[j];
|
|
|
- //过滤信号弱的数据
|
|
|
- if (!(item.proximity === 0 && item.rssi === 0)) {
|
|
|
- if (Math.abs(item.rssi) < RSSIVAL) {
|
|
|
- // console.log(item.proximity,item.rssi);
|
|
|
- if (!all.includes(item)) {
|
|
|
- all.push(BeaconUtils.clone(item));
|
|
|
- }
|
|
|
- }
|
|
|
+ wx.onBeaconUpdate((data) => {
|
|
|
+ console.log(data, "onBeaconUpdate");
|
|
|
+ if (!isCollect) {
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ if (this.data.isAndroid) {
|
|
|
+ updateTO && clearTimeout(updateTO)
|
|
|
+
|
|
|
+ updateTO = setTimeout(() => {
|
|
|
+ console.log('重置updateingBeacon');
|
|
|
+ updateingBeacon = false
|
|
|
+ }, 10000);
|
|
|
+
|
|
|
+ updateingBeacon = true
|
|
|
+ }
|
|
|
+
|
|
|
+ console.log("还在收集…………");
|
|
|
+ // 需要收集十组数据,索引号最大的组是最旧的
|
|
|
+ if (!aveArr.includes(data.beacons)) {
|
|
|
+ if (aveArr.length >= AveLength) {
|
|
|
+ //当超过十组时,应该将索引号大的组淘汰掉
|
|
|
+ aveArr.pop();
|
|
|
+ }
|
|
|
+ aveArr.unshift(BeaconUtils.clone(data.beacons)); //在队列前面插入
|
|
|
+ }
|
|
|
+
|
|
|
+ let all = []; //获取所有data.beacons数据
|
|
|
+ for (let i = 0; i < aveArr.length; i++) {
|
|
|
+ let ele = aveArr[i];
|
|
|
+ for (let j = 0; j < ele.length; j++) {
|
|
|
+ let item = ele[j];
|
|
|
+ //过滤信号弱的数据
|
|
|
+ // if (!(item.proximity === 0 && item.rssi === 0)) {
|
|
|
+ if (Math.abs(item.rssi) < RSSIVAL) {
|
|
|
+ // console.log(item.accuracy,'accuracy------');
|
|
|
+ if (!all.includes(item)) {
|
|
|
+ all.push(BeaconUtils.clone(item));
|
|
|
}
|
|
|
}
|
|
|
- }
|
|
|
+ // }
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- let accuracyList = {};
|
|
|
- // classfiy = {10003:[{},{},···],10002:[{},{},···],10001:[{},{},···]}
|
|
|
- let classfiy = BeaconUtils.classification(all, "major");
|
|
|
+ let accuracyList = {};
|
|
|
+ // classfiy = {10003:[{},{},···],10002:[{},{},···],10001:[{},{},···]}
|
|
|
+ let classfiy = BeaconUtils.classification(all, "major");
|
|
|
|
|
|
- // console.log(classfiy,'classfiy');
|
|
|
+ // console.log(classfiy,'classfiy');
|
|
|
|
|
|
- Object.keys(classfiy).forEach((key) => {
|
|
|
- //每个major的AveLength个元素数组,元素为rssi
|
|
|
- let arr = classfiy[key].map((item) => {
|
|
|
- return item.rssi;
|
|
|
- });
|
|
|
+ Object.keys(classfiy).forEach((key) => {
|
|
|
+ //每个major的AveLength个元素数组,元素为rssi
|
|
|
+ let arr = classfiy[key].map((item) => {
|
|
|
+ return item.rssi;
|
|
|
+ });
|
|
|
|
|
|
- //每个major的rssi平均值
|
|
|
- let ave = BeaconUtils.arrayAverage(arr);
|
|
|
-
|
|
|
- //计算平均差
|
|
|
- let meanDeviation = BeaconUtils.getMeanDeviation(arr, ave);
|
|
|
-
|
|
|
- //计算各rssi的高斯模糊权重
|
|
|
- let guassionArr = []; //存放权重数组
|
|
|
- for (let i = 0; i < arr.length; ++i) {
|
|
|
- guassionArr.push(
|
|
|
- BeaconUtils.getOneGuassionArray(
|
|
|
- arr.length,
|
|
|
- i,
|
|
|
- meanDeviation
|
|
|
- )
|
|
|
- );
|
|
|
- }
|
|
|
+ //每个major的rssi平均值
|
|
|
+ let ave = BeaconUtils.arrayAverage(arr);
|
|
|
+
|
|
|
+ //计算平均差
|
|
|
+ let meanDeviation = BeaconUtils.getMeanDeviation(arr, ave);
|
|
|
+
|
|
|
+ //计算各rssi的高斯模糊权重
|
|
|
+ let guassionArr = []; //存放权重数组
|
|
|
+ for (let i = 0; i < arr.length; ++i) {
|
|
|
+ guassionArr.push(
|
|
|
+ BeaconUtils.getOneGuassionArray(
|
|
|
+ arr.length,
|
|
|
+ i,
|
|
|
+ meanDeviation
|
|
|
+ )
|
|
|
+ );
|
|
|
+ }
|
|
|
|
|
|
- //计算高斯模糊后的rssi值
|
|
|
- let rssiArr = []; //模糊后的rssi数组
|
|
|
- for (let i = 0; i < arr.length; ++i) {
|
|
|
- let sum = 0;
|
|
|
- for (let j = 0; j < arr.length; ++j) {
|
|
|
- if (guassionArr[i].length == 0) {
|
|
|
- sum = arr[j];
|
|
|
- break;
|
|
|
- }
|
|
|
- sum += guassionArr[i][j] * arr[j];
|
|
|
- }
|
|
|
- rssiArr.push(sum);
|
|
|
+ //计算高斯模糊后的rssi值
|
|
|
+ let rssiArr = []; //模糊后的rssi数组
|
|
|
+ for (let i = 0; i < arr.length; ++i) {
|
|
|
+ let sum = 0;
|
|
|
+ for (let j = 0; j < arr.length; ++j) {
|
|
|
+ if (guassionArr[i].length == 0) {
|
|
|
+ sum = arr[j];
|
|
|
+ break;
|
|
|
}
|
|
|
+ sum += guassionArr[i][j] * arr[j];
|
|
|
+ }
|
|
|
+ rssiArr.push(sum);
|
|
|
+ }
|
|
|
|
|
|
- //时间加权后求rssi平均值
|
|
|
- let aveOnTime = BeaconUtils.arrayAverage(
|
|
|
- rssiArr
|
|
|
- .slice(0, Math.floor(rssiArr.length / 3))
|
|
|
- .concat(rssiArr)
|
|
|
- );
|
|
|
-
|
|
|
- //测距,根据时间加权后的rssi计算距离
|
|
|
- // classfiy[key].forEach((item) => {
|
|
|
- let tmp = BeaconUtils.calculateAccuracy(TXPOWER, aveOnTime, N);
|
|
|
-
|
|
|
- if (!accuracyList[key]) {
|
|
|
- //如果还没有对应的“信标号”
|
|
|
- accuracyList[key] = [tmp];
|
|
|
- } else {
|
|
|
- accuracyList[key].push(tmp);
|
|
|
- }
|
|
|
- // });
|
|
|
- });
|
|
|
+ //时间加权后求rssi平均值
|
|
|
+ let aveOnTime = BeaconUtils.arrayAverage(
|
|
|
+ rssiArr
|
|
|
+ .slice(0, Math.floor(rssiArr.length / 3))
|
|
|
+ .concat(rssiArr)
|
|
|
+ );
|
|
|
|
|
|
- Object.keys(accuracyList).forEach((item) => {
|
|
|
- console.log(accuracyList[item] + "---------" + item);
|
|
|
- });
|
|
|
+ //测距,根据时间加权后的rssi计算距离
|
|
|
+ // classfiy[key].forEach((item) => {
|
|
|
+ let tmp = BeaconUtils.calculateAccuracy(TXPOWER, aveOnTime, N);
|
|
|
|
|
|
- console.log("--------分隔--------");
|
|
|
+ if (!accuracyList[key]) {
|
|
|
+ //如果还没有对应的“信标号”
|
|
|
+ accuracyList[key] = [tmp];
|
|
|
+ } else {
|
|
|
+ accuracyList[key].push(tmp);
|
|
|
+ }
|
|
|
+ // });
|
|
|
+ });
|
|
|
|
|
|
- // 筛选器,筛选出配对的一组信标
|
|
|
- let signSelect = new Array(21).fill(0); //记录各组的信标出现数量,投票选择最多的,依次是prologue,annexHall,mainHall
|
|
|
- // const prologue = ['10001','10002'] //序厅
|
|
|
- // const annexHall = ['10003','10004','10005','10006','10007'] //附厅
|
|
|
- // const mainHall = ['10008'] //主厅
|
|
|
+ Object.keys(accuracyList).forEach((item) => {
|
|
|
+ console.log(accuracyList[item] + "---------" + item);
|
|
|
+ });
|
|
|
|
|
|
- Object.keys(accuracyList).forEach((key) => {
|
|
|
- let aveAccuracy = BeaconUtils.arrayAverage(accuracyList[key]);
|
|
|
+ console.log("--------分隔--------");
|
|
|
|
|
|
- if (aveAccuracy < R) {
|
|
|
- for (let i = 0; i < group.length; i++) {
|
|
|
- if (group[i].includes(key)) {
|
|
|
- signSelect[i] += 1 / (aveAccuracy + 0.01); //取距离的反比例函数值,距离越近,值越大,+0.01是为了防止除数为0
|
|
|
- }
|
|
|
- }
|
|
|
+ // 筛选器,筛选出配对的一组信标
|
|
|
+ let signSelect = new Array(19).fill(0); //记录各组的信标出现数量,投票选择最多的,依次是prologue,annexHall,mainHall
|
|
|
+ // const prologue = ['10001','10002'] //序厅
|
|
|
+ // const annexHall = ['10003','10004','10005','10006','10007'] //附厅
|
|
|
+ // const mainHall = ['10008'] //主厅
|
|
|
+
|
|
|
+ Object.keys(accuracyList).forEach((key) => {
|
|
|
+ let aveAccuracy = BeaconUtils.arrayAverage(accuracyList[key]);
|
|
|
+
|
|
|
+ if (aveAccuracy < R) {
|
|
|
+ for (let i = 0; i < group.length; i++) {
|
|
|
+ if (group[i].includes(key)) {
|
|
|
+ signSelect[i] += 1 / (aveAccuracy + 0.01); //取距离的反比例函数值,距离越近,值越大,+0.01是为了防止除数为0
|
|
|
}
|
|
|
- });
|
|
|
- console.log(signSelect);
|
|
|
- //对小于预设半径的信号进行数量投票
|
|
|
- result = BeaconUtils.maxIndex(signSelect);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ });
|
|
|
+ console.log(signSelect);
|
|
|
+ //对小于预设半径的信号进行数量投票
|
|
|
+ result = BeaconUtils.maxIndex(signSelect);
|
|
|
|
|
|
- console.log("result", result);
|
|
|
- if (result != null && result !== oldResult) {
|
|
|
+ console.log("result音频结果", result,group[result]);
|
|
|
+ if (result != null && result !== oldResult) {
|
|
|
+ wx.hideLoading({ fail() {} });
|
|
|
+ this.playAudio(AudioAddress[result]);
|
|
|
+ oldResult = result;
|
|
|
+ }
|
|
|
+ if (result === null && oldResult != -1) {
|
|
|
+ changeTO && clearTimeout(changeTO);
|
|
|
+ changeTO = setTimeout(() => {
|
|
|
wx.hideLoading({ fail() {} });
|
|
|
- this.playAudio(AudioAddress[result]);
|
|
|
- oldResult = result;
|
|
|
- }
|
|
|
- if (result === null && oldResult != -1) {
|
|
|
- wx.showLoading({
|
|
|
- title: "音频切换中…",
|
|
|
- mask: true,
|
|
|
- });
|
|
|
- changeTO && clearTimeout(changeTO);
|
|
|
- changeTO = setTimeout(() => {
|
|
|
- wx.hideLoading({ fail() {} });
|
|
|
- }, 4000);
|
|
|
- this.stopAndDestroyAudio();
|
|
|
- }
|
|
|
+ }, 4000);
|
|
|
+
|
|
|
+ this.stopAndDestroyAudio();
|
|
|
+ // isalwaysNullTO && clearTimeout(isalwaysNullTO);
|
|
|
+ // isalwaysNullTO = setTimeout(() => {
|
|
|
+ // (result === null && oldResult != -1) && this.stopAndDestroyAudio();
|
|
|
+ // }, 1000);
|
|
|
+ }
|
|
|
+
|
|
|
+ let temp = DISTRIBUTION2.find((item) => {
|
|
|
+ return item.position.some((sub) => sub == result);
|
|
|
+ });
|
|
|
|
|
|
- let temp = DISTRIBUTION.find((item) => {
|
|
|
- return item.position.some((sub) => sub == result);
|
|
|
- });
|
|
|
+ this.setData({
|
|
|
+ classfiy,
|
|
|
+ targetObj: temp || {},
|
|
|
+ result,
|
|
|
+ });
|
|
|
+ });
|
|
|
+ }
|
|
|
|
|
|
- this.setData({
|
|
|
- classfiy,
|
|
|
- targetObj: temp || {},
|
|
|
- result,
|
|
|
- });
|
|
|
- });
|
|
|
+ this.openBluetooth(() => {
|
|
|
+ wx.showLoading({
|
|
|
+ title: "正在连接…",
|
|
|
+ mask: true,
|
|
|
+ });
|
|
|
+ startBeaconDiscovery({
|
|
|
+ uuids: ["FDA50693-A4E2-4FB1-AFCF-C6EB07647825"],
|
|
|
+ })
|
|
|
+ .then(() => {
|
|
|
+ fn()
|
|
|
})
|
|
|
.catch((err) => {
|
|
|
- console.log(err,'1111');
|
|
|
+ console.log(err);
|
|
|
if (err.errCode == 11002) {
|
|
|
wx.showToast({
|
|
|
title: "请打开手机定位服务",
|
|
|
- icon: "error",
|
|
|
- duration: 500,
|
|
|
+ icon: "none",
|
|
|
+ duration: 1000,
|
|
|
});
|
|
|
- } else {
|
|
|
+ } else if (err.errCode == 11005) {
|
|
|
+ if (this.data.isAndroid) {
|
|
|
+ fn()
|
|
|
+ } else{
|
|
|
+ wx.showToast({
|
|
|
+ title: "您的系统暂不支持该功能",
|
|
|
+ icon: "none",
|
|
|
+ duration: 1000,
|
|
|
+ });
|
|
|
+ }
|
|
|
+ } else {
|
|
|
wx.showToast({
|
|
|
title: "连接失败",
|
|
|
icon: "error",
|
|
|
- duration: 500,
|
|
|
+ duration: 1000,
|
|
|
});
|
|
|
}
|
|
|
});
|
|
@@ -392,23 +407,26 @@ Component({
|
|
|
|
|
|
innerAudioContext.pause();
|
|
|
innerAudioContext.stop();
|
|
|
- innerAudioContext.src = null;
|
|
|
innerAudioContext.destroy();
|
|
|
+ innerAudioContext.src = 'none';
|
|
|
innerAudioContext = null;
|
|
|
},
|
|
|
|
|
|
playAudio(src) {
|
|
|
- if (!innerAudioContext) {
|
|
|
- innerAudioContext = wx.createInnerAudioContext({
|
|
|
- useWebAudioImplement: true,
|
|
|
- });
|
|
|
+ if (innerAudioContext) {
|
|
|
+ innerAudioContext.pause();
|
|
|
+ innerAudioContext.stop();
|
|
|
+ innerAudioContext.destroy();
|
|
|
+ innerAudioContext.src = 'none';
|
|
|
}
|
|
|
|
|
|
+ innerAudioContext = null;
|
|
|
+ innerAudioContext = wx.createInnerAudioContext();
|
|
|
innerAudioContext.src = src;
|
|
|
innerAudioContext.loop = true;
|
|
|
innerAudioContext.onCanplay(() => {
|
|
|
innerAudioContext.play();
|
|
|
- });
|
|
|
+ });
|
|
|
// innerAudioContext.play();
|
|
|
},
|
|
|
|
|
@@ -442,31 +460,6 @@ Component({
|
|
|
});
|
|
|
},
|
|
|
|
|
|
- // 扫一扫
|
|
|
- toScanCode() {
|
|
|
- this.setData({
|
|
|
- isScanPlay: true,
|
|
|
- });
|
|
|
- wx.scanCode({
|
|
|
- success: (res) => {
|
|
|
- this.stopBeaconDiscovery(true);
|
|
|
- this.playAudio(res["result"]);
|
|
|
- },
|
|
|
- fail: () => {
|
|
|
- console.log("fail innerAudioContext", innerAudioContext);
|
|
|
- this.setData({
|
|
|
- isScanPlay: false,
|
|
|
- });
|
|
|
- return;
|
|
|
- },
|
|
|
- complete() {
|
|
|
- this.setData({
|
|
|
- isScanPlay: false,
|
|
|
- });
|
|
|
- },
|
|
|
- });
|
|
|
- },
|
|
|
-
|
|
|
resetPage() {
|
|
|
this.stopBeaconDiscovery(true);
|
|
|
},
|