【问题标题】:How to reveal search bar on ListView pull down action in flutter?如何在颤动中显示 ListView 下拉动作上的搜索栏?
【发布时间】:2021-06-07 07:35:01
【问题描述】:

我想实现一个搜索栏,当用户在ListView 中执行下拉操作时显示它,并在用户滚动ListView 时隐藏它(就像在 iOS 中一样)。但是找不到任何有关如何实现这一点的相关信息。 This answer wasn't helpful at all as RefreshIndicator 只返回一个刷新指示器。没有可显示的代码,因为我不知道如何在 Flutter 中做到这一点。

编辑:

代码:

NestedScrollView(
                  headerSliverBuilder:
                      (BuildContext context, bool innerBoxIsScrolled) =>
                          <Widget>[
                    SliverOverlapAbsorber(
                        handle: NestedScrollView.sliverOverlapAbsorberHandleFor(
                            context),
                        sliver: SliverAppBar(
                          collapsedHeight: 100,
                          expandedHeight: 100,
                          toolbarHeight: 100,
                          leadingWidth: 0,
                          leading: Container(),
                          backgroundColor: Colors.red,
                          title: TextField(),
                        )),
                  ],
                  body: ListView.builder(
                      itemCount: _itemCount,
                      itemBuilder: (BuildContext context, int index) {
                        return Text('Item $index');
                      }),
                ),

谢谢!

【问题讨论】:

  • 您可以使用SliverAppBar() 进行一些自定义设计,您可以实现这一目标。查看SliverAppBar()api.flutter.dev/flutter/material/SliverAppBar-class.html的完整文档
  • @ChiragBargoojar 编辑了我的帖子并添加了一些代码,几乎可以按预期工作,但是知道如何默认隐藏SliverAppBar()(在用户执行下拉操作之前不要显示它)?
  • 你有没有想过这个问题?如果你不这样做,你可以使用pub.dev/packages/pull_to_reveal 我需要做同样的事情,但对于自定义滚动视图

标签: flutter searchbar flutter-listview


【解决方案1】:

我找到了一个很好的方法来使用颤振的原生材料showSearch 函数。 showSearch + 它的委托处理搜索显示部分,因此您必须使用这条路线的物质处理方式(下图)

然后,要执行“拖动”功能,您可以在此类中包装一个可滚动的小部件:

注意下面的代码使用了flutter hooks包,如果你不使用钩子,只需使用一个有状态的小部件来管理isDragFromEdge

import 'package:flutter/widgets.dart';
import 'package:flutter_hooks/flutter_hooks.dart';

// The drag delta needed to trigger the onPull function
const kDragTriggerDelta = 15;

class PullScrollable extends HookWidget {
  final Widget child;
  final Function onPull;

  const PullScrollable({
    Key? key,
    required this.child,
    required this.onPull,
  }) : super(key: key);

  @override
  Widget build(BuildContext context) {
    final isDragFromEdge = useState(false);

    // Detects if the drag started from the top of the scrollable
    bool getIsDragFromEdge(ScrollStartNotification notification) {
      return notification.metrics.extentBefore == 0.0 &&
          isDragFromEdge.value == false;
    }

    bool handleDragFromEdge() {
      isDragFromEdge.value = true;

      return false;
    }

    bool handleDragEnd() {
      isDragFromEdge.value = false;

      return false;
    }

    // Detects if the drag is in an upwards motion exceeding the trigger delta
    bool getIsOverscroll(ScrollNotification notification) {
      if (!isDragFromEdge.value) return false;

      if ((notification is ScrollUpdateNotification &&
              (notification.dragDetails?.primaryDelta ?? 0) >
                  kDragTriggerDelta) ||
          (notification is OverscrollNotification &&
              (notification.dragDetails?.primaryDelta ?? 0) >
                  kDragTriggerDelta)) {
        return true;
      }

      return false;
    }

    // On overscroll, trigger the onPull function
    bool handleOverscroll() {
      onPull();

      isDragFromEdge.value = false;

      return false;
    }

    return NotificationListener<ScrollNotification>(
      child: child,
      onNotification: (notification) {
        if (notification is ScrollStartNotification &&
            getIsDragFromEdge(notification)) handleDragFromEdge();

        if (notification is ScrollEndNotification) handleDragEnd();

        if (getIsOverscroll(notification)) handleOverscroll();

        return false;
      },
    );
  }
}

将两者结合起来,您就有了类似的东西

class ListView extends StatelessWidget {
  const ListView({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return PullScrollable(
      onPull: () {
        showSearch(context: context, delegate: YourDelegate());
      },
      child: ListView(),
    );
  }
}

【讨论】:

    猜你喜欢
    • 2018-09-04
    • 2021-02-22
    • 2020-11-01
    • 2020-12-20
    • 2021-11-21
    • 2021-05-21
    • 1970-01-01
    • 2021-07-11
    相关资源
    最近更新 更多