import 'package:flutter/material.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:go_router/go_router.dart'; import 'package:momo/models/image_list_resp.dart'; import 'package:momo/models/image_resp.dart'; import 'package:momo/provider/rerender.dart'; import 'package:momo/request/http_client.dart'; class Gallery extends ConsumerWidget { const Gallery({Key? key}) : super(key: key); @override Widget build(BuildContext context, WidgetRef ref) { UniqueKey key = ref.watch(uniqueIdProvider); return Container( color: Colors.white, child: ImageGrid( key: key, ), ); } } class ImageGrid extends StatefulWidget { const ImageGrid({Key? key}) : super(key: key); @override State createState() => _ImageGridState(); } class _ImageGridState extends State { late ScrollController _scrollController; List imageList = []; int pageNum = 1; int pageSize = 10; bool hasMore = true; bool loading = false; Future loadImages() async { loading = true; if (!hasMore) { loading = false; return; } print(pageNum); var resp = await dio.get("/image/history", queryParameters: {"page": pageNum, "size": pageSize}); ImageListResp imageListResp = ImageListResp.fromJson(resp.data); hasMore = imageListResp.hasNext; pageNum = pageNum + 1; if (mounted) { setState(() { imageList.addAll(imageListResp.list); }); loading = false; } } @override void initState() { // TODO: implement initState super.initState(); print("init"); _scrollController = ScrollController(initialScrollOffset: 5.0) ..addListener(() { if (_scrollController.offset >= _scrollController.position.maxScrollExtent && !_scrollController.position.outOfRange) { print("到底了 controller $loading"); if (!loading) { loadImages(); } } }); loadImages(); } @override Widget build(BuildContext context) { return GridView.builder( itemCount: imageList.length, controller: _scrollController, gridDelegate: SliverGridDelegateWithFixedCrossAxisCount( crossAxisCount: MediaQuery.of(context).size.width > 640 ? 5 : 3), itemBuilder: (BuildContext context, int index) { return InkWell( onTap: () { context.go(Uri( path: "/detail", queryParameters: {"id": "${imageList[index].id}"}) .toString()); }, child: Image.network( "${dio.options.baseUrl}/image/thumbnail/${imageList[index].file_path}", fit: BoxFit.cover, errorBuilder: (BuildContext context, o, err) { return const Icon(Icons.error_outline); }, ), ); }); } }