Browse Source

添加录制

master
chendingwei 2 years ago
parent
commit
37558d3f26
  1. 1
      components.d.ts
  2. 5
      src/store/index.ts
  3. 66
      src/views/page/Aside/cameraRightMenu.vue
  4. 164
      src/views/page/cameraCenter.vue

1
components.d.ts

@ -17,6 +17,7 @@ declare module '@vue/runtime-core' {
AMenu: typeof import('ant-design-vue/es')['Menu']
AMenuItem: typeof import('ant-design-vue/es')['MenuItem']
AModal: typeof import('ant-design-vue/es')['Modal']
APopconfirm: typeof import('ant-design-vue/es')['Popconfirm']
ARow: typeof import('ant-design-vue/es')['Row']
ASelect: typeof import('ant-design-vue/es')['Select']
ATree: typeof import('ant-design-vue/es')['Tree']

5
src/store/index.ts

@ -20,6 +20,8 @@ export const useStore = defineStore('Index', {
labelGroupList: [],
//是否截图
screenshot:<boolean>false,
//是否录制
record:<boolean>false,
}
},
@ -58,5 +60,8 @@ export const useStore = defineStore('Index', {
updateScreenshot(screenshot: any) {
this.screenshot = screenshot
},
updateRecord(record: any) {
this.record = record
},
},
})

66
src/views/page/Aside/cameraRightMenu.vue

@ -5,7 +5,8 @@
<ul>
<!-- <p @click="addLabelFn('视频标签')">视频标签</p>
<p @click="addLabelFn('建筑标签')">建筑标签</p> -->
<p class="labelList" v-for="item in labelList" :key="item.id" @click="addLabelFn(item.name,item.id)">{{ item.name }}</p>
<p class="labelList" v-for="item in labelList" :key="item.id"
@click="addLabelFn(item.name, item.id)">{{ item.name }}</p>
<!-- <p></p> -->
</ul>
</template>
@ -16,8 +17,8 @@
<div class="buttomItem" title="截图" @click="clickScreenshot">
<div class="buttomName">截图</div>
</div>
<div class="buttomItem" title="录像">
<div class="buttomName">录像</div>
<div class="buttomItem" :title="recordText" @click="clickRecord">
<div class="buttomName">{{ recordText }}</div>
</div>
<div class="buttomItem" title="3D缩放">
<div class="buttomName">3D缩放</div>
@ -35,8 +36,8 @@
<Popover placement="left" trigger="hover">
<template #content>
<ul>
<p class="setup" @click="openSetting('user')">用户设置</p>
<p class="setup" @click="openSetting('camera')">相机设置</p>
<p class="setup" @click="openSetting('user')">用户设置</p>
<p class="setup" @click="openSetting('camera')">相机设置</p>
</ul>
</template>
<div class="buttomItem">
@ -44,16 +45,11 @@
</div>
</Popover>
</div>
<a-modal
v-model:visible="visible"
:title="type == 'user'? '用户设置': '相机设置'"
width="90%"
wrapClassName="full-modal"
:footer="null"
>
<userEdit v-if="type == 'user'"></userEdit>
<CameraEdit v-if="type == 'camera'"></CameraEdit>
</a-modal>
<a-modal v-model:visible="visible" :title="type == 'user' ? '用户设置' : '相机设置'" width="90%" wrapClassName="full-modal"
:footer="null">
<userEdit v-if="type == 'user'"></userEdit>
<CameraEdit v-if="type == 'camera'"></CameraEdit>
</a-modal>
</template>
@ -64,27 +60,40 @@ import { Popover } from 'ant-design-vue';
import { useStore } from '@/store/index';
import * as markGroupApi from '@/axios/cameraMark/markGroupApi';
import CameraEdit from './rightMenuItem/cameraEdit.vue';
import { storeToRefs } from 'pinia';
let piniaStore = useStore();
const visible = ref(false)
const labelList :any=ref([])
const labelList: any = ref([])
const type = ref('') //
function openSetting(editType:string) {
const recordText = ref('录制')//
const record = storeToRefs(piniaStore).record
function openSetting(editType: string) {
visible.value = !visible.value
type.value = editType
}
let piniaStore = useStore();
function addLabelFn(str: string,id:number) {
piniaStore.updateIsAddLabel({ cmMarkGroupId:id,labelType: str, isAddLabel: true })
function addLabelFn(str: string, id: number) {
piniaStore.updateIsAddLabel({ cmMarkGroupId: id, labelType: str, isAddLabel: true })
}
function clickScreenshot(){
//
function clickScreenshot() {
piniaStore.updateScreenshot(true)
}
//
function clickRecord() {
piniaStore.updateRecord(!record.value)
if (record.value) {
recordText.value = "停止录制"
} else {
recordText.value = "录制"
}
}
function init() {
markGroupApi.GetList().then((res: any) => {
console.log(res, 'markGroupApi');
let result = res.data
if (result.code == 200) {
labelList.value=result.data
labelList.value = result.data
piniaStore.updateLabelGroupList(result.data)
}
})
@ -148,14 +157,15 @@ onMounted(() => {
z-index: 2;
font-size: 0.8em;
}
ul{
ul {
padding: 0;
margin: 0;
p:last-child{
margin: 0;
}
}
p:last-child {
margin: 0;
}
}
</style>
<style lang="less" >
.full-modal {

164
src/views/page/cameraCenter.vue

@ -6,13 +6,10 @@
@mousedown="mouseDownVideo">
</video> -->
<div id="videoPlayer" @mousedown="mouseDownVideo"></div>
<div v-for="item in labelList"
:class="`labels ${item.groupName == '视频标签' ? 'lavels-video' : 'lavels-build'}`"
:key="item.id"
:id="item.id"
:style="`top:${canvasHeight * item.canvasTopRatio}px;left:${canvasWidth * item.canvasLeftRatio}px`"
@click="itemClick(item)"
>
<div v-for="item in labelList" :class="`labels ${item.groupName == '视频标签' ? 'lavels-video' : 'lavels-build'}`"
:key="item.id" :id="item.id"
:style="`top:${canvasHeight * item.canvasTopRatio}px;left:${canvasWidth * item.canvasLeftRatio}px`"
@click="itemClick(item)">
<a-dropdown :trigger="['contextmenu']">
<div class="labels-item" v-if="item.groupName == '视频标签'">
<!-- <div class="labels-item" v-if="item.inFlag"> -->
@ -35,9 +32,22 @@
</a-menu>
</template>
</a-dropdown>
<a-popconfirm
placement="bottomRight"
ok-text="Yes"
cancel-text="No"
:visible="item.windowVisible"
@cancel="windowCancel(item)"
>
<template #title>
<cameraWindow :itemData="item"></cameraWindow>
</template>
<!-- <a-button>TL</a-button> -->
</a-popconfirm>
</div>
<div class="labels lavels-build" v-if="addLabel.isAddLabel && addLabel.labelType == '建筑标签'"
:style="` pointer-events: none;top:${addLabelTop}px;left:${addLabelLeft}px`">
:style="` pointer-events: none;top:${addLabelTop}px;left:${addLabelLeft}px`">
<div class="labels-item" alt="">
<img src="@/assets/images/buildLabelLine.png">
<div>
@ -47,7 +57,7 @@
</div>
</div>
<div class="labels lavels-video" v-if="addLabel.isAddLabel && addLabel.labelType == '视频标签'"
:style="`top:${addLabelTop}px;left:${addLabelLeft}px`">
:style="`top:${addLabelTop}px;left:${addLabelLeft}px`">
<div class="labels-item">
<!-- <div class="labels-item" v-if="item.inFlag"> -->
<div>
@ -66,15 +76,15 @@
<script setup lang='ts'>
////@ts-nocheck
import {ExclamationCircleOutlined} from '@ant-design/icons-vue';
import {Modal} from 'ant-design-vue';
import {ref, h, onMounted, getCurrentInstance, ComponentInternalInstance, onUnmounted, watch, createVNode} from "vue";
import { ExclamationCircleOutlined } from '@ant-design/icons-vue';
import { Modal } from 'ant-design-vue';
import { ref, h, onMounted, getCurrentInstance, ComponentInternalInstance, onUnmounted, watch, createVNode } from "vue";
import * as markLabelApi from '@/axios/cameraMark/markLabelApi';
import * as markSearchApi from '@/axios/core/markSearchApi';
import * as zlmApi from '@/axios/core/zlmApi';
import {useStore} from '@/store/index';
import {apiUrl} from "@/axios";
import {storeToRefs} from 'pinia';
import { useStore } from '@/store/index';
import { apiUrl } from "@/axios";
import { storeToRefs } from 'pinia';
import Msg from "@/utils/message";
import CameraLeftMenu from '@/views/page/Aside/cameraLeftMenu.vue'
import CameraRightMenu from '@/views/page/Aside/cameraRightMenu.vue'
@ -82,8 +92,7 @@ import LabelEditModel from '@/views/page/Model/LabelEditModel.vue'
import cameraWindow from '@/views/page/cameraWindow.vue'
import popup from "@/utils/popup";
import VideoControlSimple from './VideoControl/VideoControlSimple.vue';
const {proxy} = getCurrentInstance() as ComponentInternalInstance;
const { proxy } = getCurrentInstance() as ComponentInternalInstance;
let piniaStore = useStore();
let player = <HTMLVideoElement>document.querySelector('#videoPlayer')
let canvasWidth = ref(0)
@ -94,6 +103,7 @@ let cameraMap = storeToRefs(piniaStore).cameraMap
let isActiveChoose = ref(false)
let labelList = ref<any[]>([])
let addLabel = storeToRefs(piniaStore).addLabel
let screenshot = storeToRefs(piniaStore).screenshot
let addLabelLeft = ref(0);
let addLabelTop = ref(0);
var jessibuca = ref();
@ -106,6 +116,22 @@ onMounted(() => {
}
})
watch(screenshot, (newVal, oldVal) => {
if (newVal) {
console.log(123);
//jessibuca.value.isPlaying()
if (!jessibuca.value.isPlaying()) {
Msg.info("请先选择监控画面")
piniaStore.updateScreenshot(false)
return
}
jessibuca.value.screenshot("", "png", 1)
piniaStore.updateScreenshot(false)
}
})
watch(curSelectKey, (newVal, oldVal) => {
switchCamera(newVal)
})
@ -115,6 +141,7 @@ watch(closeVideoKey, (newVal, oldVal) => {
piniaStore.updateCloseVideoKey("")
piniaStore.updateCurSelectKey("")
}
})
watch(addLabel, (newVal, oldVal) => {
if (newVal.isAddLabel) {
@ -126,7 +153,6 @@ watch(addLabel, (newVal, oldVal) => {
}
}
})
function closeVideo() {
jessibuca.value.close();
labelList.value = []
@ -134,75 +160,53 @@ function closeVideo() {
//
function deleteLabel(id: number) {
markLabelApi.Delete({id}).then((res: any) => {
if (judgeResponse(res)) return;
let flag = res.data.data;
let msg = flag === true ? "删除成功" : "删除失败";
if (flag) {
labelList.value = labelList.value.filter((element: any) => {
return element.id != id;
});
Msg.success("删除成功");
} else {
Msg.error("删除失败");
markLabelApi.Delete({ id }).then((res: any) => {
console.log(res.data);
if (res.data.code == 200) {
let msg = res.data.data == true ? "删除成功" : "删除失败"
if (res.data.data) {
labelList.value = labelList.value.filter((element: any) => {
return element.id != id
});
Msg.success("删除成功")
return
}
}
Msg.error("删除失败")
})
}
//
function itemClick(item: any) {
// console.log("",item);
popup("监控画面", [h(cameraWindow, {windowData: item})], "cameraWindow");
// popup("", [h(cameraWindow, { windowData: item })], "cameraWindow");
//
item.windowVisible = true
}
//
function windowCancel(item: any){
item.windowVisible = false
}
function loadVideoPlayer() {
var showOperateBtns = false; //
var forceNoOffscreen = true; //
jessibuca.value = new Jessibuca({
container: player,
videoBuffer: 0.2, //
isResize: false,
text: "",
loadingText: "",
autoWasm: true,
useMSE: false,
debug: true,
showBandwidth: showOperateBtns, //
operateBtns: {
fullscreen: showOperateBtns,
screenshot: showOperateBtns,
play: showOperateBtns,
audio: false,
recorder: false
},
forceNoOffscreen: forceNoOffscreen,
hasAudio: false,
isNotMute: false,
},);
jessibuca.value.onLog = (msg: any) => console.error(msg);
jessibuca.value.onRecord = (status: any) => console.log('onRecord', status);
jessibuca.value.onPause = () => console.log('onPause');
jessibuca.value.onPlay = () => console.log('onPlay');
jessibuca.value.onFullscreen = (msg: any) => console.log('onFullscreen', msg);
jessibuca.value.onMute = (msg: any) => console.log('onMute', msg);
let elmId = 'videoPlayer';
let url = apiUrl.WebRtcUrl;
// webRtcServer.value = new WebRtcStreamer(elmId, url);
}
function loadVideoCanvas() {
window.addEventListener('resize', () => {
changeVideoCanvasSize();
});
changeVideoCanvasSize();
}
const onContextMenuClick = (item: any, menuKey: string,) => {
console.log(`labelId: ${item.id}, menuKey: ${menuKey}`);
// console.log(`item: ${item}`);
// console.log(item);
//key
if (menuKey == "edit") {
popup("编辑标签", [h(LabelEditModel, {modelData: item})], "editLabel");
popup("编辑标签", [h(LabelEditModel, { modelData: item })], "editLabel");
} else if (menuKey == "delete") {
Modal.confirm({
zIndex: 10000,
@ -211,11 +215,11 @@ const onContextMenuClick = (item: any, menuKey: string,) => {
content: () =>
h(
"span",
{style: {color: "black"}},
{ style: { color: "black" } },
"是否确认删除该标签?"
),
okText:
// () => h('span', { style: { color: 'black' } }, ''),
// () => h('span', { style: { color: 'black' } }, ''),
"确定",
// okType: 'primary',
cancelText: () => "取消",
@ -236,7 +240,6 @@ const onContextMenuClick = (item: any, menuKey: string,) => {
}
};
function changeVideoCanvasSize() {
canvasWidth.value = player.clientWidth;
canvasHeight.value = player.clientHeight;
@ -244,6 +247,7 @@ function changeVideoCanvasSize() {
function mouseDownVideo(e: MouseEvent) {
if (!isActiveChoose.value) return;
// e.buttons == 1
if (e.buttons == 1) {
@ -272,6 +276,7 @@ function mouseDownVideo(e: MouseEvent) {
if (judgeResponse(res)) return;
let markLabelId: number = res.data.data;
console.log(markLabelId);
if (markLabelId <= 0) return;
markSearchApi.ActivateMarkLabel({
'cameraId': cameraId,
@ -279,6 +284,7 @@ function mouseDownVideo(e: MouseEvent) {
}).then((res: any) => {
if (judgeResponse(res)) return;
let ret: boolean = res.data.data;
console.log(ret, 'ret');
if (ret) {
let obj = {
cbCameraId: cameraId,
@ -290,18 +296,20 @@ function mouseDownVideo(e: MouseEvent) {
isDelete: false,
inFlag: true,
name: name,
groupName: name
groupName: name,
windowVisible: false //
}
labelList.value.push(obj)
isActiveChoose.value = false
piniaStore.updateIsAddLabel({cmMarkGroupId: 0, labelType: "", isAddLabel: false})
piniaStore.updateIsAddLabel({ cmMarkGroupId: 0, labelType: "", isAddLabel: false })
}
});
})
} else {
//
isActiveChoose.value = false
piniaStore.updateIsAddLabel({cmMarkGroupId: 0, labelType: "", isAddLabel: false})
piniaStore.updateIsAddLabel({ cmMarkGroupId: 0, labelType: "", isAddLabel: false })
}
}
@ -312,8 +320,10 @@ function switchCamera(cameraId: string) {
console.log('get camera obj.', cameraMap.value);
let cameraObj = cameraMap.value.get(cameraId);
console.log(cameraObj, 'cameraObj');
if (!cameraObj) {
console.log('camera obj not found.');
return;
}
curVideoKey.value = cameraId;
@ -353,6 +363,7 @@ function switchCamera(cameraId: string) {
console.log('load camera labels');
getLabel(cameraObj.id);
loadMarkLabelsByLoop(cameraObj);
}
});
} else {
@ -364,7 +375,6 @@ function switchCamera(cameraId: string) {
// step5, load camera labels.
}
function getLabel(cbCameraId: string | number) {
let str = JSON.stringify({cbCameraId})
markLabelApi.GetList({queryJson: str}).then((res: any) => {
@ -382,7 +392,6 @@ function getLabel(cbCameraId: string | number) {
console.log(labelList.value, 'labelList.value');
});
}
function loadMarkLabelsByLoop(cameraObj: any, ms: number = 1000) {
if (curSelectKey.value !== cameraObj.id) {
console.log('load camera labels end.');
@ -394,7 +403,6 @@ function loadMarkLabelsByLoop(cameraObj: any, ms: number = 1000) {
// clearTimeout(timer)
// }, ms);
}
function loadMarkLabels(cameraObj: any) {
markSearchApi.GetMarkLabelCalcResultList({
'cameraId': cameraObj.id
@ -402,6 +410,7 @@ function loadMarkLabels(cameraObj: any) {
if (judgeResponse(res)) return;
let list: Array<any> = res.data.data;
console.log(list);
list.forEach((element: any) => {
labelList.value.forEach((item: any, index: number) => {
if (element.id == item.id) {
@ -409,11 +418,12 @@ function loadMarkLabels(cameraObj: any) {
labelList.value[index].canvasTopRatio = element.canvasTopRatio
labelList.value[index].inFlag = element.inFlag
}
});
});
});
}
function judgeResponse(res: any): boolean {
let flag = false;
if (flag) promptError();
@ -423,7 +433,6 @@ function judgeResponse(res: any): boolean {
function promptError() {
// promptError
}
//
window.onbeforeunload = () => {
jessibuca.value.destroy()
@ -462,7 +471,7 @@ onUnmounted(() => {
justify-content: center;
align-items: center;
> div {
>div {
position: relative;
}
@ -471,6 +480,7 @@ onUnmounted(() => {
top: 50%;
left: 50%;
transform: translate(-50%, -55%);
color: white;
}
img {

Loading…
Cancel
Save