简体   繁体   English

键盘关闭 Flutter 中的 Modal BottomSheet

[英]Keyboard closes the Modal BottomSheet in Flutter

When I want to write some text in Textfield, the Keyboard closes my modal bottom sheet.当我想在 Textfield 中写一些文本时,键盘会关闭我的模态底页。 I can't understand, why this is happening.我不明白,为什么会这样。 I try to used this line of code:我尝试使用这行代码:

padding: EdgeInsets.only(bottom: MediaQuery.of(context).viewInsets.bottom)

But in output I get textfield, which stretches.但是在 output 中,我得到了延伸的文本字段。

在此处输入图像描述

I spent a lot of time to solve this problem and I really want to close this issue.我花了很多时间来解决这个问题,我真的很想关闭这个问题。

This is full code这是完整的代码

import 'package:flutter/material.dart';
class NutritionScreen extends StatefulWidget {
  @override
  _NutritionScreenState createState() => _NutritionScreenState();
}

class _NutritionScreenState extends State<NutritionScreen> {
  double height = 500.0;
  void _modalBottomSheetMenu(){
    showModalBottomSheet(
        context: context,
        builder: (builder){
          return new Container(
            height: height,
            color: Colors.transparent, //could change this to Color(0xFF737373),
            //so you don't have to change MaterialApp canvasColor
            child: new Container(
                decoration: new BoxDecoration(
                    color: Colors.white,
                    borderRadius: new BorderRadius.only(
                        topLeft: const Radius.circular(10.0),
                        topRight: const Radius.circular(10.0))),
                child: SingleChildScrollView(
                child: Column(
                  crossAxisAlignment: CrossAxisAlignment.center,
                  mainAxisSize: MainAxisSize.max,
                  mainAxisAlignment: MainAxisAlignment.end,
                  children: <Widget>[
                    Padding(
                        padding: const EdgeInsets.all(8.0),
                        child: Text(
                          "Питание",
                          textAlign: TextAlign.center,
                          style: TextStyle(color: Colors.black, fontSize: 26.0),
                        )),
                    Padding(
                        padding: EdgeInsets.only(
                            bottom: 8.0,
                            top: 8.0,
                            right: 8.0,
                            left: 8.0
                        ),
                        child: TextField(
                          maxLines: 1,
                          textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                        style: TextStyle(
                          color: Colors.lightGreen[400],
                          fontSize: 18.5),
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.only(bottom: 4.0),
                          labelText: "Возраст",
                          alignLabelWithHint: false,
                      ),
                          keyboardType: TextInputType.phone,
                          textInputAction: TextInputAction.done,
                    )),
                    Padding(
                        padding: EdgeInsets.only(
                            bottom: 8.0,
                            top: 8.0,
                            right: 8.0,
                            left: 8.0
                        ),
                        child: TextField(
                          maxLines: 1,
                          textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                          style: TextStyle(
                              color: Colors.lightGreen[400],
                              fontSize: 18.5),
                          decoration: InputDecoration(
                            contentPadding: EdgeInsets.only(bottom: 4.0),
                            labelText: "Рост",
                            alignLabelWithHint: false,
                          ),
                          keyboardType: TextInputType.phone,
                          textInputAction: TextInputAction.done,
                        )),
                    Padding(
                        padding: EdgeInsets.only(
                            bottom: MediaQuery.of(context).viewInsets.bottom,
                            top: 8.0,
                            right: 8.0,
                            left: 8.0
                        ),
                        child: TextField(
                          maxLines: 1,
                          textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                          style: TextStyle(
                              color: Colors.lightGreen[400],
                              fontSize: 18.5),
                          decoration: InputDecoration(
                            contentPadding: EdgeInsets.only(bottom: 4.0),
                            labelText: "Вес",
                            alignLabelWithHint: false,
                          ),
                          keyboardType: TextInputType.phone,
                          textInputAction: TextInputAction.done,
                        )),
                    Padding(
                        padding: EdgeInsets.only(
                            bottom: MediaQuery.of(context).viewInsets.bottom,
                            top: 8.0,
                            right: 8.0,
                            left: 8.0
                        ),
                        child: TextField(
                          maxLines: 1,
                          textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                          style: TextStyle(
                              color: Colors.lightGreen[400],
                              fontSize: 18.5),
                          decoration: InputDecoration(
                            contentPadding: EdgeInsets.only(bottom: 4.0),
                            labelText: "Целевой вес",
                            alignLabelWithHint: false,
                          ),
                          keyboardType: TextInputType.phone,
                          textInputAction: TextInputAction.done,
                        )),
                  ],
                )),
          ));
        }
    );
  }

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      resizeToAvoidBottomInset: false,
      backgroundColor: Color(0xff2b2b2b),
      appBar: AppBar(
        backgroundColor: Colors.lightGreen[400],
        title: Text(
          'Питание',
          style: new TextStyle(
            color: Colors.white
          ),),
        leading: IconButton(
          icon:Icon(Icons.arrow_back),
          color: Colors.white ,
          onPressed:() => Navigator.of(context).pop(),
        ),
      ),
      body: Container(
        alignment: Alignment.center,
        margin: const EdgeInsets.only(bottom: 45.0),
          child: Column(
            crossAxisAlignment: CrossAxisAlignment.center,
            mainAxisSize: MainAxisSize.max,
            mainAxisAlignment: MainAxisAlignment.end,
            children: <Widget>[
              Padding(
                  padding: const EdgeInsets.only(bottom: 200.0),
                  child: Text(
                    "Нажми на кнопку, чтобы добавить правильный рацион питания.",
                    textAlign: TextAlign.center,
                    style: TextStyle(color: Colors.white, fontSize: 20.0),
                  )),
              FloatingActionButton(
                heroTag: "tag3",
                backgroundColor: Color(0xffFF7070),
                child: Icon(Icons.add, color: Colors.white),
                onPressed: () {
                  _modalBottomSheetMenu();
                }),
            ],
          ),
      ),
    );
  }
}

You don't need to wrap each filed with padding widget - simply wrap your primary Container with padding widget with- 你并不需要每个包裹提交给美国padding部件-简单地包装您的主Containerpadding部件与-

padding: EdgeInsets.only(
             bottom: MediaQuery.of(context).viewInsets.bottom)

.

Updated Code: 更新的代码:

class NutritionScreen extends StatefulWidget {
  @override
  _NutritionScreenState createState() => _NutritionScreenState();
}

class _NutritionScreenState extends State<NutritionScreen> {
  double height = 500.0;
  void _modalBottomSheetMenu() {
    showModalBottomSheet(
        context: context,
        builder: (builder) {
          return Padding(
            padding: EdgeInsets.only(
                bottom: MediaQuery.of(context).viewInsets.bottom),
            child: new Container(
                height: height,
                color: Colors
                    .transparent, //could change this to Color(0xFF737373),
                //so you don't have to change MaterialApp canvasColor
                child: new Container(
                  decoration: new BoxDecoration(
                      color: Colors.white,
                      borderRadius: new BorderRadius.only(
                          topLeft: const Radius.circular(10.0),
                          topRight: const Radius.circular(10.0))),
                  child: SingleChildScrollView(
                      child: Column(
                    crossAxisAlignment: CrossAxisAlignment.center,
                    mainAxisSize: MainAxisSize.max,
                    mainAxisAlignment: MainAxisAlignment.end,
                    children: <Widget>[
                      Text(
                        "Питание",
                        textAlign: TextAlign.center,
                        style:
                            TextStyle(color: Colors.black, fontSize: 26.0),
                      ),
                      TextField(
                        maxLines: 1,
                        textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                        style: TextStyle(
                            color: Colors.lightGreen[400], fontSize: 18.5),
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.only(bottom: 4.0),
                          labelText: "Возраст",
                          alignLabelWithHint: false,
                        ),
                        keyboardType: TextInputType.phone,
                        textInputAction: TextInputAction.done,
                      ),
                      TextField(
                        maxLines: 1,
                        textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                        style: TextStyle(
                            color: Colors.lightGreen[400], fontSize: 18.5),
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.only(bottom: 4.0),
                          labelText: "Рост",
                          alignLabelWithHint: false,
                        ),
                        keyboardType: TextInputType.phone,
                        textInputAction: TextInputAction.done,
                      ),
                      TextField(
                        maxLines: 1,
                        textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                        style: TextStyle(
                            color: Colors.lightGreen[400], fontSize: 18.5),
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.only(bottom: 4.0),
                          labelText: "Вес",
                          alignLabelWithHint: false,
                        ),
                        keyboardType: TextInputType.phone,
                        textInputAction: TextInputAction.done,
                      ),
                      TextField(
                        maxLines: 1,
                        textDirection: TextDirection.ltr,
//                        controller: customcintroller,
                        style: TextStyle(
                            color: Colors.lightGreen[400], fontSize: 18.5),
                        decoration: InputDecoration(
                          contentPadding: EdgeInsets.only(bottom: 4.0),
                          labelText: "Целевой вес",
                          alignLabelWithHint: false,
                        ),
                        keyboardType: TextInputType.phone,
                        textInputAction: TextInputAction.done,
                      ),
                    ],
                  )),
                )),
          );
        });
  }

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      resizeToAvoidBottomInset: false,
      backgroundColor: Color(0xff2b2b2b),
      appBar: AppBar(
        backgroundColor: Colors.lightGreen[400],
        title: Text(
          'Питание',
          style: new TextStyle(color: Colors.white),
        ),
        leading: IconButton(
          icon: Icon(Icons.arrow_back),
          color: Colors.white,
          onPressed: () => Navigator.of(context).pop(),
        ),
      ),
      body: Container(
        alignment: Alignment.center,
        margin: const EdgeInsets.only(bottom: 45.0),
        child: Column(
          crossAxisAlignment: CrossAxisAlignment.center,
          mainAxisSize: MainAxisSize.max,
          mainAxisAlignment: MainAxisAlignment.end,
          children: <Widget>[
            Padding(
                padding: const EdgeInsets.only(bottom: 200.0),
                child: Text(
                  "Нажми на кнопку, чтобы добавить правильный рацион питания.",
                  textAlign: TextAlign.center,
                  style: TextStyle(color: Colors.white, fontSize: 20.0),
                )),
            FloatingActionButton(
                heroTag: "tag3",
                backgroundColor: Color(0xffFF7070),
                child: Icon(Icons.add, color: Colors.white),
                onPressed: () {
                  _modalBottomSheetMenu();
                }),
          ],
        ),
      ),
    );
  }
}

在此处输入图片说明

Modal Bottom Sheet which sticks to top of keyboard粘在键盘顶部的模态底板

MBS: Modal Bottom Sheet MBS:模态底板

In Container use margin for keyboard space and use padding for content.在 Container 中,键盘空间使用边距,内容使用填充。 This reduce height of MBS by keyboard height and stick MBS to top of keyboards (This can seen when keyboard opening or closing).这会通过键盘高度降低 MBS 的高度,并将 MBS 粘贴到键盘顶部(这可以在键盘打开或关闭时看到)。

  • isScrollControlled: true for allow to change heigth of MBS isScrollControlled: true允许改变 MBS 的高度
  • margin for giving empty space for keyboard with MediaQuery使用margin为键盘提供空白空间的边距
  • padding optionel content padding padding选项内容填充
showModalBottomSheet(
 isScrollControlled: true,
 builder: (BuildContext context) {
    return Container(
        margin: EdgeInsets.only(bottom: MediaQuery.of(context).viewInsets.bottom), // Keyboard margin
        padding: const EdgeInsets.all(20) // Content padding
        child: ... // You wiget tree
    );
  },
);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM