From 38151ad6a8e1fdf2e0d6b31e5f57d428e919471c Mon Sep 17 00:00:00 2001 From: Zeikrom251 Date: Wed, 30 Sep 2026 20:34:13 +0200 Subject: [PATCH] feat(desktop): fold the race page's side panel The quick log and incident feed fold to a thin strip from a button in the Quick log header, so the standings get the full width. The strip keeps an unfold button and one-click logging (a missed incident while LMU is offline). The choice is a display preference (racePanelFolded), kept across restarts. --- apps/desktop/src-tauri/src/display.rs | 10 +++- .../src/pages/race/QuickLog.module.scss | 6 ++ apps/desktop/src/pages/race/QuickLog.tsx | 11 +++- .../src/pages/race/RacePage.module.scss | 18 ++++++ apps/desktop/src/pages/race/RacePage.tsx | 59 ++++++++++++++++--- apps/desktop/src/workspace/useDisplay.ts | 1 + packages/shared/src/api.ts | 2 + 7 files changed, 97 insertions(+), 10 deletions(-) diff --git a/apps/desktop/src-tauri/src/display.rs b/apps/desktop/src-tauri/src/display.rs index b97fe1f..1bbc3b8 100644 --- a/apps/desktop/src-tauri/src/display.rs +++ b/apps/desktop/src-tauri/src/display.rs @@ -27,11 +27,19 @@ pub struct DisplayPrefs { pub hidden_columns: Vec, /// Inspector section ids kept folded. pub collapsed_sections: Vec, + /// Race page: the quick log + feed folded to a thin strip. + pub race_panel_folded: bool, } impl Default for DisplayPrefs { fn default() -> Self { - Self { density: Density::Compact, text_scale: 100, hidden_columns: Vec::new(), collapsed_sections: Vec::new() } + Self { + density: Density::Compact, + text_scale: 100, + hidden_columns: Vec::new(), + collapsed_sections: Vec::new(), + race_panel_folded: false, + } } } diff --git a/apps/desktop/src/pages/race/QuickLog.module.scss b/apps/desktop/src/pages/race/QuickLog.module.scss index 4ab2b96..c2020aa 100644 --- a/apps/desktop/src/pages/race/QuickLog.module.scss +++ b/apps/desktop/src/pages/race/QuickLog.module.scss @@ -13,6 +13,12 @@ gap: 8px; } +.fold { + width: 26px; + height: 26px; + margin-right: -6px; +} + .foot > button:first-child { padding-left: 2px; } diff --git a/apps/desktop/src/pages/race/QuickLog.tsx b/apps/desktop/src/pages/race/QuickLog.tsx index db6944c..536c0f0 100644 --- a/apps/desktop/src/pages/race/QuickLog.tsx +++ b/apps/desktop/src/pages/race/QuickLog.tsx @@ -115,13 +115,22 @@ function LiveActions({ live }: { live: Snapshot }) { } /** Docked quick-log panel: selection, stamp preview, and the one big button. */ -export function QuickLog({ live }: { live: Snapshot }) { +export function QuickLog({ live, onFold }: { live: Snapshot; onFold: () => void }) { return (
Quick log +
{live.session.connected ? : }
diff --git a/apps/desktop/src/pages/race/RacePage.module.scss b/apps/desktop/src/pages/race/RacePage.module.scss index f7fe899..1ea70c7 100644 --- a/apps/desktop/src/pages/race/RacePage.module.scss +++ b/apps/desktop/src/pages/race/RacePage.module.scss @@ -8,6 +8,24 @@ border-left: 1px solid var(--color-border); } +.strip { + flex: none; + display: flex; + flex-direction: column; + align-items: center; + gap: 10px; + padding: 12px 8px; + background: var(--color-surface); + border-left: 1px solid var(--color-border); +} + +// Beats .btn's padding whatever order the stylesheets load in. +.strip > .stripLog { + width: 34px; + height: 34px; + padding: 0; +} + .loading { margin: auto; color: var(--color-text-muted); diff --git a/apps/desktop/src/pages/race/RacePage.tsx b/apps/desktop/src/pages/race/RacePage.tsx index 07546af..fba2fb4 100644 --- a/apps/desktop/src/pages/race/RacePage.tsx +++ b/apps/desktop/src/pages/race/RacePage.tsx @@ -1,3 +1,4 @@ +import type { Snapshot } from '../../backend/backend' import { useLive } from '../../backend/LiveProvider' import { Inspector } from '../../inspector/Inspector' import { Icon } from '../../icons' @@ -6,6 +7,8 @@ import { cx } from '../../ui/primitives' import ui from '../../ui/ui.module.scss' import { useWorkspace } from '../../workspace/Workspace' import { useDataSource } from '../../workspace/useDataSource' +import { useDisplay } from '../../workspace/useDisplay' +import { useIncidentActions } from '../../workspace/useIncidentActions' import { IncidentFeed } from './IncidentFeed' import { QuickLog } from './QuickLog' import { Standings } from './Standings' @@ -45,6 +48,53 @@ function WaitingForLmu({ lastSeen }: { lastSeen: number }) { ) } +/** Folded, the panel keeps one button: Log incident live, Log a missed incident offline. */ +function FoldedPanel({ connected, onUnfold }: { connected: boolean; onUnfold: () => void }) { + const { quickLog, logMissed } = useIncidentActions() + const log = connected ? 'Log incident (Space)' : 'Log a missed incident' + return ( + + ) +} + +/** The right-hand panel: quick log + feed, or a thin strip so the timing tower gets the width. */ +function RacePanel({ live }: { live: Snapshot }) { + const { prefs, update } = useDisplay() + if (prefs.racePanelFolded) { + return ( + update({ racePanelFolded: false })} + /> + ) + } + return ( + + ) +} + /** Race control (design/02, 03, 08): timing tower left, quick log + feed or the inspector right. */ export function RacePage() { const live = useLive() @@ -59,14 +109,7 @@ export function RacePage() { ) : ( )} - {open ? ( - - ) : ( - - )} + {open ? : } ) } diff --git a/apps/desktop/src/workspace/useDisplay.ts b/apps/desktop/src/workspace/useDisplay.ts index 3a00fab..7e0078a 100644 --- a/apps/desktop/src/workspace/useDisplay.ts +++ b/apps/desktop/src/workspace/useDisplay.ts @@ -11,6 +11,7 @@ export const DEFAULT_DISPLAY: DisplayPrefs = { textScale: 100, hiddenColumns: [], collapsedSections: [], + racePanelFolded: false, } /** Settings → Display, read and written through the saved config. */ diff --git a/packages/shared/src/api.ts b/packages/shared/src/api.ts index b12a1f3..13adadf 100644 --- a/packages/shared/src/api.ts +++ b/packages/shared/src/api.ts @@ -77,6 +77,8 @@ export interface DisplayPrefs { hiddenColumns: string[] /** Inspector section ids kept folded. */ collapsedSections: string[] + /** Race page: the quick log + feed folded to a thin strip, for a wider timing tower. */ + racePanelFolded: boolean } export interface AppConfig {