Unverified Commit 913e21e4 authored by Darren Austin's avatar Darren Austin Committed by GitHub

First pass at keyboard navigation for the Material Date Picker (#59279)

parent 0093c6a4
...@@ -8,6 +8,7 @@ import 'package:flutter/widgets.dart'; ...@@ -8,6 +8,7 @@ import 'package:flutter/widgets.dart';
import '../color_scheme.dart'; import '../color_scheme.dart';
import '../icon_button.dart'; import '../icon_button.dart';
import '../material.dart';
import '../text_theme.dart'; import '../text_theme.dart';
import '../theme.dart'; import '../theme.dart';
...@@ -127,69 +128,65 @@ class DatePickerHeader extends StatelessWidget { ...@@ -127,69 +128,65 @@ class DatePickerHeader extends StatelessWidget {
switch (orientation) { switch (orientation) {
case Orientation.portrait: case Orientation.portrait:
return Column( return SizedBox(
crossAxisAlignment: CrossAxisAlignment.start, height: _datePickerHeaderPortraitHeight,
children: <Widget>[ child: Material(
Container( color: primarySurfaceColor,
height: _datePickerHeaderPortraitHeight, child: Padding(
color: primarySurfaceColor, padding: const EdgeInsetsDirectional.only(
padding: const EdgeInsetsDirectional.only( start: 24,
start: 24, end: 12,
end: 12, ),
), child: Column(
child: Column( crossAxisAlignment: CrossAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[
children: <Widget>[ const SizedBox(height: 16),
const SizedBox(height: 16), Flexible(child: help),
Flexible(child: help), const SizedBox(height: 38),
const SizedBox(height: 38), Row(
Row( children: <Widget>[
children: <Widget>[ Expanded(child: title),
Expanded(child: title), icon,
icon, ],
], ),
), ],
], ),
), ),
), ),
], );
);
case Orientation.landscape: case Orientation.landscape:
return Row( return SizedBox(
crossAxisAlignment: CrossAxisAlignment.start, width: _datePickerHeaderLandscapeWidth,
children: <Widget>[ child: Material(
Container( color: primarySurfaceColor,
width: _datePickerHeaderLandscapeWidth, child: Column(
color: primarySurfaceColor, crossAxisAlignment: CrossAxisAlignment.start,
child: Column( children: <Widget>[
crossAxisAlignment: CrossAxisAlignment.start, const SizedBox(height: 16),
children: <Widget>[ Padding(
const SizedBox(height: 16), padding: const EdgeInsets.symmetric(
Padding( horizontal: _headerPaddingLandscape,
),
child: help,
),
SizedBox(height: isShort ? 16 : 56),
Expanded(
child: Padding(
padding: const EdgeInsets.symmetric( padding: const EdgeInsets.symmetric(
horizontal: _headerPaddingLandscape, horizontal: _headerPaddingLandscape,
), ),
child: help, child: title,
), ),
SizedBox(height: isShort ? 16 : 56), ),
Expanded( Padding(
child: Padding( padding: const EdgeInsets.symmetric(
padding: const EdgeInsets.symmetric( horizontal: 4,
horizontal: _headerPaddingLandscape,
),
child: title,
),
),
Padding(
padding: const EdgeInsets.symmetric(
horizontal: 4,
),
child: icon,
), ),
], child: icon,
), ),
],
), ),
], ),
); );
} }
return null; return null;
......
...@@ -803,8 +803,7 @@ void main() { ...@@ -803,8 +803,7 @@ void main() {
await prepareDatePicker(tester, (Future<DateTime> date) async { await prepareDatePicker(tester, (Future<DateTime> date) async {
// Header // Header
expect( expect(tester.getSemantics(find.text('SELECT DATE')), matchesSemantics(
tester.getSemantics(find.text('SELECT DATE')), matchesSemantics(
label: 'SELECT DATE\nFri, Jan 15', label: 'SELECT DATE\nFri, Jan 15',
)); ));
...@@ -819,8 +818,7 @@ void main() { ...@@ -819,8 +818,7 @@ void main() {
)); ));
// Year mode drop down button // Year mode drop down button
expect( expect(tester.getSemantics(find.text('January 2016')), matchesSemantics(
tester.getSemantics(find.text('January 2016')), matchesSemantics(
label: 'Select year', label: 'Select year',
isButton: true, isButton: true,
)); ));
...@@ -983,7 +981,6 @@ void main() { ...@@ -983,7 +981,6 @@ void main() {
hasEnabledState: true, hasEnabledState: true,
isFocusable: true, isFocusable: true,
)); ));
}); });
semantics.dispose(); semantics.dispose();
...@@ -1107,6 +1104,63 @@ void main() { ...@@ -1107,6 +1104,63 @@ void main() {
}); });
}); });
group('Keyboard navigation', () {
testWidgets('Can toggle to calendar entry mode', (WidgetTester tester) async {
await prepareDatePicker(tester, (Future<DateTime> date) async {
expect(find.byType(TextField), findsNothing);
// Navigate to the entry toggle button and activate it
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
// Should be in the input mode
expect(find.byType(TextField), findsOneWidget);
});
});
testWidgets('Can toggle to year mode', (WidgetTester tester) async {
await prepareDatePicker(tester, (Future<DateTime> date) async {
expect(find.text('2016'), findsNothing);
// Navigate to the year selector and activate it
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
// The years should be visible
expect(find.text('2016'), findsOneWidget);
});
});
testWidgets('Can navigate next/previous months', (WidgetTester tester) async {
await prepareDatePicker(tester, (Future<DateTime> date) async {
expect(find.text('January 2016'), findsOneWidget);
// Navigate to the previous month button and activate it twice
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
// Should be showing Nov 2015
expect(find.text('November 2015'), findsOneWidget);
// Navigate to the next month button and activate it four times
await tester.sendKeyEvent(LogicalKeyboardKey.tab);
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
await tester.sendKeyEvent(LogicalKeyboardKey.space);
await tester.pumpAndSettle();
// Should be on Mar 2016
expect(find.text('March 2016'), findsOneWidget);
});
});
});
group('Screen configurations', () { group('Screen configurations', () {
// Test various combinations of screen sizes, orientations and text scales // Test various combinations of screen sizes, orientations and text scales
// to ensure the layout doesn't overflow and cause an exception to be thrown. // to ensure the layout doesn't overflow and cause an exception to be thrown.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment