Files
bigscreenWeb/src/views/SagTraceResult_WX/index.vue

471 lines
14 KiB
Vue
Raw Normal View History

2025-09-25 13:32:47 +08:00
<template>
<div id="index" ref="appRef">
<div class="bg">
<dv-loading v-if="loading">Loading...</dv-loading>
<div v-else class="host-body">
<!-- <div class="d-flex jc-center">
<dv-decoration-10 class="dv-dec-10" :color="color[1]" />
<div class="d-flex jc-center">
<dv-decoration-8 class="dv-dec-8" :color="color[2]" />
<div class="title">
<span class="title-text" @click="handleTitleClick">{{
title
}}</span>
</div>
<dv-decoration-8
class="dv-dec-8"
:reverse="true"
:color="color[2]"
/>
</div>
<dv-decoration-10 class="dv-dec-10-s" :color="color[1]" />
</div>
<div class="d-flex secondLine">
<div class="react-right mr-3">
<span class="text fw-b">
{{ timeInfo.dateYear }} {{ timeInfo.dateWeek }}
{{ timeInfo.dateDay }}</span
>
</div>
<el-dropdown placement="bottom">
<el-icon :size="20" :color="color[0][1]">
<Menu />
</el-icon>
<template #dropdown>
<el-dropdown-menu>
<el-dropdown-item @click="handleClick('1')"
>接线图配置</el-dropdown-item
>
</el-dropdown-menu>
</template>
</el-dropdown>
</div> -->
<div class="d-flex jc-center">
<div class="react-left">
<span class="text fw-b">
{{ timeInfo.dateYear }} {{ timeInfo.dateWeek }}
{{ timeInfo.dateDay }}</span
>
</div>
<dv-decoration-10 class="dv-dec-10" :color="color[1]" />
<div class="d-flex jc-center">
<dv-decoration-8 class="dv-dec-8" :color="color[2]" />
<div class="title">
<span class="title-text">{{ title }}</span>
</div>
<dv-decoration-8
class="dv-dec-8"
:reverse="true"
:color="color[2]"
/>
</div>
<dv-decoration-10 class="dv-dec-10-s" :color="color[1]" />
</div>
<div class="d-flex secondLine">
<div class="react-right mr-1">
<span class="text fw-b" style="display: flex">
<datePicker
ref="datePickerRef"
@timeChangeInfo="timeChangeInfo"
/>
</span>
</div>
<el-icon
size="22"
:color="color[1][0]"
class="mt-0.5 mt5"
style="cursor: pointer"
>
<Menu @click="openDialog" />
</el-icon>
<Management
ref="createRef"
@project-change="onProjectChange"
></Management>
</div>
<div class="body-box">
<!-- 第三行数据 -->
<div class="content-box">
<dv-border-box-10 :color="color[0]" style="position: relative">
<Plan :project="currentProject" />
<!-- flag 值传递给 SecurityDetail 组件 -->
<!-- showDetail从SecurityDetail 组件传过来 -->
<SecurityDetail
ref="securityDetail"
:current-flag="currentFlag"
style="position: absolute; bottom: 0px; width: 100%"
@show-detail-change="handleShowDetailChange"
/>
<IframeDia
:event-list="eventListData as []"
style="position: absolute; top: 0px; right: 0px; left: 0px"
/>
<!-- 图元颜色提示框 -->
<div
v-if="!showDetail"
style="
position: absolute;
left: 0px;
bottom: 40px;
padding: 10px;
"
>
<div style="display: flex">
2025-10-27 10:37:25 +08:00
<span class="iconfont" style="color: #7ac1f9">&#xe67a;</span>
2025-09-25 13:32:47 +08:00
<div style="margin-left: 10px; font-size: 12px">监测点</div>
</div>
<div style="display: flex" v-if="currentFlag == 0">
2025-10-27 10:37:25 +08:00
<span class="iconfont blink-basic" style="color: #375db4"
>&#xe67a;</span
>
<!-- <img
2025-09-25 13:32:47 +08:00
src="@/assets/icon/传输设备 (3).png"
style="width: 20px; height: 20px"
class="blink-basic"
2025-10-27 10:37:25 +08:00
/> -->
2025-09-25 13:32:47 +08:00
<div style="margin-left: 10px; font-size: 12px">
暂降发生测点
</div>
</div>
<div style="display: flex" v-if="currentFlag == 1">
2025-10-27 10:37:25 +08:00
<!-- <img
2025-09-25 13:32:47 +08:00
src="@/assets/icon/传输设备 (4).png"
style="width: 20px; height: 20px"
class="blink-basic"
2025-10-27 10:37:25 +08:00
/> -->
<span class="iconfont blink-basic" style="color:#0936f4"
>&#xe67a;</span
>
2025-09-25 13:32:47 +08:00
<div style="margin-left: 10px; font-size: 12px">背景测点</div>
</div>
<div style="display: flex">
2025-10-27 10:37:25 +08:00
<!-- <img
2025-09-25 13:32:47 +08:00
src="@/assets/icon/传输设备 (2).png"
style="width: 20px; height: 20px"
class="blink-basic"
2025-10-27 10:37:25 +08:00
/> -->
<span
v-if="currentFlag == 0"
class="iconfont blink-basic"
style="color: #1dd1a1"
>&#xe67a;</span
>
<span
v-if="currentFlag == 1"
class="iconfont blink-basic"
style="color: #09ee06"
>&#xe67a;</span
>
<span
v-if="currentFlag == 2"
class="iconfont blink-basic"
style="color: #f08a0a"
>&#xe67a;</span
>
2025-09-25 13:32:47 +08:00
<div style="margin-left: 10px; font-size: 12px">
<span v-if="currentFlag == 0">暂降溯源关联测点</span>
<span v-if="currentFlag == 1">责任测点</span>
<span v-if="currentFlag == 2">发生谐波放大测点</span>
</div>
</div>
<div style="display: flex" v-if="currentFlag != 2">
2025-10-27 10:37:25 +08:00
<!-- <img
2025-09-25 13:32:47 +08:00
src="@/assets/icon/传输设备 (1).png"
style="width: 20px; height: 20px"
class="blink-basic"
2025-10-27 10:37:25 +08:00
/> -->
<span
v-if="currentFlag == 0"
class="iconfont blink-basic"
style="color: #f9065b"
>&#xe67a;</span
>
<span
v-else
class="iconfont blink-basic"
style="color: #c708fe"
>&#xe67a;</span
>
2025-09-25 13:32:47 +08:00
<div style="margin-left: 10px; font-size: 12px">
2025-10-27 10:37:25 +08:00
{{ currentFlag == 0 ? "暂降源测点" : "责任占比最高测点" }}
2025-09-25 13:32:47 +08:00
</div>
</div>
</div>
<!-- 还原按钮 -->
<!-- <div>
<el-button @click="back" icon="el-icon-Back">还原</el-button>
</div> -->
</dv-border-box-10>
<div class="content-left">
<dv-border-box-13 :color="color[0]">
<ScaleStatistics ref="scaleStatistics" />
</dv-border-box-13>
<dv-border-box-13 :color="color[0]">
<EventStatistics
ref="eventStatistics"
@data-updated="handleDataUpdate"
@flag-changed="handleFlagChange"
@expand-detail="handleExpandDetail"
@refresh-security-detail="refreshSecurityDetail"
2025-09-25 13:32:47 +08:00
/>
</dv-border-box-13>
<!-- <dv-border-box-13 :color="color[0]">
<Table />
</dv-border-box-13> -->
</div>
</div>
</div>
</div>
</div>
</div>
</template>
<!--index.vue-->
<script lang="ts" setup>
import { defineComponent, ref, reactive, onMounted, onUnmounted } from "vue";
import { formatTime } from "@/utils/index"; //引入封装好的
import useDraw from "@/utils/useDraw"; // 引入封装好的屏幕适配方法
import { WEEK, title, subtitle, moduleInfo, color } from "@/constant/index_wx"; //引入封装的标题日期
import { Menu } from "@element-plus/icons-vue";
//页面组件
import Plan from "./components/plan.vue"; // 引入计划组件
import ScaleStatistics from "./components/scaleStatistics/index.vue"; // 引入计划组件
import EventStatistics from "./components/eventStatistics/index.vue"; // 引入计划组件
import Table from "./components/table.vue"; // 引入计划组件
import datePicker from "@/components/datePicker/index.vue";
import Management from "./components/manage/index.vue";
import SecurityDetail from "./components/manage/securityDetail.vue";
import IframeDia from "./components/manage/iframeDia.vue";
// 传给iframe页面的参数
const currentProject = ref<{ id: string; name: string } | null>(null);
// 项目管理页面传过来的事件 点击激活 获取首页展示
const onProjectChange = (project: { id: string; name: string }) => {
currentProject.value = project;
};
const smsQueriesRef = ref(); // 短信查询组件引用
const smsConfigRef = ref(); // 短信查询组件引用
const sendRef = ref(); // 短信查询组件引用
// * 加载标识
const loading = ref<boolean>(true);
// * 时间内容
const timeInfo: any = reactive({
setInterval: 0,
dateDay: "",
dateYear: "",
dateWeek: "",
});
const scaleStatistics = ref();
const eventStatistics = ref();
const securityDetail = ref();
// 适配处理
const { appRef, calcRate, windowDraw, unWindowDraw } = useDraw();
// 闪烁点list eventStatistics/index.vue
const eventListData = ref([]);
// 添加用于存储当前 flag 值的响应式变量
const currentFlag = ref(0);
// 添加 showDetail 响应式变量
const showDetail = ref(false);
// 处理 showDetail 变化
const handleShowDetailChange = (value: boolean) => {
showDetail.value = value;
};
// 处理 EventStatistics 组件传递过来的 flag 值变化
const handleFlagChange = (flagValue: number) => {
currentFlag.value = flagValue;
};
// 处理数据更新
const handleDataUpdate = (data: string[]) => {
eventListData.value = data;
};
const refreshSecurityDetail = () => {
// 调用 securityDetail 组件的刷新方法
if (securityDetail.value) {
securityDetail.value.refreshResponsibilityList();
}
};
2025-09-25 13:32:47 +08:00
// 初始化并获取数据
const initComponents = () => {
if (eventStatistics.value) {
// eventStatistics.value.initHasEventList();
// 定时获取 eventList 数据并传递给 iframeDia
const interval = setInterval(() => {
const data = eventStatistics.value.getEventList();
if (data && data.length > 0) {
eventListData.value = data;
}
}, 3000);
}
};
// 处理展开详情面板的函数
const handleExpandDetail = (flagValue: number) => {
// 设置当前 flag
currentFlag.value = flagValue;
// 通知 SecurityDetail 组件展开详情面板
showDetail.value = true;
// 同时通知 SecurityDetail 组件更新 showDetail 状态
securityDetail.value?.setShowDetail(true);
};
// 生命周期
onMounted(() => {
cancelLoading();
handleTime();
// todo 屏幕适应
windowDraw();
calcRate();
});
onUnmounted(() => {
unWindowDraw();
clearInterval(timeInfo.setInterval);
});
// methods
// todo 处理 loading 展示
const cancelLoading = () => {
setTimeout(() => {
loading.value = false;
}, 500);
};
// todo 处理时间监听
const handleTime = () => {
timeInfo.setInterval = setInterval(() => {
const date = new Date();
timeInfo.dateDay = formatTime(date, "HH: mm: ss");
timeInfo.dateYear = formatTime(date, "yyyy-MM-dd");
timeInfo.dateWeek = WEEK[date.getDay()];
}, 1000);
};
// todo 处理菜单点击事件
const handleClick = (type: string) => {
if (type === "1") {
smsQueriesRef.value.open("已发送短信查询");
} else if (type === "2") {
smsConfigRef.value.open("短信配置");
} else if (type === "3") {
sendRef.value.open("短信发送");
}
};
// 切换时间
const timeChangeInfo = async () => {
inquire();
};
const inquireTimer: any = ref(null);
const inquire = async () => {
// 清除上一次的定时器
if (inquireTimer.value) {
clearTimeout(inquireTimer.value);
}
// 设置新的定时器延迟300毫秒执行
inquireTimer.value = setTimeout(async () => {
scaleStatistics.value.initialData(); //监测点规模统计
eventStatistics.value.init(); //暂降溯源统计
securityDetail.value.init(); //报警信息详情
// 定时获取 eventList 数据并传递给 iframeDia
// initComponents()
// 执行完毕后重置定时器变量
inquireTimer.value = null;
}, 500);
};
// 打开管理页面弹框
const createRef = ref();
const openDialog = () => {
createRef.value.open();
};
</script>
<style lang="scss" scoped>
@import "@/assets/scss/SagTraceResult_WX.scss";
.react-right {
width: 460px !important;
}
.count {
position: absolute;
top: -8px;
left: 23px;
background-color: #ff2501;
color: #fff;
height: 15px;
line-height: 15px;
padding: 0 3px;
border-radius: 40%;
font-size: 10px;
text-align: center;
}
.icon {
position: absolute;
top: 8px;
right: 25px;
}
.significant {
position: absolute;
top: 12px;
left: 15px;
.count {
top: -3px;
left: 13px;
height: 13px;
}
}
.react-left {
position: absolute;
left: 140px;
top: 30px;
font-size: 18px;
line-height: 35px;
}
.titles {
margin-right: 10px;
.react-right {
width: 50px !important;
line-height: 20px !important;
font-size: 14px !important;
}
}
.iconfont {
2025-10-27 10:37:25 +08:00
font-size: 20px !important;
2025-09-25 13:32:47 +08:00
}
/* 基本闪烁效果 */
.blink-basic {
animation: blink 1s linear infinite;
}
@keyframes blink {
0% {
opacity: 1;
}
50% {
opacity: 0;
}
100% {
opacity: 1;
}
}
</style>