【问题标题】:Flutter - Showing suggestion list on top of other widgetsFlutter - 在其他小部件之上显示建议列表
【发布时间】:2018-11-27 19:50:27
【问题描述】:

我正在开发一个屏幕,我必须在 textfield 下方显示建议列表。

我想实现这个

到目前为止我已经开发了这个

以下代码在列表中显示textfield 和建议。

  @override
  Widget build(BuildContext context) {
    final header = new Container(
      height: 39.0,
      padding: const EdgeInsets.only(left: 16.0, right: 2.0),
      decoration: _textFieldBorderDecoration,
      child: new Row(
        children: <Widget>[
          new Expanded(
            child: new TextField(
              maxLines: 1,
              controller: _controller,
              style: _textFieldTextStyle,
              decoration:
                  const InputDecoration.collapsed(hintText: 'Enter location'),
              onChanged: (v) {
                _onTextChanged.add(v);
                if (widget.onStartTyping != null) {
                  widget.onStartTyping();
                }
              },
            ),
          ),
          new Container(
            height: 32.0,
            width: 32.0,
            child: new InkWell(
              child: new Icon(
                Icons.clear,
                size: 20.0,
                color: const Color(0xFF7C7C7C),
              ),
              borderRadius: new BorderRadius.circular(35.0),
              onTap: (){
                setState(() {
                  _controller.clear();
                  _places = [];
                  if (widget.onClearPressed != null) {
                    widget.onClearPressed();
                  }
                });
              },
            ),
          ),
        ],
      ),
    );

    if (_places.length > 0) {
      final body = new Material(
        elevation: 8.0,
        child: new SingleChildScrollView(
          child: new ListBody(
            children: _places.map((p) {
              return new InkWell(
                child: new Container(
                  height: 38.0,
                  padding: const EdgeInsets.only(left: 16.0, right: 16.0),
                  alignment: Alignment.centerLeft,
                  decoration: _suggestionBorderDecoration,
                  child: new Text(
                    p.formattedAddress,
                    overflow: TextOverflow.ellipsis,
                    maxLines: 1,
                    style: _suggestionTextStyle,
                  ),
                ),
                onTap: () {
                  _getPlaceDetail(p);
                },
              );
            }).toList(growable: false),
          ),
        ),
      );

      return new Container(
        child: new Column(
          children: <Widget>[header, body],
        ),
      );
    } else {
      return new Container(
        child: new Column(
          children: <Widget>[header],
        ),
      );
    }
  }

Header(Textfield) 和 body(Suggestions List - SingleChildScrollView with ListBody) 被包裹在 Column 小部件中,并且列根据子项的总高度展开。 现在的问题是随着 Column 的扩展,布局系统将屏幕上的其他小部件推到底部。但我希望其他小部件保持在其位置,但建议列表开始出现在其他小部件之上。

如何在其他小部件之上显示建议列表?建议列表是动态的,因为用户类型我调用 Google Places API 并更新建议列表。

我看到有showMenu&lt;T&gt;() 方法和RelativeRect 位置,但它不符合我的目的,我的建议列表是动态的(根据用户输入而变化)并且我拥有的每个项目的样式都不同于PopupMenuItem 提供。

有一种可能性,我可以考虑将 Stack 小部件用作此屏幕的根小部件,并按绝对位置排列所有内容,并将建议列表作为堆栈子列表的最后一个子项。但我认为这不是正确的解决方案。

我还需要研究哪些其他可能性?在这个用例中还可以使用哪些其他小部件?

同样的用例很简单,在屏幕上的其他小部件上叠加建议列表,当用户点击列表中的任何项目时,然后隐藏这个叠加的建议列表。

【问题讨论】:

  • 这不是一个完整的答案,因为它并不能真正解决您提出的直接问题。但是你见过this 包吗?它可能会更轻松地完成您正在寻找的事情,或者至少您可以蚕食它的一部分。它不是自动完成内联,而是推送到不同的页面......这具有最大化屏幕空间以提供建议的优势。
  • 谢谢@rmtmckenzie 我已经看过了,这正是我正在做的,但方式不同。我还看到了这个包中的代码,知道有一些相关的代码可以覆盖小部件,但我没有找到任何相关的东西。但是感谢您写答案。
  • 您应该查看medium.com/saugo360/… 和pub.dartlang.org/packages/flutter_typeahead 以了解如何执行此操作的示例。

标签: dart flutter flutter-layout


【解决方案1】:

您的自动完成列表将其下方的小部件下推的原因是因为列表正在容器上展开。您可以使用 Flutter 的 Autocomplete widget,它应该会在其他小部件上增加自动完成列表。

var fruits = ['Apple', 'Banana', 'Mango', 'Orange'];

_autoCompleteTextField() {
  return Autocomplete(
    optionsBuilder: (TextEditingValue textEditingValue) {
      if (textEditingValue.text == '') {
        return const Iterable<String>.empty();
      }
      return fruits.where((String option) {
        return option
            .toLowerCase()
            .contains(textEditingValue.text.toLowerCase());
      });
    },
    onSelected: (String selection) {
      debugPrint('You just selected $selection');
    },
  );
}

【讨论】:

    猜你喜欢
    • 2015-03-24
    • 1970-01-01
    • 2021-12-08
    • 1970-01-01
    • 1970-01-01
    • 2017-10-06
    • 2020-10-17
    • 2013-12-09
    • 2019-08-29
    相关资源
    最近更新 更多