0

我有个问题。在我的代码中,我调用showModalBottomSheet并在其中有一个反馈表。用户可以选择一个反应,然后发表评论以提交。

因此,我不得不在模态框内使用 aStatefulBuilder来使用setState。不过,它TextField有一个奇怪的行为——当我点击它时,键盘会出现一瞬间,然后模式会重置为原始状态。如果我删除StatefulBuilder并保留GestureDetector作为主小部件,一切都会按预期工作(键盘出现,模式移动以显示它,等等)。

有什么办法可以使StatefulBuilderTextField共存吗?下面有一段代码,适当地切割以关注这个问题。

TextEditingController feedbackTextFieldController = TextEditingController();

...

showModalBottomSheet<void>(
    context: context,
    isScrollControlled: true, // makes content maxHeight = full device height
    builder: (BuildContext context) {
      bool _isFeedbackLoading = false;

      return StatefulBuilder(
        builder: (context, setState) => GestureDetector(
          onTap: () {
            // the following is needed to dismiss the keyboard on tap outside of it
            FocusScopeNode currentFocus = FocusScope.of(context);

            if (!currentFocus.hasPrimaryFocus) {
              currentFocus.unfocus();
            }
          },
          child: AnimatedPadding(
            // to make the modal move when the keyboard is shown
            padding: MediaQuery.of(context).viewInsets,
            duration: const Duration(milliseconds: 100),
            curve: Curves.decelerate,
            child: Container(
              child: _isFeedbackLoading
                  ? Center(
                      child: CircularProgressIndicator(),
                    )
                  : TextField(
                      controller: feedbackTextFieldController,
                      textInputAction: TextInputAction.done,
                      textCapitalization: TextCapitalization.sentences,
                      maxLines: 2,
                      style: ...,
                      decoration: ...,
                    ),
            ),
          ),
        ),
      );
    },
  );

谢谢!

4

1 回答 1

1

您可以尝试以下代码

showModalBottomSheet<void>(
    context: context,
    isScrollControlled: true, // makes content maxHeight = full device height
    builder: (BuildContext context) {
      bool _isFeedbackLoading = false;

      return StatefulBuilder(
        // it could also because of you may reaching the wrong context
        // builder: (context, setState) => GestureDetector(
        builder: (_, setState) => GestureDetector(
          // may be you are not able to tap
          behavior: HitTestBehavior.opaque,
          onTap: () {
            // the following is needed to dismiss the keyboard on tap outside of it
            FocusScopeNode currentFocus = FocusScope.of(context);

            if (!currentFocus.hasPrimaryFocus) {
              currentFocus.unfocus();
            }
          },
          child: AnimatedPadding(
            // to make the modal move when the keyboard is shown
            padding: MediaQuery.of(context).viewInsets,
            duration: const Duration(milliseconds: 100),
            curve: Curves.decelerate,
            child: Container(
              child: _isFeedbackLoading
                  ? Center(
                      child: CircularProgressIndicator(),
                    )
                  : TextField(
                      controller: feedbackTextFieldController,
                      textInputAction: TextInputAction.done,
                      textCapitalization: TextCapitalization.sentences,
                      maxLines: 2,
                      style: ...,
                      decoration: ...,
                    ),
            ),
          ),
        ),
      );
    },
  );

或者您可以尝试为此制作另一个StatefulWidget,如下所示

showModalBottomSheet<void>(
    context: context,
    isScrollControlled: true, // makes content maxHeight = full device height
    builder: (BuildContext context) {
      return YourRefactoredStatefulWidget();
    }
.....
于 2021-10-13T10:33:55.717 回答