3.7 KiB
3.7 KiB
【Demo】TextField 输入框(登录表单)
源文件:
lib/pages/demo/input_demo.dart| 分类:基础布局 一句话:输入框 + 密码"小眼睛"切换 —— 表单最基础的零件。
一、这个 Demo 解决什么问题
做一个最简单的登录表单:手机号输入框 + 密码输入框(可切换明文/密文)。 核心是搞懂 TextEditingController 的用法——Flutter 里输入框不叫"双向绑定", 而是"控制器持有值,代码里随时读写"。
二、怎么运行 / 演示内容
runApp(const MaterialApp(home: InputDemoPage()));
- 手机号框:弹数字键盘(
keyboardType: TextInputType.phone); - 密码框:右侧眼睛图标切换密文/明文;
- 点"登录":控制台打印两个输入框的内容。
三、核心知识点(新手向)
1. 对照 Vue 的 v-model
| Vue | Flutter |
|---|---|
v-model="phone" |
TextEditingController + controller.text |
| 框架自动同步 | 手动 controller.text 读写 |
Flutter 没有隐式的双向绑定:controller.text 改了就同步到输入框,
输入框内容变了 controller.text 也会读到 —— 但没有"响应式":
想根据输入内容实时刷新 UI(如"输入满 11 位才能点登录"),要自己 addListener 或 setState。
2. TextEditingController 生命周期(红线)
final TextEditingController _userCtrl = TextEditingController();
@override
void dispose() {
_userCtrl.dispose(); // 必须在 dispose 释放,防内存泄漏
super.dispose();
}
凡是用
Controller命名的东西(Text/Scroll/Animation/Tab),基本都要 dispose。
3. 密码眼睛切换
bool _showPwd = false;
TextField(
controller: _pwdCtrl,
obscureText: !_showPwd, // 密文/明文由状态决定
decoration: InputDecoration(
labelText: "密码",
prefixIcon: const Icon(Icons.lock),
border: const OutlineInputBorder(),
suffixIcon: IconButton(
icon: Icon(_showPwd ? Icons.visibility : Icons.visibility_off),
onPressed: () => setState(() => _showPwd = !_showPwd),
),
),
)
4. InputDecoration 常用参数
labelText:浮动标签(聚焦时缩小浮到边框上);hintText:灰色占位提示;prefixIcon:左侧图标;suffixIcon:右侧(按钮/图标);border: OutlineInputBorder():带边框的圆角样式(默认是下划线)。
四、关键代码剖析
// 读取输入内容(点登录时)
String user = _userCtrl.text;
String pwd = _pwdCtrl.text;
if (kDebugMode) {
print("账号:$user,密码:$pwd"); // kDebugMode:只在 debug 包打印
}
要点:
kDebugMode(来自package:flutter/foundation.dart)保证打印不会出现在 release 包;- 真实项目里读取后要走校验(见 form_demo.md)和登录接口(见 dio_demo.md)。
五、踩坑记录
- Scaffold 没有
padding参数! 外间距要写在 body 的Padding上(新手必踩)。 controller忘了 dispose → 内存泄漏(Flutter 分析器会提示)。suffixIcon用IconButton而不要用普通Icon包GestureDetector—— IconButton 自带点击区域和涟漪反馈。- 想"输入即校验"别自己写监听,直接上 Form(见 form_demo)。
六、扩展思考
- 进阶校验:
TextFormField+validator(form_demo.md)—— 本项目表单校验全家桶; - 真实登录页还要:防重复提交、加载动画、错误提示、密码安全存储(本项目用 flutter_secure_storage,见架构文档存储层);
- 输入法控制:
textInputAction: TextInputAction.next让回车键变成"下一项",最后一项变"完成"。