refactor: util for keyboard activation
This commit is contained in:
@@ -2,6 +2,7 @@ import 'dart:async';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import '../utils/keyboard_utils.dart';
|
||||
|
||||
/// A mixin that provides keyboard long-press detection for focusable widgets.
|
||||
///
|
||||
@@ -42,19 +43,11 @@ mixin KeyboardLongPressMixin<T extends StatefulWidget> on State<T> {
|
||||
/// Override to handle long press action (e.g., show context menu)
|
||||
void onKeyboardLongPress();
|
||||
|
||||
/// Check if the given key is an activation key
|
||||
bool _isActivationKey(LogicalKeyboardKey key) {
|
||||
return key == LogicalKeyboardKey.enter ||
|
||||
key == LogicalKeyboardKey.space ||
|
||||
key == LogicalKeyboardKey.select ||
|
||||
key == LogicalKeyboardKey.gameButtonA;
|
||||
}
|
||||
|
||||
/// Call this from your onKeyEvent handler to enable long-press detection.
|
||||
/// Returns [KeyEventResult.handled] if the event was an activation key,
|
||||
/// [KeyEventResult.ignored] otherwise.
|
||||
KeyEventResult handleKeyboardLongPress(KeyEvent event) {
|
||||
if (!_isActivationKey(event.logicalKey)) {
|
||||
if (!isKeyboardActivationKey(event.logicalKey)) {
|
||||
return KeyEventResult.ignored;
|
||||
}
|
||||
|
||||
|
||||
@@ -133,10 +133,7 @@ class _DiscoverScreenState extends State<DiscoverScreen>
|
||||
KeyEventResult _handleHeroKeyEvent(FocusNode node, KeyEvent event) {
|
||||
if (event is KeyDownEvent) {
|
||||
// Enter/Space to play current hero item
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
if (_onDeck.isNotEmpty && _currentHeroIndex < _onDeck.length) {
|
||||
navigateToVideoPlayer(context, metadata: _onDeck[_currentHeroIndex]);
|
||||
return KeyEventResult.handled;
|
||||
|
||||
@@ -1028,10 +1028,7 @@ class _LibrariesScreenState extends State<LibrariesScreen>
|
||||
focusNode: _libraryDropdownFocusNode,
|
||||
onKeyEvent: (node, event) {
|
||||
if (event is KeyDownEvent) {
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
_libraryDropdownKey.currentState?.showButtonMenu();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
@@ -1133,10 +1130,7 @@ class _LibrariesScreenState extends State<LibrariesScreen>
|
||||
onKeyEvent: (node, event) {
|
||||
if (event is KeyDownEvent) {
|
||||
// Activation keys
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
onPressed();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
@@ -1668,24 +1662,17 @@ class _LibraryManagementSheetState extends State<_LibraryManagementSheet> {
|
||||
if (index < maxIndex) onMove(1);
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
onEndMove();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
if (event.logicalKey == LogicalKeyboardKey.escape ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonB) {
|
||||
if (isBackKey(event.logicalKey)) {
|
||||
onCancelMove();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
} else {
|
||||
// Not moving - Enter/Space starts move
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
onStartMove();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
@@ -1749,10 +1736,7 @@ class _LibraryManagementSheetState extends State<_LibraryManagementSheet> {
|
||||
if (event is! KeyDownEvent) return KeyEventResult.ignored;
|
||||
|
||||
// Handle activation
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
onPressed();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
|
||||
@@ -438,10 +438,7 @@ class _LibraryBrowseTabState extends State<LibraryBrowseTab>
|
||||
return Focus(
|
||||
onKeyEvent: (node, event) {
|
||||
if (event is KeyDownEvent) {
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
onPressed();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
|
||||
@@ -13,3 +13,11 @@ bool isBackKeyEvent(KeyEvent event) {
|
||||
if (event is! KeyDownEvent) return false;
|
||||
return isBackKey(event.logicalKey);
|
||||
}
|
||||
|
||||
/// Check if the given key should activate/select an item
|
||||
bool isKeyboardActivationKey(LogicalKeyboardKey key) {
|
||||
return key == LogicalKeyboardKey.enter ||
|
||||
key == LogicalKeyboardKey.space ||
|
||||
key == LogicalKeyboardKey.select ||
|
||||
key == LogicalKeyboardKey.gameButtonA;
|
||||
}
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import '../models/plex_metadata.dart';
|
||||
import '../utils/keyboard_utils.dart';
|
||||
|
||||
/// Individual item in the folder tree
|
||||
/// Can be either a folder (expandable) or a file (tappable)
|
||||
@@ -54,15 +55,9 @@ class _FolderTreeItemState extends State<FolderTreeItem> {
|
||||
}
|
||||
}
|
||||
|
||||
bool _isActivationKey(LogicalKeyboardKey key) {
|
||||
return key == LogicalKeyboardKey.enter ||
|
||||
key == LogicalKeyboardKey.space ||
|
||||
key == LogicalKeyboardKey.select ||
|
||||
key == LogicalKeyboardKey.gameButtonA;
|
||||
}
|
||||
|
||||
KeyEventResult _handleKeyEvent(FocusNode node, KeyEvent event) {
|
||||
if (event is KeyDownEvent && _isActivationKey(event.logicalKey)) {
|
||||
if (event is KeyDownEvent &&
|
||||
isKeyboardActivationKey(event.logicalKey)) {
|
||||
_isKeyboardActivation = true;
|
||||
return KeyEventResult.ignored; // Let InkWell handle the activation
|
||||
}
|
||||
|
||||
@@ -7,6 +7,7 @@ import 'horizontal_scroll_with_arrows.dart';
|
||||
import 'hub_navigation_controller.dart';
|
||||
import '../i18n/strings.g.dart';
|
||||
import 'focus/focus_indicator.dart';
|
||||
import '../utils/keyboard_utils.dart';
|
||||
|
||||
/// Shared hub section widget used in both discover and library screens
|
||||
/// Displays a hub title with icon and a horizontal scrollable list of items
|
||||
@@ -162,10 +163,7 @@ class _HubSectionState extends State<HubSection> {
|
||||
|
||||
KeyEventResult _handleHeaderKeyEvent(FocusNode node, KeyEvent event) {
|
||||
if (event is KeyDownEvent && widget.hub.more) {
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
_navigateToHubDetail();
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
|
||||
@@ -1498,10 +1498,7 @@ class _FocusableContextMenuSheetState
|
||||
}
|
||||
|
||||
// Select with Enter/Space
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
Navigator.pop(context, widget.actions[_focusedIndex].value);
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
@@ -1628,10 +1625,7 @@ class _FocusablePopupMenuState extends State<_FocusablePopupMenu> {
|
||||
}
|
||||
|
||||
// Select with Enter/Space
|
||||
if (event.logicalKey == LogicalKeyboardKey.enter ||
|
||||
event.logicalKey == LogicalKeyboardKey.space ||
|
||||
event.logicalKey == LogicalKeyboardKey.select ||
|
||||
event.logicalKey == LogicalKeyboardKey.gameButtonA) {
|
||||
if (isKeyboardActivationKey(event.logicalKey)) {
|
||||
Navigator.pop(context, widget.actions[_focusedIndex].value);
|
||||
return KeyEventResult.handled;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user