Flutter如何隐藏键盘下FloatingActionButton且不遮挡TextFormField并解决焦点问题
解决方案
问题1:仅隐藏键盘弹出时的FloatingActionButton,同时保证TextFormField不被遮挡
- 首先删掉Scaffold上的
resizeToAvoidBottomInset: false配置,保留默认的true状态,此时页面会在键盘弹出时自动上移,输入框不会被遮挡 - 然后通过
MediaQuery.of(context).viewInsets.bottom判断键盘是否弹出,动态控制FAB的显示/隐藏:键盘弹出(该值大于0)时隐藏FAB,键盘收起时显示FAB
问题2:TextFormField每次仅聚焦第一个输入框
- 该问题是因为动态生成的Card和输入框没有配置唯一的
Key,Flutter在重绘widget树时无法正确区分不同输入框的状态,导致聚焦错位。只需要给每个动态生成的Card、以及每个TextFormField添加对应index的唯一Key即可解决。
完整修改后代码
import 'package:flutter/material.dart'; void main() { runApp(App()); } class App extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: CardWithTextformfield(), ); } } class CardWithTextformfield extends StatefulWidget { const CardWithTextformfield({Key? key}) : super(key: key); @override _CardWithTextformfieldState createState() => _CardWithTextformfieldState(); } class _CardWithTextformfieldState extends State<CardWithTextformfield> { var name =<TextEditingController>[]; var id =<TextEditingController>[]; var addCard =1; bool cardOneVisibility=true; bool cardTwoVisibility=false; bool cardThreeVisibility=false; bool cardFourVisibility=false; bool cardFiveVisibility=false; bool cardSixVisibility=false; void incrementcard(){ setState(() { if(addCard==0){ cardOneVisibility=true; } else if(addCard==1){ cardOneVisibility=true; cardTwoVisibility=true; } else if(addCard==2){ cardOneVisibility=true; cardTwoVisibility=true; cardThreeVisibility=true; } else if(addCard==3){ cardOneVisibility=true; cardTwoVisibility=true; cardThreeVisibility=true; cardFourVisibility=true; } else if(addCard==4){ cardOneVisibility=true; cardTwoVisibility=true; cardThreeVisibility=true; cardFourVisibility=true; cardFiveVisibility=true; } else if(addCard==5){ cardOneVisibility=true; cardTwoVisibility=true; cardThreeVisibility=true; cardFourVisibility=true; cardFiveVisibility=true; cardSixVisibility=true; } addCard++; }); } @override Widget build(BuildContext context) { // 判断键盘是否弹出 bool isKeyboardShow = MediaQuery.of(context).viewInsets.bottom > 0; return Scaffold( // 已删除resizeToAvoidBottomInset: false配置,保留默认值 appBar: AppBar( title: Text('Card with TextformField'), ), // 动态控制FAB显示隐藏 floatingActionButton: isKeyboardShow ? SizedBox.shrink() : FloatingActionButton( onPressed: addCard>=6 ? null : incrementcard, child: Icon(Icons.add), ), body: Container( child:SingleChildScrollView( child: Column( children: [ Visibility(visible: cardOneVisibility,child: cardslist(0)), Visibility(visible: cardTwoVisibility,child: cardslist(1)), Visibility(visible: cardThreeVisibility,child: cardslist(2)), Visibility(visible: cardFourVisibility,child: cardslist(3)), Visibility(visible: cardFiveVisibility,child: cardslist(4)), Visibility(visible: cardSixVisibility,child: cardslist(5)), ], ), ), ), ); } Widget cardslist(int index){ if(name.length <= index){ name.add(TextEditingController()); id.add(TextEditingController()); } return Card( // 给Card添加唯一Key key: Key('card_$index'), margin: EdgeInsets.all(10), child: Container( child: Column( children: [ Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Container( margin: EdgeInsets.all(10), child: Text('Team Name: ')), Expanded(child: TextFormField( // 给名称输入框添加唯一Key key: Key('name_input_$index'), controller: name[index], decoration: InputDecoration(hintText: 'Team Name'), ),), Container( margin: EdgeInsets.all(10), child: Text('Team Id: '),), Expanded(child: TextFormField( // 给ID输入框添加唯一Key key: Key('id_input_$index'), controller: id[index], decoration: InputDecoration(hintText: 'Team Id'), ),), ], ), Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ GestureDetector( child: Container( width: 50,height: 50, margin: EdgeInsets.all(10), decoration: BoxDecoration( shape: BoxShape.rectangle, color:Colors.grey, ), child: Center(child: Text('IT'),), ), ), GestureDetector( child: Container( width: 50,height: 50, margin: EdgeInsets.all(10), decoration: BoxDecoration( shape: BoxShape.rectangle, color: Colors.grey, ), child: Center(child: Text('DEV'),), ), ), GestureDetector( child: Container( width: 50,height: 50, margin: EdgeInsets.all(10), decoration: BoxDecoration( shape: BoxShape.rectangle, color: Colors.grey, ), child: Center(child: Text('TEST'),), ), ), GestureDetector( child: Container( width: 50,height: 50, margin: EdgeInsets.all(10), decoration: BoxDecoration( shape: BoxShape.rectangle, color: Colors.grey, ), child: Center(child: Text('HR'),), ), ), ], ) ], ), ), ); } }
内容的提问来源于stack exchange,提问作者Shanmukha
相关产品推荐
相关产品推荐

