Newer
Older
sensorHubPlusFront / src / layouts / components / Tools / alarmList.vue
liyaguang 8 days ago 12 KB 系统基础修改
<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>