10.Flutter(Widget)-表单组件

截屏2022-07-27 16.25.32.png

1.TextField (新增 errorText)

截屏2022-07-27 12.54.14.png
import 'package:flutter/material.dart';

class ZFLTextFieldPage extends StatefulWidget {
  @override
  _ZFLTextFieldPageState createState() => _ZFLTextFieldPageState();
}

class _ZFLTextFieldPageState extends State<ZFLTextFieldPage> {
  var _userNameController = TextEditingController();
  var _passWord = '';
  var _passWord1 = '';
  var errorText = '';
  List<FocusNode> focusNodes = [
    new FocusNode(),
    new FocusNode(),
    new FocusNode(),
    new FocusNode(),
    new FocusNode(),

  ];
  //
  bool isLocalPage = true;//离开页面 焦点会消失。

  @override
  void initState() {
    super.initState();
    _userNameController.text = "初始值";

    ///可以处理其他的操作
    focusNodes[0].addListener(() {
      if(!focusNodes[0].hasFocus) {
        if(isLocalPage == false) return;
      }
    });
    focusNodes[1].addListener(() {
      if(!focusNodes[1].hasFocus) {
        if(isLocalPage == false) return;
      }
    });
    focusNodes[2].addListener(() {
      if(!focusNodes[2].hasFocus) {
        if(isLocalPage == false) return;
      }
    });
    focusNodes[3].addListener(() {
      if(!focusNodes[3].hasFocus) {
        if(isLocalPage == false) return;
      }
    });
  }

  @override
  void dispose() {
    super.dispose();
    _dispose();
  }

  _dispose() {
    for (int i = 0; i < focusNodes.length; i++) {
      focusNodes[i].dispose();
    }
  }

  @override
  Widget build(BuildContext context) {
    //光标没有位于最后的位置
    _userNameController.selection = TextSelection.fromPosition(TextPosition(
        affinity: TextAffinity.downstream,
        offset: _userNameController.text.length));
    //点击任意区域收键盘
    return GestureDetector(
      behavior: HitTestBehavior.translucent,
      onTap: () {
        FocusScope.of(context).requestFocus(FocusNode());
      },
      child: Scaffold(
        appBar: AppBar(
          title: Text('输入框'),
        ),
        body: Container(
          child: Column(
            children: [
              TextField(
                  decoration: InputDecoration(
                      hintText: '请输入用户名',
                      errorText: errorText,
                      filled: true,
                      border: OutlineInputBorder()),
                  focusNode: focusNodes[0],
                  autofocus: true,
                  controller: _userNameController,
                  onChanged: (value) {
                    setState(() {
                      _userNameController.text = value;
                      if (_userNameController.text == 'aofeilin') {
                        errorText = 'aofeilin错误啦';
                      }
                    });
                  },
                  onEditingComplete: () {
//                    focusNodes[0].unfocus();//焦点使用
                    FocusScope.of(context).requestFocus(focusNodes[1]);// 非焦点离开时直接使用
                  }),
              SizedBox(
                height: 10,
              ),
              TextField(
                obscureText: true,
                focusNode: focusNodes[1],
                decoration: InputDecoration(hintText: '密码'),
                onChanged: (value) {
                  setState(() {
                    this._passWord = value;
                  });
                },
                onEditingComplete: () {
//                  focusNodes[1].unfocus();//焦点使用
                  FocusScope.of(context).requestFocus(focusNodes[2]);  //非焦点离开时直接使用 替换监听焦点
                },
              ),
              TextField(
                maxLines: 4,
                focusNode: focusNodes[2],
                onChanged: (value) {
                  setState(() {
                    this._passWord1 = value;
                  });
                },
                onEditingComplete: () {
//                  focusNodes[2].unfocus();//焦点使用
                  FocusScope.of(context).requestFocus(focusNodes[3]); //非焦点离开时直接使用 替换监听焦点
                },
              ),
              SizedBox(
                height: 10,
              ),
              TextField(
                focusNode: focusNodes[3],
                decoration: InputDecoration(
                    border: OutlineInputBorder(), labelText: '用户名',errorText: errorText),
                onChanged: (value) {
                  setState(() {
                    this._passWord1 = value;
                    if(this._passWord1 == 'aofeilin') {
                      errorText = '错误啦';
                    }
                  });
                },
                onEditingComplete: () {
//                  focusNodes[3].unfocus();//焦点使用
                  FocusScope.of(context).requestFocus(focusNodes[4]); //非焦点离开时直接使用 替换监听焦点
                },
              ),
              SizedBox(
                height: 10,
              ),
              TextField(
                focusNode: focusNodes[4],
                decoration: InputDecoration(
                  icon: Icon(Icons.add_a_photo),
//                  border: OutlineInputBorder(),
//                  labelText: '用户名'
                ),
                onChanged: (value) {
                  setState(() {
                    this._passWord1 = value;
                  });
                },
                onEditingComplete: () {
                  focusNodes[4].unfocus();
                },
              )
            ],
          ),
        ),
      ),
    );
  }
}


2.选择框 CheckBox

截屏2022-07-27 14.10.44.png
import 'package:flutter/material.dart';

class ZFLCheckBoxPage extends StatefulWidget {
  @override
  _ZFLCheckBoxPageState createState() => _ZFLCheckBoxPageState();
}

class _ZFLCheckBoxPageState extends State<ZFLCheckBoxPage> {
  bool isSelected = false;
  bool isBoxListTitleSelected = false;
  bool isCustomSelected = false;
  bool isCustomSelected1 = false;

  @override
  Widget build(BuildContext context) {
    return Container(
      child: Scaffold(
        appBar: AppBar(
          title: Text('选择框'),
        ),
        body: Column(
          children: [
            checkBoxWidget(),
            Divider(
              height: 1,
            ),
            checkBoxTitleWidget(),
            Divider(
              height: 1,
            ),
            customCheckBoxCheckBoxWidget(),
            Divider(
              height: 1,
            ),
            customCheckBoxCheckBoxWidget2()
          ],
        ),
      ),
    );
  }

  customCheckBoxCheckBoxWidget() {
    return InkWell(
      child: Container(
        padding: EdgeInsets.all(14),
        child: Row(
          children: [
            ZFLCheckBoxWidget(
              value: isCustomSelected,
              width: 20,
              height: 20,
            ),
            SizedBox(
              width: 10,
            ),
            Text('软件开发11')
          ],
        ),
      ),
      onTap: () {
        isCustomSelected = !isCustomSelected;
        setState(() {});
      },
    );
  }

  customCheckBoxCheckBoxWidget2() {
    return InkWell(
      child: Container(
        padding: EdgeInsets.all(14),
        child: Row(
          children: [
            ZFLCheckBoxWidget(
              value: isCustomSelected1,
              isCircle: false,
              width: 20,
              height: 20,
            ),
            SizedBox(
              width: 10,
            ),
            Text('软件开发11')
          ],
        ),
      ),
      onTap: () {
        isCustomSelected1 = !isCustomSelected1;
        setState(() {});
      },
    );
  }

  checkBoxWidget() {
    return InkWell(
      child: Row(
        children: [
          Checkbox(
            activeColor: Colors.green,
            value: isSelected, //选中
            onChanged: (value) {
              isSelected = value;
              setState(() {});
            },
          ),
          Text('软件开发')
        ],
      ),
      onTap: () {
        isSelected = !isSelected;
        setState(() {});
      },
    );
  }

  checkBoxTitleWidget() {
    return CheckboxListTile(
        activeColor: Colors.green,
        value: isBoxListTitleSelected,
        title: Text('白象'),
        subtitle: Text('白象方便面'),
        secondary: Icon(Icons.home),
        onChanged: (value) {
          isBoxListTitleSelected = value;
          setState(() {});
        });
  }
}

class ZFLCheckBoxWidget extends StatefulWidget {
  final bool value;
  final double width;
  final double height;
  final bool isCircle;

  ZFLCheckBoxWidget(
      {Key key, this.value, this.width, this.height, this.isCircle = true})
      : super(key: key);

  @override
  _ZFLCheckBoxWidgetState createState() => _ZFLCheckBoxWidgetState();
}

class _ZFLCheckBoxWidgetState extends State<ZFLCheckBoxWidget> {
  @override
  Widget build(BuildContext context) {
    return Container(
        width: this.widget.width,
        height: this.widget.height,
        child: this.widget.isCircle == true
            ? widget.value
                ? Icon(
                    Icons.check_circle,
                    size: this.widget.width,
                    color: Colors.green,
                  )
                : Icon(
                    Icons.panorama_fish_eye,
                    size: this.widget.width,
                    color: Colors.grey,
                  )
            : widget.value
                ? Icon(
                    Icons.check_box,
                    size: this.widget.width,
                    color: Colors.green,
                  )
                : Icon(
                    Icons.check_box_outline_blank,
                    size: this.widget.width,
                    color: Colors.grey,
                  ));
  }
}

3.单选按钮 Radio RadioListTile

截屏2022-07-27 14.47.47.png
import 'package:flutter/material.dart';
class ZFLRadioPage extends StatefulWidget {
  @override
  _ZFLRadioPageState createState() => _ZFLRadioPageState();
}

class _ZFLRadioPageState extends State<ZFLRadioPage> {
  int sexGroupValue = -1;
  int schoolGroupValue = -2;

  @override
  Widget build(BuildContext context) {
    return Container(
      child: Column(
        children: [
          Container(
            padding: EdgeInsets.only(left: 30,top: 50),
            child: Row(
              children: [
                Text('男'),
                sexRadioWidget(1),
                Text('女'),
                sexRadioWidget(2),
              ],
            ),
          ),
          Divider(height: 1,),
          schoolRadioWidget(11),
          Divider(height: 1,),
          schoolRadioWidget(12),
          Divider(height: 1,),
        ],
      ),
    );
  }

  sexRadioWidget(value) {
    return Radio(
        value: value,
        groupValue: sexGroupValue,
        activeColor: Colors.green,
        onChanged: (value) {
          setState(() {
            sexGroupValue = value;
          });
        });
  }

  schoolRadioWidget(value) {
    return RadioListTile(value: value, groupValue: schoolGroupValue,title: Text('客厅'),
        subtitle: Text('电视机'),
        secondary:Icon(Icons.star),
        onChanged: (value) {
          setState(() {
            schoolGroupValue = value;
          });
    });
  }
}

4.提交信息

截屏2022-07-27 16.23.49.png
import 'package:flutter/material.dart';
class ZFLFormPage extends StatefulWidget {
  @override
  _ZFLFormPageState createState() => _ZFLFormPageState();
}

class _ZFLFormPageState extends State<ZFLFormPage> {
  String username = '';
  int groupValue = 1; //sex
  String printStr = '';
  List hobby = [
    {"checked": true, "title": "吃饭"},
    {"checked": false, "title": "睡觉"},
    {"checked": true, "title": "写代码"}
  ];

  @override
  Widget build(BuildContext context) {
    return Container(
      child: Scaffold(
        appBar: AppBar(
          title: Text('登记系统'),
        ),
        bottomNavigationBar: submitWidget(),
          
        body: Padding(
          padding: EdgeInsets.all(20),
          child: Column(
            children: [
              userWidget(), //用户输入框
              sexWidget(), //性别
              checkBoxWidget(),
              Text('$printStr'),
            ],
          ),
        ),
      ),
    );
  }

  userWidget() {
    return TextField(
      decoration: InputDecoration(hintText: '请输入用户信息'),
      onChanged: (text) {
        setState(() {
          username = text;
        });
      },
      onEditingComplete: () {
        setState(() {});
      },
      onTap: () {},
    );
  }

  sexWidget() {
    return Row(
      children: [
        Text('男'),
        Radio(
            value: 1,
            groupValue: groupValue,
            onChanged: (value) {
              setState(() {
                groupValue = value;
              });
            }),
        Text('女'),
        Radio(
            value: 2,
            groupValue: groupValue,
            onChanged: (value) {
              setState(() {
                groupValue = value;
              });
            }),
      ],
    );
  }

  checkBoxWidget() {
    return Expanded(
      child: ListView.builder(
          itemCount: hobby.length,
          itemBuilder: (context, index) {
            return Row(
              children: [
                Text('${hobby[index]['title']}'),
                Checkbox(
                    value: hobby[index]['checked'],
                    onChanged: (value) {
                      setState(() {
                        hobby[index]['checked'] = value;
                      });
                    })
              ],
            );
          }),
    );
  }

  submitWidget() {
    String str = '';
//  List list = hobby.where((element) => element['checked'] == true);
    for (int i = 0; i < hobby.length; i++) {
      if (hobby[i]['checked'] == true) {
        str += '${hobby[i]['title']} ,';
      }
    }

    return Container(
      height: 70,
      padding: EdgeInsets.all(10),
      width: MediaQuery.of(context).size.width,
      child: RaisedButton(
          child: Text('提交信息'),
          textColor: Colors.white,
          color: Colors.blue,
          onPressed: () {
            setState(() {
              printStr =
              '用户名:${this.username} \n 性别: ${groupValue == 1 ? '男' : '女'}  \n 爱好:$str';
            });

          }),
    );
  }
}
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,386评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,142评论 3 394
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,704评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,702评论 1 294
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,716评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,573评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,314评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,230评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,680评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,873评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,991评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,706评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,329评论 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,910评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,038评论 1 270
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,158评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,941评论 2 355

推荐阅读更多精彩内容