| | |
| | | font-family: 'Inter', sans-serif; |
| | | background-color: #f5f7fa; |
| | | } |
| | | |
| | | .layui-card { |
| | | margin-bottom: 16px; |
| | | } |
| | | |
| | | .layui-card-header { |
| | | font-weight: 600; |
| | | } |
| | | |
| | | .status-online { |
| | | color: #10b981; |
| | | } |
| | | |
| | | .status-offline { |
| | | color: #ef4444; |
| | | } |
| | | |
| | | .chart-container { |
| | | height: 300px; |
| | | } |
| | | |
| | | .realtime-container { |
| | | height: 160px; |
| | | overflow-y: auto; |
| | |
| | | </style> |
| | | </head> |
| | | <body> |
| | | <div id="app"> |
| | | <!-- 顶部导航栏 --> |
| | | <lay-header height="60px" bg-color="#fff" shadow> |
| | | <template #left> |
| | | <div class="flex items-center space-x-2"> |
| | | <i class="fa fa-android text-2xl" style="color: #3b82f6"></i> |
| | | <h1 class="text-xl font-bold" style="color: #1e293b">机器人数据监控</h1> |
| | | </div> |
| | | </template> |
| | | <template #right> |
| | | <div class="flex items-center space-x-4"> |
| | | <lay-input placeholder="搜索机器人..." prefix-icon="search" style="width: 200px"></lay-input> |
| | | <lay-button type="primary" @click="refreshData"> |
| | | <i class="fa fa-refresh mr-1"></i> 刷新 |
| | | </lay-button> |
| | | </div> |
| | | </template> |
| | | </lay-header> |
| | | <div id="app"> |
| | | <!-- 顶部导航栏 --> |
| | | <lay-header height="60px" bg-color="#fff" shadow> |
| | | <template #left> |
| | | <div class="flex items-center space-x-2"> |
| | | <i class="fa fa-android text-2xl" style="color: #3b82f6"></i> |
| | | <h1 class="text-xl font-bold" style="color: #1e293b">机器人数据监控</h1> |
| | | </div> |
| | | </template> |
| | | <template #right> |
| | | <div class="flex items-center space-x-4"> |
| | | <lay-input placeholder="搜索机器人..." prefix-icon="search" style="width: 200px"></lay-input> |
| | | <lay-button type="primary" @click="refreshData"> |
| | | <i class="fa fa-refresh mr-1"></i> 刷新 |
| | | </lay-button> |
| | | </div> |
| | | </template> |
| | | </lay-header> |
| | | |
| | | <!-- 主内容区 --> |
| | | <lay-container style="padding: 20px"> |
| | | <!-- 状态概览 --> |
| | | <lay-row :gutter="16"> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">总机器人数</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #1e293b">24</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #dbeafe; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-microchip text-xl" style="color: #3b82f6"></i> |
| | | </div> |
| | | <!-- 主内容区 --> |
| | | <lay-container style="padding: 20px"> |
| | | <!-- 状态概览 --> |
| | | <lay-row :gutter="16"> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">总机器人数</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #1e293b">24</h3> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">在线机器人</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #10b981">18</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #d1fae5; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-check-circle text-xl" style="color: #10b981"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">离线机器人</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #ef4444">6</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #fee2e2; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-exclamation-circle text-xl" style="color: #ef4444"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">今日数据量</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #f59e0b">1.2k</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #fef3c7; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-database text-xl" style="color: #f59e0b"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | </lay-row> |
| | | |
| | | <!-- 数据图表 --> |
| | | <lay-row :gutter="16" style="margin-top: 16px"> |
| | | <lay-col :span="12"> |
| | | <lay-card shadow> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">上行数据趋势</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm" type="primary">小时</lay-button> |
| | | <lay-button size="sm">天</lay-button> |
| | | <lay-button size="sm">周</lay-button> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <div class="chart-container"> |
| | | <canvas ref="upDataChart"></canvas> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="12"> |
| | | <lay-card shadow> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">下行数据趋势</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm" type="primary">小时</lay-button> |
| | | <lay-button size="sm">天</lay-button> |
| | | <lay-button size="sm">周</lay-button> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <div class="chart-container"> |
| | | <canvas ref="downDataChart"></canvas> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | </lay-row> |
| | | |
| | | <!-- 设备数据表格 --> |
| | | <lay-card shadow style="margin-top: 16px"> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">机器人数据列表</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm"> |
| | | <i class="fa fa-filter mr-1"></i> 筛选 |
| | | </lay-button> |
| | | <lay-button size="sm"> |
| | | <i class="fa fa-download mr-1"></i> 导出 |
| | | </lay-button> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #dbeafe; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-microchip text-xl" style="color: #3b82f6"></i> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <lay-table :data="devices" :height="400"> |
| | | <lay-table-column prop="id" label="设备ID" width="120"></lay-table-column> |
| | | <lay-table-column prop="name" label="设备名称" width="150"></lay-table-column> |
| | | <lay-table-column prop="status" label="状态" width="100"> |
| | | <template #default="{ row }"> |
| | | <lay-badge v-if="row.status === 'online'" type="success">在线</lay-badge> |
| | | <lay-badge v-else type="danger">离线</lay-badge> |
| | | </template> |
| | | </lay-table-column> |
| | | <lay-table-column prop="upData" label="上行数据" width="120"></lay-table-column> |
| | | <lay-table-column prop="downData" label="下行数据" width="120"></lay-table-column> |
| | | <lay-table-column prop="lastComm" label="最后通信" width="150"></lay-table-column> |
| | | <lay-table-column label="操作" width="150"> |
| | | <template #default="{ row }"> |
| | | <lay-button size="sm" type="primary" style="margin-right: 8px"> |
| | | <i class="fa fa-eye"></i> |
| | | </lay-button> |
| | | <lay-button size="sm" type="warning" style="margin-right: 8px"> |
| | | <i class="fa fa-edit"></i> |
| | | </lay-button> |
| | | <lay-button size="sm" type="danger"> |
| | | <i class="fa fa-trash"></i> |
| | | </lay-button> |
| | | </template> |
| | | </lay-table-column> |
| | | </lay-table> |
| | | <div class="flex justify-between items-center mt-4"> |
| | | <p style="color: #64748b; font-size: 14px">显示 1-10 条,共 24 条</p> |
| | | <lay-pagination |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">在线机器人</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #10b981">18</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #d1fae5; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-check-circle text-xl" style="color: #10b981"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">离线机器人</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #ef4444">6</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #fee2e2; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-exclamation-circle text-xl" style="color: #ef4444"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="6"> |
| | | <lay-card shadow> |
| | | <div class="flex items-center justify-between"> |
| | | <div> |
| | | <p style="color: #64748b; font-size: 14px">今日数据量</p> |
| | | <h3 style="font-size: 24px; font-weight: bold; color: #f59e0b">1.2k</h3> |
| | | </div> |
| | | <div style="width: 48px; height: 48px; border-radius: 50%; background-color: #fef3c7; display: flex; align-items: center; justify-content: center"> |
| | | <i class="fa fa-database text-xl" style="color: #f59e0b"></i> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | </lay-row> |
| | | |
| | | <!-- 数据图表 --> |
| | | <lay-row :gutter="16" style="margin-top: 16px"> |
| | | <lay-col :span="12"> |
| | | <lay-card shadow> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">上行数据趋势</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm" type="primary">小时</lay-button> |
| | | <lay-button size="sm">天</lay-button> |
| | | <lay-button size="sm">周</lay-button> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <div class="chart-container"> |
| | | <canvas ref="upDataChart"></canvas> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | <lay-col :span="12"> |
| | | <lay-card shadow> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">下行数据趋势</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm" type="primary">小时</lay-button> |
| | | <lay-button size="sm">天</lay-button> |
| | | <lay-button size="sm">周</lay-button> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <div class="chart-container"> |
| | | <canvas ref="downDataChart"></canvas> |
| | | </div> |
| | | </lay-card> |
| | | </lay-col> |
| | | </lay-row> |
| | | |
| | | <!-- 设备数据表格 --> |
| | | <lay-card shadow style="margin-top: 16px"> |
| | | <template #header> |
| | | <div class="flex justify-between items-center"> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">机器人数据列表</h2> |
| | | <div class="flex space-x-2"> |
| | | <lay-button size="sm"> |
| | | <i class="fa fa-filter mr-1"></i> 筛选 |
| | | </lay-button> |
| | | <lay-button size="sm"> |
| | | <i class="fa fa-download mr-1"></i> 导出 |
| | | </lay-button> |
| | | </div> |
| | | </div> |
| | | </template> |
| | | <lay-table :data="devices" :height="400"> |
| | | <lay-table-column prop="id" label="设备ID" width="120"></lay-table-column> |
| | | <lay-table-column prop="name" label="设备名称" width="150"></lay-table-column> |
| | | <lay-table-column prop="status" label="状态" width="100"> |
| | | <template #default="{ row }"> |
| | | <lay-badge v-if="row.status === 'online'" type="success">在线</lay-badge> |
| | | <lay-badge v-else type="danger">离线</lay-badge> |
| | | </template> |
| | | </lay-table-column> |
| | | <lay-table-column prop="upData" label="上行数据" width="120"></lay-table-column> |
| | | <lay-table-column prop="downData" label="下行数据" width="120"></lay-table-column> |
| | | <lay-table-column prop="lastComm" label="最后通信" width="150"></lay-table-column> |
| | | <lay-table-column label="操作" width="150"> |
| | | <template #default="{ row }"> |
| | | <lay-button size="sm" type="primary" style="margin-right: 8px"> |
| | | <i class="fa fa-eye"></i> |
| | | </lay-button> |
| | | <lay-button size="sm" type="warning" style="margin-right: 8px"> |
| | | <i class="fa fa-edit"></i> |
| | | </lay-button> |
| | | <lay-button size="sm" type="danger"> |
| | | <i class="fa fa-trash"></i> |
| | | </lay-button> |
| | | </template> |
| | | </lay-table-column> |
| | | </lay-table> |
| | | <div class="flex justify-between items-center mt-4"> |
| | | <p style="color: #64748b; font-size: 14px">显示 1-10 条,共 24 条</p> |
| | | <lay-pagination |
| | | v-model:current="currentPage" |
| | | v-model:limit="pageSize" |
| | | :total="total" |
| | | :limits="[10, 20, 50, 100]" |
| | | layout="prev, pager, next, jumper, sizes, total" |
| | | ></lay-pagination> |
| | | </div> |
| | | </lay-card> |
| | | |
| | | <!-- 实时数据更新 --> |
| | | <lay-card shadow style="margin-top: 16px"> |
| | | <template #header> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">实时数据更新</h2> |
| | | </template> |
| | | <div class="realtime-container p-2 border border-gray-200 rounded-lg"> |
| | | <div v-for="(item, index) in realtimeData" :key="index" class="py-1 border-b border-gray-100"> |
| | | <span style="color: #64748b; font-size: 12px">{{ item.timestamp }}</span> |
| | | <span style="color: #1e293b; margin-left: 10px">{{ item.message }}</span> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-container> |
| | | |
| | | <!-- 页脚 --> |
| | | <lay-footer height="60px" bg-color="#fff" shadow> |
| | | <div class="text-center" style="color: #64748b; font-size: 14px"> |
| | | © 2026 机器人数据监控系统 | 版本 1.0.0 |
| | | ></lay-pagination> |
| | | </div> |
| | | </lay-footer> |
| | | </div> |
| | | </lay-card> |
| | | |
| | | <script> |
| | | const { createApp, ref, onMounted } = Vue; |
| | | const app = createApp({ |
| | | components: { |
| | | LayHeader: layui.LayHeader, |
| | | LayContainer: layui.LayContainer, |
| | | LayRow: layui.LayRow, |
| | | LayCol: layui.LayCol, |
| | | LayCard: layui.LayCard, |
| | | LayInput: layui.LayInput, |
| | | LayButton: layui.LayButton, |
| | | LayTable: layui.LayTable, |
| | | LayTableColumn: layui.LayTableColumn, |
| | | LayBadge: layui.LayBadge, |
| | | LayPagination: layui.LayPagination, |
| | | LayFooter: layui.LayFooter |
| | | }, |
| | | setup() { |
| | | // 模拟机器人数据 |
| | | const devices = ref([ |
| | | { id: 'ROB-001', name: '配送机器人1号', status: 'online', upData: '2.4KB', downData: '0.8KB', lastComm: '2分钟前' }, |
| | | { id: 'ROB-002', name: '配送机器人2号', status: 'online', upData: '1.8KB', downData: '0.5KB', lastComm: '5分钟前' }, |
| | | { id: 'ROB-003', name: '巡检机器人1号', status: 'offline', upData: '0KB', downData: '0KB', lastComm: '2小时前' }, |
| | | { id: 'ROB-004', name: '配送机器人3号', status: 'online', upData: '3.2KB', downData: '1.2KB', lastComm: '1分钟前' }, |
| | | { id: 'ROB-005', name: '巡检机器人2号', status: 'online', upData: '1.5KB', downData: '0.6KB', lastComm: '3分钟前' }, |
| | | { id: 'ROB-006', name: '配送机器人4号', status: 'offline', upData: '0KB', downData: '0KB', lastComm: '5小时前' }, |
| | | { id: 'ROB-007', name: '巡检机器人3号', status: 'online', upData: '2.1KB', downData: '0.9KB', lastComm: '4分钟前' }, |
| | | { id: 'ROB-008', name: '配送机器人5号', status: 'online', upData: '2.8KB', downData: '1.1KB', lastComm: '2分钟前' }, |
| | | { id: 'ROB-009', name: '巡检机器人4号', status: 'offline', upData: '0KB', downData: '0KB', lastComm: '1天前' }, |
| | | { id: 'ROB-010', name: '配送机器人6号', status: 'online', upData: '1.9KB', downData: '0.7KB', lastComm: '6分钟前' } |
| | | ]); |
| | | <!-- 实时数据更新 --> |
| | | <lay-card shadow style="margin-top: 16px"> |
| | | <template #header> |
| | | <h2 style="font-size: 16px; font-weight: 600; color: #1e293b">实时数据更新</h2> |
| | | </template> |
| | | <div class="realtime-container p-2 border border-gray-200 rounded-lg"> |
| | | <div v-for="(item, index) in realtimeData" :key="index" class="py-1 border-b border-gray-100"> |
| | | <span style="color: #64748b; font-size: 12px">{{ item.timestamp }}</span> |
| | | <span style="color: #1e293b; margin-left: 10px">{{ item.message }}</span> |
| | | </div> |
| | | </div> |
| | | </lay-card> |
| | | </lay-container> |
| | | |
| | | // 分页数据 |
| | | const currentPage = ref(1); |
| | | const pageSize = ref(10); |
| | | const total = ref(24); |
| | | <!-- 页脚 --> |
| | | <lay-footer height="60px" bg-color="#fff" shadow> |
| | | <div class="text-center" style="color: #64748b; font-size: 14px"> |
| | | © 2026 机器人数据监控系统 | 版本 1.0.0 |
| | | </div> |
| | | </lay-footer> |
| | | </div> |
| | | |
| | | // 实时数据 |
| | | const realtimeData = ref([]); |
| | | <script> |
| | | const {createApp, ref, onMounted} = Vue; |
| | | const app = createApp({ |
| | | components: { |
| | | LayHeader: layui.LayHeader, |
| | | LayContainer: layui.LayContainer, |
| | | LayRow: layui.LayRow, |
| | | LayCol: layui.LayCol, |
| | | LayCard: layui.LayCard, |
| | | LayInput: layui.LayInput, |
| | | LayButton: layui.LayButton, |
| | | LayTable: layui.LayTable, |
| | | LayTableColumn: layui.LayTableColumn, |
| | | LayBadge: layui.LayBadge, |
| | | LayPagination: layui.LayPagination, |
| | | LayFooter: layui.LayFooter |
| | | }, |
| | | setup() { |
| | | // 模拟机器人数据 |
| | | const devices = ref([ |
| | | { |
| | | id: 'ROB-001', |
| | | name: '配送机器人1号', |
| | | status: 'online', |
| | | upData: '2.4KB', |
| | | downData: '0.8KB', |
| | | lastComm: '2分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-002', |
| | | name: '配送机器人2号', |
| | | status: 'online', |
| | | upData: '1.8KB', |
| | | downData: '0.5KB', |
| | | lastComm: '5分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-003', |
| | | name: '巡检机器人1号', |
| | | status: 'offline', |
| | | upData: '0KB', |
| | | downData: '0KB', |
| | | lastComm: '2小时前' |
| | | }, |
| | | { |
| | | id: 'ROB-004', |
| | | name: '配送机器人3号', |
| | | status: 'online', |
| | | upData: '3.2KB', |
| | | downData: '1.2KB', |
| | | lastComm: '1分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-005', |
| | | name: '巡检机器人2号', |
| | | status: 'online', |
| | | upData: '1.5KB', |
| | | downData: '0.6KB', |
| | | lastComm: '3分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-006', |
| | | name: '配送机器人4号', |
| | | status: 'offline', |
| | | upData: '0KB', |
| | | downData: '0KB', |
| | | lastComm: '5小时前' |
| | | }, |
| | | { |
| | | id: 'ROB-007', |
| | | name: '巡检机器人3号', |
| | | status: 'online', |
| | | upData: '2.1KB', |
| | | downData: '0.9KB', |
| | | lastComm: '4分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-008', |
| | | name: '配送机器人5号', |
| | | status: 'online', |
| | | upData: '2.8KB', |
| | | downData: '1.1KB', |
| | | lastComm: '2分钟前' |
| | | }, |
| | | { |
| | | id: 'ROB-009', |
| | | name: '巡检机器人4号', |
| | | status: 'offline', |
| | | upData: '0KB', |
| | | downData: '0KB', |
| | | lastComm: '1天前' |
| | | }, |
| | | { |
| | | id: 'ROB-010', |
| | | name: '配送机器人6号', |
| | | status: 'online', |
| | | upData: '1.9KB', |
| | | downData: '0.7KB', |
| | | lastComm: '6分钟前' |
| | | } |
| | | ]); |
| | | |
| | | // 图表引用 |
| | | const upDataChart = ref(null); |
| | | const downDataChart = ref(null); |
| | | // 分页数据 |
| | | const currentPage = ref(1); |
| | | const pageSize = ref(10); |
| | | const total = ref(24); |
| | | |
| | | // 刷新数据 |
| | | const refreshData = () => { |
| | | console.log('刷新数据'); |
| | | // 这里可以添加实际的刷新逻辑 |
| | | }; |
| | | // 实时数据 |
| | | const realtimeData = ref([]); |
| | | |
| | | // 初始化图表 |
| | | const initCharts = () => { |
| | | // 上行数据图表 |
| | | const upCtx = upDataChart.value.getContext('2d'); |
| | | new Chart(upCtx, { |
| | | type: 'line', |
| | | data: { |
| | | labels: ['00:00', '03:00', '06:00', '09:00', '12:00', '15:00', '18:00', '21:00'], |
| | | datasets: [{ |
| | | label: '上行数据 (KB)', |
| | | data: [12, 19, 15, 25, 22, 30, 28, 35], |
| | | borderColor: '#3b82f6', |
| | | backgroundColor: 'rgba(59, 130, 246, 0.1)', |
| | | tension: 0.4, |
| | | fill: true |
| | | }] |
| | | // 图表引用 |
| | | const upDataChart = ref(null); |
| | | const downDataChart = ref(null); |
| | | |
| | | // 刷新数据 |
| | | const refreshData = () => { |
| | | console.log('刷新数据'); |
| | | // 这里可以添加实际的刷新逻辑 |
| | | }; |
| | | |
| | | // 初始化图表 |
| | | const initCharts = () => { |
| | | // 上行数据图表 |
| | | const upCtx = upDataChart.value.getContext('2d'); |
| | | new Chart(upCtx, { |
| | | type: 'line', |
| | | data: { |
| | | labels: ['00:00', '03:00', '06:00', '09:00', '12:00', '15:00', '18:00', '21:00'], |
| | | datasets: [{ |
| | | label: '上行数据 (KB)', |
| | | data: [12, 19, 15, 25, 22, 30, 28, 35], |
| | | borderColor: '#3b82f6', |
| | | backgroundColor: 'rgba(59, 130, 246, 0.1)', |
| | | tension: 0.4, |
| | | fill: true |
| | | }] |
| | | }, |
| | | options: { |
| | | responsive: true, |
| | | maintainAspectRatio: false, |
| | | plugins: { |
| | | legend: { |
| | | display: false |
| | | } |
| | | }, |
| | | options: { |
| | | responsive: true, |
| | | maintainAspectRatio: false, |
| | | plugins: { |
| | | legend: { |
| | | display: false |
| | | } |
| | | }, |
| | | scales: { |
| | | y: { |
| | | beginAtZero: true |
| | | } |
| | | scales: { |
| | | y: { |
| | | beginAtZero: true |
| | | } |
| | | } |
| | | }); |
| | | |
| | | // 下行数据图表 |
| | | const downCtx = downDataChart.value.getContext('2d'); |
| | | new Chart(downCtx, { |
| | | type: 'line', |
| | | data: { |
| | | labels: ['00:00', '03:00', '06:00', '09:00', '12:00', '15:00', '18:00', '21:00'], |
| | | datasets: [{ |
| | | label: '下行数据 (KB)', |
| | | data: [5, 8, 6, 12, 10, 15, 13, 18], |
| | | borderColor: '#10b981', |
| | | backgroundColor: 'rgba(16, 185, 129, 0.1)', |
| | | tension: 0.4, |
| | | fill: true |
| | | }] |
| | | }, |
| | | options: { |
| | | responsive: true, |
| | | maintainAspectRatio: false, |
| | | plugins: { |
| | | legend: { |
| | | display: false |
| | | } |
| | | }, |
| | | scales: { |
| | | y: { |
| | | beginAtZero: true |
| | | } |
| | | } |
| | | } |
| | | }); |
| | | }; |
| | | |
| | | // 模拟实时数据更新 |
| | | const simulateRealtimeData = () => { |
| | | const messages = [ |
| | | 'ROB-001 配送机器人1号: 运行中,位置: A1区', |
| | | 'ROB-002 配送机器人2号: 待机中,位置: B2区', |
| | | 'ROB-004 配送机器人3号: 充电中,电量: 85%', |
| | | 'ROB-005 巡检机器人2号: 巡检中,已完成3/5任务', |
| | | 'ROB-007 巡检机器人3号: 待机中,位置: C3区', |
| | | 'ROB-008 配送机器人5号: 运行中,位置: D4区' |
| | | ]; |
| | | |
| | | setInterval(() => { |
| | | const message = messages[Math.floor(Math.random() * messages.length)]; |
| | | const timestamp = new Date().toLocaleTimeString(); |
| | | realtimeData.value.unshift({ timestamp, message }); |
| | | // 限制显示条数 |
| | | if (realtimeData.value.length > 20) { |
| | | realtimeData.value.pop(); |
| | | } |
| | | }, 2000); |
| | | }; |
| | | |
| | | // 页面加载完成后初始化 |
| | | onMounted(() => { |
| | | initCharts(); |
| | | simulateRealtimeData(); |
| | | } |
| | | }); |
| | | |
| | | return { |
| | | devices, |
| | | currentPage, |
| | | pageSize, |
| | | total, |
| | | realtimeData, |
| | | upDataChart, |
| | | downDataChart, |
| | | refreshData |
| | | }; |
| | | } |
| | | }); |
| | | app.mount('#app'); |
| | | </script> |
| | | // 下行数据图表 |
| | | const downCtx = downDataChart.value.getContext('2d'); |
| | | new Chart(downCtx, { |
| | | type: 'line', |
| | | data: { |
| | | labels: ['00:00', '03:00', '06:00', '09:00', '12:00', '15:00', '18:00', '21:00'], |
| | | datasets: [{ |
| | | label: '下行数据 (KB)', |
| | | data: [5, 8, 6, 12, 10, 15, 13, 18], |
| | | borderColor: '#10b981', |
| | | backgroundColor: 'rgba(16, 185, 129, 0.1)', |
| | | tension: 0.4, |
| | | fill: true |
| | | }] |
| | | }, |
| | | options: { |
| | | responsive: true, |
| | | maintainAspectRatio: false, |
| | | plugins: { |
| | | legend: { |
| | | display: false |
| | | } |
| | | }, |
| | | scales: { |
| | | y: { |
| | | beginAtZero: true |
| | | } |
| | | } |
| | | } |
| | | }); |
| | | }; |
| | | |
| | | // 模拟实时数据更新 |
| | | const simulateRealtimeData = () => { |
| | | const messages = [ |
| | | 'ROB-001 配送机器人1号: 运行中,位置: A1区', |
| | | 'ROB-002 配送机器人2号: 待机中,位置: B2区', |
| | | 'ROB-004 配送机器人3号: 充电中,电量: 85%', |
| | | 'ROB-005 巡检机器人2号: 巡检中,已完成3/5任务', |
| | | 'ROB-007 巡检机器人3号: 待机中,位置: C3区', |
| | | 'ROB-008 配送机器人5号: 运行中,位置: D4区' |
| | | ]; |
| | | |
| | | setInterval(() => { |
| | | const message = messages[Math.floor(Math.random() * messages.length)]; |
| | | const timestamp = new Date().toLocaleTimeString(); |
| | | realtimeData.value.unshift({timestamp, message}); |
| | | // 限制显示条数 |
| | | if (realtimeData.value.length > 20) { |
| | | realtimeData.value.pop(); |
| | | } |
| | | }, 2000); |
| | | }; |
| | | |
| | | // 页面加载完成后初始化 |
| | | onMounted(() => { |
| | | initCharts(); |
| | | simulateRealtimeData(); |
| | | }); |
| | | |
| | | return { |
| | | devices, |
| | | currentPage, |
| | | pageSize, |
| | | total, |
| | | realtimeData, |
| | | upDataChart, |
| | | downDataChart, |
| | | refreshData |
| | | }; |
| | | } |
| | | }); |
| | | app.mount('#app'); |
| | | </script> |
| | | </body> |
| | | </html> |