优化路由结构,删除多余页面
This commit is contained in:
parent
d8a8b1c94f
commit
659c462d91
|
|
@ -1,17 +1,174 @@
|
|||
<script setup lang="ts">
|
||||
import type { FormInstance, FormRules } from 'element-plus'
|
||||
import { onMounted, reactive, ref } from 'vue'
|
||||
|
||||
import { useRouter } from 'vue-router'
|
||||
import { runApi } from '~/composables/api'
|
||||
|
||||
const router = useRouter()
|
||||
|
||||
const runCheckBtnRef = ref()
|
||||
const isRunningCheck = ref(false)
|
||||
const vidPaths = ref<string[]>([])
|
||||
|
||||
interface RuleForm {
|
||||
vidPath: string
|
||||
function: string[]
|
||||
}
|
||||
const ruleFormRef = ref<FormInstance>()
|
||||
const ruleForm = reactive<RuleForm>({
|
||||
vidPath: '',
|
||||
function: [
|
||||
// 'runSam3',
|
||||
// 'runHazardCheck',
|
||||
// 'runGenerateReport',
|
||||
// 'runAudioRecognition',
|
||||
],
|
||||
})
|
||||
|
||||
const rules = reactive<FormRules<RuleForm>>({
|
||||
vidPath: [
|
||||
{
|
||||
type: 'string',
|
||||
required: true,
|
||||
message: '请选择视频',
|
||||
trigger: 'change',
|
||||
},
|
||||
],
|
||||
})
|
||||
|
||||
async function runCheck(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
const valid = await formEl.validate((valid, fields) => {
|
||||
if (valid) {
|
||||
// console.log('submit!', ruleForm)
|
||||
}
|
||||
else {
|
||||
console.error('error submit!', fields)
|
||||
}
|
||||
})
|
||||
if (valid) {
|
||||
isRunningCheck.value = true
|
||||
await runApi('/run', {
|
||||
vid_file: vidPaths.value[vidPaths.value.indexOf(ruleForm.vidPath)],
|
||||
run_sam3: ruleForm.function.includes('runSam3'),
|
||||
run_inspection: ruleForm.function.includes('runHazardCheck'),
|
||||
gen_report: ruleForm.function.includes('runGenerateReport'),
|
||||
}).then((res) => {
|
||||
isRunningCheck.value = false
|
||||
// 判定是否成功运行
|
||||
if (res !== 'error') {
|
||||
router.push({
|
||||
path: '/nav/hazardCheckResult',
|
||||
query: { vid_file: vidPaths.value[vidPaths.value.indexOf(ruleForm.vidPath)] },
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
async function reloadFiles() {
|
||||
await runApi('/reload_files', {}).then((res) => {
|
||||
for (const item of (res as any)[0].choices) {
|
||||
vidPaths.value.push(item[0])
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
function resetForm(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
formEl.resetFields()
|
||||
}
|
||||
|
||||
async function goToResult(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
await formEl.validate((valid, fields) => {
|
||||
if (valid) {
|
||||
// console.log('跳转结果页')
|
||||
router.push({
|
||||
path: '/nav/hazardCheckResult',
|
||||
query: { vid_file: 'santai5.mp4' },
|
||||
})
|
||||
}
|
||||
else {
|
||||
console.error('error submit!', fields)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
reloadFiles()
|
||||
})
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<!-- <Logos my="4" />
|
||||
<HelloWorld msg="Hello Vue 3 + Element Plus + Vite" /> -->
|
||||
<div class="container mx-auto">
|
||||
<div class="py-8 text-center text-4xl font-bold">
|
||||
安责险隐患检查
|
||||
</div>
|
||||
<div class="grid grid-cols-3 gap-4">
|
||||
<el-button class="bg-gray-200 p-4" @click="$router.push('/nav/hazardCheck')">
|
||||
本地视频隐患检查
|
||||
</el-button>
|
||||
<el-button class="bg-gray-200 p-4" @click="$router.push('/nav/VideoTrackDemo')">
|
||||
物体跟踪 demo
|
||||
</el-button>
|
||||
</div>
|
||||
</div>
|
||||
<!-- 最外层容器:占满整个视口 -->
|
||||
<el-container style="margin: 0; height: 100%; flex-direction: column;">
|
||||
<!-- 内层容器:自动填充剩余高度 -->
|
||||
<el-main class="main" style="flex: 1; min-height: 0;">
|
||||
<el-form
|
||||
ref="ruleFormRef"
|
||||
style="max-width: 600px"
|
||||
:model="ruleForm"
|
||||
:rules="rules"
|
||||
label-width="auto"
|
||||
>
|
||||
<el-form-item label="视频" prop="vidPath">
|
||||
<el-select v-model="ruleForm.vidPath" placeholder="视频">
|
||||
<el-option v-for="item in vidPaths" :key="item" :label="item" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="功能选择" prop="function">
|
||||
<el-checkbox-group v-model="ruleForm.function" class="checkbox-group">
|
||||
<el-checkbox value="runSam3" name="function">
|
||||
物体识别
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runHazardCheck" name="function">
|
||||
隐患检查
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runGenerateReport" name="function">
|
||||
生成报告
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runAudioRecognition" name="function">
|
||||
音频识别
|
||||
</el-checkbox>
|
||||
</el-checkbox-group>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-button @click="resetForm(ruleFormRef)">
|
||||
重置表单
|
||||
</el-button>
|
||||
<el-button @click="goToResult(ruleFormRef)">
|
||||
查看结果
|
||||
</el-button>
|
||||
<el-button
|
||||
ref="runCheckBtnRef"
|
||||
type="primary"
|
||||
:loading="isRunningCheck"
|
||||
@click="runCheck(ruleFormRef)"
|
||||
>
|
||||
运行检查
|
||||
</el-button>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</el-main>
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.main {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: start;
|
||||
}
|
||||
|
||||
.checkbox-group {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 16px;
|
||||
justify-content: flex-start;
|
||||
}
|
||||
</style>
|
||||
|
|
|
|||
|
|
@ -312,9 +312,6 @@ onMounted(() => {
|
|||
<el-breadcrumb-item :to="{ path: '/' }">
|
||||
主页
|
||||
</el-breadcrumb-item>
|
||||
<el-breadcrumb-item :to="{ path: '/nav/hazardCheck/' }">
|
||||
隐患检查
|
||||
</el-breadcrumb-item>
|
||||
<el-breadcrumb-item>隐患检查结果</el-breadcrumb-item>
|
||||
</el-breadcrumb>
|
||||
</el-header>
|
||||
|
|
@ -1,156 +0,0 @@
|
|||
<script setup>
|
||||
import { ref } from 'vue'
|
||||
|
||||
const videoRef = ref(null)
|
||||
const currentTime = ref(0)
|
||||
const currentBoxes = ref([])
|
||||
const selectedBox = ref(null)
|
||||
|
||||
// 内置跟踪数据
|
||||
const trackData = ref([
|
||||
{
|
||||
id: 1,
|
||||
label: '人物',
|
||||
color: '#FF4D4F',
|
||||
frames: [
|
||||
{ time: 0, x: 60, y: 40, width: 160, height: 280 },
|
||||
{ time: 1, x: 80, y: 40, width: 160, height: 280 },
|
||||
{ time: 2, x: 100, y: 40, width: 160, height: 280 },
|
||||
{ time: 3, x: 120, y: 40, width: 160, height: 280 },
|
||||
{ time: 4, x: 140, y: 40, width: 160, height: 280 },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
label: '车辆',
|
||||
color: '#1890FF',
|
||||
frames: [
|
||||
{ time: 0, x: 300, y: 150, width: 240, height: 140 },
|
||||
{ time: 1, x: 320, y: 150, width: 240, height: 140 },
|
||||
{ time: 2, x: 340, y: 150, width: 240, height: 140 },
|
||||
],
|
||||
},
|
||||
])
|
||||
|
||||
// 视频时间更新
|
||||
function onTimeUpdate() {
|
||||
const t = videoRef.value.currentTime
|
||||
currentTime.value = t
|
||||
|
||||
const boxes = []
|
||||
trackData.value.forEach((item) => {
|
||||
const frame = item.frames.findLast(f => f.time <= t)
|
||||
if (frame) {
|
||||
boxes.push({
|
||||
id: item.id,
|
||||
label: item.label,
|
||||
color: item.color,
|
||||
...frame,
|
||||
})
|
||||
}
|
||||
})
|
||||
currentBoxes.value = boxes
|
||||
}
|
||||
|
||||
// 点击标注框
|
||||
function handleBoxClick(box) {
|
||||
selectedBox.value = box
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="demo-container" style="max-width: 1200px; margin: 20px auto">
|
||||
<el-card header="视频实时物体跟踪(支持点击标注框)">
|
||||
<div class="video-wrapper">
|
||||
<video
|
||||
ref="videoRef"
|
||||
src="https://www.w3school.com.cn/i/movie.mp4"
|
||||
controls
|
||||
class="video"
|
||||
@timeupdate="onTimeUpdate"
|
||||
/>
|
||||
|
||||
<!-- 标注层 -->
|
||||
<div class="annotations-layer">
|
||||
<div
|
||||
v-for="box in currentBoxes"
|
||||
:key="box.id"
|
||||
class="box"
|
||||
:class="{ active: selectedBox?.id === box.id }"
|
||||
:style="{
|
||||
left: `${box.x}px`,
|
||||
top: `${box.y}px`,
|
||||
width: `${box.width}px`,
|
||||
height: `${box.height}px`,
|
||||
borderColor: box.color,
|
||||
}"
|
||||
@click.stop="handleBoxClick(box)"
|
||||
>
|
||||
<span class="label">{{ box.label }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div style="margin-top: 16px; display: flex; gap: 10px">
|
||||
<el-tag type="primary">
|
||||
当前时间:{{ currentTime.toFixed(2) }}s
|
||||
</el-tag>
|
||||
<el-tag v-if="selectedBox" type="warning">
|
||||
已选中 ID:{{ selectedBox.id }} | 标签:{{ selectedBox.label }}
|
||||
</el-tag>
|
||||
</div>
|
||||
</el-card>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.video-wrapper {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
background: #000;
|
||||
border-radius: 8px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.video {
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.annotations-layer {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.box {
|
||||
position: absolute;
|
||||
border: 2px solid;
|
||||
background: rgba(0, 0, 0, 0.1);
|
||||
pointer-events: auto;
|
||||
cursor: pointer;
|
||||
box-sizing: border-box;
|
||||
transform-origin: center center;
|
||||
}
|
||||
|
||||
.box.active {
|
||||
border-width: 4px;
|
||||
background: rgba(255, 255, 0, 0.1);
|
||||
transform: translate(-1px, -1px); /* 完美抵消边框变粗偏移 */
|
||||
}
|
||||
|
||||
.label {
|
||||
position: absolute;
|
||||
top: -22px;
|
||||
left: 0;
|
||||
background: rgba(0, 0, 0, 0.7);
|
||||
color: #fff;
|
||||
font-size: 13px;
|
||||
padding: 2px 6px;
|
||||
border-radius: 3px;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -1,241 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { ref } from 'vue'
|
||||
|
||||
// =============== 1. 定义 TS 类型 ===============
|
||||
/** 单个帧位置信息 */
|
||||
interface TrackFrame {
|
||||
time: number
|
||||
x: number
|
||||
y: number
|
||||
width: number
|
||||
height: number
|
||||
}
|
||||
|
||||
/** 单个跟踪目标 */
|
||||
interface TrackItem {
|
||||
id: number
|
||||
label: string
|
||||
color: string
|
||||
frames: TrackFrame[]
|
||||
}
|
||||
|
||||
/** 渲染到页面的标注框 */
|
||||
interface RenderBox extends TrackFrame {
|
||||
id: number
|
||||
label: string
|
||||
color: string
|
||||
}
|
||||
|
||||
// =============== 2. 响应式数据 ===============
|
||||
const 隐患列表 = ref<string[]>(['隐患1', '隐患2', '隐患3', '隐患4', '隐患5'])
|
||||
const 物体列表 = ref<string[]>(['物体1', '物体2', '物体3', '物体4', '物体5'])
|
||||
|
||||
const videoRef = ref<HTMLVideoElement | null>(null)
|
||||
const currentTime = ref<number>(0)
|
||||
const currentBoxes = ref<RenderBox[]>([])
|
||||
const selectedBox = ref<RenderBox | null>(null)
|
||||
|
||||
// 内置跟踪数据
|
||||
const trackData = ref<TrackItem[]>([
|
||||
{
|
||||
id: 1,
|
||||
label: '人物',
|
||||
color: '#FF4D4F',
|
||||
frames: [
|
||||
{ time: 0, x: 60, y: 40, width: 160, height: 280 },
|
||||
{ time: 1, x: 80, y: 40, width: 160, height: 280 },
|
||||
{ time: 2, x: 100, y: 40, width: 160, height: 280 },
|
||||
{ time: 3, x: 120, y: 40, width: 160, height: 280 },
|
||||
{ time: 4, x: 140, y: 40, width: 160, height: 280 },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
label: '车辆',
|
||||
color: '#1890FF',
|
||||
frames: [
|
||||
{ time: 0, x: 300, y: 150, width: 240, height: 140 },
|
||||
{ time: 1, x: 320, y: 150, width: 240, height: 140 },
|
||||
{ time: 2, x: 340, y: 150, width: 240, height: 140 },
|
||||
],
|
||||
},
|
||||
])
|
||||
|
||||
// =============== 3. 函数 ===============
|
||||
/** 视频时间更新 */
|
||||
function onTimeUpdate(): void {
|
||||
if (!videoRef.value)
|
||||
return
|
||||
|
||||
const t = videoRef.value.currentTime
|
||||
currentTime.value = t
|
||||
|
||||
const boxes: RenderBox[] = []
|
||||
trackData.value.forEach((item) => {
|
||||
const frame = item.frames.findLast(f => f.time <= t)
|
||||
if (frame) {
|
||||
boxes.push({
|
||||
id: item.id,
|
||||
label: item.label,
|
||||
color: item.color,
|
||||
...frame,
|
||||
})
|
||||
}
|
||||
})
|
||||
currentBoxes.value = boxes
|
||||
}
|
||||
|
||||
/** 点击标注框 */
|
||||
function handleBoxClick(box: RenderBox): void {
|
||||
selectedBox.value = box
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<!-- 最外层容器:占满整个视口 -->
|
||||
<el-container style="margin: 0; height: 100%; flex-direction: column;">
|
||||
<el-header style="height: 60px; display: flex; align-items: center; border-bottom: 1px solid var(--ep-border-color);">
|
||||
<el-breadcrumb separator="/">
|
||||
<el-breadcrumb-item :to="{ path: '/' }">
|
||||
主页
|
||||
</el-breadcrumb-item>
|
||||
<el-breadcrumb-item>隐患检查</el-breadcrumb-item>
|
||||
</el-breadcrumb>
|
||||
</el-header>
|
||||
|
||||
<!-- 内层容器:自动填充剩余高度 -->
|
||||
<el-container style="flex: 1; min-height: 0;">
|
||||
<el-aside width="200px" style="border-right: 1px solid var(--ep-border-color);">
|
||||
<el-row class="flex flex-col" style="border-bottom: 1px solid var(--ep-border-color);">
|
||||
<el-row style="min-height: 20px;">
|
||||
隐患列表
|
||||
</el-row>
|
||||
<el-row style="flex: 1; overflow-y: auto;">
|
||||
<el-row v-for="item in 隐患列表" :key="item">
|
||||
<el-button>
|
||||
{{ item }}
|
||||
</el-button>
|
||||
</el-row>
|
||||
</el-row>
|
||||
</el-row>
|
||||
<el-row>物体列表</el-row>
|
||||
<el-row style="flex: 1; overflow-y: auto;">
|
||||
<el-row v-for="item in 物体列表" :key="item">
|
||||
<el-button>
|
||||
{{ item }}
|
||||
</el-button>
|
||||
</el-row>
|
||||
</el-row>
|
||||
</el-aside>
|
||||
<el-main style="border-right: 1px solid var(--ep-border-color); padding: 0;">
|
||||
<div class="vid_box" style="border-bottom: 1px solid var(--ep-border-color);">
|
||||
<div class="video-wrapper">
|
||||
<video
|
||||
ref="videoRef"
|
||||
src="https://www.w3school.com.cn/i/movie.mp4"
|
||||
controls
|
||||
class="video"
|
||||
@timeupdate="onTimeUpdate"
|
||||
/>
|
||||
|
||||
<!-- 标注层 -->
|
||||
<div class="annotations-layer">
|
||||
<div
|
||||
v-for="box in currentBoxes"
|
||||
:key="box.id"
|
||||
class="box"
|
||||
:class="{ active: selectedBox?.id === box.id }"
|
||||
:style="{
|
||||
left: `${box.x}px`,
|
||||
top: `${box.y}px`,
|
||||
width: `${box.width}px`,
|
||||
height: `${box.height}px`,
|
||||
borderColor: box.color,
|
||||
}"
|
||||
@click.stop="handleBoxClick(box)"
|
||||
>
|
||||
<span class="label">{{ box.label }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="vid_track">
|
||||
轨道
|
||||
</div>
|
||||
</el-main>
|
||||
<el-aside width="300px">
|
||||
<el-row style="border-bottom: 1px solid var(--ep-border-color);">
|
||||
<el-col>
|
||||
<el-row class="text-left">
|
||||
隐患描述
|
||||
</el-row>
|
||||
<el-row class="text-left">
|
||||
依据
|
||||
</el-row>
|
||||
<el-row class="text-left">
|
||||
整改建议
|
||||
</el-row>
|
||||
</el-col>
|
||||
</el-row>
|
||||
<el-row>
|
||||
<el-button>
|
||||
查看报告
|
||||
</el-button>
|
||||
</el-row>
|
||||
</el-aside>
|
||||
</el-container>
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.video-wrapper {
|
||||
position: relative;
|
||||
width: calc(100% - 8px);
|
||||
background: #000;
|
||||
border-radius: 8px;
|
||||
overflow: hidden;
|
||||
margin: 4px;
|
||||
}
|
||||
|
||||
.video {
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: auto;
|
||||
}
|
||||
|
||||
.annotations-layer {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.box {
|
||||
position: absolute;
|
||||
border: 2px solid;
|
||||
background: rgba(0, 0, 0, 0.1);
|
||||
pointer-events: auto;
|
||||
cursor: pointer;
|
||||
box-sizing: border-box;
|
||||
transform-origin: center center;
|
||||
}
|
||||
|
||||
.box.active {
|
||||
border-width: 4px;
|
||||
background: rgba(255, 255, 0, 0.1);
|
||||
transform: translate(-1px, -1px); /* 完美抵消边框变粗偏移 */
|
||||
}
|
||||
|
||||
.label {
|
||||
position: absolute;
|
||||
top: -22px;
|
||||
left: 0;
|
||||
background: rgba(0, 0, 0, 0.7);
|
||||
color: #fff;
|
||||
font-size: 13px;
|
||||
padding: 2px 6px;
|
||||
border-radius: 3px;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -1,188 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import type { FormInstance, FormRules } from 'element-plus'
|
||||
import { onMounted, reactive, ref } from 'vue'
|
||||
|
||||
import { useRouter } from 'vue-router'
|
||||
import { runApi } from '~/composables/api'
|
||||
|
||||
const router = useRouter()
|
||||
|
||||
const runCheckBtnRef = ref()
|
||||
const isRunningCheck = ref(false)
|
||||
const vidPaths = ref<string[]>([])
|
||||
|
||||
interface RuleForm {
|
||||
vidPath: string
|
||||
function: string[]
|
||||
}
|
||||
const ruleFormRef = ref<FormInstance>()
|
||||
const ruleForm = reactive<RuleForm>({
|
||||
vidPath: '',
|
||||
function: [
|
||||
// 'runSam3',
|
||||
// 'runHazardCheck',
|
||||
// 'runGenerateReport',
|
||||
// 'runAudioRecognition',
|
||||
],
|
||||
})
|
||||
|
||||
const rules = reactive<FormRules<RuleForm>>({
|
||||
vidPath: [
|
||||
{
|
||||
type: 'string',
|
||||
required: true,
|
||||
message: '请选择视频',
|
||||
trigger: 'change',
|
||||
},
|
||||
],
|
||||
})
|
||||
|
||||
async function runCheck(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
const valid = await formEl.validate((valid, fields) => {
|
||||
if (valid) {
|
||||
// console.log('submit!', ruleForm)
|
||||
}
|
||||
else {
|
||||
console.error('error submit!', fields)
|
||||
}
|
||||
})
|
||||
if (valid) {
|
||||
isRunningCheck.value = true
|
||||
await runApi('/run', {
|
||||
vid_file: vidPaths.value[vidPaths.value.indexOf(ruleForm.vidPath)],
|
||||
run_sam3: ruleForm.function.includes('runSam3'),
|
||||
run_inspection: ruleForm.function.includes('runHazardCheck'),
|
||||
gen_report: ruleForm.function.includes('runGenerateReport'),
|
||||
}).then((res) => {
|
||||
isRunningCheck.value = false
|
||||
// 判定是否成功运行
|
||||
if (res !== 'error') {
|
||||
router.push({
|
||||
path: '/nav/hazardCheck/hazardCheckResult',
|
||||
query: { vid_file: vidPaths.value[vidPaths.value.indexOf(ruleForm.vidPath)] },
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
async function reloadFiles() {
|
||||
await runApi('/reload_files', {}).then((res) => {
|
||||
for (const item of (res as any)[0].choices) {
|
||||
vidPaths.value.push(item[0])
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
function resetForm(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
formEl.resetFields()
|
||||
}
|
||||
|
||||
async function goToResult(formEl: FormInstance | undefined) {
|
||||
if (!formEl)
|
||||
return
|
||||
const valid = await formEl.validate((valid, fields) => {
|
||||
if (valid) {
|
||||
// console.log('跳转结果页')
|
||||
router.push('/nav/hazardCheck/hazardCheckResult')
|
||||
}
|
||||
else {
|
||||
console.error('error submit!', fields)
|
||||
}
|
||||
})
|
||||
if (valid) {
|
||||
isRunningCheck.value = true
|
||||
router.push({
|
||||
path: '/nav/hazardCheck/hazardCheckResult',
|
||||
query: { vid_file: 'santai5.mp4' },
|
||||
})
|
||||
// isRunningCheck.value = false
|
||||
}
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
reloadFiles()
|
||||
})
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<!-- 最外层容器:占满整个视口 -->
|
||||
<el-container style="margin: 0; height: 100%; flex-direction: column;">
|
||||
<el-header style="height: 30px; display: flex; align-items: center; border-bottom: 1px solid var(--ep-border-color);">
|
||||
<el-breadcrumb separator="/">
|
||||
<el-breadcrumb-item :to="{ path: '/' }">
|
||||
主页
|
||||
</el-breadcrumb-item>
|
||||
<el-breadcrumb-item>隐患检查</el-breadcrumb-item>
|
||||
</el-breadcrumb>
|
||||
</el-header>
|
||||
|
||||
<!-- 内层容器:自动填充剩余高度 -->
|
||||
<el-main class="main" style="flex: 1; min-height: 0;">
|
||||
<el-form
|
||||
ref="ruleFormRef"
|
||||
style="max-width: 600px"
|
||||
:model="ruleForm"
|
||||
:rules="rules"
|
||||
label-width="auto"
|
||||
>
|
||||
<el-form-item label="视频" prop="vidPath">
|
||||
<el-select v-model="ruleForm.vidPath" placeholder="视频">
|
||||
<el-option v-for="item in vidPaths" :key="item" :label="item" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="功能选择" prop="function">
|
||||
<el-checkbox-group v-model="ruleForm.function" class="checkbox-group">
|
||||
<el-checkbox value="runSam3" name="function">
|
||||
物体识别
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runHazardCheck" name="function">
|
||||
隐患检查
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runGenerateReport" name="function">
|
||||
生成报告
|
||||
</el-checkbox>
|
||||
<el-checkbox value="runAudioRecognition" name="function">
|
||||
音频识别
|
||||
</el-checkbox>
|
||||
</el-checkbox-group>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-button @click="resetForm(ruleFormRef)">
|
||||
重置表单
|
||||
</el-button>
|
||||
<el-button @click="goToResult(ruleFormRef)">
|
||||
查看结果
|
||||
</el-button>
|
||||
<el-button
|
||||
ref="runCheckBtnRef"
|
||||
type="primary"
|
||||
:loading="isRunningCheck"
|
||||
@click="runCheck(ruleFormRef)"
|
||||
>
|
||||
运行检查
|
||||
</el-button>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</el-main>
|
||||
</el-container>
|
||||
</template>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.main {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: start;
|
||||
}
|
||||
|
||||
.checkbox-group {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 16px;
|
||||
justify-content: flex-start;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -19,9 +19,6 @@ declare module 'vue-router/auto-routes' {
|
|||
*/
|
||||
export interface RouteNamedMap {
|
||||
'/': RouteRecordInfo<'/', '/', Record<never, never>, Record<never, never>>,
|
||||
'/nav/hazardCheck/': RouteRecordInfo<'/nav/hazardCheck/', '/nav/hazardCheck', Record<never, never>, Record<never, never>>,
|
||||
'/nav/hazardCheck/1_隐患检查 copy': RouteRecordInfo<'/nav/hazardCheck/1_隐患检查 copy', '/nav/hazardCheck/1_隐患检查 copy', Record<never, never>, Record<never, never>>,
|
||||
'/nav/hazardCheck/HazardCheckResult': RouteRecordInfo<'/nav/hazardCheck/HazardCheckResult', '/nav/hazardCheck/HazardCheckResult', Record<never, never>, Record<never, never>>,
|
||||
'/nav/VideoTrackDemo': RouteRecordInfo<'/nav/VideoTrackDemo', '/nav/VideoTrackDemo', Record<never, never>, Record<never, never>>,
|
||||
'/nav/HazardCheckResult/': RouteRecordInfo<'/nav/HazardCheckResult/', '/nav/HazardCheckResult', Record<never, never>, Record<never, never>>,
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue