ListView 的滚动在 Flutter 项目中不平滑



我刚开始学习长笛。我遇到了一个大问题,那就是在复杂的列表中滚动不好。假设我们在ListView中有5种不同的项目类型,有些项目类型必须显示图像,并且是无限滚动的。我读了很多关于Flutter的ListView的文章和帖子,我看到的所有东西都是带文本的简单列表。如何制作平滑滚动?

import 'dart:async';
import 'package:flutter/material.dart';
import 'package:english_words/english_words.dart';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'Startup Name Generator',
home: new RandomWords(),
);
}
}
class RandomWords extends StatefulWidget {
@override
RandomWordsState createState() => new RandomWordsState();
}
class RandomWordsState extends State<RandomWords> {
final List<WordPair> _suggestions = <WordPair>[];
final TextStyle _biggerFont = const TextStyle(fontSize: 18.0);
List<int> items = List.generate(10, (i) => i);
ScrollController _scrollController = new ScrollController();
bool isPerformingRequest = false;
@override
void initState() {
super.initState();
_scrollController.addListener(() {
if (_scrollController.position.pixels ==
_scrollController.position.maxScrollExtent) {
_getMoreData();
}
});
}
@override
void dispose() {
_scrollController.dispose();
super.dispose();
}
_getMoreData() async {
if (!isPerformingRequest) {
setState(() => isPerformingRequest = true);
List<int> newEntries = await fakeRequest(
items.length, items.length + 10); //returns empty list
if (newEntries.isEmpty) {
double edge = 50.0;
double offsetFromBottom = _scrollController.position.maxScrollExtent -
_scrollController.position.pixels;
if (offsetFromBottom < edge) {
_scrollController.animateTo(
_scrollController.offset - (edge - offsetFromBottom),
duration: new Duration(milliseconds: 500),
curve: Curves.easeOut);
}
}
setState(() {
items.addAll(newEntries);
isPerformingRequest = false;
});
}
}
Future<List<int>> fakeRequest(int from, int to) async {
return Future.delayed(Duration(seconds: 1), () {
return List.generate(to - from, (i) => i + from);
});
}
Widget _buildProgressIndicator() {
return new Padding(
padding: const EdgeInsets.all(8.0),
child: new Center(
child: new Opacity(
opacity: isPerformingRequest ? 1.0 : 0.0,
child: new CircularProgressIndicator(),
),
),
);
}
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: AppBar(
title: Text(""),
),
body: ListView.builder(
itemCount: items.length + 1,
itemBuilder: (context, index) {
if (index == items.length) {
return _buildProgressIndicator();
} else {
if (index % 5 == 0) {
return Image.network(
"http://sanctum-inle-resort.com/wp-content/uploads/2015/11/Sanctum_Inl_Resort_Myanmar_Flowers_Frangipani.jpg",
height: 200.0,
);
} else if (index.isOdd) {
return Container(
padding: EdgeInsets.all(16.0),
child: ListTile(
leading: Icon(Icons.person),
title: Text('This is title'),
),
);
} else {
return ListTile(title: new Text("Number $index"));
}
}
},
controller: _scrollController,
),
);
}
}

我认为问题在于,当用户已经在列表的末尾并且没有更多项目时,您请求数据异步,然后它执行一个加载数据的假请求,但这需要一秒钟的时间,所以这就是它阻碍的原因

_scrollController.position.maxScrollExtent

这会得到滚动列表的末尾,因此它在用户位于列表末尾的点开始加载。您可以通过偏移量更改此值,以便它更早地开始加载

要测试这一点,您可以尝试更改:

if (_scrollController.position.pixels ==
_scrollController.position.maxScrollExtent) {

收件人:

if (_scrollController.position.pixels ==
(_scrollController.position.maxScrollExtent - 50)) {

Future<List<int>> fakeRequest(int from, int to) async {
return Future.delayed(Duration(seconds: 1), () {
return List.generate(to - from, (i) => i + from);
});
}

收件人:

List<int> fakeRequest(int from, int to) {
return List.generate(to - from, (i) => i + from);
}

最新更新