Flutter - PageView(2)页面缓存

1 在使用PageView的时候 我可以发现,直接使用没有缓存的功能,通常是滑动到当前页就加载当前页,划走后就立马销毁
2 子Flutter中 提供了一个 AutomaticKeepAliveClientMixin ,我们只需要让 PageState 混入这个 mixin,且同时添加一些必要操作即可实现缓存的功能

class ItemContainerState extends State<MyItemContainerState> with AutomaticKeepAliveClientMixin{

混入后有几个关键点,需要处理一下
1 super.build(context);

 @override
  Widget build(BuildContext context) {
    super.build(context);

2

 @override
  // TODO: implement wantKeepAlive
  bool get wantKeepAlive => true;

class MyViewPagerState extends StatefulWidget {
  const MyViewPagerState({Key? key}) : super(key: key);

  @override
  State<MyViewPagerState> createState() => _MyState();
}

class _MyState extends State<MyViewPagerState> {


  @override
  Widget build(BuildContext context) {

    return Scaffold(
      appBar: AppBar(
        title: const Text("MyViewPagerState"),
      ),
      body: ConstrainedBox(
        constraints: BoxConstraints.tightFor(width: double.infinity),
        child: PageView(
          scrollDirection:Axis.vertical,
          allowImplicitScrolling: true,
          children: <Widget>[
            MyItemContainerState(colors: Colors.yellow,pageName: "yellow",),
            MyItemContainerState(colors: Colors.red,pageName: "red",),
            MyItemContainerState(colors: Colors.green,pageName: "green",),
            MyItemContainerState(colors: Colors.blue,pageName: "blue",),
            MyItemContainerState(colors: Colors.deepPurple,pageName: "deepPurple",)

          ],
        )
      ),
    );
  }
}

class MyItemContainerState extends StatefulWidget {
  const MyItemContainerState({Key? key,required this.colors,required this.pageName}) : super(key: key);


  final MaterialColor colors ;
  final String pageName ;
  @override
  State<MyItemContainerState> createState() {
    // TODO: implement createState
    return ItemContainerState(colors,pageName);
  }
}

class ItemContainerState extends State<MyItemContainerState> with AutomaticKeepAliveClientMixin{

  MaterialColor colors ;
  String pageName ;
  ItemContainerState(this.colors,this.pageName);

  @override
  // TODO: implement wantKeepAlive
  bool get wantKeepAlive => true;

  @override
  Widget build(BuildContext context) {
    super.build(context);
    print("创建$pageName");
    // TODO: implement build
    return  Container(
      width: double.infinity,
      height: double.infinity,
      color: colors,
      alignment: Alignment.center,
      child: Text(pageName,style: TextStyle(fontSize: 50,color: Colors.white),),
    );
  }

  @override
  void dispose() {
    // TODO: implement dispose
    print("销毁$pageName");
    super.dispose();

  }

}

1 运行应用 执行yellow 页面和 red页面
Flutter - PageView(2)页面缓存_第1张图片
2 运行应用 执行green
Flutter - PageView(2)页面缓存_第2张图片
3 创建 green页面 且没有销毁任何页面
Flutter - PageView(2)页面缓存_第3张图片
4 创建完5个页面有 没有再次创建,也没有销毁任何页面
Flutter - PageView(2)页面缓存_第4张图片

封装,保存代码

@override
Widget build(BuildContext context) {
  var children = <Widget>[];
  for (int i = 0; i < 6; ++i) {
    //只需要用 KeepAliveWrapper 包装一下即可
    children.add(KeepAliveWrapper(child:Page( text: '$i'));
  }
  return PageView(children: children);
}
class KeepAliveWrapper extends StatefulWidget {
  const KeepAliveWrapper({
    Key? key,
    this.keepAlive = true,
    required this.child,
  }) : super(key: key);
  final bool keepAlive;
  final Widget child;

  @override
  _KeepAliveWrapperState createState() => _KeepAliveWrapperState();
}

class _KeepAliveWrapperState extends State<KeepAliveWrapper>
    with AutomaticKeepAliveClientMixin {
  @override
  Widget build(BuildContext context) {
    super.build(context);
    return widget.child;
  }

  @override
  void didUpdateWidget(covariant KeepAliveWrapper oldWidget) {
    if(oldWidget.keepAlive != widget.keepAlive) {
      // keepAlive 状态需要更新,实现在 AutomaticKeepAliveClientMixin 中
      updateKeepAlive();
    }
    super.didUpdateWidget(oldWidget);
  }

  @override
  bool get wantKeepAlive => widget.keepAlive;
}
class KeepAliveTest extends StatelessWidget {
  const KeepAliveTest({Key? key}) : super(key: key);

  
  Widget build(BuildContext context) {
    return ListView.builder(itemBuilder: (_, index) {
      return KeepAliveWrapper(
        // 为 true 后会缓存所有的列表项,列表项将不会销毁。
        // 为 false 时,列表项滑出预加载区域后将会别销毁。
        // 使用时一定要注意是否必要,因为对所有列表项都缓存的会导致更多的内存消耗
        keepAlive: true,
        child: ListItem(index: index),
      );
    });
  }
}

class ListItem extends StatefulWidget {
  const ListItem({Key? key, required this.index}) : super(key: key);
  final int index;

  
  _ListItemState createState() => _ListItemState();
}

class _ListItemState extends State<ListItem> {
  
  Widget build(BuildContext context) {
    return ListTile(title: Text('${widget.index}'));
  }

  
  void dispose() {
    print('dispose ${widget.index}');
    super.dispose();
  }
}

你可能感兴趣的:(Flutter,flutter,缓存)