text_field_focus_test.dart 6.06 KB
Newer Older
1 2 3 4 5 6 7 8 9
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'package:flutter_test/flutter_test.dart';
import 'package:flutter/material.dart';

void main() {
  testWidgets('Request focus shows keyboard', (WidgetTester tester) async {
10
    final FocusNode focusNode = FocusNode();
11 12

    await tester.pumpWidget(
13 14 15 16
      MaterialApp(
        home: Material(
          child: Center(
            child: TextField(
17 18 19 20 21 22 23 24 25 26 27 28 29 30
              focusNode: focusNode,
            ),
          ),
        ),
      ),
    );

    expect(tester.testTextInput.isVisible, isFalse);

    FocusScope.of(tester.element(find.byType(TextField))).requestFocus(focusNode);
    await tester.idle();

    expect(tester.testTextInput.isVisible, isTrue);

31
    await tester.pumpWidget(Container());
32 33 34 35 36 37 38 39

    expect(tester.testTextInput.isVisible, isFalse);
  });

  testWidgets('Autofocus shows keyboard', (WidgetTester tester) async {
    expect(tester.testTextInput.isVisible, isFalse);

    await tester.pumpWidget(
40 41
      const MaterialApp(
        home: Material(
42 43
          child: Center(
            child: TextField(
44 45 46 47 48 49 50 51 52
              autofocus: true,
            ),
          ),
        ),
      ),
    );

    expect(tester.testTextInput.isVisible, isTrue);

53
    await tester.pumpWidget(Container());
54 55 56 57 58 59 60 61

    expect(tester.testTextInput.isVisible, isFalse);
  });

  testWidgets('Tap shows keyboard', (WidgetTester tester) async {
    expect(tester.testTextInput.isVisible, isFalse);

    await tester.pumpWidget(
62 63
      const MaterialApp(
        home: Material(
64 65
          child: Center(
            child: TextField(),
66 67 68 69 70 71 72 73
          ),
        ),
      ),
    );

    expect(tester.testTextInput.isVisible, isFalse);

    await tester.tap(find.byType(TextField));
74
    await tester.idle();
75 76 77 78 79 80 81 82

    expect(tester.testTextInput.isVisible, isTrue);

    tester.testTextInput.hide();

    expect(tester.testTextInput.isVisible, isFalse);

    await tester.tap(find.byType(TextField));
83
    await tester.idle();
84 85 86

    expect(tester.testTextInput.isVisible, isTrue);

87
    await tester.pumpWidget(Container());
88 89 90 91 92 93 94 95

    expect(tester.testTextInput.isVisible, isFalse);
  });

  testWidgets('Dialog interaction', (WidgetTester tester) async {
    expect(tester.testTextInput.isVisible, isFalse);

    await tester.pumpWidget(
96 97
      const MaterialApp(
        home: Material(
98 99
          child: Center(
            child: TextField(
100 101 102 103 104 105 106 107 108 109 110
              autofocus: true,
            ),
          ),
        ),
      ),
    );

    expect(tester.testTextInput.isVisible, isTrue);

    final BuildContext context = tester.element(find.byType(TextField));

111
    showDialog<void>(
112
      context: context,
113
      builder: (BuildContext context) => const SimpleDialog(title: Text('Dialog')),
114 115
    );

116
    await tester.pump();
117 118 119 120

    expect(tester.testTextInput.isVisible, isFalse);

    Navigator.of(tester.element(find.text('Dialog'))).pop();
121
    await tester.pump();
122 123 124 125

    expect(tester.testTextInput.isVisible, isFalse);

    await tester.tap(find.byType(TextField));
126
    await tester.idle();
127 128 129

    expect(tester.testTextInput.isVisible, isTrue);

130
    await tester.pumpWidget(Container());
131 132 133 134

    expect(tester.testTextInput.isVisible, isFalse);
  });

135
  testWidgets('Focus triggers keep-alive', (WidgetTester tester) async {
136
    final FocusNode focusNode = FocusNode();
137 138

    await tester.pumpWidget(
139 140 141
      MaterialApp(
        home: Material(
          child: ListView(
142
            children: <Widget>[
143
              TextField(
144 145
                focusNode: focusNode,
              ),
146
              Container(
147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164
                height: 1000.0,
              ),
            ],
          ),
        ),
      ),
    );

    expect(find.byType(TextField), findsOneWidget);
    expect(tester.testTextInput.isVisible, isFalse);

    FocusScope.of(tester.element(find.byType(TextField))).requestFocus(focusNode);
    await tester.pump();
    expect(find.byType(TextField), findsOneWidget);
    expect(tester.testTextInput.isVisible, isTrue);

    await tester.drag(find.byType(ListView), const Offset(0.0, -1000.0));
    await tester.pump();
165
    expect(find.byType(TextField, skipOffstage: false), findsOneWidget);
166 167 168 169 170 171 172 173 174 175
    expect(tester.testTextInput.isVisible, isTrue);

    focusNode.unfocus();
    await tester.pump();

    expect(find.byType(TextField), findsNothing);
    expect(tester.testTextInput.isVisible, isFalse);
  });

  testWidgets('Focus keep-alive works with GlobalKey reparenting', (WidgetTester tester) async {
176
    final FocusNode focusNode = FocusNode();
177 178

    Widget makeTest(String prefix) {
179 180 181
      return MaterialApp(
        home: Material(
          child: ListView(
182
            children: <Widget>[
183
              TextField(
184
                focusNode: focusNode,
185
                decoration: InputDecoration(
186 187 188
                  prefixText: prefix,
                ),
              ),
189
              Container(
190 191 192 193 194 195 196 197 198 199 200 201 202 203
                height: 1000.0,
              ),
            ],
          ),
        ),
      );
    }

    await tester.pumpWidget(makeTest(null));
    FocusScope.of(tester.element(find.byType(TextField))).requestFocus(focusNode);
    await tester.pump();
    expect(find.byType(TextField), findsOneWidget);
    await tester.drag(find.byType(ListView), const Offset(0.0, -1000.0));
    await tester.pump();
204
    expect(find.byType(TextField, skipOffstage: false), findsOneWidget);
205 206
    await tester.pumpWidget(makeTest('test'));
    await tester.pump(); // in case the AutomaticKeepAlive widget thinks it needs a cleanup frame
207
    expect(find.byType(TextField, skipOffstage: false), findsOneWidget);
208
  });
Hans Muller's avatar
Hans Muller committed
209 210 211 212 213

  testWidgets('TextField with decoration:null', (WidgetTester tester) async {
    // Regression test for https://github.com/flutter/flutter/issues/16880

    await tester.pumpWidget(
214 215
      const MaterialApp(
        home: Material(
216 217
          child: Center(
            child: TextField(
Hans Muller's avatar
Hans Muller committed
218 219 220 221 222 223 224 225 226
              decoration: null
            ),
          ),
        ),
      ),
    );

    expect(tester.testTextInput.isVisible, isFalse);
    await tester.tap(find.byType(TextField));
227
    await tester.idle();
Hans Muller's avatar
Hans Muller committed
228 229
    expect(tester.testTextInput.isVisible, isTrue);
  });
230
}