繁体   English   中英

TextField 小部件失去焦点 (Flutter)

[英]TextField widgets lose focus (Flutter)

我正在使用 Flutter TextField小部件创建一个应用程序:

class CategoryData {
  int? id;
  String name;
  String description;

  CategoryData({this.id, required this.name, required this.description});
}

class CategoriesEdit extends StatefulWidget {
  Database? db;
  CategoryData? category;

  CategoriesEdit({super.key, required this.db, required this.category});

  @override
  State<StatefulWidget> createState() => CategoriesEditState();
}

class CategoriesEditState extends State<CategoriesEdit> {
  CategoryData? category;

  void saveState(BuildContext context) {
    // ...
  }

  @override
  Widget build(BuildContext context) {
    if (category == null) {
      setState(() {
        category = widget.category ?? CategoryData(name: "", description: "");
      });
    }

    return Scaffold(
        appBar: AppBar(
          leading: InkWell(
              child: const Icon(Icons.arrow_circle_left),
              onTap: () => Navigator.pop(context)),
          title: const Text("Edit Category"),
        ),
        body: Column(children: [
          Column(key: const Key('name'), children: [
            const Text("Category name:*"),
            TextField(
                controller: TextEditingController(text: category!.name),
                onChanged: (value) {
                  setState(() {
                    category!.name = value;
                  });
                })
          ]),
          Column(key: const Key('description'), children: [
            const Text("Description:"),
            TextField(
                controller: TextEditingController(text: category!.description),
                onChanged: (value) {
                  setState(() {
                    category!.description = value;
                  });
                })
          ]),
          Row(mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [
            ElevatedButton(
              onPressed: () => saveState(context), // passing false
              child: const Text('OK'),
            ),
            OutlinedButton(
              onPressed: () => Navigator.pop(context, false),
              // passing false
              child: const Text('Cancel'),
            ),
          ]),
        ]));
  }
}

但是在我在这两个小部件中的一个中键入一个字符后,cursor 移动到第一个字符之前,并且 Android 键盘小部件消失了。 为什么? 以及如何修复该错误?

我尝试添加小部件键,但如您所见,它没有帮助。

你不必做

controller:TextEditingController(文本:类别..名称)

因为一旦您将控制器的文本连接到 TextField,控制器的文本就会自动更改。

原因是一旦您为 controller 设置了一些文本,它就会重新应用文本,从而将 cursor 移到前面。

我已经为你解决了这个问题:

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

class CategoryData {
  int? id;
  String name;
  String description;

  CategoryData({this.id, required this.name, required this.description});
}

class CategoriesEdit extends StatefulWidget {
  CategoryData? category;

  CategoriesEdit({required this.category});

  @override
  State<StatefulWidget> createState() => CategoriesEditState();
}

class CategoriesEditState extends State<CategoriesEdit> {
  CategoryData? category;
  // Database? db;
  TextEditingController nametextController =  TextEditingController();
  TextEditingController descriptionTextController = TextEditingController();
  void saveState(BuildContext context) {
    // ...
  }

  @override
  Widget build(BuildContext context) {
    if (category == null) {
      setState(() {
        category = widget.category ?? CategoryData(name: "", description: "");
      });


    }
    nametextController.text = category!.name??"";
    descriptionTextController.text = category!.description??"";



    return Scaffold(
        appBar: AppBar(
          leading: InkWell(
              child: const Icon(Icons.arrow_circle_left),
              onTap: () => Navigator.pop(context)),
          title: const Text("Edit Category"),
        ),
        body: Column(children: [
          Column(key: const Key('name'), children: [
            const Text("Category name:*"),
            TextField(
                controller: nametextController,
                onChanged: (value) {
                  setState(() {
                    category!.name = value;
                  });
                })
          ]),
          Column(key: const Key('description'), children: [
            const Text("Description:"),
            TextField(
                controller: descriptionTextController,
                onChanged: (value) {
                  setState(() {
                    category!.description = value;
                  });
                })
          ]),
          Row(mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [
            ElevatedButton(
              onPressed: () => saveState(context), // passing false
              child: const Text('OK'),
            ),
            OutlinedButton(
              onPressed: () => Navigator.pop(context, false),
              // passing false
              child: const Text('Cancel'),
            ),
          ]),
        ]));
  }
}

我已经测试了这段代码,它工作正常,如果您有任何疑问,请告诉我。 希望这对您有所帮助。

这里有很多问题,不仅仅是另一个答案中提到的东西。

  1. 将构建器中的 setState 移动到 initState 中:

     if (category == null) { setState(() { category = widget.category?? CategoryData(name: "", description: ""); }); }
  2. 不要在onChanged回调中使用setState 改变:

     onChanged: (value) { setState(() { category.;description = value; }); }

    对此:

     onChanged: (value) { category.;description = value; }
  3. 存储TextEditingController ,因为一旦我们处置 state,您就必须处置它们。

  4. 如果您已经在使用TextEditingController ,则不需要onChanged回调。 只需从 controller 中获取文本,如其他答案中所述。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM