如何在对话框中将SingleChildScrollView滚动到TextField焦点

时间:2019-08-26 09:24:48

标签: flutter flutter-layout

显示警报对话框时出现问题。我的AlertDialog太高(许多TextFields)。当我单击下面的TextFields时,键盘会使对话框变短,并且SingleChildScrollView(我将内容包装在其中)不会滚动到具有焦点的TextField。但是,当我在该文本字段上键入字符时,SingleChildScrollView可以正常工作,并自动滚动到该TextField。因此,当用户第一次单击(具有焦点)时,SingleChildScrollView如何滚动到TextField。 p / s:我尝试将侦听器添加到FocusNode中,但是它不起作用。

例如:我将单击“全名”字段(图1),键盘使对话框简短,而我看不到“全名”字段(图2)。当我键入一个字符时,scrollview会正确滚动到该字符(图3)。 enter image description here enter image description here enter image description here

@override
  Widget build(BuildContext context) {
    return AlertDialog(
      title: Text(
        'Dialog Title',
        textAlign: TextAlign.center,
      ),
      titleTextStyle: TextStyle(
        fontSize: 16.0,
        color: Theme.of(context).textTheme.title.color,
        fontWeight: FontWeight.w800,
      ),
      shape: RoundedRectangleBorder(
        borderRadius: BorderRadius.circular(8.0),
      ),
      actions: <Widget>[
        FlatButton(
          onPressed: () {
            Navigator.of(context).pop();
          },
          child: Text('Cancel'.toUpperCase()),
        ),
        FlatButton(
          onPressed: () {
            Navigator.of(context).pop();
          },
          child: Text('OK'.toUpperCase()),
        ),
      ],
      content: SingleChildScrollView(
        child: Column(
          mainAxisSize: MainAxisSize.min,
          crossAxisAlignment: CrossAxisAlignment.stretch,
          children: <Widget>[
            TextField(
              focusNode: _nodePhone,
              maxLength: 10,
              keyboardType: TextInputType.phone,
              decoration: InputDecoration(
                labelText: 'Phone number',
              ),
              textInputAction: TextInputAction.next,
              onEditingComplete: () {
                FocusScope.of(context).requestFocus(_nodeEmail);
              },
            ),
            TextField(
              focusNode: _nodeEmail,
              keyboardType: TextInputType.emailAddress,
              decoration: InputDecoration(
                labelText: 'Email',
              ),
              textInputAction: TextInputAction.next,
              onEditingComplete: () {
                FocusScope.of(context).requestFocus(_nodeFullname);
              },
            ),
            TextField(
              focusNode: _nodeFullname,
              keyboardType: TextInputType.text,
              decoration: InputDecoration(
                labelText: 'Fullname',
              ),
              textInputAction: TextInputAction.next,
              onEditingComplete: () {
                FocusScope.of(context).requestFocus(_nodePassword);
              },
            ),
            TextField(
              focusNode: _nodePassword,
              obscureText: true,
              keyboardType: TextInputType.text,
              decoration: InputDecoration(
                labelText: 'Password',
              ),
              textInputAction: TextInputAction.done,
            ),
          ],
        ),
      ),
    );
  }

1 个答案:

答案 0 :(得分:0)

我也有这个问题,我设法通过给 SingleChildScrollView 一个控制器然后在 TextField 上的 onTap 来解决它。等待几毫秒对话框折叠然后滚动到对话框末尾

这是一些示例代码

//declare first
ScrollController _scrollController = ScrollController();

//your field code
SingleChildScrollView(
    // give a controller
    controller: _scrollController,
    child: Column(
        mainAxisSize: MainAxisSize.min,
        crossAxisAlignment: CrossAxisAlignment.stretch,
        children: < Widget > [
            TextField(
                focusNode: _nodePhone,
                maxLength: 10,
                keyboardType: TextInputType.phone,
                decoration: InputDecoration(
                    labelText: 'Phone number',
                ),
                textInputAction: TextInputAction.next,
                onEditingComplete: () {
                    FocusScope.of(context).requestFocus(_nodeEmail);
                },
            ),
            //suppose this is your very last textfield
            TextField(
                focusNode: _nodeEmail,
                keyboardType: TextInputType.emailAddress,
                decoration: InputDecoration(
                    labelText: 'Email',
                ),
                textInputAction: TextInputAction.next,
                onEditingComplete: () {
                    FocusScope.of(context).requestFocus(_nodeFullname);
                },
                onTap: () {
                    Future.delayed(Duration(milliseconds: 500), () {
                        _scrollController.animateTo(
                            _scrollController.position.maxScrollExtent,
                            duration: Duration(milliseconds: 200),
                            curve: Curves.ease);
                    });
                },
            ),
        ]
    )
);