<script lang="ts" setup name="AlarmList"> import alarmDialog from './alarmDialog.vue' import useSocket from '@/store/modules/websocket' import { getAlarmList } from '@/api/home/dashboard/index' import { getAlarmLevelListPage } from '@/api/home/rule/alarm' import { fetchCacheDevice, fetchCacheWell, fetchCacheStation, fetchCacheDept, fetchCacheWell95 } from '@/utils/sessionData' import indexDB from '@/utils/indexDB' import { alarmValue } from '@/views/home/alarm/current/components/dict' // 引入音频文件 import alarmAudio from '@/assets/audio/alarm.mp3' import otherAudio from '@/assets/audio/other.mp3' import useUserStore from '@/store/modules/user' const { proxy } = getCurrentInstance() as any const messageList = ref<any[]>([]) const alarmLevelList = ref<any[]>([]) const socket = useSocket() const loading = ref(true) const $emits = defineEmits(['close']) // setTimeout(() => { // messageList.value = [ // { // id: '1', // title: '燃气浓度超限', // device: '燃气智能监测终端', // code: 'N57G215', // alarmValue: '浓度12%vol', // readStatus: '1', // time: '2024-06-29 12:05:00', // grade: '1', // }, // { // id: '2', // title: '桩倾斜报警', // device: '燃气智能监测终端', // code: 'N57G215', // alarmValue: '浓度12%vol', // readStatus: '2', // time: '2024-03-21 13:03:01', // grade: '2', // }, // { // id: '3', // title: '设备故障', // device: '燃气智能监测终端', // code: 'N57G215', // alarmValue: '浓度12%vol', // readStatus: '1', // time: '2024-02-29 02:05:40', // grade: '3', // }, // ] // }) defineExpose({ messageList }) const userStore = useUserStore() // 查看更多 const $router = useRouter() const moreList = () => { $router.push({ name: 'AlarmCurrent', }) // 通知关闭popover $emits('close') } // 查看当前行 const detailRow = (row: any) => { // console.log(row, 'row') if (!proxy.hasPerm('/alarm/current')) { return } $router.push({ name: 'AlarmCurrent', query: { row: JSON.stringify(row), type: 'alarm-pop' }, }) // 通知关闭popover $emits('close') } const play = () => { if (!localStorage.getItem('eventAudio')) { if (messageList.value.length > 0 && messageList.value.some((item: any) => item.isSound === '1')) { proxy.playAudio() } } else { proxy.pauseAudio() localStorage.setItem('eventAudio', 'pause') } } const dialogRef = ref() const pause = () => { proxy.pauseAudio() localStorage.setItem('eventAudio', 'pause') // const row = { // alarmNoteMethod: '1', // 消息提醒 1:弹窗,2:消息提醒 // isSound: '1', // 报警音效,1:开,0:关 // isSend: '1', // 报警推送,1:开,0:关 // isText: '1', // 报警短息,1:开,0:关 // alarmType: '超限', // tagNumber: 'NX5702', // alarmTime: '2024-09-09', // value: '20', // typeName: '燃气智能终端燃气智能终端', // alarmLevel: '一级', // } // dialogRef.value.initDialog(row) } const fetchData = (isLoading = false) => { loading.value = true if (isLoading) { loading.value = false } if(window.localStorage.getItem('browser-type-bj-well') === 'mobile') { loading.value = false return } getAlarmList({ }).then((res) => { messageList.value = res.data.rows.map((item: any) => ({ ...item, alarmLevelName: alarmLevelList.value.filter((citem: any) => citem.id === item.alarmLevel)[0]?.alarmLevel || '', isSound: alarmLevelList.value.filter((citem: any) => citem.id === item.alarmLevel)[0]?.isSound || '', alarmReason: item.alarmType.includes('浓度') ? `${item.alarmValue}%LEL` : (alarmValue[item.alarmValue] || '其他') })) loading.value = false if (messageList.value.length > 0 && messageList.value.some((item: any) => item.isSound === '1' && item.processStatus === '1')) { const audio = document.getElementById('eventAudio') as HTMLAudioElement // if (messageList.value.some((item: any) => item.alarmReason.includes('断线') && item.isSound === '1' && item.processStatus === '1')) { // audio.setAttribute('src', alarmAudio) // } // else { audio.setAttribute('src', otherAudio) // } proxy.playAudio() localStorage.setItem('eventAudio', '') } }).catch(() => { loading.value = false }) } watch(() => socket.data, (newVal: any) => { if (newVal && newVal.alarmNoteMethod) { // console.log(userStore.dataScope, 'userStore.dataScope') if (newVal.alarmNoteMethod === '1' && (userStore.dataScope || []).includes(newVal.deptid)) { dialogRef.value.initDialog(newVal) } // if (newVal.isSound === '1') { // proxy.playAudio() // localStorage.setItem('eventAudio', '') // } fetchData(false) if (indexDB.getStatus() && window.localStorage.getItem('browser-type-bj-well') === 'pc') { // 重新拉取缓存 fetchCacheDevice() fetchCacheWell() fetchCacheWell95() fetchCacheStation() } } }, { deep: true, immediate: true, }) const timer = ref() const clearTimer = () => { if (timer.value) { clearInterval(timer.value) timer.value = null } } onMounted(() => { getAlarmLevelListPage({ offset: 1, limit: 999 }).then((res) => { alarmLevelList.value = res.data.rows fetchData() socket.initWebSocket() }) // 启动定时器 clearTimer() timer.value = setInterval(() => { getAlarmList({ }).then((res) => { messageList.value = res.data.rows.map((item: any) => ({ ...item, alarmLevelName: alarmLevelList.value.filter((citem: any) => citem.id === item.alarmLevel)[0]?.alarmLevel || '', isSound: alarmLevelList.value.filter((citem: any) => citem.id === item.alarmLevel)[0]?.isSound || '', alarmReason: item.alarmType.includes('浓度') ? `${item.alarmValue}%LEL` : (alarmValue[item.alarmValue] || '其他') })) loading.value = false // 暂停 if (messageList.value.length > 0 && messageList.value.every((item: any) => item.processStatus !== '1')) { pause() } }).catch(() => { loading.value = false }) }, 1000* 60 * 2); }) // onUnmounted(() => { // socket.destroyWebSocket() // }) onBeforeUnmount(() => { socket.destroyWebSocket() clearTimer() }) // 页面关闭删除token 为的是先登录(页面产生交互) // window.onbeforeunload = function (event: any) { // // eslint-disable-next-line no-mixed-operators // if (event.clientX > document.body.clientWidth && event.clientY < 0 || event.altKey) { // // alert("你关闭了浏览器"); // console.log('关闭') // } // else { // // alert("你正在刷新页面"); // console.log('刷新') // window.localStorage.removeItem('token') // } // } // const { proxy } = getCurrentInstance() as any </script> <template> <div class="message-container"> <alarm-dialog ref="dialogRef" /> <div v-show="messageList.length" class="message-title"> 报警({{ messageList.length }}) </div> <el-scrollbar max-height="400px"> <div v-if="!messageList.length"> <el-empty :image-size="50" description="暂无报警" /> </div> <template v-else> <div v-for="message of messageList" :key="message.id" class="message-item"> <div class="message-content" @click="detailRow(message)"> <div class="title" :title="`${message.alarmType}${message.alarmTime}`"> <div class="container"> <div :class="`mar circle circle-${message.alarmLevelName.includes('报警') || message.alarmLevelName.includes('一级') ? '1' : message.alarmLevelName.includes('预警') || message.alarmLevelName.includes('二级') ? '2' : message.alarmLevelName.includes('三级') ? '3' : 'other'}`"> 22 </div> <div class="mar mar1"> {{ message.alarmType }} </div> <div class="mar"> {{ message.ts }} </div> </div> <div class="tag"> <el-tag :type="message.processStatus !== '1' ? 'success' : 'warning'" size="small"> {{ message.processStatus === '1' ? '未读' : '已读' }} </el-tag> <!-- <el-tag type="info" size="small" style="margin-left: 5px;" @click="detailRow(message)"> 查看 </el-tag> --> </div> </div> <div class="time"> <div> {{ message.ledgerNumber }} <span v-if="message.ledgerNumber"> | </span> {{ message.devTypeName }} <span v-if="message.devTypeName"> | </span> {{ message.alarmReason }} <!-- 单位 --> <!-- <span v-if="message.alarmValue"> {{ (message?.alarmContent || '').includes('燃气') ? '%LEL' : '' }} </span> --> </div> </div> </div> </div> </template> </el-scrollbar> <div v-if="messageList.length" class="message-footer"> <div class="close1" @click="pause"> 关闭声音 </div> <!-- <div class="close" @click="dialog"> 弹窗 </div> --> <div v-if="proxy.hasPerm('/alarm/current')" class="more" @click="moreList"> 查看更多 </div> </div> </div> </template> <style lang="scss" scoped> .message-container { width: 100%; padding: 0 5px; overflow-x: hidden; .message-title { width: 100%; text-align: center; padding-bottom: 10px; font-size: 14px; border-bottom: 1px solid #ddd; } .message-item { align-items: center; border-bottom: 1px solid #ddd; padding: 8px 5px; cursor: pointer; width: 100%; display: inline-block; &:hover { background-color: #f6f6f6; } .title { display: flex; font-size: 12px; // display: inline-block; width: 100%; flex-wrap: nowrap; // width: 70%; // display: flex; .container { align-items: center; width: 85%; display: flex; overflow: hidden; /* 确保超出的内容会被裁剪 */ white-space: nowrap; /* 确保文本在一行内显示 */ text-overflow: ellipsis; /* 超出的文本部分显示为省略号 */ .circle { // flex: 1; width: 12px !important; height: 12px !important; border-radius: 50%; color: transparent; } } .tag { width: 10%; display: flex; } .mar { margin: 0 5px; } .mar1 { width: 60%; display: inline-block; overflow: hidden; /* 确保超出的内容会被裁剪 */ white-space: nowrap; /* 确保文本在一行内显示 */ text-overflow: ellipsis; } } .circle-1 { background-color: #f56c6c; } .circle-2 { background-color: #ee9611; } .circle-3 { background-color: #ffd700; } .circle-other { background-color: #8dc6ea; } .icon { width: 26px; height: 26px; margin-right: 10px; border-radius: 40px; color: #fff; background-color: var(--el-color-primary); padding: 4px; } .message-content { // flex: 1; font-size: 14px; .time { margin-top: 3px; font-size: 12px; color: #888; overflow: hidden; /* 确保超出的内容会被裁剪 */ white-space: nowrap; /* 确保文本在一行内显示 */ text-overflow: ellipsis; } } } .message-footer { // margin-top: 10px; line-height: 2; text-align: center; cursor: pointer; display: flex; // justify-content: space-around; .close1 { border: 1px solid #ddd; border-right-color: transparent; border-top-color: transparent; flex: 1; width: 50%; &:hover { color: var(--el-color-primary); } } .more { // border-left: 0.5px solid #ddd; border: 1px solid #ddd; border-top-color: transparent; flex: 1; width: 50%; &:hover { color: var(--el-color-primary); } } } } </style>