Flutter如何无需点击按钮自动将一个TextField的值同步到另一个TextField?
方案1:共用同一个TextEditingController(最优实现)
这是性能最好、代码最简洁的实现方式,TextField会自动监听绑定的Controller变化完成局部刷新,不需要调用setState触发整个页面/表单重绘,也不需要额外的事件监听逻辑:
import "package:flutter/material.dart"; void main() => runApp(MyApp()); class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: Home(), ); } } class Home extends StatefulWidget { @override _HomeState createState() => _HomeState(); } class _HomeState extends State<Home> { // 所有需要同步的TextField共用这一个Controller即可自动双向同步 final shareController = TextEditingController(); @override void dispose() { shareController.dispose(); super.dispose(); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: Text('GeeksforGeeks'), backgroundColor: Colors.green, ), body: Column( children: [ // 第1分区的TextField Padding( padding: const EdgeInsets.all(15), child: TextField( decoration: InputDecoration(labelText: '分区1输入'), controller: shareController, ), ), SizedBox(height: 20), // 第20分区的对应TextField Padding( padding: const EdgeInsets.all(15), child: TextField( decoration: InputDecoration(labelText: '分区20同步输入'), controller: shareController, ), ), ], ), ); } }
该方案优势:
- 无需额外业务逻辑,输入内容实时同步
- 仅TextField自身完成局部刷新,不会触发整个表单的重绘,无额外性能损耗
- 支持任意数量的同步输入框,所有需要同步的字段绑定同一个Controller即可
方案2:独立Controller监听同步(适配同步后可独立修改的场景)
如果你的需求是分区1输入内容自动填充到分区20后,分区20的内容可以独立修改、不反向同步到分区1,就使用该方案:
import "package:flutter/material.dart"; void main() => runApp(MyApp()); class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: Home(), ); } } class Home extends StatefulWidget { @override _HomeState createState() => _HomeState(); } class _HomeState extends State<Home> { final zone1Controller = TextEditingController(); final zone20Controller = TextEditingController(); @override void initState() { super.initState(); // 监听分区1的输入变化 zone1Controller.addListener(() { // 直接给分区2的Controller赋值,不需要调用setState zone20Controller.text = zone1Controller.text; // 保持分区2输入框光标在末尾 zone20Controller.selection = TextSelection.fromPosition( TextPosition(offset: zone20Controller.text.length) ); }); } @override void dispose() { zone1Controller.dispose(); zone20Controller.dispose(); super.dispose(); } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: Text('GeeksforGeeks'), backgroundColor: Colors.green, ), body: Column( children: [ Padding( padding: const EdgeInsets.all(15), child: TextField( decoration: InputDecoration(labelText: '分区1输入'), controller: zone1Controller, ), ), SizedBox(height: 20), Padding( padding: const EdgeInsets.all(15), child: TextField( decoration: InputDecoration(labelText: '分区20同步输入(可独立修改)'), controller: zone20Controller, ), ), ], ), ); } }
该方案直接修改目标Controller的text属性,TextField会自动监听自身绑定的Controller变化完成更新,全程不需要调用setState,不会触发整个表单的状态变更。
内容的提问来源于stack exchange,提问作者arriff
相关产品推荐
相关产品推荐

