From 50b5107bc2b7b87461265b9fc62eb58d712e0bad Mon Sep 17 00:00:00 2001 From: lingniu Date: Sat, 18 Jul 2026 14:59:55 +0800 Subject: [PATCH] refine Semi UI mobile monitor --- .../web/src/v2/pages/MonitorPage.test.tsx | 13 +++ .../apps/web/src/v2/pages/MonitorPage.tsx | 40 +++---- .../apps/web/src/v2/styles/workspace.css | 108 ++++++++++++++++-- 3 files changed, 129 insertions(+), 32 deletions(-) diff --git a/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.test.tsx b/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.test.tsx index f06d8946..87cec160 100644 --- a/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.test.tsx +++ b/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.test.tsx @@ -396,10 +396,23 @@ test('mounts only the mobile list representation and removes its viewport listen const queryClient = new QueryClient({ defaultOptions: { queries: { retry: false } } }); const view = render(); + const filterFields = view.container.querySelector('#monitor-filter-fields'); + expect(filterFields).toHaveClass('is-mobile-collapsed'); + const expandFilters = screen.getByRole('button', { name: '展开车辆筛选,当前 0 个条件' }); + expect(expandFilters).toHaveAttribute('aria-expanded', 'false'); + fireEvent.click(expandFilters); + expect(filterFields).not.toHaveClass('is-mobile-collapsed'); + const collapseFilters = screen.getByRole('button', { name: '收起车辆筛选,当前 0 个条件' }); + expect(collapseFilters).toHaveAttribute('aria-expanded', 'true'); + fireEvent.click(collapseFilters); + expect(filterFields).toHaveClass('is-mobile-collapsed'); + fireEvent.click(screen.getByRole('tab', { name: /列表/ })); expect(await screen.findByText('车辆实时列表')).toBeInTheDocument(); await waitFor(() => expect(view.container.querySelectorAll('.v2-monitor-mobile-cards .v2-monitor-mobile-card.semi-card')).toHaveLength(1)); expect(view.container.querySelector('.v2-monitor-table-scroll')).not.toBeInTheDocument(); + expect(screen.getByRole('button', { name: '在地图中定位粤A12345' })).toHaveTextContent('地图'); + expect(view.container.querySelector('.v2-monitor-mobile-card footer')).not.toBeInTheDocument(); expect(addEventListener).toHaveBeenCalledWith('change', expect.any(Function)); view.unmount(); diff --git a/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.tsx b/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.tsx index 797a2c36..177d3513 100644 --- a/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.tsx +++ b/vehicle-data-platform/apps/web/src/v2/pages/MonitorPage.tsx @@ -16,6 +16,7 @@ import { VehicleSourceEvidencePanel } from '../shared/VehicleSourceEvidencePanel import { WorkspacePanelHeader } from '../shared/WorkspacePanelHeader'; import { formatNumber, relativeFreshness, statusLabel, vehicleStatus } from '../domain/monitor'; import { formatTelemetryValue } from '../domain/telemetry'; +import { useMobileLayout } from '../hooks/useMobileLayout'; import { MAX_MONITOR_SEARCH_TERMS, MONITOR_REFRESH, monitorFilterScope, monitorQueryParams, parseMonitorSearchTerms, useMonitorData, useMonitorVehicleCard, type MonitorViewport } from '../hooks/useMonitorData'; import { LIVE_QUERY_POLICY, QUERY_MEMORY, retainPreviousPageWithinScope } from '../queryPolicy'; import { buildMonitorPath, parseMonitorRouteContext, withMonitorReturn } from '../routing/monitorContext'; @@ -23,7 +24,6 @@ import { buildMonitorPath, parseMonitorRouteContext, withMonitorReturn } from '. const protocols = ['', 'GB32960', 'JT808', 'YUTONG_MQTT']; const statuses = ['', 'online', 'offline', 'driving', 'idle', 'no_location']; const EMPTY_VEHICLES: VehicleRealtimeRow[] = []; -const MOBILE_MONITOR_QUERY = '(max-width: 760px)'; const MONITOR_VIEW_ITEMS = [ { key: 'map', label: '地图', icon: