flutter - 如果 parent 更新,如何避免重建 child

标签 flutter dart flutter-layout flutter-animation

我有一个奇怪的要求。我看到这个this question on SO但我无法让它适用于我的情况。

我有一个代表我的屏幕的动画容器。按添加图标。我在改造屏幕like this (右侧图像中的列在主屏幕下方)。但是在那个 AnimatedContainer 里面有一个 LIST(作为 child )。

每次我做转换。该列表正在重新构建。有什么办法可以避免它。 ?

您可以想象主屏幕是用左右顶部的两个钉子钉在墙上的。当我按下 FAB 时。拔出左上钉,屏幕卡在右钉托上。当我再次按下 FAB 时,左上角再次被钉住。

这是我正在使用的小部件

https://pub.dev/packages/matrix4_transform

这里是查看重建的最少代码

import 'package:flutter/material.dart';
import 'package:matrix4_transform/matrix4_transform.dart';

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

class MyApp extends StatelessWidget {
  static const String _title = 'Flutter Code Sample';

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

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

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

_MyStatefulWidgetState? home;

class _MyStatefulWidgetState extends State<MyStatefulWidget> {
  DrawerManager drawerManager = DrawerManager();

  callSetState() {
    setState(() {});
  }

  @override
  Widget build(BuildContext context) {
    print('Rebuild');
    home = this;
    return AnimatedContainer(
      transform: Matrix4Transform()
          .translate(x: drawerManager.xOffSet, y: drawerManager.yOffSet)
          .rotate(drawerManager.angle)
          .matrix4,
      duration: Duration(milliseconds: 500),
      child: Scaffold(
        body: MyList(drawerManager),
      ),
    );
  }
}

class MyList extends StatelessWidget {
  final Data myData = Data();
  final DrawerManager drawerManager;

  MyList(this.drawerManager);

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: ListView.builder(
        physics: const BouncingScrollPhysics(),
        itemCount: myData.data.length+1,
        itemBuilder: (context, index) {
          print('Building list' + index.toString());
          if(index == 4){
            return GestureDetector(
              child: IconButton(
                  icon: Icon(Icons.add),
                  onPressed: () {
                    drawerManager.callback(drawerManager.isOpened);
                  }),
            );
          }
          else{return ListTile(
            title: Text(myData.data[index]),
          );}
        },
      ),
    );
  }
}
class Data {
  List<String> data = ['Hello1', 'Hello2', 'Hello3', 'Hello4'];
}
class DrawerManager {
  double xOffSet = 0;
  double yOffSet = 0;
  double angle = 0;
  bool isOpened = false;

  void callback(bool isOpen) {
    print('Tapped');
    if (isOpen) {
      xOffSet = 0;
      yOffSet = 0;
      angle = 0;
      isOpened = false;
    } else {
      xOffSet = 150;
      yOffSet = 80;
      angle = -0.2;
      isOpened = true;
    }
    callSetState();
  }
  void callSetState() {
    home!.callSetState();
  }
}

当您按下 + 图标时,您会看到。屏幕转换和列表正在重建。

最佳答案

请使用这个类, https://api.flutter.dev/flutter/widgets/AnimatedBuilder-class.html

Performance optimizations

If your builder function contains a subtree that does not depend on the animation, it's more efficient to build that subtree once instead of rebuilding it on every animation tick.

If you pass the pre-built subtree as the child parameter, the AnimatedBuilder will pass it back to your builder function so that you can incorporate it into your build.

关于flutter - 如果 parent 更新,如何避免重建 child ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66915451/

相关文章:

class - Flutter类继承

dom - 在 Dart 中,为什么下面的代码(关于 MutationObserver)不起作用?

Flutter - 在溢出时换行,例如插入省略号或淡入淡出

flutter - 如何在 flutter 中正确重用小部件样式?

flutter - Flutter-如何更改AppBar的高度并对齐标题垂直中心?

flutter - 将子类分配给 Dart 中的工厂构造函数

Flutter:左对齐展开的小部件

Python 可以有虚拟环境,Dart/flutter 是否有等价物?

flutter - 如何在Flutter项目中合并两个Firestore查询,以及如何从这两个流中删除重复的文档?

dart - 我应该如何使用Dart Isolate unhandledExceptionCallback?