|
|
|
@ -91,12 +91,12 @@
|
|
|
|
|
</el-button>
|
|
|
|
|
</el-button-group>
|
|
|
|
|
</div>
|
|
|
|
|
<div class="toolbar-right">
|
|
|
|
|
<el-button type="primary" @click="exportData">
|
|
|
|
|
<el-icon><Download /></el-icon>
|
|
|
|
|
导出数据
|
|
|
|
|
</el-button>
|
|
|
|
|
</div>
|
|
|
|
|
<!-- <div class="toolbar-right">-->
|
|
|
|
|
<!-- <el-button type="primary" @click="exportData">-->
|
|
|
|
|
<!-- <el-icon><Download /></el-icon>-->
|
|
|
|
|
<!-- 导出数据-->
|
|
|
|
|
<!-- </el-button>-->
|
|
|
|
|
<!-- </div>-->
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
<!-- 查询过滤器 -->
|
|
|
|
@ -385,15 +385,15 @@
|
|
|
|
|
<el-col :span="6">
|
|
|
|
|
<el-statistic title="计划保养次数" :value="maintenanceStats.planned" />
|
|
|
|
|
</el-col>
|
|
|
|
|
<el-col :span="6">
|
|
|
|
|
<el-statistic title="临时保养次数" :value="maintenanceStats.temporary" />
|
|
|
|
|
</el-col>
|
|
|
|
|
<el-col :span="6">
|
|
|
|
|
<el-statistic title="平均保养间隔" :value="maintenanceStats.avgInterval" suffix="天" />
|
|
|
|
|
</el-col>
|
|
|
|
|
<el-col :span="6">
|
|
|
|
|
<el-statistic title="下次保养时间" :value="maintenanceStats.nextDate || '未计划'" />
|
|
|
|
|
</el-col>
|
|
|
|
|
<!-- <el-col :span="6">-->
|
|
|
|
|
<!-- <el-statistic title="临时保养次数" :value="maintenanceStats.temporary" />-->
|
|
|
|
|
<!-- </el-col>-->
|
|
|
|
|
<!-- <el-col :span="6">-->
|
|
|
|
|
<!-- <el-statistic title="平均保养间隔" :value="maintenanceStats.avgInterval" suffix="天" />-->
|
|
|
|
|
<!-- </el-col>-->
|
|
|
|
|
<!-- <el-col :span="6">-->
|
|
|
|
|
<!-- <el-statistic title="下次保养时间" :value="maintenanceStats.nextDate || '未计划'" />-->
|
|
|
|
|
<!-- </el-col>-->
|
|
|
|
|
</el-row>
|
|
|
|
|
</el-card>
|
|
|
|
|
</el-col>
|
|
|
|
@ -408,13 +408,13 @@
|
|
|
|
|
<el-table-column prop="maintDate" label="保养日期" />
|
|
|
|
|
<el-table-column prop="maintPerson" label="保养人员" />
|
|
|
|
|
<el-table-column prop="maintContent" label="保养内容" show-overflow-tooltip />
|
|
|
|
|
<el-table-column prop="maintResult" label="保养结果">
|
|
|
|
|
<template #default="scope">
|
|
|
|
|
<el-tag :type="scope.row.maintResult === '合格' ? 'success' : 'warning'">
|
|
|
|
|
{{ scope.row.maintResult }}
|
|
|
|
|
</el-tag>
|
|
|
|
|
</template>
|
|
|
|
|
</el-table-column>
|
|
|
|
|
<!-- <el-table-column prop="maintResult" label="保养结果">-->
|
|
|
|
|
<!-- <template #default="scope">-->
|
|
|
|
|
<!-- <el-tag :type="scope.row.maintResult === '合格' ? 'success' : 'warning'">-->
|
|
|
|
|
<!-- {{ scope.row.maintResult }}-->
|
|
|
|
|
<!-- </el-tag>-->
|
|
|
|
|
<!-- </template>-->
|
|
|
|
|
<!-- </el-table-column>-->
|
|
|
|
|
</el-table>
|
|
|
|
|
</el-card>
|
|
|
|
|
</el-col>
|
|
|
|
@ -426,10 +426,10 @@
|
|
|
|
|
</div>
|
|
|
|
|
</template>
|
|
|
|
|
|
|
|
|
|
<script setup name="ProdBaseMachineInfo">
|
|
|
|
|
<script setup name="ProdBaseMachineInfo" lang="ts">
|
|
|
|
|
import { ref, reactive, toRefs, getCurrentInstance, onMounted, onUnmounted, shallowRef, markRaw, watch } from 'vue';
|
|
|
|
|
import { listDmsBaseMachineInfoIn, getDmsBaseMachineInfoList, getDmsBaseMachineInfo } from '@/api/dms/dmsBaseMachineInfo';
|
|
|
|
|
import { listBaseDeviceTypeInDMS, getBaseDeviceTypeListInDMS } from '@/api/dms/baseDeviceType';
|
|
|
|
|
import { listDmsBaseMachineInfo, getDmsBaseMachineInfoList, getDmsBaseMachineInfo } from '@/api/dms/dmsBaseMachineInfo';
|
|
|
|
|
import { listBaseDeviceType, getBaseDeviceTypeList } from '@/api/dms/baseDeviceType';
|
|
|
|
|
import { listDmsBaseDevicePurchase, getDmsBaseDevicePurchaseList } from '@/api/dms/dmsBaseDevicePurchase';
|
|
|
|
|
import { listDmsBaseDeviceInstall, getDmsBaseDeviceInstallList } from '@/api/dms/dmsBaseDeviceInstall';
|
|
|
|
|
import { listDmsBaseDeviceDebugging, getDmsBaseDeviceDebuggingList } from '@/api/dms/dmsBaseDeviceDebugging';
|
|
|
|
@ -459,8 +459,8 @@ import {
|
|
|
|
|
const { proxy } = getCurrentInstance();
|
|
|
|
|
|
|
|
|
|
// TODO: 需要引入完整的字典数据
|
|
|
|
|
const { machine_status, debug_status, fault_status, maint_level, maint_status } = toRefs(proxy.useDict(
|
|
|
|
|
'machine_status', 'debug_status', 'fault_status', 'maint_level', 'maint_status'
|
|
|
|
|
const { machine_status, debug_status, fault_status, maint_level, maint_status, handle_status, bills_status, active_flag } = toRefs(proxy.useDict(
|
|
|
|
|
'machine_status', 'debug_status', 'fault_status', 'maint_level', 'maint_status', 'handle_status', 'bills_status', 'active_flag'
|
|
|
|
|
));
|
|
|
|
|
// TODO: 需要补充以下字典
|
|
|
|
|
// const { active_flag } = toRefs<any>(proxy?.useDict('active_flag'));
|
|
|
|
@ -489,7 +489,7 @@ const deviceTypes = ref([]);
|
|
|
|
|
// 查询参数
|
|
|
|
|
const queryParams = ref({
|
|
|
|
|
pageNum: 1,
|
|
|
|
|
pageSize: 12,
|
|
|
|
|
pageSize: 10,
|
|
|
|
|
machineCode: undefined,
|
|
|
|
|
machineName: undefined,
|
|
|
|
|
machineLocation: undefined,
|
|
|
|
@ -618,7 +618,7 @@ const updateCurrentTime = () => {
|
|
|
|
|
const getList = async () => {
|
|
|
|
|
loading.value = true;
|
|
|
|
|
try {
|
|
|
|
|
const res = await listDmsBaseMachineInfoIn(queryParams.value);
|
|
|
|
|
const res = await listDmsBaseMachineInfo(queryParams.value);
|
|
|
|
|
machineList.value = res.rows || [];
|
|
|
|
|
total.value = res.total || 0;
|
|
|
|
|
|
|
|
|
@ -635,7 +635,7 @@ const getList = async () => {
|
|
|
|
|
// 获取设备类型列表
|
|
|
|
|
const getDeviceTypes = async () => {
|
|
|
|
|
try {
|
|
|
|
|
const res = await getBaseDeviceTypeListInDMS({ pageNum: 1, pageSize: 100 });
|
|
|
|
|
const res = await getBaseDeviceTypeList({ pageNum: 1, pageSize: 100 });
|
|
|
|
|
deviceTypes.value = res.data;
|
|
|
|
|
} catch (error) {
|
|
|
|
|
console.error('获取设备类型失败:', error);
|
|
|
|
@ -1109,10 +1109,10 @@ const viewDetails = async (machine) => {
|
|
|
|
|
]);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
// 导出数据
|
|
|
|
|
const exportData = () => {
|
|
|
|
|
proxy.$modal.msgInfo('导出功能开发中...');
|
|
|
|
|
};
|
|
|
|
|
// // 导出数据
|
|
|
|
|
// const exportData = () => {
|
|
|
|
|
// proxy.$modal.msgInfo('导出功能开发中...');
|
|
|
|
|
// };
|
|
|
|
|
|
|
|
|
|
// 定时更新
|
|
|
|
|
let timer = null;
|
|
|
|
@ -1227,14 +1227,14 @@ const loadMaintenanceStats = async (machineId) => {
|
|
|
|
|
// 加载生命周期类型统计
|
|
|
|
|
const loadLifecycleTypes = async () => {
|
|
|
|
|
if (!selectedMachine.value) return;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
const machineId = selectedMachine.value.machineId;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
try {
|
|
|
|
|
// 并行获取各类型数据的数量,使用不分页的API
|
|
|
|
|
const [
|
|
|
|
|
purchaseRes,
|
|
|
|
|
installRes,
|
|
|
|
|
installRes,
|
|
|
|
|
debugRes,
|
|
|
|
|
maintRes,
|
|
|
|
|
faultRes,
|
|
|
|
@ -1249,7 +1249,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
getDmsBillsInspectInstanceList({ machineId }).catch(() => ({ data: [] })),
|
|
|
|
|
getBaseAlarmInfoList({ machineId }).catch(() => ({ data: [] }))
|
|
|
|
|
]);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// 更新类型计数
|
|
|
|
|
lifecycleTypes.value.forEach(type => {
|
|
|
|
|
switch (type.value) {
|
|
|
|
@ -1273,7 +1273,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// 同时更新生命周期统计
|
|
|
|
|
lifecycleStats.value = {
|
|
|
|
|
faultCount: faultRes.data?.length || 0,
|
|
|
|
@ -1302,7 +1302,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
width: 100%;
|
|
|
|
|
height: 60px;
|
|
|
|
|
z-index: 0;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
svg {
|
|
|
|
|
width: 100%;
|
|
|
|
|
height: 100%;
|
|
|
|
@ -1320,7 +1320,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
border-radius: 6px;
|
|
|
|
|
margin-bottom: 8px;
|
|
|
|
|
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.panel-left {
|
|
|
|
|
.page-title {
|
|
|
|
|
font-size: 18px;
|
|
|
|
@ -1331,14 +1331,14 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
align-items: center;
|
|
|
|
|
gap: 6px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.page-subtitle {
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
color: #7f8c8d;
|
|
|
|
|
margin: 1px 0 0 0;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.panel-right {
|
|
|
|
|
.current-time {
|
|
|
|
|
display: flex;
|
|
|
|
@ -1356,7 +1356,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
|
|
|
|
|
gap: 8px;
|
|
|
|
|
margin-bottom: 8px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-item {
|
|
|
|
|
position: relative;
|
|
|
|
|
background: #fff;
|
|
|
|
@ -1365,12 +1365,12 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
|
|
|
|
|
transition: all 0.3s ease;
|
|
|
|
|
overflow: hidden;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:hover {
|
|
|
|
|
transform: translateY(-1px);
|
|
|
|
|
box-shadow: 0 3px 12px rgba(0, 0, 0, 0.15);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-bg-effect {
|
|
|
|
|
position: absolute;
|
|
|
|
|
top: 0;
|
|
|
|
@ -1381,7 +1381,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
opacity: 0.1;
|
|
|
|
|
transform: translate(25px, -25px);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-inner {
|
|
|
|
|
position: relative;
|
|
|
|
|
z-index: 2;
|
|
|
|
@ -1389,7 +1389,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
align-items: center;
|
|
|
|
|
gap: 10px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-icon-wrapper {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: center;
|
|
|
|
@ -1399,35 +1399,35 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
border-radius: 6px;
|
|
|
|
|
color: #fff;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-info {
|
|
|
|
|
flex: 1;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-number {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: baseline;
|
|
|
|
|
gap: 3px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.value-animate {
|
|
|
|
|
font-size: 20px;
|
|
|
|
|
font-weight: 700;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.unit {
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
color: #7f8c8d;
|
|
|
|
|
font-weight: 500;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-title {
|
|
|
|
|
font-size: 12px;
|
|
|
|
|
color: #7f8c8d;
|
|
|
|
|
margin-top: 1px;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-chart {
|
|
|
|
|
position: absolute;
|
|
|
|
|
bottom: 6px;
|
|
|
|
@ -1435,28 +1435,28 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
width: 50px;
|
|
|
|
|
height: 20px;
|
|
|
|
|
opacity: 0.3;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
svg {
|
|
|
|
|
width: 100%;
|
|
|
|
|
height: 100%;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.stat-total {
|
|
|
|
|
.stat-icon-wrapper { background: linear-gradient(45deg, #667eea, #764ba2); }
|
|
|
|
|
.stat-bg-effect { background: #667eea; }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.stat-running {
|
|
|
|
|
.stat-icon-wrapper { background: linear-gradient(45deg, #56ab2f, #a8e6cf); }
|
|
|
|
|
.stat-bg-effect { background: #56ab2f; }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.stat-maintenance {
|
|
|
|
|
.stat-icon-wrapper { background: linear-gradient(45deg, #f093fb, #f5576c); }
|
|
|
|
|
.stat-bg-effect { background: #f093fb; }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.stat-alarm {
|
|
|
|
|
.stat-icon-wrapper { background: linear-gradient(45deg, #fa709a, #fee140); }
|
|
|
|
|
.stat-bg-effect { background: #fa709a; }
|
|
|
|
@ -1469,7 +1469,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
justify-content: space-between;
|
|
|
|
|
align-items: center;
|
|
|
|
|
margin-bottom: 8px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.toolbar-left, .toolbar-right {
|
|
|
|
|
display: flex;
|
|
|
|
|
gap: 6px;
|
|
|
|
@ -1478,12 +1478,12 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
|
|
|
|
|
.search-filter-card {
|
|
|
|
|
margin-bottom: 8px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.filter-header {
|
|
|
|
|
display: flex;
|
|
|
|
|
justify-content: space-between;
|
|
|
|
|
align-items: center;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.filter-title {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: center;
|
|
|
|
@ -1491,11 +1491,11 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
font-weight: 600;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
:deep(.el-card__body) {
|
|
|
|
|
padding: 12px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.el-form {
|
|
|
|
|
.el-form-item {
|
|
|
|
|
margin-bottom: 8px;
|
|
|
|
@ -1510,10 +1510,10 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
grid-template-columns: repeat(3, 1fr);
|
|
|
|
|
gap: 8px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-card-wrapper {
|
|
|
|
|
cursor: pointer;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-card {
|
|
|
|
|
background: #fff;
|
|
|
|
|
border-radius: 4px;
|
|
|
|
@ -1521,22 +1521,22 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
box-shadow: 0 1px 4px rgba(0, 0, 0, 0.1);
|
|
|
|
|
transition: all 0.3s ease;
|
|
|
|
|
position: relative;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:hover {
|
|
|
|
|
transform: translateY(-1px);
|
|
|
|
|
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.selected {
|
|
|
|
|
border: 2px solid #409EFF;
|
|
|
|
|
box-shadow: 0 2px 8px rgba(64, 158, 255, 0.3);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.status-indicator {
|
|
|
|
|
position: absolute;
|
|
|
|
|
top: 6px;
|
|
|
|
|
right: 6px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.status-dot {
|
|
|
|
|
display: inline-block;
|
|
|
|
|
width: 5px;
|
|
|
|
@ -1544,17 +1544,17 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
border-radius: 50%;
|
|
|
|
|
animation: pulse 2s infinite;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.status-0 .status-dot { background: #f56c6c; }
|
|
|
|
|
&.status-1 .status-dot { background: #67c23a; }
|
|
|
|
|
&.status-2 .status-dot { background: #e6a23c; }
|
|
|
|
|
&.status-3 .status-dot { background: #909399; }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-visual {
|
|
|
|
|
text-align: center;
|
|
|
|
|
margin-bottom: 6px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-icon-bg {
|
|
|
|
|
display: inline-flex;
|
|
|
|
|
align-items: center;
|
|
|
|
@ -1566,17 +1566,17 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
color: #fff;
|
|
|
|
|
margin-bottom: 4px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-number {
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
font-weight: 600;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-details {
|
|
|
|
|
margin-bottom: 6px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-name {
|
|
|
|
|
font-size: 13px;
|
|
|
|
|
font-weight: 600;
|
|
|
|
@ -1588,7 +1588,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
text-overflow: ellipsis;
|
|
|
|
|
white-space: nowrap;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.machine-meta {
|
|
|
|
|
.meta-item {
|
|
|
|
|
display: flex;
|
|
|
|
@ -1600,19 +1600,19 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
overflow: hidden;
|
|
|
|
|
text-overflow: ellipsis;
|
|
|
|
|
white-space: nowrap;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:last-child {
|
|
|
|
|
margin-bottom: 0;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.quick-actions {
|
|
|
|
|
display: flex;
|
|
|
|
|
gap: 4px;
|
|
|
|
|
justify-content: center;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.el-button {
|
|
|
|
|
padding: 2px 6px;
|
|
|
|
|
font-size: 10px;
|
|
|
|
@ -1622,35 +1622,35 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.list-view {
|
|
|
|
|
.status-cell {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: center;
|
|
|
|
|
gap: 4px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.status-badge {
|
|
|
|
|
display: inline-block;
|
|
|
|
|
width: 5px;
|
|
|
|
|
height: 5px;
|
|
|
|
|
border-radius: 50%;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.status-0 { background: #f56c6c; }
|
|
|
|
|
&.status-1 { background: #67c23a; }
|
|
|
|
|
&.status-2 { background: #e6a23c; }
|
|
|
|
|
&.status-3 { background: #909399; }
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.date-text {
|
|
|
|
|
font-size: 12px;
|
|
|
|
|
color: #606266;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
:deep(.danger-row) {
|
|
|
|
|
background-color: rgba(245, 108, 108, 0.05);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
:deep(.warning-row) {
|
|
|
|
|
background-color: rgba(230, 162, 60, 0.05);
|
|
|
|
|
}
|
|
|
|
@ -1670,12 +1670,12 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
padding: 12px;
|
|
|
|
|
margin-bottom: 12px;
|
|
|
|
|
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.overview-header {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: center;
|
|
|
|
|
gap: 10px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.device-avatar {
|
|
|
|
|
display: flex;
|
|
|
|
|
align-items: center;
|
|
|
|
@ -1686,14 +1686,14 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
border-radius: 10px;
|
|
|
|
|
color: #fff;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.device-basic {
|
|
|
|
|
h2 {
|
|
|
|
|
margin: 0 0 3px 0;
|
|
|
|
|
font-size: 16px;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
p {
|
|
|
|
|
margin: 0;
|
|
|
|
|
font-size: 12px;
|
|
|
|
@ -1701,22 +1701,22 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.overview-stats {
|
|
|
|
|
display: grid;
|
|
|
|
|
grid-template-columns: repeat(auto-fit, minmax(80px, 1fr));
|
|
|
|
|
gap: 10px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat {
|
|
|
|
|
text-align: center;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-label {
|
|
|
|
|
display: block;
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
color: #7f8c8d;
|
|
|
|
|
margin-bottom: 3px;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.stat-value {
|
|
|
|
|
display: block;
|
|
|
|
|
font-size: 18px;
|
|
|
|
@ -1726,21 +1726,21 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.lifecycle-type-selector {
|
|
|
|
|
margin-bottom: 12px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
h3 {
|
|
|
|
|
margin: 0 0 10px 0;
|
|
|
|
|
font-size: 15px;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.type-cards {
|
|
|
|
|
display: grid;
|
|
|
|
|
grid-template-columns: repeat(auto-fit, minmax(100px, 1fr));
|
|
|
|
|
gap: 6px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.type-card {
|
|
|
|
|
background: #fff;
|
|
|
|
|
border: 2px solid #e1e6f0;
|
|
|
|
@ -1750,16 +1750,16 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
cursor: pointer;
|
|
|
|
|
transition: all 0.3s ease;
|
|
|
|
|
position: relative;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:hover {
|
|
|
|
|
border-color: #409EFF;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&.active {
|
|
|
|
|
border-color: #409EFF;
|
|
|
|
|
background: #f0f9ff;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.type-icon {
|
|
|
|
|
display: inline-flex;
|
|
|
|
|
align-items: center;
|
|
|
|
@ -1770,14 +1770,14 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
margin-bottom: 5px;
|
|
|
|
|
color: #fff;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.type-name {
|
|
|
|
|
display: block;
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
font-weight: 500;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.type-count {
|
|
|
|
|
position: absolute;
|
|
|
|
|
top: -3px;
|
|
|
|
@ -1793,28 +1793,28 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.lifecycle-timeline-container {
|
|
|
|
|
h3 {
|
|
|
|
|
margin: 0 0 10px 0;
|
|
|
|
|
font-size: 15px;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.timeline-wrapper {
|
|
|
|
|
position: relative;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.timeline-item {
|
|
|
|
|
position: relative;
|
|
|
|
|
padding-left: 35px;
|
|
|
|
|
padding-bottom: 16px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:last-child {
|
|
|
|
|
.timeline-line {
|
|
|
|
|
display: none;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.timeline-marker {
|
|
|
|
|
position: absolute;
|
|
|
|
|
left: 0;
|
|
|
|
@ -1828,47 +1828,47 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
color: #fff;
|
|
|
|
|
z-index: 2;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.timeline-content {
|
|
|
|
|
background: #fff;
|
|
|
|
|
border-radius: 6px;
|
|
|
|
|
padding: 10px;
|
|
|
|
|
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.event-header {
|
|
|
|
|
display: flex;
|
|
|
|
|
justify-content: space-between;
|
|
|
|
|
align-items: center;
|
|
|
|
|
margin-bottom: 5px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
h4 {
|
|
|
|
|
margin: 0;
|
|
|
|
|
font-size: 13px;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.event-time {
|
|
|
|
|
font-size: 11px;
|
|
|
|
|
color: #7f8c8d;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.event-description {
|
|
|
|
|
font-size: 12px;
|
|
|
|
|
color: #606266;
|
|
|
|
|
margin: 0 0 6px 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.event-tags {
|
|
|
|
|
margin-bottom: 6px;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.el-tag {
|
|
|
|
|
margin-right: 3px;
|
|
|
|
|
margin-bottom: 3px;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.timeline-line {
|
|
|
|
|
position: absolute;
|
|
|
|
|
left: 13px;
|
|
|
|
@ -1888,7 +1888,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
font-weight: 600;
|
|
|
|
|
color: #2c3e50;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
.maintenance-section {
|
|
|
|
|
.maintenance-summary {
|
|
|
|
|
margin-bottom: 12px;
|
|
|
|
@ -1899,7 +1899,7 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
.filter-btn-primary {
|
|
|
|
|
background: linear-gradient(45deg, #667eea, #764ba2);
|
|
|
|
|
border: none;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
&:hover {
|
|
|
|
|
background: linear-gradient(45deg, #5a6fd8, #6a4190);
|
|
|
|
|
}
|
|
|
|
@ -1910,12 +1910,12 @@ const loadLifecycleTypes = async () => {
|
|
|
|
|
transform: scale(0.95);
|
|
|
|
|
box-shadow: 0 0 0 0 currentColor;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
70% {
|
|
|
|
|
transform: scale(1);
|
|
|
|
|
box-shadow: 0 0 0 10px transparent;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
100% {
|
|
|
|
|
transform: scale(0.95);
|
|
|
|
|
box-shadow: 0 0 0 0 transparent;
|
|
|
|
|