Flutter:如何使用SliverList将{CupertinoActivityIndi​​cator放入customScrollView

时间:2018-04-15 10:14:57

标签: flutter flutter-sliver

这是我想要实现的模型 - 它是CupertinoSliverNavigationBar下面的CupertinoActivityIndi​​cator,用于通知用户数据正在下载。 enter image description here

下载后,它应如下所示:

enter image description here

现在,我一直在尝试使用以下代码获得此效果:

 List<Trade> trades = [];

  showLoadingDialog() {
    return trades.length == 0;
  }

  getBody() {
    if (showLoadingDialog()) {
      return getProgressDialog();
    } else {
      return getTradeItemList();
    }
  }

  getTradeItemList() {
    return new CupertinoPageScaffold(
        child: new CustomScrollView(slivers: <Widget>[
      const CupertinoSliverNavigationBar(
        largeTitle: const Text('Coffee Shop'),
      ),
      getBody(),
    ]));
  }

  getProgressDialog() {
    return new Container(
        decoration: const BoxDecoration(
          color: CupertinoColors.white,
        ),
        child: new Center(child: const CupertinoActivityIndicator()));
  }

但是,我收到此错误是因为我试图将非RenderSliv​​er类型放入Sliver中。换句话说,我将CupertinoActivityIndi​​cator放入Sliver并且代码拒绝它。

  

══╡WIDGETS图书馆的例外情况   ╞═════════════════════════════════════════════════ ══════════=   以下断言被抛出构建容器(bg:   BoxDecoration(颜色:颜色(0xffffffff))):一个RenderViewport预期a   RenderSliv​​er类型的子项,但收到了类型的子项   RenderDecoratedBox。 RenderObjects期望特定类型的子项   因为他们在布局和绘画期间与他们的孩子协调。   例如,RenderSliv​​er不能是RenderBox的子项,因为   RenderSliv​​er无法理解RenderBox布局协议。

我能达到我想要的最接近的效果显示在下面的gif中。但是,正如您可以清楚地看到的,当CupertinoActivityIndi​​cator可见时,CupertinoSliverNavigationBar不会显示。只有在下载数据后,才能看到显示“咖啡店”的CupertinoSliverNavigationBar。

enter image description here

我使用以下代码实现了上述目标:

  List<Trade> trades = [];

  showLoadingDialog() {
    return trades.length == 0;
  }

  getBody() {
    if (showLoadingDialog()) {
      return getProgressDialog();
    } else {
      return getTradeItemList();
    }
  }

  getProgressDialog() {
    return new Container(
        decoration: const BoxDecoration(
          color: CupertinoColors.white,
        ),
        child: new Center(child: const CupertinoActivityIndicator()));
  }


  getTradeItemList() {
    return new CupertinoPageScaffold(
      child: new CustomScrollView(
        slivers: <Widget>[
          const CupertinoSliverNavigationBar(
            largeTitle: const Text('Coffee Shop'),
          ),
          new SliverPadding(
            // Top media padding consumed by CupertinoSliverNavigationBar.
            // Left/Right media padding consumed by Tab1RowItem.
            padding: MediaQuery
                .of(context)
                .removePadding(
                  removeTop: true,
                  removeLeft: true,
                  removeRight: true,
                )
                .padding,
            sliver: new SliverList(
              delegate: new SliverChildBuilderDelegate(
                (BuildContext context, int index) {
                  return new Tab1RowItem(
                    index: index,
                    lastItem: index == trades.length - 1,
                    color: "Coffee Beans",
                    colorName: "Buy coffee now",
                  );
                },
                childCount: trades.length,
              ),
            ),
          )
        ],
      ),
    );
  }


  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return getBody();
  }

  @override
  void initState() {
    super.initState();
    loadDataTrades();
  }

有谁能告诉我如何达到我想要的效果?

1 个答案:

答案 0 :(得分:1)

 Widget _mainFrame;


@override
  Widget build(BuildContext context) {
    return new CustomScrollView(
      slivers: <Widget>[

        new CupertinoSliverNavigationBar(
          largeTitle: const Text("Coffe Shop"),
        ),

        _mainFrame,

      ],
    );
  }


Widget _beforeDataLoaded() {
    return new SliverFillRemaining(
      child:  new Container(
        child: new Center(
          child: new CupertinoActivityIndicator(),
        ),
      ),
    );
  }



Widget _dataLoadComplete() {
    return new SliverList(
      // Your list items
    );
  }

如果加载完成,则将_mainFrame Widget从CupertionActivityIndi​​cator更改为listview。