如何在 Flutter 中使用 SLIVERS 实现交错网格视图?

How to implement staggered grid view with SLIVERS in Flutter?

我想实现 Staggered GridView,因为我的 SliverGrid 委托需要 纵横比 ,并且我希望网格项是动态调整大小 据我所知,只有交错网格视图才有可能。

我的问题是如何实现交错网格视图并将其作为 sliver 在我的 CustomScrollView 中使用?


编辑:

我的pubspec.yaml文件:

dependencies:
  flutter:
    sdk: flutter
  flutter_localizations:
    sdk: flutter
  flutter_staggered_grid_view: ^0.5.1
  ...other packages

对于更新版本,将 GridView 换成 SliverToBoxAdapter 并将 gridView physics 设置为 NeverScrollableScrollPhysics 因为 CustomScrollView 将处理滚动事件。

SliverToBoxAdapter(
  child: GridView.custom(
    shrinkWrap: true,
    physics: const NeverScrollableScrollPhysics(),

测试小部件

Scaffold(
          body: CustomScrollView(
        slivers: [
          const SliverAppBar(
            title: Text("title"),
          ),
          SliverToBoxAdapter(
            child: GridView.custom(
              shrinkWrap: true,
              physics: const NeverScrollableScrollPhysics(),
              gridDelegate: SliverQuiltedGridDelegate(
                crossAxisCount: 4,
                mainAxisSpacing: 4,
                crossAxisSpacing: 4,
                repeatPattern: QuiltedGridRepeatPattern.inverted,
                pattern: const [
                  QuiltedGridTile(2, 2),
                  QuiltedGridTile(1, 1),
                  QuiltedGridTile(1, 1),
                  QuiltedGridTile(1, 2),
                ],
              ),
              childrenDelegate: SliverChildBuilderDelegate(
                (context, index) => Container(
                  color: Colors.cyanAccent,
                  child: Text("$index"),
                ),
                childCount: 44,
              ),
            ),
          )
        ],
      )),

flutter_staggered_grid_view: ^0.4.1 提供 SliverStaggeredGrid 用作 sliver 的 child.

 CustomScrollView(
   slivers: [
     SliverStaggeredGrid.countBuilder(...
import 'package:flutter/material.dart';
import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart';

void main() => runApp(MyApp());

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

  @override
  Widget build(BuildContext context) {
    return MaterialApp(home: Dene());
  }
}

class Dene extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return SafeArea(
      child: Scaffold(
        body: Column(
          children: [
            Expanded(
              child: StaggeredGridView.countBuilder(
                mainAxisSpacing: 16,
                crossAxisSpacing: 16,
                crossAxisCount: 2,
                itemCount: 22,
                itemBuilder: (context, index) {
                  return Container(
                    width: 200,
                    height: 100,
                    color: Colors.red,
                  );
                },
                staggeredTileBuilder: (index) {
                  return StaggeredTile.fit(1);
                },
              ),
            ),
          ],
        ),
      ),
    );
  }
}
import 'package:flutter/material.dart';
import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart';

void main() => runApp(Dene());

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

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: MyApp(),
    );
  }
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return SafeArea(
      child: Scaffold(
        body: Column(
          children: [
            Expanded(
              child: StaggeredGridView.countBuilder(
                crossAxisCount: 4,
                itemCount: 22,
                itemBuilder: (BuildContext context, int index) => new Container(
                    color: Colors.green,
                    child: new Center(
                      child: new CircleAvatar(
                        backgroundColor: Colors.white,
                        child: new Text('$index'),
                      ),
                    )),
                staggeredTileBuilder: (int index) =>
                    new StaggeredTile.count(2, index.isEven ? 2 : 1),
                mainAxisSpacing: 4.0,
                crossAxisSpacing: 4.0,
              ),
            ),
          ],
        ),
      ),
    );
  }
}