feat:修改
This commit is contained in:
1 parent
53f209d0d3
commit
3369a25a9a
17 files changed
+280
-66493
No files matched your search
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
-66430
File diff suppressed because it is too large.
Load diff
Binary file not shown.
|
Before Width: | Height: | Size: 147 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 138 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 145 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 154 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 161 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 154 KiB |
@@ -155,6 +155,7 @@ watch(() => [props.windowNum, state.checkedTreeNodes], (newVal, oldVal) => {
|
||||
if (newVal[0] !== oldVal[0]) {
|
||||
state.windowNum = newVal[0]
|
||||
}
|
||||
console.log("newVal:", newVal);
|
||||
setCheckedTreeExt()
|
||||
})
|
||||
|
||||
@@ -165,6 +166,8 @@ const setCheckedTreeExt = () => {
|
||||
}
|
||||
state.checkedTreeExtMap = {}
|
||||
const checkedTreeNodes = state.checkedTreeNodes.filter((item: any) => item.deep == 2)
|
||||
console.log("checkedTreeNodes:", checkedTreeNodes);
|
||||
|
||||
const maxLength = checkedTreeNodes.length
|
||||
let current = 0
|
||||
for (let i = 1; i <= targetNum; i++) {
|
||||
|
||||
@@ -1,14 +1,19 @@
|
||||
<template>
|
||||
<div class="video-container">
|
||||
<div class="video-container" :style="videoStyle" :class="{ 'preview-mode': currentWindowType === 0 }">
|
||||
<div v-if="loading" class="loading-mask">正在初始化...</div>
|
||||
<div id="video-plugin-preview-0" class="pane" />
|
||||
<div id="video-plugin-preview-3" class="pane" />
|
||||
<div id="video-plugin-preview-7" class="pane" />
|
||||
<div v-if="pageTotal > 1 && showBar && currentWindowType != 0" style="width: 100%; height: 40px;"></div>
|
||||
<div v-if="pageTotal > 1 && showBar" :style="videoPageStyle" class="video-container-page">
|
||||
<el-pagination class="video-pager" :current-page="pageCurrent" :page-size="pageSize" :total="pageTotal"
|
||||
layout="prev, next, total,jumper" small @size-change="onSizeChange" @current-change="onCurrentChange" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { onMounted, onUnmounted, ref } from "vue"
|
||||
import { onMounted, onUnmounted, ref, computed, defineEmits } from "vue"
|
||||
import { ElMessage } from "element-plus";
|
||||
import dayjs from "dayjs"
|
||||
|
||||
@@ -16,12 +21,13 @@ import * as VideoPlayer from "./lib/videoPlayer";
|
||||
|
||||
import * as settingApi from "/@/api/com/comDhSetting"
|
||||
|
||||
const emit = defineEmits(["changePage"])
|
||||
|
||||
|
||||
const TAG = "|视频预览|"
|
||||
|
||||
let VIDEO_PLAYER = null
|
||||
const divisionSettingList = [1, 2, 4, 6, 8, 9, 13, 16, 20, 25, 36, 64]
|
||||
let currentWindowType = null
|
||||
const currentWindowType = ref(null)
|
||||
let isReady = false
|
||||
/** @type {Array<() => void>} */
|
||||
let readyQueue = []
|
||||
@@ -41,6 +47,51 @@ let lastRealStartAt = 0
|
||||
let lastPlaybackSignature = ""
|
||||
let lastPlaybackStartAt = 0
|
||||
|
||||
const pageCurrent = ref(1)
|
||||
const pageSize = ref(9)
|
||||
const pageTotal = ref(0)
|
||||
|
||||
const videoPageStyle = computed(() => {
|
||||
if (currentWindowType.value == 0) {
|
||||
return {
|
||||
left: "0px",
|
||||
bottom: "0px",
|
||||
maxWidth: "400px",
|
||||
height: "40px",
|
||||
zIndex: 3,
|
||||
padding: "0px 10px",
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
left: "0px",
|
||||
right: "0px",
|
||||
bottom: "0px",
|
||||
width: "300px",
|
||||
height: "40px",
|
||||
zIndex: 3,
|
||||
padding: "0px 10px",
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
function onSizeChange(val) {
|
||||
if (pageSize.value != val) {
|
||||
pageSize.value = val
|
||||
emit("changePage", {
|
||||
current: pageCurrent.value,
|
||||
size: val,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
function onCurrentChange(val) {
|
||||
pageCurrent.value = val
|
||||
emit("changePage", {
|
||||
current: val,
|
||||
size: pageSize.value,
|
||||
})
|
||||
}
|
||||
|
||||
function waitForReady(type = props.windowType) {
|
||||
return new Promise((resolve) => {
|
||||
if (isReadyByType.get(type)) {
|
||||
@@ -59,14 +110,33 @@ function getContainerId(type) {
|
||||
|
||||
function getDivisionByCount(count) {
|
||||
const safeCount = Math.max(1, Number(count) || 1)
|
||||
const match = divisionSettingList.find((num) => num >= safeCount)
|
||||
return match || divisionSettingList[divisionSettingList.length - 1] || safeCount
|
||||
const list = Array.isArray(props.divisionSettingList) && props.divisionSettingList.length
|
||||
? props.divisionSettingList
|
||||
: [safeCount]
|
||||
const match = list.find((num) => num >= safeCount)
|
||||
return match || list[list.length - 1] || safeCount
|
||||
}
|
||||
|
||||
function getMaxDivisionCount() {
|
||||
const list = Array.isArray(props.divisionSettingList) ? props.divisionSettingList : []
|
||||
const last = list.length ? Number(list[list.length - 1]) : Number(props.division) || 1
|
||||
return Math.max(1, last || 1)
|
||||
}
|
||||
|
||||
function clampByDivision(list) {
|
||||
const max = getMaxDivisionCount()
|
||||
if (Array.isArray(list) && list.length > max) {
|
||||
console.log(TAG, "输入数量超过分屏上限,已截取", "max:", max, "prev:", list.length)
|
||||
return list.slice(0, max)
|
||||
}
|
||||
return list
|
||||
}
|
||||
|
||||
function applyDivisionByCount(count) {
|
||||
if (!VIDEO_PLAYER?.changeDivision) return
|
||||
const nextDivision = getDivisionByCount(count)
|
||||
const currentDivision = Number(VIDEO_PLAYER?.setting?.division)
|
||||
pageSize.value = nextDivision
|
||||
if (currentDivision === nextDivision) return
|
||||
VIDEO_PLAYER.changeDivision(nextDivision)
|
||||
}
|
||||
@@ -109,22 +179,6 @@ function buildPlaybackSignature(list) {
|
||||
}).join(";")
|
||||
}
|
||||
|
||||
/**
|
||||
* 将任务加入就绪队列;若已就绪则立即执行
|
||||
* @param {() => void} fn 任务函数
|
||||
*/
|
||||
function enqueueReadyTask(fn) {
|
||||
if (isReady) {
|
||||
try {
|
||||
fn()
|
||||
} catch (e) {
|
||||
console.log(TAG, "就绪任务执行失败,err:", e)
|
||||
}
|
||||
} else {
|
||||
readyQueue.push(fn)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 清空就绪队列并执行
|
||||
*/
|
||||
@@ -181,6 +235,12 @@ const props = defineProps({
|
||||
windowType: { type: Number, default: 0 },
|
||||
/** 默认展示的窗口数量 */
|
||||
division: { type: Number, default: 1 },
|
||||
/**
|
||||
* 分屏配置
|
||||
* 全部配置[1, 2, 4, 6, 8, 9, 13, 16, 20, 25, 36, 64]
|
||||
*/
|
||||
divisionSettingList: { type: Array, default: () => [1, 2, 4, 9, 16] },
|
||||
// divisionSettingList: { type: Array, default: () => [1] },
|
||||
/** 窗口拖拽(暂不支持,默认 false) */
|
||||
draggable: { type: Boolean, default: false },
|
||||
/** 是否显示底部操作栏 */
|
||||
@@ -194,7 +254,7 @@ const props = defineProps({
|
||||
async function initVideoPlayer(type = props.windowType) {
|
||||
if (players.has(type)) {
|
||||
VIDEO_PLAYER = players.get(type)
|
||||
currentWindowType = type
|
||||
currentWindowType.value = type
|
||||
isReady = !!isReadyByType.get(type)
|
||||
setActiveContainer(type)
|
||||
if (isReady) flushReadyQueue()
|
||||
@@ -248,7 +308,7 @@ async function initVideoPlayer(type = props.windowType) {
|
||||
// 底部操作栏, 选传,【true - 显示, false - 隐藏】
|
||||
showBar: props.showBar,
|
||||
// 如果DOM元素被插件挡住了,把DOM元素的类名传入。
|
||||
shieldClass: ["el-select__popper", "el-popper"],
|
||||
shieldClass: ["el-select__popper", "el-popper", "video-container-page"],
|
||||
// 如果插件要在dom内滚动,需要把DOM元素的类名传入,请查看案例-遮挡
|
||||
coverShieldClass: [],
|
||||
// 有 iframe 时,top层 的 dom 元素被插件挡住了,把DOM元素的类名传入。
|
||||
@@ -259,14 +319,16 @@ async function initVideoPlayer(type = props.windowType) {
|
||||
console.log(TAG, "创建播放器成功,versionInfo:", versionInfo)
|
||||
isReady = true
|
||||
isReadyByType.set(type, true)
|
||||
flushReadyQueue()
|
||||
const waiters = readyWaitersByType.get(type) || []
|
||||
waiters.forEach((fn) => {
|
||||
try { fn() } catch (_) { }
|
||||
})
|
||||
readyWaitersByType.delete(type)
|
||||
loading.value = false
|
||||
resolve(null)
|
||||
setTimeout(() => {
|
||||
flushReadyQueue()
|
||||
const waiters = readyWaitersByType.get(type) || []
|
||||
waiters.forEach((fn) => {
|
||||
try { fn() } catch (_) { }
|
||||
})
|
||||
readyWaitersByType.delete(type)
|
||||
loading.value = false
|
||||
resolve(null)
|
||||
}, 500)
|
||||
},
|
||||
// 创建播放器失败回调
|
||||
createError: (err) => {
|
||||
@@ -375,7 +437,7 @@ async function initVideoPlayer(type = props.windowType) {
|
||||
console.log(TAG, "RTSP录像下载失败,info:", info, "err:", err)
|
||||
}
|
||||
})
|
||||
currentWindowType = type
|
||||
currentWindowType.value = type
|
||||
players.set(type, VIDEO_PLAYER)
|
||||
console.log(TAG, "播放器已初始化,windowType:", type)
|
||||
})
|
||||
@@ -389,8 +451,8 @@ async function initVideoPlayer(type = props.windowType) {
|
||||
* @returns {boolean} 是否发生重新创建
|
||||
*/
|
||||
function ensureWindowType(target) {
|
||||
if (currentWindowType !== target) {
|
||||
console.log(TAG, "检测到窗口类型不一致,当前:", currentWindowType, "目标:", target, "正在重新创建")
|
||||
if (currentWindowType.value !== target) {
|
||||
console.log(TAG, "检测到窗口类型不一致,当前:", currentWindowType.value, "目标:", target, "正在重新创建")
|
||||
initVideoPlayer(target)
|
||||
return true
|
||||
}
|
||||
@@ -402,6 +464,7 @@ function ensureWindowType(target) {
|
||||
* @param {RealOptions[]} channels 播放参数数组
|
||||
*/
|
||||
async function startReal(channels) {
|
||||
channels = clampByDivision(channels)
|
||||
const myToken = ++latestRealToken
|
||||
if (!VIDEO_PLAYER) {
|
||||
initVideoPlayer(0)
|
||||
@@ -439,6 +502,7 @@ async function startReal(channels) {
|
||||
* @param {PlaybackOptions[]} items 回放参数数组
|
||||
*/
|
||||
async function startPlayback(items) {
|
||||
items = clampByDivision(items)
|
||||
const myToken = ++latestPlaybackToken
|
||||
if (!VIDEO_PLAYER) {
|
||||
initVideoPlayer(3)
|
||||
@@ -489,10 +553,10 @@ function updateVisible(visible) {
|
||||
async function handleVisibilityChange() {
|
||||
if (document.hidden) {
|
||||
if (!VIDEO_PLAYER) return
|
||||
if (currentWindowType === 0 && Array.isArray(lastRealRequest) && lastRealRequest.length) {
|
||||
if (currentWindowType.value === 0 && Array.isArray(lastRealRequest) && lastRealRequest.length) {
|
||||
VIDEO_PLAYER.closeVideo?.()
|
||||
}
|
||||
if ((currentWindowType === 3 || currentWindowType === 7) && Array.isArray(lastPlaybackRequest)) {
|
||||
if ((currentWindowType.value === 3 || currentWindowType.value === 7) && Array.isArray(lastPlaybackRequest)) {
|
||||
lastPlaybackRequest.forEach((item) => {
|
||||
if (item && typeof item.snum === "number") {
|
||||
VIDEO_PLAYER.controlPlayback?.({ snum: item.snum, state: 0 })
|
||||
@@ -503,12 +567,12 @@ async function handleVisibilityChange() {
|
||||
} else {
|
||||
if (!VIDEO_PLAYER) return
|
||||
VIDEO_PLAYER.show?.()
|
||||
if (currentWindowType === 0 && Array.isArray(lastRealRequest) && lastRealRequest.length) {
|
||||
if (currentWindowType.value === 0 && Array.isArray(lastRealRequest) && lastRealRequest.length) {
|
||||
await waitForReady(0)
|
||||
await startReal(lastRealRequest)
|
||||
}
|
||||
if ((currentWindowType === 3 || currentWindowType === 7) && Array.isArray(lastPlaybackRequest)) {
|
||||
await waitForReady(currentWindowType)
|
||||
if ((currentWindowType.value === 3 || currentWindowType.value === 7) && Array.isArray(lastPlaybackRequest)) {
|
||||
await waitForReady(currentWindowType.value)
|
||||
lastPlaybackRequest.forEach((item) => {
|
||||
if (item && typeof item.snum === "number") {
|
||||
VIDEO_PLAYER.controlPlayback?.({ snum: item.snum, state: 1 })
|
||||
@@ -595,6 +659,13 @@ async function closeVideo() {
|
||||
}
|
||||
}
|
||||
|
||||
function setTotal(total) {
|
||||
if (total > 0) {
|
||||
pageTotal.value = total
|
||||
console.log(TAG, "设置视频总数,total:", total)
|
||||
}
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
document.addEventListener("visibilitychange", handleVisibilityChange)
|
||||
})
|
||||
@@ -623,6 +694,7 @@ defineExpose({
|
||||
startPlayback,
|
||||
updateVisible,
|
||||
closeVideo,
|
||||
setTotal,
|
||||
})
|
||||
</script>
|
||||
|
||||
@@ -631,16 +703,18 @@ defineExpose({
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
background: #2F3235;
|
||||
}
|
||||
|
||||
.pane {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
flex: 1;
|
||||
display: none;
|
||||
}
|
||||
|
||||
@@ -662,4 +736,39 @@ defineExpose({
|
||||
z-index: 2;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.video-container-page {
|
||||
position: absolute;
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
:deep(.video-pager) {
|
||||
background: #2F3236;
|
||||
border-radius: 20px;
|
||||
padding: 6px 10px;
|
||||
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
|
||||
}
|
||||
|
||||
:deep(.el-pagination) {
|
||||
margin: 0 !important;
|
||||
}
|
||||
|
||||
:deep(.el-pagination .btn-prev),
|
||||
:deep(.el-pagination .btn-next),
|
||||
:deep(.el-pagination.is-background .el-pager li) {
|
||||
background-color: transparent;
|
||||
color: #c9d8e3;
|
||||
}
|
||||
|
||||
:deep(.el-pagination .el-select .el-select__wrapper) {
|
||||
background-color: transparent;
|
||||
border-color: #B4BAC2;
|
||||
color: #c9d8e3;
|
||||
}
|
||||
|
||||
@media (max-width: 1150px) {
|
||||
.preview-mode .video-container-page {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
@@ -27,9 +27,9 @@
|
||||
<el-table-column prop="channelName" width="160" label="通道名" />
|
||||
<el-table-column prop="deviceIp" width="120" label="ip" />
|
||||
<el-table-column prop="devicePort" width="120" label="端口" />
|
||||
<el-table-column prop="devicePort" width="120" label="状态">
|
||||
<el-table-column prop="deviceIsOnline" width="120" label="状态">
|
||||
<template #default="{ row }">
|
||||
<tag-online :isOnline="row.isOnline == 1" />
|
||||
<tag-online :isOnline="row.deviceIsOnline == 1" />
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table-column>
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
</el-tree>
|
||||
</div>
|
||||
<div class="flex-1 overflow-hidden video-container">
|
||||
<RtspPluginVideo ref="previewVideoRef" style="height: 500px;" />
|
||||
<RtspPluginVideo ref="previewVideoRef" style="height: 500px;" @changePage="videoChangePage" />
|
||||
</div>
|
||||
</div>
|
||||
<template #footer>
|
||||
@@ -40,6 +40,8 @@ const state = reactive({
|
||||
channelList: [],
|
||||
loading: false,
|
||||
treeLoading: false,
|
||||
current: 1,
|
||||
size: 64,
|
||||
})
|
||||
|
||||
const detail = reactive<any>({})
|
||||
@@ -63,6 +65,32 @@ const openDialog = async (id: string) => {
|
||||
await getDeviceChannelList()
|
||||
};
|
||||
|
||||
const videoChangePage = async ({ current, size }: any) => {
|
||||
state.current = current
|
||||
state.size = size
|
||||
console.log("state:", state);
|
||||
const channelList: any[] = []
|
||||
for (let i = 0; i < channel.list.length; i++) {
|
||||
const v: any = channel.list[i]
|
||||
channelList.push({
|
||||
channelId: v.channelCode,
|
||||
channelName: v.channelName,
|
||||
// 默认辅码流
|
||||
streamType: 2
|
||||
})
|
||||
}
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
const pageList = channelList.slice(start, end).map((v: any, idx: number) => ({
|
||||
...v,
|
||||
snum: idx
|
||||
}))
|
||||
await previewVideoRef.value?.closeVideo()
|
||||
previewVideoRef.value?.setTotal(channelList.length)
|
||||
previewVideoRef.value?.startReal(pageList)
|
||||
}
|
||||
|
||||
// 点击树
|
||||
const handleNodeClick = (e: any) => {
|
||||
if (e.id == -1) {
|
||||
@@ -78,7 +106,15 @@ const handleNodeClick = (e: any) => {
|
||||
streamType: 2
|
||||
})
|
||||
}
|
||||
previewVideoRef.value?.startReal(channelList)
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
const pageList = channelList.slice(start, end).map((v: any, idx: number) => ({
|
||||
...v,
|
||||
snum: idx
|
||||
}))
|
||||
previewVideoRef.value?.setTotal(channelList.length)
|
||||
previewVideoRef.value?.startReal(pageList)
|
||||
return
|
||||
}
|
||||
const targetChannel = channel.list.find((v: any) => v.channelCode == e.channelCode)
|
||||
@@ -146,7 +182,12 @@ const getDeviceChannelList = async () => {
|
||||
streamType: 2
|
||||
})
|
||||
}
|
||||
previewVideoRef.value?.startReal(channelList)
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
const pageList = channelList.slice(start, end)
|
||||
previewVideoRef.value?.setTotal(channelList.length)
|
||||
previewVideoRef.value?.startReal(pageList)
|
||||
} catch (error: any) {
|
||||
console.error("|查询通道树|,意外的错误", error);
|
||||
useMessage().error(error?.msg ?? "意外的错误");
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
<div class="flex-1 overflow-hidden video-container" style="height: 500px;">
|
||||
<RtspPluginVideo ref="replayVideoRef" style="height: 500px;" />
|
||||
<RtspPluginVideo ref="replayVideoRef" style="height: 500px;" @changePage="videoChangePage" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -73,7 +73,9 @@ const state = reactive<any>({
|
||||
treeLoading: false,
|
||||
numList: [1, 4, 9, 16, 25],
|
||||
type: "device",
|
||||
code: null
|
||||
code: null,
|
||||
current: 1,
|
||||
size: 64,
|
||||
})
|
||||
|
||||
const detail = reactive<any>({})
|
||||
@@ -84,7 +86,9 @@ const queryForm = reactive({
|
||||
isInclude: null,
|
||||
streamType: "0",
|
||||
recordSource: "2",
|
||||
videoDateList: getDefaultDateRange()
|
||||
videoDateList: getDefaultDateRange(),
|
||||
current: 1,
|
||||
size: 64,
|
||||
})
|
||||
|
||||
const channel = reactive<any>({
|
||||
@@ -136,6 +140,37 @@ const handleClose = () => {
|
||||
state.dialogVisible = false
|
||||
}
|
||||
|
||||
const videoChangePage = async ({ current, size }: any) => {
|
||||
state.current = current
|
||||
state.size = size
|
||||
console.log("state:", state);
|
||||
const channelList: any[] = []
|
||||
for (let i = 0; i < channel.list.length; i++) {
|
||||
const v: any = channel.list[i]
|
||||
channelList.push({
|
||||
channelId: v.channelCode,
|
||||
channelName: v.channelName,
|
||||
snum: i,
|
||||
// 默认辅码流
|
||||
streamType: Number(queryForm.streamType),
|
||||
// 默认前3天(格式YYYY-MM-DD HH:mm:ss)
|
||||
startTime: queryForm.videoDateList[0],
|
||||
endTime: queryForm.videoDateList[1],
|
||||
// 录像来源:2-设备录像 3-中心录像
|
||||
recordSource: Number(queryForm.recordSource)
|
||||
})
|
||||
}
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
const pageList = channelList.slice(start, end).map((v: any, idx: number) => ({
|
||||
...v,
|
||||
snum: idx
|
||||
}))
|
||||
await replayVideoRef.value?.closeVideo()
|
||||
replayVideoRef.value?.setTotal(channelList.length)
|
||||
replayVideoRef.value?.startPlayback(pageList)
|
||||
}
|
||||
// 点击树
|
||||
const handleNodeClick = (e: any) => {
|
||||
if (e.id == -1) {
|
||||
@@ -156,8 +191,15 @@ const handleNodeClick = (e: any) => {
|
||||
recordSource: Number(queryForm.recordSource)
|
||||
})
|
||||
}
|
||||
replayVideoRef.value?.closeVideo()
|
||||
replayVideoRef.value?.startPlayback([...channelList])
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
const pageList = channelList.slice(start, end).map((v: any, idx: number) => ({
|
||||
...v,
|
||||
snum: idx
|
||||
}))
|
||||
replayVideoRef.value?.setTotal(channelList.length)
|
||||
replayVideoRef.value?.startPlayback(pageList)
|
||||
return
|
||||
}
|
||||
const targetChannel = channel.list.find((v: any) => v.channelCode == e.channelCode)
|
||||
@@ -175,7 +217,6 @@ const handleNodeClick = (e: any) => {
|
||||
recordSource: Number(queryForm.recordSource)
|
||||
}
|
||||
]
|
||||
replayVideoRef.value?.closeVideo()
|
||||
replayVideoRef.value?.startPlayback([...channelList])
|
||||
}
|
||||
|
||||
@@ -251,8 +292,17 @@ const getDeviceChannelList = async (codeStr: any) => {
|
||||
recordSource: Number(queryForm.recordSource)
|
||||
})
|
||||
}
|
||||
replayVideoRef.value?.closeVideo()
|
||||
replayVideoRef.value?.startPlayback([...channelList])
|
||||
// 按照分页截取
|
||||
const start = (state.current - 1) * state.size
|
||||
const end = start + state.size
|
||||
|
||||
const pageList = channelList.slice(start, end).map((v: any, idx: number) => ({
|
||||
...v,
|
||||
snum: idx
|
||||
}))
|
||||
|
||||
replayVideoRef.value?.setTotal(channelList.length)
|
||||
replayVideoRef.value?.startPlayback(pageList)
|
||||
} catch (error: any) {
|
||||
console.error(error);
|
||||
useMessage().error(error?.msg ?? "意外的错误");
|
||||
|
||||
@@ -10,7 +10,8 @@
|
||||
<el-tab-pane v-for="(v, i) in data.tabs" :key="v.name" :label="v.label" :name="v.name" />
|
||||
</el-tabs>
|
||||
<div class="w-full h-full flex-1 overflow-hidden" v-loading="videoLoading">
|
||||
<RtspPluginVideo ref="previewVideoRef" v-if="state.currentTab == 'PREVIEW'" />
|
||||
<RtspPluginVideo ref="previewVideoRef" @changePage="videoChangePage"
|
||||
:divisionSettingList="divisionSettingList" v-if="state.currentTab == 'PREVIEW'" />
|
||||
<div class="w-full h-full flex flex-col" v-if="state.currentTab == 'REPLAY'">
|
||||
<el-row shadow="hover" class="ml10">
|
||||
<el-form :model="state.replayForm" ref="queryRef" :inline="true"
|
||||
@@ -40,7 +41,8 @@
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</el-row>
|
||||
<RtspPluginVideo class="flex-1 overflow-hidden" ref="replayVideoRef" />
|
||||
<RtspPluginVideo class="flex-1 overflow-hidden" ref="replayVideoRef"
|
||||
:divisionSettingList="divisionSettingList" @changePage="videoChangePage" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -63,6 +65,8 @@ const queryRef = ref()
|
||||
|
||||
const videoLoading = ref(false)
|
||||
|
||||
const divisionSettingList = ref([9])
|
||||
|
||||
// 定义查询字典
|
||||
const { dh_replay_source, dh_video_stream_type } = useDict("dh_replay_source", "dh_video_stream_type")
|
||||
|
||||
@@ -79,7 +83,9 @@ const data = {
|
||||
]
|
||||
}
|
||||
|
||||
const state = reactive({
|
||||
const state = reactive<any>({
|
||||
current: 1,
|
||||
size: 64,
|
||||
currentTab: data.tabs[0].name,
|
||||
deviceTreeMap: [],
|
||||
channelCodeList: [],
|
||||
@@ -96,10 +102,6 @@ onMounted(() => {
|
||||
|
||||
})
|
||||
|
||||
const windowNumChanged = (num: any) => {
|
||||
state.windowNum = num
|
||||
}
|
||||
|
||||
// 树节点选择时
|
||||
const handleGetSelectNode = async (curClickedNode: any, checkedTreeNodes: any, isDeepTree: boolean, selectMap: any) => {
|
||||
if (!checkedTreeNodes || !checkedTreeNodes.length) return
|
||||
@@ -117,20 +119,28 @@ function tabClick(e: any) {
|
||||
init(e.paneName)
|
||||
}
|
||||
|
||||
const videoChangePage = ({ current, size }: any) => {
|
||||
state.current = current
|
||||
state.size = size
|
||||
init(state.currentTab)
|
||||
}
|
||||
|
||||
function init(type: string) {
|
||||
nextTick(async () => {
|
||||
videoLoading.value = true
|
||||
await new Promise(resolve => setTimeout(resolve, 500))
|
||||
// 查询通道列表
|
||||
let channelRecords = []
|
||||
let total = 0
|
||||
try {
|
||||
const _params = {
|
||||
current: 1,
|
||||
size: 64,
|
||||
current: state.current,
|
||||
size: state.size,
|
||||
deviceTreeMap: state.deviceTreeMap ?? null
|
||||
}
|
||||
let { code, data } = await deviceChannelApi.getChannelPage(_params);
|
||||
if (code != 0) throw new Error("")
|
||||
total = data?.total ?? 0
|
||||
if (data.records && data.records.length) {
|
||||
channelRecords = data.records
|
||||
}
|
||||
@@ -150,7 +160,9 @@ function init(type: string) {
|
||||
streamType: 2
|
||||
})
|
||||
}
|
||||
state.windowNum = doorChannelList.length > 9 ? 9 : doorChannelList.length
|
||||
previewVideoRef?.value?.closeVideo()
|
||||
previewVideoRef?.value?.setTotal(total)
|
||||
previewVideoRef.value?.startReal([...doorChannelList])
|
||||
break;
|
||||
case 'REPLAY':
|
||||
@@ -170,7 +182,9 @@ function init(type: string) {
|
||||
recordSource: Number(state.replayForm.recordSource)
|
||||
})
|
||||
}
|
||||
state.windowNum = replayChannelList.length > 9 ? 9 : replayChannelList.length
|
||||
replayVideoRef?.value?.closeVideo()
|
||||
replayVideoRef?.value?.setTotal(total)
|
||||
replayVideoRef.value?.startPlayback([...replayChannelList])
|
||||
break;
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user