dont allow focus on buttons
This commit is contained in:
+52
-17
@@ -57,6 +57,7 @@ import 'package:weblibre/features/user/domain/repositories/general_settings.dart
|
|||||||
import 'package:weblibre/presentation/hooks/cached_future.dart';
|
import 'package:weblibre/presentation/hooks/cached_future.dart';
|
||||||
import 'package:weblibre/presentation/hooks/menu_controller.dart';
|
import 'package:weblibre/presentation/hooks/menu_controller.dart';
|
||||||
import 'package:weblibre/presentation/icons/tor_icons.dart';
|
import 'package:weblibre/presentation/icons/tor_icons.dart';
|
||||||
|
import 'package:weblibre/presentation/widgets/non_focusable.dart';
|
||||||
import 'package:weblibre/presentation/widgets/selectable_chips.dart';
|
import 'package:weblibre/presentation/widgets/selectable_chips.dart';
|
||||||
import 'package:weblibre/presentation/widgets/url_icon.dart';
|
import 'package:weblibre/presentation/widgets/url_icon.dart';
|
||||||
|
|
||||||
@@ -325,6 +326,7 @@ class BrowserTabBar extends HookConsumerWidget {
|
|||||||
|
|
||||||
return Visibility(
|
return Visibility(
|
||||||
visible: tabBarReaderView || readerabilityStateActive,
|
visible: tabBarReaderView || readerabilityStateActive,
|
||||||
|
child: NonFocusable(
|
||||||
child: ReaderButton(
|
child: ReaderButton(
|
||||||
buttonBuilder: (isLoading, readerActive, icon) =>
|
buttonBuilder: (isLoading, readerActive, icon) =>
|
||||||
InkWell(
|
InkWell(
|
||||||
@@ -336,7 +338,9 @@ class BrowserTabBar extends HookConsumerWidget {
|
|||||||
readerableScreenControllerProvider
|
readerableScreenControllerProvider
|
||||||
.notifier,
|
.notifier,
|
||||||
)
|
)
|
||||||
.toggleReaderView(!readerActive);
|
.toggleReaderView(
|
||||||
|
!readerActive,
|
||||||
|
);
|
||||||
},
|
},
|
||||||
child: Padding(
|
child: Padding(
|
||||||
padding: const EdgeInsets.symmetric(
|
padding: const EdgeInsets.symmetric(
|
||||||
@@ -347,11 +351,13 @@ class BrowserTabBar extends HookConsumerWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
if (showExtensionShortcut)
|
if (showExtensionShortcut)
|
||||||
ExtensionShortcutMenu(
|
NonFocusable(
|
||||||
|
child: ExtensionShortcutMenu(
|
||||||
controller: extensionMenuController,
|
controller: extensionMenuController,
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
@@ -364,8 +370,10 @@ class BrowserTabBar extends HookConsumerWidget {
|
|||||||
icon: const Icon(MdiIcons.puzzle),
|
icon: const Icon(MdiIcons.puzzle),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
if (selectedTabId != null)
|
if (selectedTabId != null)
|
||||||
TabMenu(
|
NonFocusable(
|
||||||
|
child: TabMenu(
|
||||||
controller: trippleDotMenuController,
|
controller: trippleDotMenuController,
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
builder: (context, controller, child) {
|
builder: (context, controller, child) {
|
||||||
@@ -387,17 +395,22 @@ class BrowserTabBar extends HookConsumerWidget {
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
|
),
|
||||||
if (showMainToolbarTabsCount)
|
if (showMainToolbarTabsCount)
|
||||||
TabsCountButton(
|
NonFocusable(
|
||||||
|
child: TabsCountButton(
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
displayedSheet: displayedSheet,
|
displayedSheet: displayedSheet,
|
||||||
showLongPressMenu: true,
|
showLongPressMenu: true,
|
||||||
),
|
),
|
||||||
|
),
|
||||||
if (showMainToolbarNavigationButton)
|
if (showMainToolbarNavigationButton)
|
||||||
NavigationMenuButton(
|
NonFocusable(
|
||||||
|
child: NavigationMenuButton(
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
showNavigationButtons: true,
|
showNavigationButtons: true,
|
||||||
),
|
),
|
||||||
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@@ -440,12 +453,15 @@ class ContextualToolbar extends HookConsumerWidget {
|
|||||||
children: [
|
children: [
|
||||||
if (tabState?.historyState.canGoBack == true ||
|
if (tabState?.historyState.canGoBack == true ||
|
||||||
tabState?.isLoading == true)
|
tabState?.isLoading == true)
|
||||||
NavigateBackButton(
|
NonFocusable(
|
||||||
|
child: NavigateBackButton(
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
isLoading: tabState?.isLoading ?? false,
|
isLoading: tabState?.isLoading ?? false,
|
||||||
|
),
|
||||||
)
|
)
|
||||||
else
|
else
|
||||||
IconButton(
|
NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
await BookmarkListRoute(
|
await BookmarkListRoute(
|
||||||
entryGuid: BookmarkRoot.root.id,
|
entryGuid: BookmarkRoot.root.id,
|
||||||
@@ -453,20 +469,27 @@ class ContextualToolbar extends HookConsumerWidget {
|
|||||||
},
|
},
|
||||||
icon: const Icon(MdiIcons.bookmarkMultiple),
|
icon: const Icon(MdiIcons.bookmarkMultiple),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
if (tabState?.historyState.canGoForward == true)
|
if (tabState?.historyState.canGoForward == true)
|
||||||
NavigateForwardButton(selectedTabId: selectedTabId)
|
NonFocusable(
|
||||||
|
child: NavigateForwardButton(selectedTabId: selectedTabId),
|
||||||
|
)
|
||||||
else
|
else
|
||||||
ShareMenuButton(selectedTabId: selectedTabId),
|
NonFocusable(child: ShareMenuButton(selectedTabId: selectedTabId)),
|
||||||
const AddTabButton(),
|
const NonFocusable(child: AddTabButton()),
|
||||||
TabsCountButton(
|
NonFocusable(
|
||||||
|
child: TabsCountButton(
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
displayedSheet: displayedSheet,
|
displayedSheet: displayedSheet,
|
||||||
showLongPressMenu: false,
|
showLongPressMenu: false,
|
||||||
),
|
),
|
||||||
NavigationMenuButton(
|
),
|
||||||
|
NonFocusable(
|
||||||
|
child: NavigationMenuButton(
|
||||||
selectedTabId: selectedTabId,
|
selectedTabId: selectedTabId,
|
||||||
showNavigationButtons: false,
|
showNavigationButtons: false,
|
||||||
),
|
),
|
||||||
|
),
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@@ -628,7 +651,8 @@ class ShareMenuButton extends HookConsumerWidget {
|
|||||||
ShowQrCodeMenuItemButton(selectedTabId: selectedTabId),
|
ShowQrCodeMenuItemButton(selectedTabId: selectedTabId),
|
||||||
],
|
],
|
||||||
builder: (context, controller, child) {
|
builder: (context, controller, child) {
|
||||||
return IconButton(
|
return NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
if (controller.isOpen) {
|
if (controller.isOpen) {
|
||||||
controller.close();
|
controller.close();
|
||||||
@@ -637,6 +661,7 @@ class ShareMenuButton extends HookConsumerWidget {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
icon: const Icon(Icons.share),
|
icon: const Icon(Icons.share),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
@@ -705,7 +730,8 @@ class NavigationMenuButton extends HookConsumerWidget {
|
|||||||
alignment: WrapAlignment.center,
|
alignment: WrapAlignment.center,
|
||||||
children: [
|
children: [
|
||||||
...pageExtensions.map(
|
...pageExtensions.map(
|
||||||
(extension) => IconButton(
|
(extension) => NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
//Use parents .ref because after onPressed this consumer gets disposed already
|
//Use parents .ref because after onPressed this consumer gets disposed already
|
||||||
await addonService.invokeAddonAction(
|
await addonService.invokeAddonAction(
|
||||||
@@ -719,6 +745,7 @@ class NavigationMenuButton extends HookConsumerWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
@@ -947,7 +974,8 @@ class NavigateForwardButton extends HookConsumerWidget {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context, WidgetRef ref) {
|
Widget build(BuildContext context, WidgetRef ref) {
|
||||||
return IconButton(
|
return NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: canGoForward
|
onPressed: canGoForward
|
||||||
? () async {
|
? () async {
|
||||||
final controller = ref.read(
|
final controller = ref.read(
|
||||||
@@ -959,6 +987,7 @@ class NavigateForwardButton extends HookConsumerWidget {
|
|||||||
}
|
}
|
||||||
: null,
|
: null,
|
||||||
icon: const Icon(Icons.arrow_forward),
|
icon: const Icon(Icons.arrow_forward),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -979,7 +1008,8 @@ class NavigateBackButton extends HookConsumerWidget {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context, WidgetRef ref) {
|
Widget build(BuildContext context, WidgetRef ref) {
|
||||||
return IconButton(
|
return NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: (canGoBack || isLoading)
|
onPressed: (canGoBack || isLoading)
|
||||||
? () async {
|
? () async {
|
||||||
final controller = ref.read(
|
final controller = ref.read(
|
||||||
@@ -1005,7 +1035,10 @@ class NavigateBackButton extends HookConsumerWidget {
|
|||||||
menuControllerToClose?.close();
|
menuControllerToClose?.close();
|
||||||
}
|
}
|
||||||
: null,
|
: null,
|
||||||
icon: isLoading ? const Icon(Icons.close) : const Icon(Icons.arrow_back),
|
icon: isLoading
|
||||||
|
? const Icon(Icons.close)
|
||||||
|
: const Icon(Icons.arrow_back),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1019,6 +1052,7 @@ class AddTabButton extends HookConsumerWidget {
|
|||||||
|
|
||||||
return TabCreationMenu(
|
return TabCreationMenu(
|
||||||
controller: tabMenuController,
|
controller: tabMenuController,
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
onPressed: () async {
|
onPressed: () async {
|
||||||
final settings = ref.read(generalSettingsWithDefaultsProvider);
|
final settings = ref.read(generalSettingsWithDefaultsProvider);
|
||||||
@@ -1042,6 +1076,7 @@ class AddTabButton extends HookConsumerWidget {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+11
-2
@@ -26,6 +26,7 @@ import 'package:hooks_riverpod/hooks_riverpod.dart';
|
|||||||
import 'package:nullability/nullability.dart';
|
import 'package:nullability/nullability.dart';
|
||||||
import 'package:weblibre/core/design/app_colors.dart';
|
import 'package:weblibre/core/design/app_colors.dart';
|
||||||
import 'package:weblibre/features/geckoview/domain/entities/states/tab.dart';
|
import 'package:weblibre/features/geckoview/domain/entities/states/tab.dart';
|
||||||
|
import 'package:weblibre/presentation/widgets/non_focusable.dart';
|
||||||
import 'package:weblibre/features/geckoview/domain/providers/tab_state.dart';
|
import 'package:weblibre/features/geckoview/domain/providers/tab_state.dart';
|
||||||
import 'package:weblibre/features/geckoview/domain/repositories/tab.dart';
|
import 'package:weblibre/features/geckoview/domain/repositories/tab.dart';
|
||||||
import 'package:weblibre/features/geckoview/features/browser/presentation/widgets/tab_icon.dart';
|
import 'package:weblibre/features/geckoview/features/browser/presentation/widgets/tab_icon.dart';
|
||||||
@@ -152,6 +153,7 @@ class GridTabPreview extends HookConsumerWidget {
|
|||||||
child: Text('Close all from ${tabState.url.host}'),
|
child: Text('Close all from ${tabState.url.host}'),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
visualDensity: const VisualDensity(
|
visualDensity: const VisualDensity(
|
||||||
horizontal: -4.0,
|
horizontal: -4.0,
|
||||||
@@ -170,6 +172,7 @@ class GridTabPreview extends HookConsumerWidget {
|
|||||||
icon: const Icon(Icons.close),
|
icon: const Icon(Icons.close),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
?trailingChild,
|
?trailingChild,
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
@@ -348,6 +351,7 @@ class ListTabPreview extends HookConsumerWidget {
|
|||||||
child: Text('Close all from ${tabState.url.host}'),
|
child: Text('Close all from ${tabState.url.host}'),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
onPressed: onDelete,
|
onPressed: onDelete,
|
||||||
onLongPress: onDeleteAll != null
|
onLongPress: onDeleteAll != null
|
||||||
@@ -362,6 +366,7 @@ class ListTabPreview extends HookConsumerWidget {
|
|||||||
icon: const Icon(Icons.close),
|
icon: const Icon(Icons.close),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
?trailingChild,
|
?trailingChild,
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
@@ -625,12 +630,14 @@ class SuggestedSingleGridTabPreview extends StatelessWidget {
|
|||||||
tabId: tabId,
|
tabId: tabId,
|
||||||
isActive: tabId == activeTabId,
|
isActive: tabId == activeTabId,
|
||||||
onTap: onTap,
|
onTap: onTap,
|
||||||
trailingChild: const IconButton(
|
trailingChild: const NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
visualDensity: VisualDensity(horizontal: -4.0, vertical: -4.0),
|
visualDensity: VisualDensity(horizontal: -4.0, vertical: -4.0),
|
||||||
icon: Icon(MdiIcons.creation),
|
icon: Icon(MdiIcons.creation),
|
||||||
onPressed: null,
|
onPressed: null,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -657,12 +664,14 @@ class SuggestedSingleListTabPreview extends StatelessWidget {
|
|||||||
tabId: tabId,
|
tabId: tabId,
|
||||||
isActive: tabId == activeTabId,
|
isActive: tabId == activeTabId,
|
||||||
onTap: onTap,
|
onTap: onTap,
|
||||||
trailingChild: const IconButton(
|
trailingChild: const NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
visualDensity: VisualDensity(horizontal: -4.0, vertical: -4.0),
|
visualDensity: VisualDensity(horizontal: -4.0, vertical: -4.0),
|
||||||
icon: Icon(MdiIcons.creation),
|
icon: Icon(MdiIcons.creation),
|
||||||
onPressed: null,
|
onPressed: null,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+16
-3
@@ -26,6 +26,7 @@ import 'package:weblibre/features/geckoview/features/tabs/presentation/widgets/c
|
|||||||
import 'package:weblibre/features/tor/presentation/controllers/start_tor_proxy.dart';
|
import 'package:weblibre/features/tor/presentation/controllers/start_tor_proxy.dart';
|
||||||
import 'package:weblibre/features/user/domain/repositories/general_settings.dart';
|
import 'package:weblibre/features/user/domain/repositories/general_settings.dart';
|
||||||
import 'package:weblibre/presentation/hooks/menu_controller.dart';
|
import 'package:weblibre/presentation/hooks/menu_controller.dart';
|
||||||
|
import 'package:weblibre/presentation/widgets/non_focusable.dart';
|
||||||
import 'package:weblibre/presentation/widgets/speech_to_text_button.dart';
|
import 'package:weblibre/presentation/widgets/speech_to_text_button.dart';
|
||||||
import 'package:weblibre/utils/ui_helper.dart' as ui_helper;
|
import 'package:weblibre/utils/ui_helper.dart' as ui_helper;
|
||||||
|
|
||||||
@@ -82,13 +83,16 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
Row(
|
Row(
|
||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
children: [
|
children: [
|
||||||
IconButton(
|
NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
icon: const Icon(MdiIcons.tabSearch),
|
icon: const Icon(MdiIcons.tabSearch),
|
||||||
iconSize: 18,
|
iconSize: 18,
|
||||||
padding: EdgeInsets.zero,
|
padding: EdgeInsets.zero,
|
||||||
tooltip: 'Search inside tabs',
|
tooltip: 'Search inside tabs',
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
switch (ref.read(tabsViewModeControllerProvider)) {
|
switch (ref.read(
|
||||||
|
tabsViewModeControllerProvider,
|
||||||
|
)) {
|
||||||
case TabsViewMode.tree:
|
case TabsViewMode.tree:
|
||||||
case TabsViewMode.list:
|
case TabsViewMode.list:
|
||||||
break;
|
break;
|
||||||
@@ -104,6 +108,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
searchTextFocus.requestFocus();
|
searchTextFocus.requestFocus();
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
|
),
|
||||||
const SizedBox(
|
const SizedBox(
|
||||||
height: 32,
|
height: 32,
|
||||||
child: VerticalDivider(indent: 4, endIndent: 4),
|
child: VerticalDivider(indent: 4, endIndent: 4),
|
||||||
@@ -126,6 +131,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
),
|
),
|
||||||
)
|
)
|
||||||
.toList(),
|
.toList(),
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
tooltip: 'Change view mode',
|
tooltip: 'Change view mode',
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
@@ -144,6 +150,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
if (enableAiFeatures &&
|
if (enableAiFeatures &&
|
||||||
switch (tabsViewMode) {
|
switch (tabsViewMode) {
|
||||||
TabsViewMode.list || TabsViewMode.grid => true,
|
TabsViewMode.list || TabsViewMode.grid => true,
|
||||||
@@ -167,6 +174,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
style: const TextStyle(fontSize: 10),
|
style: const TextStyle(fontSize: 10),
|
||||||
)
|
)
|
||||||
: null,
|
: null,
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton.filledTonal(
|
child: IconButton.filledTonal(
|
||||||
icon: const Icon(MdiIcons.imageAutoAdjust),
|
icon: const Icon(MdiIcons.imageAutoAdjust),
|
||||||
isSelected: tabSuggestionsEnabled,
|
isSelected: tabSuggestionsEnabled,
|
||||||
@@ -202,6 +210,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
@@ -504,6 +513,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
},
|
},
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
child: NonFocusable(
|
||||||
child: IconButton(
|
child: IconButton(
|
||||||
tooltip: 'Tab actions',
|
tooltip: 'Tab actions',
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
@@ -516,6 +526,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
icon: const Icon(MdiIcons.dotsVertical),
|
icon: const Icon(MdiIcons.dotsVertical),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
else
|
else
|
||||||
@@ -537,7 +548,8 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
searchTextController.text = data;
|
searchTextController.text = data;
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
IconButton(
|
NonFocusable(
|
||||||
|
child: IconButton(
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
searchTextController.clear();
|
searchTextController.clear();
|
||||||
searchTextFocus.requestFocus();
|
searchTextFocus.requestFocus();
|
||||||
@@ -545,6 +557,7 @@ class TabViewHeader extends HookConsumerWidget {
|
|||||||
},
|
},
|
||||||
icon: const Icon(Icons.clear),
|
icon: const Icon(Icons.clear),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|||||||
+4
-1
@@ -26,6 +26,7 @@ import 'package:weblibre/features/geckoview/features/tabs/data/entities/containe
|
|||||||
import 'package:weblibre/features/geckoview/features/tabs/domain/providers.dart';
|
import 'package:weblibre/features/geckoview/features/tabs/domain/providers.dart';
|
||||||
import 'package:weblibre/features/geckoview/features/tabs/domain/providers/selected_container.dart';
|
import 'package:weblibre/features/geckoview/features/tabs/domain/providers/selected_container.dart';
|
||||||
import 'package:weblibre/features/geckoview/features/tabs/utils/container_colors.dart';
|
import 'package:weblibre/features/geckoview/features/tabs/utils/container_colors.dart';
|
||||||
|
import 'package:weblibre/presentation/widgets/non_focusable.dart';
|
||||||
|
|
||||||
class TabsActionButton extends HookConsumerWidget {
|
class TabsActionButton extends HookConsumerWidget {
|
||||||
final bool isActive;
|
final bool isActive;
|
||||||
@@ -56,7 +57,8 @@ class TabsActionButton extends HookConsumerWidget {
|
|||||||
selectedContainerDataProvider.select((value) => value.value?.color),
|
selectedContainerDataProvider.select((value) => value.value?.color),
|
||||||
);
|
);
|
||||||
|
|
||||||
return InkWell(
|
return NonFocusable(
|
||||||
|
child: InkWell(
|
||||||
onTap: onTap,
|
onTap: onTap,
|
||||||
onDoubleTap: onDoubleTap,
|
onDoubleTap: onDoubleTap,
|
||||||
onLongPress: onLongPress,
|
onLongPress: onLongPress,
|
||||||
@@ -117,6 +119,7 @@ class TabsActionButton extends HookConsumerWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,45 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2024-2025 Fabian Freund.
|
||||||
|
*
|
||||||
|
* This file is part of WebLibre
|
||||||
|
* (see https://weblibre.eu).
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU Affero General Public License as
|
||||||
|
* published by the Free Software Foundation, either version 3 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU Affero General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Affero General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
/// A wrapper that prevents a widget from receiving keyboard focus.
|
||||||
|
///
|
||||||
|
/// This fixes the issue where arrow keys on a bluetooth keyboard navigate
|
||||||
|
/// to toolbar buttons instead of moving the text cursor in input fields.
|
||||||
|
///
|
||||||
|
/// Example:
|
||||||
|
/// ```dart
|
||||||
|
/// NonFocusable(
|
||||||
|
/// child: IconButton(
|
||||||
|
/// onPressed: () {},
|
||||||
|
/// icon: Icon(Icons.menu),
|
||||||
|
/// ),
|
||||||
|
/// )
|
||||||
|
/// ```
|
||||||
|
class NonFocusable extends StatelessWidget {
|
||||||
|
final Widget child;
|
||||||
|
|
||||||
|
const NonFocusable({required this.child, super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Focus(canRequestFocus: false, skipTraversal: true, child: child);
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user