main
liutao 1 week ago
parent 3f33f3f0dd
commit 11c8bd2131

@ -177,6 +177,60 @@ export default {
}
}
},
Dashboard3: {
Header: {
title: 'Device Operation Overview',
subTitle: 'IOT Real-Time Monitoring Center',
currentTime: 'Current Time: ',
lastUpdate: 'Last Updated: ',
refreshRate: 'Refresh: ',
refreshRateValue: 'Every {seconds}s'
},
Metrics: {
total: 'Total Devices',
online: 'Online',
offline: 'Offline',
running: 'Running',
standby: 'Idle',
fault: 'Alarms'
},
Status: {
running: 'Running',
standby: 'Idle',
fault: 'Alarm',
offline: 'Offline'
},
AlarmBoard: {
currentDevice: 'Alarm Device',
todayAlarmDuration: 'Today Alarm Duration',
lastReportTime: 'Last Reported',
alarmPrefix: 'Alarm',
empty: 'No alarm devices'
},
Detail: {
title: 'Device Operation Details',
carouselText: '{page} · Auto Carousel',
columns: {
deviceName: 'Device Name',
currentStatus: 'Status',
runningTime: 'Running Time (Today)',
standbyTime: 'Idle Time (Today)',
alarmTime: 'Alarm Time (Today)',
efficiency: 'Efficiency (Today)'
},
empty: 'No device operation data'
},
Charts: {
last24Hours: 'Last 24 Hours Operation Rate',
last7Days: 'Last 7 Days Operation Rate',
averageRate: 'Average: {value}'
},
Time: {
minute: '{minute}m',
hour: '{hour}h',
hourMinute: '{hour}h {minute}m'
}
},
Dashboard8: {
Header: {
title: 'Smart Manufacturing Line Task Overview',

@ -177,6 +177,60 @@ export default {
}
}
},
Dashboard3: {
Header: {
title: '设备运行总览大屏标题',
subTitle: 'IOT 实时监控中心副标题',
currentTime: '当前时间:',
lastUpdate: '最后更新:',
refreshRate: '刷新频率:',
refreshRateValue: '{seconds} 秒刷新'
},
Metrics: {
total: '设备总数',
online: '在线',
offline: '离线',
running: '运行',
standby: '空闲',
fault: '报警'
},
Status: {
running: '运行',
standby: '空闲',
fault: '报警',
offline: '离线'
},
AlarmBoard: {
currentDevice: '当前报警设备',
todayAlarmDuration: '今日累计报警时长',
lastReportTime: '最后上报时间',
alarmPrefix: '报警',
empty: '暂无报警设备'
},
Detail: {
title: '设备运行明细',
carouselText: '{page} · 自动轮播',
columns: {
deviceName: '设备名称',
currentStatus: '当前状态',
runningTime: '运行时间(今日)',
standbyTime: '空闲时间(今日)',
alarmTime: '报警时间(今日)',
efficiency: '运行效率(今日)'
},
empty: '暂无设备运行数据'
},
Charts: {
last24Hours: '近 24 小时运行率趋势',
last7Days: '近 7 天运行率趋势',
averageRate: '平均运行率:{value}'
},
Time: {
minute: '{minute}分',
hour: '{hour}小时',
hourMinute: '{hour}小时{minute}分'
}
},
Dashboard8: {
Header: {
title: '智能制造产线任务总览',

@ -655,10 +655,10 @@ const remainingRouter: AppRouteRecordRaw[] = [
},
{
path: '/iot/report/dashboardPage/Dashboard3',
component: () => import('@/views/report/dashboardPage/dashboard3/index.vue'),
component: () => import('@/views/report/dashboardPage/dashboard1/dashboard3/index.vue'),
name: 'IotReportDashboard3',
meta: {
title: '设备运行总览大屏',
title: t('Dashboard3.Header.title'),
hidden: true,
noTagsView: true,
canTo: true

@ -7,14 +7,14 @@
<div class="brand-icon">
<Icon icon="ep:cpu" />
</div>
<div class="brand-text">IOT 实时监控中心副标题</div>
<div class="brand-text">{{ t('Header.subTitle') }}</div>
</div>
<h1>设备运行总览大屏标题</h1>
<h1>{{ t('Header.title') }}</h1>
<div class="header-meta">
<div><span>当前时间</span>{{ currentTime }}</div>
<div><span>最后更新</span>{{ lastUpdateTime || '-' }}</div>
<div><span>{{ t('Header.currentTime') }}</span>{{ currentTime }}</div>
<div><span>{{ t('Header.lastUpdate') }}</span>{{ lastUpdateTime || '-' }}</div>
<div class="refresh-row">
<span>刷新频率</span>15 秒刷新
<span>{{ t('Header.refreshRate') }}</span>{{ t('Header.refreshRateValue', { seconds: 15 }) }}
<button type="button" class="screen-btn" @click="toggleFullscreen">
<Icon :icon="isFullscreen ? 'zmdi:fullscreen-exit' : 'zmdi:fullscreen'" />
</button>
@ -42,34 +42,34 @@
<div class="alarm-board panel">
<div class="alarm-head">
<span>当前报警设备</span>
<span>今日累计报警时长</span>
<span>最后上报时间</span>
<span>{{ t('AlarmBoard.currentDevice') }}</span>
<span>{{ t('AlarmBoard.todayAlarmDuration') }}</span>
<span>{{ t('AlarmBoard.lastReportTime') }}</span>
</div>
<div v-if="alarmDevices.length" class="alarm-list">
<div v-for="item in alarmDevices" :key="item.id" class="alarm-item">
<strong :title="item.name">{{ item.name }}</strong>
<span>报警 {{ formatMinutes(item.alarmMinutes) }}</span>
<span>{{ t('AlarmBoard.alarmPrefix') }} {{ formatMinutes(item.alarmMinutes) }}</span>
<span>{{ item.lastReportTime }}</span>
</div>
</div>
<div v-else class="empty-line">暂无报警设备</div>
<div v-else class="empty-line">{{ t('AlarmBoard.empty') }}</div>
</div>
</section>
<section class="panel detail-panel">
<div class="panel-title">
<h2>设备运行明细</h2>
<span>{{ detailPageText }} · 自动轮播</span>
<h2>{{ t('Detail.title') }}</h2>
<span>{{ t('Detail.carouselText', { page: detailPageText }) }}</span>
</div>
<div class="detail-table">
<div class="table-header table-row">
<span>设备名称</span>
<span>当前状态</span>
<span>运行时间(今日)</span>
<span>空闲时间(今日)</span>
<span>报警时间(今日)</span>
<span>运行效率(今日)</span>
<span>{{ t('Detail.columns.deviceName') }}</span>
<span>{{ t('Detail.columns.currentStatus') }}</span>
<span>{{ t('Detail.columns.runningTime') }}</span>
<span>{{ t('Detail.columns.standbyTime') }}</span>
<span>{{ t('Detail.columns.alarmTime') }}</span>
<span>{{ t('Detail.columns.efficiency') }}</span>
</div>
<div v-if="pagedRows.length" class="table-body">
<div
@ -88,22 +88,22 @@
<span class="rate">{{ formatPercent(row.utilizationRate) }}</span>
</div>
</div>
<div v-else class="empty-table">暂无设备运行数据</div>
<div v-else class="empty-table">{{ t('Detail.empty') }}</div>
</div>
</section>
<section class="chart-row">
<div class="panel chart-panel">
<div class="panel-title">
<h2> 24 小时运行率趋势</h2>
<span>平均运行率{{ formatPercent(todayAverageRate) }}</span>
<h2>{{ t('Charts.last24Hours') }}</h2>
<span>{{ t('Charts.averageRate', { value: formatPercent(todayAverageRate) }) }}</span>
</div>
<div ref="hourChartRef" class="chart"></div>
</div>
<div class="panel chart-panel">
<div class="panel-title">
<h2> 7 天运行率趋势</h2>
<span>平均运行率{{ formatPercent(sevenDayAverageRate) }}</span>
<h2>{{ t('Charts.last7Days') }}</h2>
<span>{{ t('Charts.averageRate', { value: formatPercent(sevenDayAverageRate) }) }}</span>
</div>
<div ref="weekChartRef" class="chart"></div>
</div>
@ -123,6 +123,8 @@ import { OrganizationApi } from '@/api/mes/organization'
defineOptions({ name: 'IotReportDashboard3' })
const { t } = useI18n('Dashboard3')
type RunStatus = 'running' | 'standby' | 'fault' | 'offline'
interface OrganizationFilterItem {
@ -168,12 +170,12 @@ let clockTimer: number | undefined
let refreshTimer: number | undefined
let carouselTimer: number | undefined
const statusText: Record<RunStatus, string> = {
running: '运行',
standby: '空闲',
fault: '报警',
offline: '离线'
}
const statusText = computed<Record<RunStatus, string>>(() => ({
running: t('Status.running'),
standby: t('Status.standby'),
fault: t('Status.fault'),
offline: t('Status.offline')
}))
const metricValueMap = computed(() => {
return overviewData.value.metrics.reduce<Record<string, number>>((acc, item) => {
@ -197,7 +199,7 @@ const summaryMap = computed(() => {
const statusCards = computed(() => [
{
key: 'total',
label: '设备总数',
label: t('Metrics.total'),
icon: 'ep:connection',
value:
overviewData.value.totalDevices ||
@ -207,7 +209,7 @@ const statusCards = computed(() => [
},
{
key: 'online',
label: '在线',
label: t('Metrics.online'),
icon: 'ep:cpu',
value: Math.max(0, totalDeviceCount.value - offlineDeviceCount.value),
percent: 100 - (summaryMap.value.offline || 0),
@ -215,7 +217,7 @@ const statusCards = computed(() => [
},
{
key: 'offline',
label: '离线',
label: t('Metrics.offline'),
icon: 'ep:link',
value: offlineDeviceCount.value,
percent: summaryMap.value.offline || 0,
@ -223,7 +225,7 @@ const statusCards = computed(() => [
},
{
key: 'running',
label: '运行',
label: t('Metrics.running'),
icon: 'ep:video-play',
value: getMetricValue(['running', 'run', 'runningDevices']) ?? getRowsByStatus('running').length,
percent: summaryMap.value.running || 0,
@ -231,7 +233,7 @@ const statusCards = computed(() => [
},
{
key: 'standby',
label: '空闲',
label: t('Metrics.standby'),
icon: 'ep:video-pause',
value: getMetricValue(['standby', 'idle', 'standbyDevices']) ?? getRowsByStatus('standby').length,
percent: summaryMap.value.standby || 0,
@ -239,7 +241,7 @@ const statusCards = computed(() => [
},
{
key: 'fault',
label: '报警',
label: t('Metrics.fault'),
icon: 'ep:bell',
value: getMetricValue(['fault', 'alarm', 'faultDevices']) ?? getRowsByStatus('fault').length,
percent: summaryMap.value.fault || 0,
@ -303,9 +305,9 @@ const formatMinutes = (minutes: number) => {
const safeMinutes = Math.max(0, Math.round(minutes || 0))
const hours = Math.floor(safeMinutes / 60)
const rest = safeMinutes % 60
if (!hours) return `${rest}`
if (!rest) return `${hours}小时`
return `${hours}小时${rest}`
if (!hours) return t('Time.minute', { minute: rest })
if (!rest) return t('Time.hour', { hour: hours })
return t('Time.hourMinute', { hour: hours, minute: rest })
}
const average = (values: number[]) => {

Loading…
Cancel
Save