From 74be8e1ea98d3f76fcb1a7e86a0e2de8561be6dd Mon Sep 17 00:00:00 2001 From: ZhuchkaTriplesix Date: Sun, 25 Oct 2026 21:29:59 +0300 Subject: [PATCH 1/2] fix(shortcuts): the screen's global shortcuts stay quiet while a dialog is on top (#1820) --- lib/features/main_screen/main_screen.dart | 357 +++++++++--------- .../main_screen/sidebar_toggle_test.dart | 55 ++- 2 files changed, 238 insertions(+), 174 deletions(-) diff --git a/lib/features/main_screen/main_screen.dart b/lib/features/main_screen/main_screen.dart index 30c0d718..e4543f61 100644 --- a/lib/features/main_screen/main_screen.dart +++ b/lib/features/main_screen/main_screen.dart @@ -104,6 +104,9 @@ class _MainScreenState extends State { bool _handleGlobalKeyEvent(KeyEvent event) { if (event is! KeyDownEvent) return false; + // A dialog or sheet is on top: the screen's shortcuts must not reach + // through it (Ctrl+N over the welcome tour opened a second dialog, #1820). + if (ModalRoute.of(context)?.isCurrent == false) return false; final keyboard = HardwareKeyboard.instance; final shortcut = MainScreenShortcuts.resolve( @@ -175,14 +178,14 @@ class _MainScreenState extends State { builder: (context, workspace, _) { return QueryaCommandHost( onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), - onNewConnection: () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + onNewConnection: () => + unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), onReloadConnections: () => unawaited( _connectionsPanelKey.currentState?.reloadConnectionsFromDb() ?? Future.value()), onShowQuickSwitcher: _nav.openQuickSwitcher, onOpenSchemaObject: _nav.onOpenSchemaObject, - onGoHome: - workspace.activeConnection != null ? _nav.onGoHome : null, + onGoHome: workspace.activeConnection != null ? _nav.onGoHome : null, onCloseWorkspace: _nav.hasCloseableWorkspace(workspace) ? () => unawaited(_nav.closeWorkspace()) : null, @@ -210,185 +213,197 @@ class _MainScreenState extends State { onOpenWelcomeTour: _dialogs.onOpenWelcomeTour, selectedConnectionId: workspace.activeConnection?.id, child: FocusScope( - autofocus: true, - child: material.CallbackShortcuts( - bindings: { - // New Database Connection: Ctrl+N / Cmd+N - const material.SingleActivator( - LogicalKeyboardKey.keyN, - meta: true, - ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - const material.SingleActivator( - LogicalKeyboardKey.keyN, - control: true, - ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + autofocus: true, + child: material.CallbackShortcuts( + bindings: { + // New Database Connection: Ctrl+N / Cmd+N + const material.SingleActivator( + LogicalKeyboardKey.keyN, + meta: true, + ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + const material.SingleActivator( + LogicalKeyboardKey.keyN, + control: true, + ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - // New Query Tab: Ctrl+Shift+N / Cmd+Shift+N - const material.SingleActivator( - LogicalKeyboardKey.keyN, - meta: true, - shift: true, - ): () => _invoke(const NewSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyN, - control: true, - shift: true, - ): () => _invoke(const NewSqlIntent()), + // New Query Tab: Ctrl+Shift+N / Cmd+Shift+N + const material.SingleActivator( + LogicalKeyboardKey.keyN, + meta: true, + shift: true, + ): () => _invoke(const NewSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyN, + control: true, + shift: true, + ): () => _invoke(const NewSqlIntent()), - // Open SQL File: Ctrl+O / Cmd+O - const material.SingleActivator( - LogicalKeyboardKey.keyO, - meta: true, - ): () => _invoke(const OpenSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyO, - control: true, - ): () => _invoke(const OpenSqlIntent()), + // Open SQL File: Ctrl+O / Cmd+O + const material.SingleActivator( + LogicalKeyboardKey.keyO, + meta: true, + ): () => _invoke(const OpenSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyO, + control: true, + ): () => _invoke(const OpenSqlIntent()), - // Save SQL File: Ctrl+S / Cmd+S - const material.SingleActivator( - LogicalKeyboardKey.keyS, - meta: true, - ): () => _invoke(const SaveSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyS, - control: true, - ): () => _invoke(const SaveSqlIntent()), + // Save SQL File: Ctrl+S / Cmd+S + const material.SingleActivator( + LogicalKeyboardKey.keyS, + meta: true, + ): () => _invoke(const SaveSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyS, + control: true, + ): () => _invoke(const SaveSqlIntent()), - // Toggle Left Sidebar: Ctrl+B / Cmd+B - const material.SingleActivator( - LogicalKeyboardKey.keyB, - control: true, - ): () => _splitKey.currentState?.toggleSidebar(), - const material.SingleActivator( - LogicalKeyboardKey.keyB, - meta: true, - ): () => _splitKey.currentState?.toggleSidebar(), + // Toggle Left Sidebar: Ctrl+B / Cmd+B + const material.SingleActivator( + LogicalKeyboardKey.keyB, + control: true, + ): () => _splitKey.currentState?.toggleSidebar(), + const material.SingleActivator( + LogicalKeyboardKey.keyB, + meta: true, + ): () => _splitKey.currentState?.toggleSidebar(), - const material.SingleActivator( - LogicalKeyboardKey.keyP, - control: true, - ): () => unawaited(showCommandPalette(context)), - const material.SingleActivator( - LogicalKeyboardKey.keyP, - meta: true, - ): () => unawaited(showCommandPalette(context)), - const material.SingleActivator( - LogicalKeyboardKey.keyK, - control: true, - ): () => _nav.openQuickSwitcher(), - const material.SingleActivator( - LogicalKeyboardKey.keyK, - meta: true, - ): () => _nav.openQuickSwitcher(), + const material.SingleActivator( + LogicalKeyboardKey.keyP, + control: true, + ): () => unawaited(showCommandPalette(context)), + const material.SingleActivator( + LogicalKeyboardKey.keyP, + meta: true, + ): () => unawaited(showCommandPalette(context)), + const material.SingleActivator( + LogicalKeyboardKey.keyK, + control: true, + ): () => _nav.openQuickSwitcher(), + const material.SingleActivator( + LogicalKeyboardKey.keyK, + meta: true, + ): () => _nav.openQuickSwitcher(), - // Welcome Tour & Tutorial: F1 / Cmd+Shift+H / Ctrl+Shift+H - const material.SingleActivator( - LogicalKeyboardKey.f1, - ): () => _dialogs.onOpenWelcomeTour(), - const material.SingleActivator( - LogicalKeyboardKey.keyH, - meta: true, - shift: true, - ): () => _dialogs.onOpenWelcomeTour(), - const material.SingleActivator( - LogicalKeyboardKey.keyH, - control: true, - shift: true, - ): () => _dialogs.onOpenWelcomeTour(), + // Welcome Tour & Tutorial: F1 / Cmd+Shift+H / Ctrl+Shift+H + const material.SingleActivator( + LogicalKeyboardKey.f1, + ): () => _dialogs.onOpenWelcomeTour(), + const material.SingleActivator( + LogicalKeyboardKey.keyH, + meta: true, + shift: true, + ): () => _dialogs.onOpenWelcomeTour(), + const material.SingleActivator( + LogicalKeyboardKey.keyH, + control: true, + shift: true, + ): () => _dialogs.onOpenWelcomeTour(), - // Return to Start / Home Screen: Cmd+Shift+0 / Ctrl+Shift+0 - const material.SingleActivator( - LogicalKeyboardKey.digit0, - meta: true, - shift: true, - ): _nav.onGoHome, - const material.SingleActivator( - LogicalKeyboardKey.digit0, - control: true, - shift: true, - ): _nav.onGoHome, - }, - child: QueryaPlatformMenuBar( - onNewConnection: () => - unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - onNewQueryTab: () => _invoke(const NewSqlIntent()), - onOpenSqlScript: () => _invoke(const OpenSqlIntent()), - onSaveQuery: () => _invoke(const SaveSqlIntent()), - onExecuteQuery: () => - SqlEditorCommandBridge.instance.invokeExecute(), - onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), - onOpenPreferences: () => showPreferencesDialog(context), - onOpenWelcomeTour: () => _dialogs.onOpenWelcomeTour(), - onOpenLogsFolder: () => unawaited(openLogsFolder(context)), - onCopyDiagnostics: () => unawaited(copyDiagnostics(context)), - onGoHome: _nav.onGoHome, - child: SqlEditorGlobalActions( - activeConnection: workspace.activeConnection, - onOpenSqlWorkspace: _nav.openSqlWorkspaceForConnection, - child: material.Scaffold( - backgroundColor: wb.canvas, - body: WindowBorder( - color: wb.borderSubtle.withValues(alpha: 0.35), - width: 1, - child: Column( - children: [ - ShellTitleBar( - workspace: workspace, - isSidebarVisible: _isSidebarVisible, - connectionsPanelKey: _connectionsPanelKey, - onToggleSidebar: () => - _splitKey.currentState?.toggleSidebar(), - dialogs: _dialogs, - nav: _nav, - ), - QueryaDivider( - height: 1, - color: wb.borderSubtle.withValues(alpha: 0.22)), - Expanded( - child: MainContentSplit( - key: _splitKey, - connectionsPanelKey: _connectionsPanelKey, - workspace: _workspace, - onSidebarVisibilityChanged: (v) => - _isSidebarVisible.value = v, - onConnectionSelected: _nav.onConnectionSelected, - onPostgresObjectSelected: _nav.onPostgresObjectSelected, - onMysqlObjectSelected: _nav.onMysqlObjectSelected, - onSqliteObjectSelected: _nav.onSqliteObjectSelected, - onExtensionObjectSelected: _nav.onExtensionObjectSelected, - onRedisDatabaseSelected: _nav.onRedisDatabaseSelected, - onMongoDBDatabaseSelected: _nav.onMongoDBDatabaseSelected, - onMongoCollectionSelected: _nav.onMongoCollectionSelected, - onPostgresOpenSqlWorkspace: _nav.onPostgresOpenSqlWorkspace, - onMysqlOpenSqlWorkspace: _nav.onMysqlOpenSqlWorkspace, - onSqliteOpenSqlWorkspace: _nav.onSqliteOpenSqlWorkspace, - onRequestNewConnection: _dialogs.openNewConnectionFromHero, - onRequestNewConnectionFromUrl: - _dialogs.onNewDatabaseConnectionFromUrl, - onRequestOpenSqlite: _dialogs.openSqliteFromHero, - onRequestLaunchDemo: _dialogs.onLaunchDemoPlayground, - onRequestOpenTour: _dialogs.onOpenWelcomeTour, - onOpenConnection: _nav.onConnectionSelected, - initialMongoCollection: _nav.pendingMongoCollection, + // Return to Start / Home Screen: Cmd+Shift+0 / Ctrl+Shift+0 + const material.SingleActivator( + LogicalKeyboardKey.digit0, + meta: true, + shift: true, + ): _nav.onGoHome, + const material.SingleActivator( + LogicalKeyboardKey.digit0, + control: true, + shift: true, + ): _nav.onGoHome, + }, + child: QueryaPlatformMenuBar( + onNewConnection: () => + unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + onNewQueryTab: () => _invoke(const NewSqlIntent()), + onOpenSqlScript: () => _invoke(const OpenSqlIntent()), + onSaveQuery: () => _invoke(const SaveSqlIntent()), + onExecuteQuery: () => + SqlEditorCommandBridge.instance.invokeExecute(), + onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), + onOpenPreferences: () => showPreferencesDialog(context), + onOpenWelcomeTour: () => _dialogs.onOpenWelcomeTour(), + onOpenLogsFolder: () => unawaited(openLogsFolder(context)), + onCopyDiagnostics: () => unawaited(copyDiagnostics(context)), + onGoHome: _nav.onGoHome, + child: SqlEditorGlobalActions( + activeConnection: workspace.activeConnection, + onOpenSqlWorkspace: _nav.openSqlWorkspaceForConnection, + child: material.Scaffold( + backgroundColor: wb.canvas, + body: WindowBorder( + color: wb.borderSubtle.withValues(alpha: 0.35), + width: 1, + child: Column( + children: [ + ShellTitleBar( + workspace: workspace, + isSidebarVisible: _isSidebarVisible, + connectionsPanelKey: _connectionsPanelKey, + onToggleSidebar: () => + _splitKey.currentState?.toggleSidebar(), + dialogs: _dialogs, + nav: _nav, + ), + QueryaDivider( + height: 1, + color: wb.borderSubtle.withValues(alpha: 0.22)), + Expanded( + child: MainContentSplit( + key: _splitKey, + connectionsPanelKey: _connectionsPanelKey, + workspace: _workspace, + onSidebarVisibilityChanged: (v) => + _isSidebarVisible.value = v, + onConnectionSelected: _nav.onConnectionSelected, + onPostgresObjectSelected: + _nav.onPostgresObjectSelected, + onMysqlObjectSelected: _nav.onMysqlObjectSelected, + onSqliteObjectSelected: + _nav.onSqliteObjectSelected, + onExtensionObjectSelected: + _nav.onExtensionObjectSelected, + onRedisDatabaseSelected: + _nav.onRedisDatabaseSelected, + onMongoDBDatabaseSelected: + _nav.onMongoDBDatabaseSelected, + onMongoCollectionSelected: + _nav.onMongoCollectionSelected, + onPostgresOpenSqlWorkspace: + _nav.onPostgresOpenSqlWorkspace, + onMysqlOpenSqlWorkspace: + _nav.onMysqlOpenSqlWorkspace, + onSqliteOpenSqlWorkspace: + _nav.onSqliteOpenSqlWorkspace, + onRequestNewConnection: + _dialogs.openNewConnectionFromHero, + onRequestNewConnectionFromUrl: + _dialogs.onNewDatabaseConnectionFromUrl, + onRequestOpenSqlite: _dialogs.openSqliteFromHero, + onRequestLaunchDemo: + _dialogs.onLaunchDemoPlayground, + onRequestOpenTour: _dialogs.onOpenWelcomeTour, + onOpenConnection: _nav.onConnectionSelected, + initialMongoCollection: + _nav.pendingMongoCollection, + ), + ), + ShellStatusBar( + workspace: workspace, + isSidebarVisible: _isSidebarVisible, + onToggleSidebar: () => + _splitKey.currentState?.toggleSidebar(), + ), + ], ), ), - ShellStatusBar( - workspace: workspace, - isSidebarVisible: _isSidebarVisible, - onToggleSidebar: () => - _splitKey.currentState?.toggleSidebar(), - ), - ], + ), ), ), ), - ), ), - ), - ), - ); - }, - ); -} + ); + }, + ); + } } diff --git a/test/features/main_screen/sidebar_toggle_test.dart b/test/features/main_screen/sidebar_toggle_test.dart index 9c51bd26..ad815eb9 100644 --- a/test/features/main_screen/sidebar_toggle_test.dart +++ b/test/features/main_screen/sidebar_toggle_test.dart @@ -1,6 +1,9 @@ -import 'package:flutter/widgets.dart'; +import 'dart:async'; import 'dart:io'; +import 'package:flutter/services.dart'; +import 'package:flutter/widgets.dart'; + import 'package:flutter/material.dart' as material; import 'package:flutter_test/flutter_test.dart'; import 'package:path_provider_platform_interface/path_provider_platform_interface.dart'; @@ -47,8 +50,7 @@ void main() { }); group('Fluid Collapsible Sidebar (#557)', () { - test('AppSettings preserves sidebarVisible across sets and gets', - () async { + test('AppSettings preserves sidebarVisible across sets and gets', () async { expect(await AppSettings.instance.getSidebarVisible(), isTrue); await AppSettings.instance.setSidebarVisible(false); @@ -252,6 +254,53 @@ void main() { ); }); + testWidgets('Ctrl+B does not reach through an open dialog (#1820)', + (tester) async { + await tester.pumpWidget( + queryaThemeTestShell( + child: const material.SizedBox( + width: 1200, + height: 800, + child: MainScreen(), + ), + ), + ); + await tester.pumpAndSettle(); + + bool sidebarHidden() => find + .ancestor( + of: find.byType(ConnectionsPanel, skipOffstage: false), + matching: find.byWidgetPredicate( + (w) => w is material.Offstage && w.offstage, + skipOffstage: false, + ), + ) + .evaluate() + .isNotEmpty; + + final context = tester.element(find.byType(MainScreen)); + unawaited(material.showDialog( + context: context, + builder: (_) => const material.AlertDialog(content: Text('modal')), + )); + await tester.pumpAndSettle(); + + await tester.sendKeyDownEvent(LogicalKeyboardKey.controlLeft); + await tester.sendKeyEvent(LogicalKeyboardKey.keyB); + await tester.sendKeyUpEvent(LogicalKeyboardKey.controlLeft); + await tester.pumpAndSettle(); + expect(sidebarHidden(), isFalse); + + material.Navigator.of(context).pop(); + await tester.pumpAndSettle(); + + await tester.sendKeyDownEvent(LogicalKeyboardKey.controlLeft); + await tester.sendKeyEvent(LogicalKeyboardKey.keyB); + await tester.sendKeyUpEvent(LogicalKeyboardKey.controlLeft); + await tester.pumpAndSettle(); + expect(sidebarHidden(), isTrue); + }); + testWidgets( 'isolates workspace layout constraints during sidebar spring animation (#984)', (tester) async { From 52ad9ea7f0221f5edf590d740c061975e25e5919 Mon Sep 17 00:00:00 2001 From: ZhuchkaTriplesix Date: Sun, 25 Oct 2026 21:30:10 +0300 Subject: [PATCH 2/2] fix(shortcuts): keep the guard change minimal, no reformat (#1820) --- lib/features/main_screen/main_screen.dart | 354 +++++++++++----------- 1 file changed, 171 insertions(+), 183 deletions(-) diff --git a/lib/features/main_screen/main_screen.dart b/lib/features/main_screen/main_screen.dart index e4543f61..40b3a932 100644 --- a/lib/features/main_screen/main_screen.dart +++ b/lib/features/main_screen/main_screen.dart @@ -178,14 +178,14 @@ class _MainScreenState extends State { builder: (context, workspace, _) { return QueryaCommandHost( onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), - onNewConnection: () => - unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + onNewConnection: () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), onReloadConnections: () => unawaited( _connectionsPanelKey.currentState?.reloadConnectionsFromDb() ?? Future.value()), onShowQuickSwitcher: _nav.openQuickSwitcher, onOpenSchemaObject: _nav.onOpenSchemaObject, - onGoHome: workspace.activeConnection != null ? _nav.onGoHome : null, + onGoHome: + workspace.activeConnection != null ? _nav.onGoHome : null, onCloseWorkspace: _nav.hasCloseableWorkspace(workspace) ? () => unawaited(_nav.closeWorkspace()) : null, @@ -213,197 +213,185 @@ class _MainScreenState extends State { onOpenWelcomeTour: _dialogs.onOpenWelcomeTour, selectedConnectionId: workspace.activeConnection?.id, child: FocusScope( - autofocus: true, - child: material.CallbackShortcuts( - bindings: { - // New Database Connection: Ctrl+N / Cmd+N - const material.SingleActivator( - LogicalKeyboardKey.keyN, - meta: true, - ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - const material.SingleActivator( - LogicalKeyboardKey.keyN, - control: true, - ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + autofocus: true, + child: material.CallbackShortcuts( + bindings: { + // New Database Connection: Ctrl+N / Cmd+N + const material.SingleActivator( + LogicalKeyboardKey.keyN, + meta: true, + ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + const material.SingleActivator( + LogicalKeyboardKey.keyN, + control: true, + ): () => unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - // New Query Tab: Ctrl+Shift+N / Cmd+Shift+N - const material.SingleActivator( - LogicalKeyboardKey.keyN, - meta: true, - shift: true, - ): () => _invoke(const NewSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyN, - control: true, - shift: true, - ): () => _invoke(const NewSqlIntent()), + // New Query Tab: Ctrl+Shift+N / Cmd+Shift+N + const material.SingleActivator( + LogicalKeyboardKey.keyN, + meta: true, + shift: true, + ): () => _invoke(const NewSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyN, + control: true, + shift: true, + ): () => _invoke(const NewSqlIntent()), - // Open SQL File: Ctrl+O / Cmd+O - const material.SingleActivator( - LogicalKeyboardKey.keyO, - meta: true, - ): () => _invoke(const OpenSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyO, - control: true, - ): () => _invoke(const OpenSqlIntent()), + // Open SQL File: Ctrl+O / Cmd+O + const material.SingleActivator( + LogicalKeyboardKey.keyO, + meta: true, + ): () => _invoke(const OpenSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyO, + control: true, + ): () => _invoke(const OpenSqlIntent()), - // Save SQL File: Ctrl+S / Cmd+S - const material.SingleActivator( - LogicalKeyboardKey.keyS, - meta: true, - ): () => _invoke(const SaveSqlIntent()), - const material.SingleActivator( - LogicalKeyboardKey.keyS, - control: true, - ): () => _invoke(const SaveSqlIntent()), + // Save SQL File: Ctrl+S / Cmd+S + const material.SingleActivator( + LogicalKeyboardKey.keyS, + meta: true, + ): () => _invoke(const SaveSqlIntent()), + const material.SingleActivator( + LogicalKeyboardKey.keyS, + control: true, + ): () => _invoke(const SaveSqlIntent()), - // Toggle Left Sidebar: Ctrl+B / Cmd+B - const material.SingleActivator( - LogicalKeyboardKey.keyB, - control: true, - ): () => _splitKey.currentState?.toggleSidebar(), - const material.SingleActivator( - LogicalKeyboardKey.keyB, - meta: true, - ): () => _splitKey.currentState?.toggleSidebar(), + // Toggle Left Sidebar: Ctrl+B / Cmd+B + const material.SingleActivator( + LogicalKeyboardKey.keyB, + control: true, + ): () => _splitKey.currentState?.toggleSidebar(), + const material.SingleActivator( + LogicalKeyboardKey.keyB, + meta: true, + ): () => _splitKey.currentState?.toggleSidebar(), - const material.SingleActivator( - LogicalKeyboardKey.keyP, - control: true, - ): () => unawaited(showCommandPalette(context)), - const material.SingleActivator( - LogicalKeyboardKey.keyP, - meta: true, - ): () => unawaited(showCommandPalette(context)), - const material.SingleActivator( - LogicalKeyboardKey.keyK, - control: true, - ): () => _nav.openQuickSwitcher(), - const material.SingleActivator( - LogicalKeyboardKey.keyK, - meta: true, - ): () => _nav.openQuickSwitcher(), + const material.SingleActivator( + LogicalKeyboardKey.keyP, + control: true, + ): () => unawaited(showCommandPalette(context)), + const material.SingleActivator( + LogicalKeyboardKey.keyP, + meta: true, + ): () => unawaited(showCommandPalette(context)), + const material.SingleActivator( + LogicalKeyboardKey.keyK, + control: true, + ): () => _nav.openQuickSwitcher(), + const material.SingleActivator( + LogicalKeyboardKey.keyK, + meta: true, + ): () => _nav.openQuickSwitcher(), - // Welcome Tour & Tutorial: F1 / Cmd+Shift+H / Ctrl+Shift+H - const material.SingleActivator( - LogicalKeyboardKey.f1, - ): () => _dialogs.onOpenWelcomeTour(), - const material.SingleActivator( - LogicalKeyboardKey.keyH, - meta: true, - shift: true, - ): () => _dialogs.onOpenWelcomeTour(), - const material.SingleActivator( - LogicalKeyboardKey.keyH, - control: true, - shift: true, - ): () => _dialogs.onOpenWelcomeTour(), + // Welcome Tour & Tutorial: F1 / Cmd+Shift+H / Ctrl+Shift+H + const material.SingleActivator( + LogicalKeyboardKey.f1, + ): () => _dialogs.onOpenWelcomeTour(), + const material.SingleActivator( + LogicalKeyboardKey.keyH, + meta: true, + shift: true, + ): () => _dialogs.onOpenWelcomeTour(), + const material.SingleActivator( + LogicalKeyboardKey.keyH, + control: true, + shift: true, + ): () => _dialogs.onOpenWelcomeTour(), - // Return to Start / Home Screen: Cmd+Shift+0 / Ctrl+Shift+0 - const material.SingleActivator( - LogicalKeyboardKey.digit0, - meta: true, - shift: true, - ): _nav.onGoHome, - const material.SingleActivator( - LogicalKeyboardKey.digit0, - control: true, - shift: true, - ): _nav.onGoHome, - }, - child: QueryaPlatformMenuBar( - onNewConnection: () => - unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), - onNewQueryTab: () => _invoke(const NewSqlIntent()), - onOpenSqlScript: () => _invoke(const OpenSqlIntent()), - onSaveQuery: () => _invoke(const SaveSqlIntent()), - onExecuteQuery: () => - SqlEditorCommandBridge.instance.invokeExecute(), - onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), - onOpenPreferences: () => showPreferencesDialog(context), - onOpenWelcomeTour: () => _dialogs.onOpenWelcomeTour(), - onOpenLogsFolder: () => unawaited(openLogsFolder(context)), - onCopyDiagnostics: () => unawaited(copyDiagnostics(context)), - onGoHome: _nav.onGoHome, - child: SqlEditorGlobalActions( - activeConnection: workspace.activeConnection, - onOpenSqlWorkspace: _nav.openSqlWorkspaceForConnection, - child: material.Scaffold( - backgroundColor: wb.canvas, - body: WindowBorder( - color: wb.borderSubtle.withValues(alpha: 0.35), - width: 1, - child: Column( - children: [ - ShellTitleBar( - workspace: workspace, - isSidebarVisible: _isSidebarVisible, - connectionsPanelKey: _connectionsPanelKey, - onToggleSidebar: () => - _splitKey.currentState?.toggleSidebar(), - dialogs: _dialogs, - nav: _nav, - ), - QueryaDivider( - height: 1, - color: wb.borderSubtle.withValues(alpha: 0.22)), - Expanded( - child: MainContentSplit( - key: _splitKey, - connectionsPanelKey: _connectionsPanelKey, - workspace: _workspace, - onSidebarVisibilityChanged: (v) => - _isSidebarVisible.value = v, - onConnectionSelected: _nav.onConnectionSelected, - onPostgresObjectSelected: - _nav.onPostgresObjectSelected, - onMysqlObjectSelected: _nav.onMysqlObjectSelected, - onSqliteObjectSelected: - _nav.onSqliteObjectSelected, - onExtensionObjectSelected: - _nav.onExtensionObjectSelected, - onRedisDatabaseSelected: - _nav.onRedisDatabaseSelected, - onMongoDBDatabaseSelected: - _nav.onMongoDBDatabaseSelected, - onMongoCollectionSelected: - _nav.onMongoCollectionSelected, - onPostgresOpenSqlWorkspace: - _nav.onPostgresOpenSqlWorkspace, - onMysqlOpenSqlWorkspace: - _nav.onMysqlOpenSqlWorkspace, - onSqliteOpenSqlWorkspace: - _nav.onSqliteOpenSqlWorkspace, - onRequestNewConnection: - _dialogs.openNewConnectionFromHero, - onRequestNewConnectionFromUrl: - _dialogs.onNewDatabaseConnectionFromUrl, - onRequestOpenSqlite: _dialogs.openSqliteFromHero, - onRequestLaunchDemo: - _dialogs.onLaunchDemoPlayground, - onRequestOpenTour: _dialogs.onOpenWelcomeTour, - onOpenConnection: _nav.onConnectionSelected, - initialMongoCollection: - _nav.pendingMongoCollection, - ), - ), - ShellStatusBar( - workspace: workspace, - isSidebarVisible: _isSidebarVisible, - onToggleSidebar: () => - _splitKey.currentState?.toggleSidebar(), - ), - ], + // Return to Start / Home Screen: Cmd+Shift+0 / Ctrl+Shift+0 + const material.SingleActivator( + LogicalKeyboardKey.digit0, + meta: true, + shift: true, + ): _nav.onGoHome, + const material.SingleActivator( + LogicalKeyboardKey.digit0, + control: true, + shift: true, + ): _nav.onGoHome, + }, + child: QueryaPlatformMenuBar( + onNewConnection: () => + unawaited(_dialogs.onNewDatabaseConnectionFromMenu()), + onNewQueryTab: () => _invoke(const NewSqlIntent()), + onOpenSqlScript: () => _invoke(const OpenSqlIntent()), + onSaveQuery: () => _invoke(const SaveSqlIntent()), + onExecuteQuery: () => + SqlEditorCommandBridge.instance.invokeExecute(), + onToggleSidebar: () => _splitKey.currentState?.toggleSidebar(), + onOpenPreferences: () => showPreferencesDialog(context), + onOpenWelcomeTour: () => _dialogs.onOpenWelcomeTour(), + onOpenLogsFolder: () => unawaited(openLogsFolder(context)), + onCopyDiagnostics: () => unawaited(copyDiagnostics(context)), + onGoHome: _nav.onGoHome, + child: SqlEditorGlobalActions( + activeConnection: workspace.activeConnection, + onOpenSqlWorkspace: _nav.openSqlWorkspaceForConnection, + child: material.Scaffold( + backgroundColor: wb.canvas, + body: WindowBorder( + color: wb.borderSubtle.withValues(alpha: 0.35), + width: 1, + child: Column( + children: [ + ShellTitleBar( + workspace: workspace, + isSidebarVisible: _isSidebarVisible, + connectionsPanelKey: _connectionsPanelKey, + onToggleSidebar: () => + _splitKey.currentState?.toggleSidebar(), + dialogs: _dialogs, + nav: _nav, + ), + QueryaDivider( + height: 1, + color: wb.borderSubtle.withValues(alpha: 0.22)), + Expanded( + child: MainContentSplit( + key: _splitKey, + connectionsPanelKey: _connectionsPanelKey, + workspace: _workspace, + onSidebarVisibilityChanged: (v) => + _isSidebarVisible.value = v, + onConnectionSelected: _nav.onConnectionSelected, + onPostgresObjectSelected: _nav.onPostgresObjectSelected, + onMysqlObjectSelected: _nav.onMysqlObjectSelected, + onSqliteObjectSelected: _nav.onSqliteObjectSelected, + onExtensionObjectSelected: _nav.onExtensionObjectSelected, + onRedisDatabaseSelected: _nav.onRedisDatabaseSelected, + onMongoDBDatabaseSelected: _nav.onMongoDBDatabaseSelected, + onMongoCollectionSelected: _nav.onMongoCollectionSelected, + onPostgresOpenSqlWorkspace: _nav.onPostgresOpenSqlWorkspace, + onMysqlOpenSqlWorkspace: _nav.onMysqlOpenSqlWorkspace, + onSqliteOpenSqlWorkspace: _nav.onSqliteOpenSqlWorkspace, + onRequestNewConnection: _dialogs.openNewConnectionFromHero, + onRequestNewConnectionFromUrl: + _dialogs.onNewDatabaseConnectionFromUrl, + onRequestOpenSqlite: _dialogs.openSqliteFromHero, + onRequestLaunchDemo: _dialogs.onLaunchDemoPlayground, + onRequestOpenTour: _dialogs.onOpenWelcomeTour, + onOpenConnection: _nav.onConnectionSelected, + initialMongoCollection: _nav.pendingMongoCollection, ), ), - ), + ShellStatusBar( + workspace: workspace, + isSidebarVisible: _isSidebarVisible, + onToggleSidebar: () => + _splitKey.currentState?.toggleSidebar(), + ), + ], ), ), ), + ), ), - ); - }, - ); - } + ), + ), + ); + }, + ); +} }