焦点和文本框
当一个文本框(输入框)被选中并接受输入时,被称为获得了“焦点”。通常情况下,用户能够通过点击文本框以使其聚焦,开发人员也可以使用本文所描述的方法来让文本框得到焦点。
管理焦点是一种直观地创建表单流程的基本方法。例如,假设我们有一个带有文本框的搜索页面。当用户导航到搜索页面时,我们可以聚焦文本框的搜索项。这将允许用户在搜索页面可见时能够立即开始输入,而无需手动点击文本框。
在本文中,我们将学习如何聚焦到文本框上,以及点击按钮时聚焦文本框。
一旦文本框可见,就将其聚焦
#为了在文本框可见时将其聚焦,我们可以使用 autofocus 属性。
TextField(
  autofocus: true,
);有关处理输入和创建文本框的更多信息,请参阅 实用教程的 Forms 部分。
点击按钮时聚焦文本框
#我们也可能需要在之后的某个时间点聚焦特定的文本框,而不是立即聚焦它。在这个例子中,我们将看到在用户按下按钮后如何聚焦文本框。在实际开发中,你还可能需要聚焦特定的文本框以响应 api 调用或错误校验。
- 
创建一个 FocusNode
- 
将 FocusNode传递给TextField
- 
通过点击按钮聚焦 TextField
1. 创建一个 FocusNode
            #
          首先,我们需要创建一个 FocusNode。我们将使用 FocusNode 来识别 Flutter 的“focus tree”中的特定的 TextField。这将允许我们能够在接下来的步骤中聚焦 TextField。
由于 focus node 是长寿命对象,我们需要使用 State 类来管理生命周期。为此,需要在 State 类的 initState 方法中创建 FocusNode 实例,并在 dispose 方法中清除它们。
// Define a custom Form widget.
class MyCustomForm extends StatefulWidget {
  const MyCustomForm({super.key});
  @override
  State<MyCustomForm> createState() => _MyCustomFormState();
}
// Define a corresponding State class.
// This class holds data related to the form.
class _MyCustomFormState extends State<MyCustomForm> {
  // Define the focus node. To manage the lifecycle, create the FocusNode in
  // the initState method, and clean it up in the dispose method.
  late FocusNode myFocusNode;
  @override
  void initState() {
    super.initState();
    myFocusNode = FocusNode();
  }
  @override
  void dispose() {
    // Clean up the focus node when the Form is disposed.
    myFocusNode.dispose();
    super.dispose();
  }
  @override
  Widget build(BuildContext context) {
    // Fill this out in the next step.
  }
}2. 将 FocusNode 传递给 TextField
            #
          现在已经有了 FocusNode,我们可以将这个 TextField 传递给 build() 方法。
@override
Widget build(BuildContext context) {
  return TextField(focusNode: myFocusNode);
}3. 通过点击按钮聚焦 TextField
            #
          最后,当用户点击 floating action button 时,我们将要聚焦文本框!为此我们将要使用 requestFocus() 方法来完成此操作。
FloatingActionButton(
  // When the button is pressed,
  // give focus to the text field using myFocusNode.
  onPressed: () => myFocusNode.requestFocus(),
),交互式样例
#import 'package:flutter/material.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
  const MyApp({super.key});
  @override
  Widget build(BuildContext context) {
    return const MaterialApp(title: 'Text Field Focus', home: MyCustomForm());
  }
}
// Define a custom Form widget.
class MyCustomForm extends StatefulWidget {
  const MyCustomForm({super.key});
  @override
  State<MyCustomForm> createState() => _MyCustomFormState();
}
// Define a corresponding State class.
// This class holds data related to the form.
class _MyCustomFormState extends State<MyCustomForm> {
  // Define the focus node. To manage the lifecycle, create the FocusNode in
  // the initState method, and clean it up in the dispose method.
  late FocusNode myFocusNode;
  @override
  void initState() {
    super.initState();
    myFocusNode = FocusNode();
  }
  @override
  void dispose() {
    // Clean up the focus node when the Form is disposed.
    myFocusNode.dispose();
    super.dispose();
  }
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Text Field Focus')),
      body: Padding(
        padding: const EdgeInsets.all(16),
        child: Column(
          children: [
            // The first text field is focused on as soon as the app starts.
            const TextField(autofocus: true),
            // The second text field is focused on when a user taps the
            // FloatingActionButton.
            TextField(focusNode: myFocusNode),
          ],
        ),
      ),
      floatingActionButton: FloatingActionButton(
        // When the button is pressed,
        // give focus to the text field using myFocusNode.
        onPressed: () => myFocusNode.requestFocus(),
        tooltip: 'Focus Second Text Field',
        child: const Icon(Icons.edit),
      ), // This trailing comma makes auto-formatting nicer for build methods.
    );
  }
}
除非另有说明,本文档之所提及适用于 Flutter 的最新稳定版本,本页面最后更新时间: 2025-10-09。 查看文档源码 或者 为本页面内容提出建议.