Newer
Older
smartwell_front / src / views / home / station / video / index.vue
liyaguang 26 days ago 9 KB 细节修复
<!--
  Description: 场站管理-视频轮询
  Author: 李亚光
  Date: 2024-09-05
 -->
<script lang="ts" setup name="StationDeviceVideo">
import { ElMessage } from 'element-plus'
import { toTreeList, findPid, findParentPids1 } from '@/utils/structure'
import { getDeptTreeList } from '@/api/system/dept'
import { getDeptStation } from '@/api/home/station/station'
import type { TreeNodeData } from 'element-plus/es/components/tree-v2/src/types'
import { getDeviceID, getVideoUrl, getVideoBackUrl } from '@/api/home/station/video'
import indexDB from '@/utils/indexDB'
import player from '@/components/HKplayer/index.vue'
import { indexDBHandler } from '@/utils/sessionData'
const loadingTree = ref<boolean>(false)
const searchQuery = ref('')
const defaultProps = {
  children: 'children',
  label: 'name',
  value: 'id'
}


const playRef1 = ref()
const playRef2 = ref()
const playRef3 = ref()
const playRef4 = ref()
const playerVideo = (devcode: string, playRef) => {
  if (!devcode) {
    ElMessage.warning('设备编号为空')
    return
  }
  getDeviceID(devcode).then(res => {
    const deviceId = res.data
    if (!deviceId) {
      ElMessage('设备ID为空,无法获取视频')
      return
    }
    getVideoUrl({
      deviceId: deviceId,
      streamType: '0'
    }).then(res => {
      const videoUrl = res.data
      if (!videoUrl) {
        ElMessage('视频地址为空,无法播放')
        return
      }
      // 播放视频
      unref(playRef).playerFun.createPlayer(videoUrl, 1)
    })
  }).catch(() => {
    ElMessage.warning('获取设备ID失败')
  })
}
const treeData = ref<any[]>([])
const videoList = ref([])
const expandedKeys = ref<string[]>([]) // 默认展开的节点
const treeRef = ref()
// 点击树形结构
const handleNodeClick = (data: any, status: boolean) => {
  if (!data.DEVCODE && status) {
    ElMessage.warning('设备编号为空')
    treeRef.value.setChecked(data.id, false)
    return
  }
  if (data.id.includes('station') && status) {
    if (videoList.value.filter((item: any) => item.name).length === 4) {
      ElMessage.warning('最多同时查看4台设备')
      treeRef.value.setChecked(data.id, false)
      return
    }
    const player = () => {
      console.log(videoList.value)
      const index = videoList.value.findIndex((item: any) => !item.name)
      console.log(index, '需要播放')
      if (index !== -1) {
        videoList.value[index] = data
      }
      else {
        videoList.value.push(data)
      }
      setTimeout(() => {
        const plater = {
          0: playRef1.value,
          1: playRef2.value,
          2: playRef3.value,
          3: playRef4.value,
        }
        playerVideo(data.DEVCODE, index === -1 ? plater[videoList.value.length - 1] : plater[index])
      }, 100)
    }
    if (videoList.value.filter((item: any) => item.name).length < 4) {
      player()
    }
    else {
      player()
      // treeRef.value.setChecked(videoList.value[0].id, false)
      // unref(playerRef.value[0]).playerFun.stopAllPlay()
      // videoList.value.shift()
      // setTimeout(() => {
      //   player()
      // })
    }
  }
  else if (data.id.includes('station') && !status) {
    const index = videoList.value.findIndex((item) => item.id === data.id)
    videoList.value[index] = {}
  }
}
// 查询组织机构
const search = (value: string) => {
  treeRef.value!.filter(value)
}
const filterTree = (query: string, node: TreeNodeData) => {
  return node.name!.includes(query)
}
// 获取组织列表树数据
const fetchTreeData = () => {
  loadingTree.value = true
  const setData = (data1: any[], data2: any[]) => {
    const data = data2.filter((item: any) => item.DEPTID).map((item: any) => ({
      ...item,
      checked: false,
      code: '',
      id: `station-${item.DEVCODE}-${item.LEDGER_CODE}`,
      // id: `station-${'WXD7507'}-${item.LEDGER_CODE}`,
      name: `${item.LEDGER_NAME}云台`,
      open: false,
      pCodes: '',
      pid: item.DEPTID,
      value: '',
    }))
    // ...data
    const all = [...data1.map(item => ({ ...item, disabled: true })).filter((item: any) => item.pid), ...data]
    expandedKeys.value = []
    all.forEach(element => {
      if (!element.id.includes('station')) {
        expandedKeys.value.push(element.id)
      }
    })

    treeData.value = toTreeList(all, '0', true)
    // 设置默认选中
    setTimeout(() => {
      // data
      // treeRef.value.setCurrentKey()
    })
  }
  const fetch = async () => {
    try {
      const res = await getDeptTreeList({ deptType: '' })
      indexDBHandler('all-dept-list', JSON.stringify(res.data))
      const res1 = await getDeptStation({})
      indexDBHandler('all-video-list', JSON.stringify(res1.data))
      setData(res.data, res1.data)
      loadingTree.value = false
    } catch (error) {
      loadingTree.value = false
    }
  }
  indexDB.getAll().then(allData => {
    if (allData.filter((item: any) => item.name === 'all-dept-list').length) {
      const list = JSON.parse(allData.filter((item: any) => item.name === 'all-dept-list')[0].data).filter((item: any) => item.id !== '0')
      if (allData.filter((item: any) => item.name === 'all-video-list').length) {
        const list1 = JSON.parse(allData.filter((item: any) => item.name === 'all-video-list')[0].data)
        setData(list, list1)
        loadingTree.value = false
      }
      else {
        fetch()
      }
    }
    else {
      fetch()
    }
  })

}
// 视频播放失败
const playerError = (info: string) => {
  ElMessage.error(info)
}
const treeHeight = ref(0)
const calcHeight = () => {
  const ele = document.getElementsByClassName('el-user-dept-scroll-video')[0] as HTMLElement
  if (ele) {
    treeHeight.value = ele.offsetHeight
  }
}
onMounted(() => {
  calcHeight()
  setTimeout(() => {
    fetchTreeData()
  }, 500)
})
window.addEventListener('resize', () => {
  calcHeight()
})
onBeforeUnmount(() => {
  window.addEventListener('resize', () => { })
})
</script>

<template>
  <app-container style="overflow: hidden;">
    <div class="container">
      <!-- 左侧组织机构 -->
      <div v-loading="loadingTree" class="left-container">
        <div class="dept-div">
          <el-card class="box-card" shadow="always">
            <template #header>
              <div class="clearfix">
                <!-- <div>监控点列表</div> -->
                <el-input v-model="searchQuery" @change="search" placeholder="请输入搜索内容" clearable />
              </div>
            </template>
            <el-scrollbar height="100%" class="user-dept-scroll el-user-dept-scroll-video">
              <el-tree-v2 v-if="treeData.length" ref="treeRef" :data="treeData" :props="defaultProps"
                :height="treeHeight" :check-on-click-node="true" :default-expanded-keys="expandedKeys"
                @check-change="handleNodeClick" :filter-method="filterTree" empty-text="暂无组织数据" show-checkbox
                :highlight-current="true" />
            </el-scrollbar>
          </el-card>
        </div>
      </div>
      <!-- 右侧表格 -->
      <div ref="tableContainer" class="table">
        <el-card class="box-card" shadow="always">
          <div style="display: flex;flex-wrap: wrap;justify-content: space-around;">
            <div class="video mar-bottom">
              <span class="title">{{ videoList[0]?.name }}</span>
              <player v-if="videoList[0]?.name" :playId="`video-player-${0}`" ref="playRef1" @error="playerError" />
              <div v-else style="width: 100%;height: 100%;background-color: #000;"></div>
            </div>
            <div class="video mar-bottom">
              <span class="title">{{ videoList[1]?.name }}</span>
              <player v-if="videoList[1]?.name" :playId="`video-player-${1}`" ref="playRef2" @error="playerError" />
              <div v-else style="width: 100%;height: 100%;background-color: #000;"></div>
            </div>
            <div class="video mar-bottom">
              <span class="title">{{ videoList[2]?.name }}</span>
              <player v-if="videoList[2]?.name" :playId="`video-player-${2}`" ref="playRef3" @error="playerError" />
              <div v-else style="width: 100%;height: 100%;background-color: #000;"></div>
            </div>
            <div class="video mar-bottom">
              <span class="title">{{ videoList[3]?.name }}</span>
              <player v-if="videoList[3]?.name" :playId="`video-player-${3}`" ref="playRef4" @error="playerError" />
              <div v-else style="width: 100%;height: 100%;background-color: #000;"></div>
            </div>
            <!-- <div v-for="(item, index) in videoList" class="video" :class="`${index <= 2 ? 'mar-bottom' : ''}`">
              <span class="title">{{ item.name }}</span>
              <player :playId="`video-player-${index}`" ref="playerRef" @error="playerError" />
            </div>
            <div v-for="item in 4 - videoList.length" :key="item" class="video"
              :class="`${item <= 2 ? 'mar-bottom' : ''}`" style="background-color: #000;"></div> -->
          </div>
        </el-card>
      </div>
    </div>
  </app-container>
</template>

<style lang="scss" scoped>
// ::v-deep(.el-tree-node__content) {
//   i,label {
//     display: none;
//   }
// }
// 样式
.container {
  width: 100%;
  display: flex;

  .left-container {
    width: 22%;
  }

  :deep(.el-radio__label) {
    display: none;
  }

  .table {
    width: 78%;
  }
}

.video {
  width: 49%;
  height: 40vh;
  position: relative;

  .title {
    position: absolute;
    top: 5px;
    right: 5px;
    text-align: right;
    color: #fff;
    z-index: 9;
    left: 10px;
  }
}

.mar-bottom {
  margin-bottom: 8px;
}

.dept-div {
  padding-right: 12px;

  :deep(.el-card) {
    height: 85vh;
    background-color: #fff;
  }

  .box-card {
    width: 100%;

    .user-dept-scroll {
      width: 100%;
      height: calc(100vh - 120px);
    }
  }
}
</style>