Fix ActivateIntent overriding the spacebar for text entry (#91129)
This commit is contained in:
parent
acf6464996
commit
a24d55660b
@ -1149,6 +1149,10 @@ class WidgetsApp extends StatefulWidget {
|
||||
/// with "s".
|
||||
static bool debugAllowBannerOverride = true;
|
||||
|
||||
// Any shortcuts added here have the potential to conflict with normal text
|
||||
// input. If this should not happen and text input should take preference,
|
||||
// then add a shortcut for the relevant key in DefaultTextEditingShortcuts
|
||||
// mapped to DoNothingAndStopPropagationTextIntent.
|
||||
static const Map<ShortcutActivator, Intent> _defaultShortcuts = <ShortcutActivator, Intent>{
|
||||
// Activation
|
||||
SingleActivator(LogicalKeyboardKey.enter): ActivateIntent(),
|
||||
@ -1206,6 +1210,11 @@ class WidgetsApp extends StatefulWidget {
|
||||
};
|
||||
|
||||
// Default shortcuts for the macOS platform.
|
||||
//
|
||||
// Any shortcuts added here have the potential to conflict with normal text
|
||||
// input. If this should not happen and text input should take preference,
|
||||
// then add a shortcut for the relevant key in DefaultTextEditingShortcuts
|
||||
// mapped to DoNothingAndStopPropagationTextIntent.
|
||||
static const Map<ShortcutActivator, Intent> _defaultAppleOsShortcuts = <ShortcutActivator, Intent>{
|
||||
// Activation
|
||||
SingleActivator(LogicalKeyboardKey.enter): ActivateIntent(),
|
||||
|
@ -160,6 +160,13 @@ class DefaultTextEditingShortcuts extends Shortcuts {
|
||||
child: child,
|
||||
);
|
||||
|
||||
static const Map<ShortcutActivator, Intent> _commonShortcuts = <ShortcutActivator, Intent>{
|
||||
// Allows space and enter to be used as input instead of a shortcut by
|
||||
// another widget. See https://github.com/flutter/flutter/issues/90907
|
||||
SingleActivator(LogicalKeyboardKey.space): DoNothingAndStopPropagationTextIntent(),
|
||||
SingleActivator(LogicalKeyboardKey.enter): DoNothingAndStopPropagationTextIntent(),
|
||||
};
|
||||
|
||||
static const Map<ShortcutActivator, Intent> _androidShortcuts = <ShortcutActivator, Intent>{
|
||||
SingleActivator(LogicalKeyboardKey.backspace): DeleteTextIntent(),
|
||||
SingleActivator(LogicalKeyboardKey.backspace, control: true): DeleteByWordTextIntent(),
|
||||
@ -532,7 +539,7 @@ class DefaultTextEditingShortcuts extends Shortcuts {
|
||||
SingleActivator(LogicalKeyboardKey.keyA, meta: true): DoNothingAndStopPropagationTextIntent(),
|
||||
};
|
||||
|
||||
static Map<ShortcutActivator, Intent> get _shortcuts {
|
||||
static Map<ShortcutActivator, Intent> get _platformShortcuts {
|
||||
if (kIsWeb) {
|
||||
return _webShortcuts;
|
||||
}
|
||||
@ -552,4 +559,11 @@ class DefaultTextEditingShortcuts extends Shortcuts {
|
||||
return _windowsShortcuts;
|
||||
}
|
||||
}
|
||||
|
||||
static Map<ShortcutActivator, Intent> get _shortcuts {
|
||||
return <ShortcutActivator, Intent>{
|
||||
..._commonShortcuts,
|
||||
..._platformShortcuts,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
@ -8,6 +8,7 @@ import 'package:flutter/gestures.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter/widgets.dart';
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
|
||||
import '../rendering/mock_canvas.dart';
|
||||
@ -8635,6 +8636,71 @@ void main() {
|
||||
await tester.pump();
|
||||
expect(scrollController.offset.roundToDouble(), 0.0);
|
||||
});
|
||||
|
||||
// Regression test for https://github.com/flutter/flutter/issues/90907.
|
||||
testWidgets("ActivateIntent doesn't block space entry", (WidgetTester tester) async {
|
||||
final FocusNode focusNode = FocusNode();
|
||||
bool invoked = false;
|
||||
|
||||
await tester.pumpWidget(MaterialApp(
|
||||
home: Scaffold(
|
||||
body: Align(
|
||||
alignment: Alignment.topLeft,
|
||||
child: SizedBox(
|
||||
width: 100,
|
||||
child: ListTile(
|
||||
title: Actions(
|
||||
actions: <Type, Action<Intent>>{
|
||||
ActivateIntent: CallbackAction<ActivateIntent>(
|
||||
onInvoke: (ActivateIntent intent) {
|
||||
invoked = true;
|
||||
},
|
||||
),
|
||||
},
|
||||
child: Column(
|
||||
children: <Widget>[
|
||||
EditableText(
|
||||
autofocus: true,
|
||||
showSelectionHandles: true,
|
||||
maxLines: 2,
|
||||
controller: TextEditingController(),
|
||||
focusNode: FocusNode(),
|
||||
cursorColor: Colors.red,
|
||||
backgroundCursorColor: Colors.blue,
|
||||
style: Typography.material2018(platform: TargetPlatform.android).black.subtitle1!.copyWith(fontFamily: 'Roboto'),
|
||||
keyboardType: TextInputType.text,
|
||||
),
|
||||
Focus(
|
||||
focusNode: focusNode,
|
||||
child: const Text('Hello'),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
));
|
||||
|
||||
await tester.sendKeyEvent(LogicalKeyboardKey.space);
|
||||
await tester.sendKeyEvent(LogicalKeyboardKey.enter);
|
||||
await tester.pump();
|
||||
expect(invoked, isFalse);
|
||||
|
||||
focusNode.requestFocus();
|
||||
await tester.pump();
|
||||
await tester.sendKeyEvent(LogicalKeyboardKey.space);
|
||||
await tester.pump();
|
||||
expect(invoked, isTrue);
|
||||
|
||||
invoked = false;
|
||||
await tester.pump();
|
||||
await tester.sendKeyEvent(LogicalKeyboardKey.enter);
|
||||
await tester.pump();
|
||||
// On the web, enter doesn't activate any controls except for buttons.
|
||||
expect(invoked, kIsWeb ? isFalse : isTrue);
|
||||
});
|
||||
}
|
||||
|
||||
class UnsettableController extends TextEditingController {
|
||||
|
Loading…
x
Reference in New Issue
Block a user