随着行数的增加,颤振列滚动变得非常滞后

Hai*_*m55 2 flutter flutter-web

所以我正在尝试为我的 flutter 项目构建一个多平台表。但是,当行数超过几百时,滚动就会变得非常缓慢,尤其是在 Web 应用程序中。构建过程也需要近 5 秒。为了构建选项卡,我在 SingleChildScrollView 中使用具有相同构建行的列。Flutter 的 Table 类也有同样的问题,我在 pub.dev jet 上找不到工作包。

即使在仅存在此表的项目中,滚动也是不可接受的。我可以做什么来构建 1000 或更多的大行数并平滑滚动?

这是简化的代码:

import 'package:flutter/material.dart';

class MyTable extends StatefulWidget{
  @override
  State<MyTable> createState() => _MyTableState();
}

class _MyTableState extends State<MyTable> {

  final double columnSpace = 5;
  final double rowSpace = 5;

  final decoration = BoxDecoration(
    borderRadius: BorderRadius.circular(5),
    color: Colors.grey,
  );

  @override
  Widget build(BuildContext context) {
    return SingleChildScrollView(
      child: Column(
        children: List.generate(1000, (index) => _buildRow(index)),
      ),
    );
  }

  _buildRow(int index){
    return Column(
      children: [
        SizedBox(
          height: 40,
          child: Row(
            children: [
              _buildExpandedCell(10, index.toString()),
              SizedBox(width: rowSpace,),
              _buildExpandedCell(4, index.toString()),
              SizedBox(width: rowSpace,),
              _buildExpandedCell(3, index.toString()),
              SizedBox(width: rowSpace,),
              _buildExpandedCell(3, index.toString()),
              SizedBox(width: rowSpace,),
              _buildExpandedCell(3, index.toString()),
              SizedBox(width: rowSpace,),
              Container(
                decoration: decoration,
                width: 90,
              ),
            ],
          ),
        ),
        SizedBox(height: columnSpace,),
      ],
    );
  }
  _buildExpandedCell(int flex, String content){
    return Expanded(
        flex: flex,
        child: Container(
          height: double.infinity,
          decoration: decoration,
          child: Center(child: Text(content)),
        ),
      );
  }
}
Run Code Online (Sandbox Code Playgroud)

Ivo*_*ers 5

你应该使用ListView.builder一个Column

对于你的例子来说,这将是

@override
Widget build(BuildContext context) {
  return SingleChildScrollView(
    child: Column(
      children: List.generate(1000, (index) => _buildRow(index)),
    ),
  );
}
Run Code Online (Sandbox Code Playgroud)

@override
Widget build(BuildContext context) {
  return ListView.builder(
    itemCount: 1000,
    itemBuilder: (context, index) => _buildRow(index),
  );
}
Run Code Online (Sandbox Code Playgroud)

原因是Columns 将所有子项加载到内存中,甚至是不可见的子项。使用 aListView.builder它只会加载屏幕上可见的内容。