You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让Flutter中的TextField像聊天应用一样自动增高?

解决Flutter聊天TextField动态高度问题

你的代码里存在多处固定高度约束,导致TextField无法随内容换行动态扩展,以下是针对性的修改方案:

问题根源

  • 底部输入区域的SizedBox使用固定高度_textFieldHeight,限制了整体输入栏的高度变化
  • _chatBox中的Container设置了固定height:56.h,直接约束了TextField的可扩展空间
  • TextField的minLines设为3,不符合单行为初始状态的需求

修改后的完整代码片段

class ChatScreen extends StatefulWidget {
  const ChatScreen({super.key});

  @override
  State<ChatScreen> createState() => _ChatScreenState();
}

class _ChatScreenState extends State<ChatScreen> {
  late TextEditingController _chatTextController;
  late bool _isEnabled;
  late FocusNode _chatTextFocusNode;
  ScrollController textFieldScrollController = ScrollController();

  @override
  void initState() {
    super.initState();
    _chatTextController = TextEditingController();
    _isEnabled = true;
    _chatTextFocusNode = FocusNode();
  }

  @override
  void dispose() {
    _chatTextController.dispose();
    _chatTextFocusNode.dispose();
    _isEnabled = false;
    textFieldScrollController.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: () => FocusManager.instance.primaryFocus?.unfocus(),
      child: SafeArea(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.spaceBetween,
          children: [
            Row(
              children: [
                Gap(4.w),
                const CustomBackButton(
                  previousScreen: 'welcome',
                  assetIcon: 'assets/icons/home.png',
                ),
                Gap(4.w),
                Text(
                  'Chat Screen',
                  style: TextStyle(
                    fontSize: 22.sp,
                    fontWeight: FontWeight.w400,
                    color: AppColors.titleTextBlack,
                  ),
                ),
              ],
            ),
            // 移除固定高度的SizedBox,让输入栏随内容自适应
            Column(
              mainAxisSize: MainAxisSize.min,
              children: [
                Divider(
                  height: 0,
                  thickness: 1.h,
                  color: const Color(0xFFBEC9C7),
                ),
                Padding(
                  padding: EdgeInsets.symmetric(vertical: 16.h, horizontal: 24.w),
                  child: Row(
                    crossAxisAlignment: CrossAxisAlignment.end, // 让发送按钮始终对齐底部
                    children: [
                      _chatBox(),
                      Gap(8.w),
                      ChatBoxIconButton(
                        onPressed: () {
                          print('*********');
                        },
                        icon: Icons.send_rounded,
                        backgroundColor: AppColors.mainGreen,
                      ),
                    ],
                  ),
                ),
              ],
            ),
          ],
        ),
      ),
    );
  }

  Widget _chatBox() {
    return Container(
      width: 308.w,
      padding: EdgeInsets.only(left: 16.w, top: 12.h, bottom: 12.h), // 调整内边距适配多行文本
      decoration: BoxDecoration(
        border: Border.all(color: AppColors.regularTextGrey),
        borderRadius: BorderRadius.circular(100.r),
      ),
      child: Row(
        crossAxisAlignment: CrossAxisAlignment.center,
        children: [
          Expanded(
            child: TextField(
              cursorHeight: 18.sp,
              cursorColor: AppColors.mainGreen,
              controller: _chatTextController,
              scrollController: textFieldScrollController,
              focusNode: _chatTextFocusNode,
              keyboardType: TextInputType.multiline,
              onChanged: (value) {
                WidgetsBinding.instance.addPostFrameCallback((_) {
                  textFieldScrollController.jumpTo(textFieldScrollController.position.maxScrollExtent);
                });
              },
              minLines: 1, // 初始显示单行
              maxLines: 3, // 限制最大扩展行数,可按需修改
              style: TextStyle(fontSize: 16.sp, color: AppColors.regularTextBlack),
              decoration: InputDecoration(
                hintText: 'Ask me anything',
                hintStyle: TextStyle(fontSize: 16.sp, color: AppColors.regularTextGrey),
                border: InputBorder.none,
                contentPadding: EdgeInsets.symmetric(vertical: 0), // 移除默认垂直内边距,避免多余高度
              ),
            ),
          ),
          ChatBoxIconButton(
            onPressed: () {
              print('*********');
            },
            icon: CupertinoIcons.mic,
            backgroundColor: Colors.white,
            iconColor: AppColors.regularTextGrey,
          ),
        ],
      ),
    );
  }
}

关键修改点说明

  1. 移除固定高度约束:删除SizedBox的固定高度和_chatBox中Container的固定高度,让Widget根据内容自动调整高度
  2. 优化TextField参数:设置minLines:1保证初始单行显示,maxLines:3限制最大扩展高度(可根据需求调整)
  3. 对齐方式调整:输入区域的Row添加crossAxisAlignment: CrossAxisAlignment.end,确保发送按钮始终保持在底部
  4. 滚动逻辑修正:在onChanged中使用WidgetsBinding.instance.addPostFrameCallback,确保滚动到最底部的操作在UI更新后执行
  5. 内边距适配:调整Container和TextField的内边距,让多行文本显示更自然

内容的提问来源于stack exchange,提问作者Mehedi Hasan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.28 17:24:56