@@ -31,6 +31,7 @@ | |||||
"vue-baidu-map": "^0.21.22", | "vue-baidu-map": "^0.21.22", | ||||
"vue-cookies": "^1.7.4", | "vue-cookies": "^1.7.4", | ||||
"vue-esign": "^1.0.5", | "vue-esign": "^1.0.5", | ||||
"vue-qrcode-reader": "^3.1.0", | |||||
"vue-router": "^3.0.1", | "vue-router": "^3.0.1", | ||||
"vue-search-tree": "^1.9.9", | "vue-search-tree": "^1.9.9", | ||||
"vuex": "^3.6.2", | "vuex": "^3.6.2", | ||||
@@ -708,3 +708,12 @@ export function getCaseNum(query) { | |||||
params: query | params: query | ||||
}) | }) | ||||
} | } | ||||
// 查询手机监控 | |||||
export function getMonitor(query) { | |||||
return request({ | |||||
url: '/enforce/monitor/query', | |||||
method: 'get', | |||||
params: query | |||||
}) | |||||
} |
@@ -0,0 +1,274 @@ | |||||
// qrcode.vue | |||||
<template> | |||||
<div> | |||||
<p class="error">{{ error }}</p> | |||||
<!--错误信息--> | |||||
<p class="decode-result"> | |||||
扫描结果: | |||||
<b>{{ result }}</b> | |||||
</p> | |||||
<!--扫描结果--> | |||||
<p @click="openCamera">打开相机</p> | |||||
<div v-show="show" class="cameraMessage"> | |||||
<p @click="closeCamera">关闭相机</p> | |||||
<p @click="openFlash">打开手电筒</p> | |||||
<p @click="switchCamera">相机反转</p> | |||||
</div> | |||||
<qrcode-stream | |||||
v-show="qrcode" | |||||
:camera="camera" | |||||
:torch="torchActive" | |||||
@decode="onDecode" | |||||
@init="onInit" | |||||
> | |||||
<div> | |||||
<div class="qr-scanner"> | |||||
<div class="box"> | |||||
<div class="line"></div> | |||||
<div class="angle"></div> | |||||
</div> | |||||
<div class="txt"> | |||||
将二维码/条码放入框内,即自动扫描 | |||||
<div class="myQrcode">我的二维码</div> | |||||
</div> | |||||
</div> | |||||
</div> | |||||
</qrcode-stream> | |||||
</div> | |||||
</template> | |||||
<script> | |||||
// 下载插件 | |||||
// cnpm install --save vue-qrcode-reader | |||||
// 引入 | |||||
import { QrcodeStream } from 'vue-qrcode-reader'; | |||||
export default { | |||||
// 注册 | |||||
components: { QrcodeStream }, | |||||
data() { | |||||
return { | |||||
result: '', // 扫码结果信息 | |||||
error: '', // 错误信息 | |||||
show: false, | |||||
qrcode: false, | |||||
qrcode: true, | |||||
torchActive: false, | |||||
camera: 'front', | |||||
}; | |||||
}, | |||||
methods: { | |||||
onDecode(result) { | |||||
console.log(result); | |||||
this.result = result; | |||||
}, | |||||
async onInit(promise) { | |||||
const { capabilities } = await promise; | |||||
const TORCH_IS_SUPPORTED = !!capabilities.torch; | |||||
try { | |||||
await promise; | |||||
} catch (error) { | |||||
if (error.name === 'NotAllowedError') { | |||||
this.error = 'ERROR: 您需要授予相机访问权限'; | |||||
} else if (error.name === 'NotFoundError') { | |||||
this.error = 'ERROR: 这个设备上没有摄像头'; | |||||
} else if (error.name === 'NotSupportedError') { | |||||
this.error = 'ERROR: 所需的安全上下文(HTTPS、本地主机)'; | |||||
} else if (error.name === 'NotReadableError') { | |||||
this.error = 'ERROR: 相机被占用'; | |||||
} else if (error.name === 'OverconstrainedError') { | |||||
this.error = 'ERROR: 安装摄像头不合适'; | |||||
} else if (error.name === 'StreamApiNotSupportedError') { | |||||
this.error = 'ERROR: 此浏览器不支持流API'; | |||||
} | |||||
} | |||||
}, | |||||
// 打开相机 | |||||
openCamera() { | |||||
this.camera = 'rear' | |||||
this.qrcode = true | |||||
this.show = true | |||||
}, | |||||
// 关闭相机 | |||||
closeCamera() { | |||||
this.camera = 'off' | |||||
this.qrcode = false | |||||
this.show = false | |||||
}, | |||||
// 打开手电筒 | |||||
openFlash() { | |||||
switch (this.torchActive) { | |||||
case true: | |||||
this.torchActive = false | |||||
break | |||||
case false: | |||||
this.torchActive = true | |||||
break | |||||
} | |||||
}, | |||||
// 相机反转 | |||||
switchCamera() { | |||||
// console.log(this.camera); | |||||
switch (this.camera) { | |||||
case 'front': | |||||
this.camera = 'rear' | |||||
console.log(this.camera) | |||||
break | |||||
case 'rear': | |||||
this.camera = 'front' | |||||
console.log(this.camera) | |||||
break | |||||
} | |||||
} | |||||
}, | |||||
}; | |||||
</script> | |||||
<style scoped> | |||||
.error { | |||||
font-weight: bold; | |||||
color: red; | |||||
} | |||||
.cameraMessage { | |||||
width: 100%; | |||||
height: 60px; | |||||
} | |||||
.qr-scanner { | |||||
background-image: linear-gradient( | |||||
0deg, | |||||
transparent 24%, | |||||
rgba(32, 255, 77, 0.1) 25%, | |||||
rgba(32, 255, 77, 0.1) 26%, | |||||
transparent 27%, | |||||
transparent 74%, | |||||
rgba(32, 255, 77, 0.1) 75%, | |||||
rgba(32, 255, 77, 0.1) 76%, | |||||
transparent 77%, | |||||
transparent | |||||
), | |||||
linear-gradient( | |||||
90deg, | |||||
transparent 24%, | |||||
rgba(32, 255, 77, 0.1) 25%, | |||||
rgba(32, 255, 77, 0.1) 26%, | |||||
transparent 27%, | |||||
transparent 74%, | |||||
rgba(32, 255, 77, 0.1) 75%, | |||||
rgba(32, 255, 77, 0.1) 76%, | |||||
transparent 77%, | |||||
transparent | |||||
); | |||||
background-size: 3rem 3rem; | |||||
background-position: -1rem -1rem; | |||||
width: 100%; | |||||
/* height: 100%; */ | |||||
height: 100vh; | |||||
/* height: 288px; */ | |||||
position: relative; | |||||
background-color: #1110; | |||||
/* background-color: #111; */ | |||||
} | |||||
/* .qrcode-stream-wrapper { | |||||
display: flex; | |||||
justify-content: center; | |||||
align-items: center; | |||||
margin-top: 82px; | |||||
clear: both; | |||||
} */ | |||||
/* .qrcode-stream-wrapper >>> .qrcode-stream-camera { | |||||
width: 213px; | |||||
height: 210px; | |||||
clear: both; | |||||
margin-top: 39px; | |||||
} */ | |||||
.qr-scanner .box { | |||||
width: 213px; | |||||
height: 213px; | |||||
position: absolute; | |||||
left: 50%; | |||||
top: 50%; | |||||
transform: translate(-50%, -50%); | |||||
overflow: hidden; | |||||
border: 0.1rem solid rgba(0, 255, 51, 0.2); | |||||
/* background: url('http://resource.beige.world/imgs/gongconghao.png') no-repeat center center; */ | |||||
} | |||||
.qr-scanner .txt { | |||||
width: 100%; | |||||
height: 35px; | |||||
line-height: 35px; | |||||
font-size: 14px; | |||||
text-align: center; | |||||
/* color: #f9f9f9; */ | |||||
margin: 0 auto; | |||||
position: absolute; | |||||
top: 70%; | |||||
left: 0; | |||||
} | |||||
.qr-scanner .myQrcode { | |||||
text-align: center; | |||||
color: #00ae10; | |||||
} | |||||
.qr-scanner .line { | |||||
height: calc(100% - 2px); | |||||
width: 100%; | |||||
background: linear-gradient(180deg, rgba(0, 255, 51, 0) 43%, #00ff33 211%); | |||||
border-bottom: 3px solid #00ff33; | |||||
transform: translateY(-100%); | |||||
animation: radar-beam 2s infinite alternate; | |||||
animation-timing-function: cubic-bezier(0.53, 0, 0.43, 0.99); | |||||
animation-delay: 1.4s; | |||||
} | |||||
.qr-scanner .box:after, | |||||
.qr-scanner .box:before, | |||||
.qr-scanner .angle:after, | |||||
.qr-scanner .angle:before { | |||||
content: ''; | |||||
display: block; | |||||
position: absolute; | |||||
width: 3vw; | |||||
height: 3vw; | |||||
border: 0.2rem solid transparent; | |||||
} | |||||
.qr-scanner .box:after, | |||||
.qr-scanner .box:before { | |||||
top: 0; | |||||
border-top-color: #00ff33; | |||||
} | |||||
.qr-scanner .angle:after, | |||||
.qr-scanner .angle:before { | |||||
bottom: 0; | |||||
border-bottom-color: #00ff33; | |||||
} | |||||
.qr-scanner .box:before, | |||||
.qr-scanner .angle:before { | |||||
left: 0; | |||||
border-left-color: #00ff33; | |||||
} | |||||
.qr-scanner .box:after, | |||||
.qr-scanner .angle:after { | |||||
right: 0; | |||||
border-right-color: #00ff33; | |||||
} | |||||
@keyframes radar-beam { | |||||
0% { | |||||
transform: translateY(-100%); | |||||
} | |||||
100% { | |||||
transform: translateY(0); | |||||
} | |||||
} | |||||
</style> |
@@ -9,21 +9,21 @@ | |||||
<p class="tit">设备</p> | <p class="tit">设备</p> | ||||
<!-- <p class="content">农业农村管理方面法律及法规规定的行政处罚</p>--> | <!-- <p class="content">农业农村管理方面法律及法规规定的行政处罚</p>--> | ||||
<van-grid :column-num="2" :border="false"> | <van-grid :column-num="2" :border="false"> | ||||
<van-grid-item :to="{name:'lawEnforcementCaseAllocation'}"> | |||||
<van-grid-item> | |||||
<div class="onDiv"> | <div class="onDiv"> | ||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_01.png"/> | <img src="../../../../static/images/lawEnforcement/icon/monitor_icon_01.png"/> | ||||
<div class="onDiv_text"> | <div class="onDiv_text"> | ||||
<p>4<span>台</span></p> | |||||
<p>{{monitorList.length}}<span>台</span></p> | |||||
<p>在线设备</p> | <p>在线设备</p> | ||||
</div> | </div> | ||||
</div> | </div> | ||||
</van-grid-item> | </van-grid-item> | ||||
<van-grid-item :to="{name:'waitingProcessing'}"> | |||||
<van-grid-item> | |||||
<div class="onDiv outDiv"> | <div class="onDiv outDiv"> | ||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_01.png"/> | <img src="../../../../static/images/lawEnforcement/icon/monitor_icon_01.png"/> | ||||
<div class="onDiv_text"> | <div class="onDiv_text"> | ||||
<p>4<span>台</span></p> | |||||
<p>在线设备</p> | |||||
<p>{{monitorList2.length}}<span>台</span></p> | |||||
<p>离线设备</p> | |||||
</div> | </div> | ||||
</div> | </div> | ||||
</van-grid-item> | </van-grid-item> | ||||
@@ -32,71 +32,23 @@ | |||||
<van-tabs v-model="active" animated> | <van-tabs v-model="active" animated> | ||||
<van-tab title="在线设备"> | <van-tab title="在线设备"> | ||||
<div class="onList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">接入时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">接入时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList"> | |||||
<div class="onList" v-for="(item,index) in monitorList"> | |||||
<div class="onList_tit"> | <div class="onList_tit"> | ||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | <img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | ||||
<p>手持执法仪</p> | |||||
<p>{{item.belongTeam}}</p> | |||||
</div> | </div> | ||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">接入时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">接入时间:08/21 15:00</p> | |||||
<p class="onList_num">{{item.monitorCode}}</p> | |||||
<p class="onList_time">接入时间:{{item.createTime.substr(0,10)}}</p> | |||||
</div> | </div> | ||||
</van-tab> | </van-tab> | ||||
<van-tab title="离线设备"> | <van-tab title="离线设备"> | ||||
<div class="onList offList"> | |||||
<div class="onList offList" v-for="(item,index) in monitorList2"> | |||||
<div class="onList_tit"> | <div class="onList_tit"> | ||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | <img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | ||||
<p>手持执法仪</p> | |||||
<p>{{item.belongTeam}}</p> | |||||
</div> | </div> | ||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">最近时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList offList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">最近时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList offList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">最近时间:08/21 15:00</p> | |||||
</div> | |||||
<div class="onList offList"> | |||||
<div class="onList_tit"> | |||||
<img src="../../../../static/images/lawEnforcement/icon/monitor_icon_02.png" alt=""> | |||||
<p>手持执法仪</p> | |||||
</div> | |||||
<p class="onList_num">Y-01</p> | |||||
<p class="onList_time">最近时间:08/21 15:00</p> | |||||
<p class="onList_num">{{item.monitorCode}}</p> | |||||
<p class="onList_time">最近时间:{{item.createTime.substr(0,10)}}</p> | |||||
</div> | </div> | ||||
</van-tab> | </van-tab> | ||||
</van-tabs> | </van-tabs> | ||||
@@ -108,6 +60,7 @@ | |||||
<script> | <script> | ||||
import lawNew from "@/components/common/lawNew_footer"; | import lawNew from "@/components/common/lawNew_footer"; | ||||
import {getMonitor} from "@/api/lawEnforcement"; | |||||
export default { | export default { | ||||
name: "caseAllocation", | name: "caseAllocation", | ||||
components: { | components: { | ||||
@@ -116,13 +69,30 @@ | |||||
data() { | data() { | ||||
return { | return { | ||||
active: 0, | active: 0, | ||||
queryParams:{ | |||||
sysNormalDisable:'0' | |||||
}, | |||||
queryParams2:{ | |||||
sysNormalDisable:'1' | |||||
}, | |||||
monitorList:[], | |||||
monitorList2:[], | |||||
}; | }; | ||||
}, | }, | ||||
created() { | created() { | ||||
this.getList(); | |||||
}, | }, | ||||
methods: { | methods: { | ||||
getList(){ | |||||
getMonitor(this.queryParams).then(response => { | |||||
console.log(response) | |||||
this.monitorList = response.rows; | |||||
}); | |||||
getMonitor(this.queryParams2).then(response => { | |||||
console.log(response) | |||||
this.monitorList2 = response.rows; | |||||
}); | |||||
}, | |||||
}, | }, | ||||
} | } | ||||
</script> | </script> | ||||
@@ -52,14 +52,18 @@ | |||||
</div> | </div> | ||||
</div> | </div> | ||||
<vue-qrcode /> | |||||
</div> | </div> | ||||
</template> | </template> | ||||
<script> | <script> | ||||
import { getScheme } from "@/api/lawEnforcement/index"; | import { getScheme } from "@/api/lawEnforcement/index"; | ||||
import qrcode from '@/components/qrcode/qrcode.vue'; | |||||
export default { | export default { | ||||
name: "programmeDetail", | name: "programmeDetail", | ||||
components: { | |||||
'vue-qrcode': qrcode, | |||||
}, | |||||
data() { | data() { | ||||
return { | return { | ||||
showBankType:false, | showBankType:false, | ||||