multipage: thumbnail request cancellation
This commit is contained in:
parent
ff517925f6
commit
8fa3f18aef
7 changed files with 35 additions and 16 deletions
|
@ -172,6 +172,15 @@ class AvesEntry {
|
|||
addressChangeNotifier.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (other.runtimeType != runtimeType) return false;
|
||||
return other is AvesEntry && other.uri == uri && other.pageId == pageId && other._dateModifiedSecs == _dateModifiedSecs;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => hashValues(uri, pageId, _dateModifiedSecs);
|
||||
|
||||
@override
|
||||
String toString() => '$runtimeType#${shortHash(this)}{uri=$uri, path=$path, pageId=$pageId}';
|
||||
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
import 'package:flutter/foundation.dart';
|
||||
|
||||
class MultiPageInfo {
|
||||
final String uri;
|
||||
final List<SinglePageInfo> pages;
|
||||
|
||||
int get pageCount => pages.length;
|
||||
|
||||
MultiPageInfo({
|
||||
@required this.uri,
|
||||
this.pages,
|
||||
}) {
|
||||
if (pages.isNotEmpty) {
|
||||
|
@ -18,8 +20,11 @@ class MultiPageInfo {
|
|||
}
|
||||
}
|
||||
|
||||
factory MultiPageInfo.fromPageMaps(List<Map> pageMaps) {
|
||||
return MultiPageInfo(pages: pageMaps.map((page) => SinglePageInfo.fromMap(page)).toList());
|
||||
factory MultiPageInfo.fromPageMaps(String uri, List<Map> pageMaps) {
|
||||
return MultiPageInfo(
|
||||
uri: uri,
|
||||
pages: pageMaps.map((page) => SinglePageInfo.fromMap(page)).toList(),
|
||||
);
|
||||
}
|
||||
|
||||
SinglePageInfo get defaultPage => pages.firstWhere((page) => page.isDefault, orElse: () => null);
|
||||
|
@ -29,7 +34,7 @@ class MultiPageInfo {
|
|||
SinglePageInfo getById(int pageId) => pages.firstWhere((page) => page.pageId == pageId, orElse: () => null);
|
||||
|
||||
@override
|
||||
String toString() => '$runtimeType#${shortHash(this)}{pages=$pages}';
|
||||
String toString() => '$runtimeType#${shortHash(this)}{uri=$uri, pages=$pages}';
|
||||
}
|
||||
|
||||
class SinglePageInfo implements Comparable<SinglePageInfo> {
|
||||
|
|
|
@ -89,7 +89,7 @@ class MetadataService {
|
|||
'uri': entry.uri,
|
||||
});
|
||||
final pageMaps = (result as List).cast<Map>();
|
||||
return MultiPageInfo.fromPageMaps(pageMaps);
|
||||
return MultiPageInfo.fromPageMaps(entry.uri, pageMaps);
|
||||
} on PlatformException catch (e) {
|
||||
debugPrint('getMultiPageInfo failed with code=${e.code}, exception=${e.message}, details=${e.details}');
|
||||
}
|
||||
|
|
|
@ -43,7 +43,10 @@ class InteractiveThumbnail extends StatelessWidget {
|
|||
entry: entry,
|
||||
extent: tileExtent,
|
||||
collection: collection,
|
||||
isScrollingNotifier: isScrollingNotifier,
|
||||
// when the user is scrolling faster than we can retrieve the thumbnails,
|
||||
// the retrieval task queue can pile up for thumbnails that got disposed
|
||||
// in this case we pause the image retrieval task to get it out of the queue
|
||||
cancellableNotifier: isScrollingNotifier,
|
||||
),
|
||||
),
|
||||
);
|
||||
|
|
|
@ -9,7 +9,7 @@ class DecoratedThumbnail extends StatelessWidget {
|
|||
final AvesEntry entry;
|
||||
final double extent;
|
||||
final CollectionLens collection;
|
||||
final ValueNotifier<bool> isScrollingNotifier;
|
||||
final ValueNotifier<bool> cancellableNotifier;
|
||||
final bool selectable, highlightable;
|
||||
|
||||
static final Color borderColor = Colors.grey.shade700;
|
||||
|
@ -20,7 +20,7 @@ class DecoratedThumbnail extends StatelessWidget {
|
|||
@required this.entry,
|
||||
@required this.extent,
|
||||
this.collection,
|
||||
this.isScrollingNotifier,
|
||||
this.cancellableNotifier,
|
||||
this.selectable = true,
|
||||
this.highlightable = true,
|
||||
}) : super(key: key);
|
||||
|
@ -40,7 +40,7 @@ class DecoratedThumbnail extends StatelessWidget {
|
|||
: RasterImageThumbnail(
|
||||
entry: entry,
|
||||
extent: extent,
|
||||
isScrollingNotifier: isScrollingNotifier,
|
||||
cancellableNotifier: cancellableNotifier,
|
||||
heroTag: heroTag,
|
||||
);
|
||||
|
||||
|
|
|
@ -9,14 +9,14 @@ import 'package:flutter/material.dart';
|
|||
class RasterImageThumbnail extends StatefulWidget {
|
||||
final AvesEntry entry;
|
||||
final double extent;
|
||||
final ValueNotifier<bool> isScrollingNotifier;
|
||||
final ValueNotifier<bool> cancellableNotifier;
|
||||
final Object heroTag;
|
||||
|
||||
const RasterImageThumbnail({
|
||||
Key key,
|
||||
@required this.entry,
|
||||
@required this.extent,
|
||||
this.isScrollingNotifier,
|
||||
this.cancellableNotifier,
|
||||
this.heroTag,
|
||||
}) : super(key: key);
|
||||
|
||||
|
@ -70,11 +70,7 @@ class _RasterImageThumbnailState extends State<RasterImageThumbnail> {
|
|||
}
|
||||
|
||||
void _pauseProvider() {
|
||||
final isScrolling = widget.isScrollingNotifier?.value ?? false;
|
||||
// when the user is scrolling faster than we can retrieve the thumbnails,
|
||||
// the retrieval task queue can pile up for thumbnails that got disposed
|
||||
// in this case we pause the image retrieval task to get it out of the queue
|
||||
if (isScrolling) {
|
||||
if (widget.cancellableNotifier?.value ?? false) {
|
||||
_fastThumbnailProvider?.pause();
|
||||
_sizedThumbnailProvider?.pause();
|
||||
}
|
||||
|
|
|
@ -27,6 +27,7 @@ class MultiPageOverlay extends StatefulWidget {
|
|||
}
|
||||
|
||||
class _MultiPageOverlayState extends State<MultiPageOverlay> {
|
||||
final _cancellableNotifier = ValueNotifier(true);
|
||||
ScrollController _scrollController;
|
||||
bool _syncScroll = true;
|
||||
|
||||
|
@ -90,7 +91,8 @@ class _MultiPageOverlayState extends State<MultiPageOverlay> {
|
|||
future: controller.info,
|
||||
builder: (context, snapshot) {
|
||||
final multiPageInfo = snapshot.data;
|
||||
if ((multiPageInfo?.pageCount ?? 0) <= 1) return SizedBox.shrink();
|
||||
if ((multiPageInfo?.pageCount ?? 0) <= 1) return SizedBox();
|
||||
if (multiPageInfo.uri != mainEntry.uri) return SizedBox();
|
||||
return Container(
|
||||
height: extent + separatorWidth * 2,
|
||||
child: Stack(
|
||||
|
@ -125,6 +127,10 @@ class _MultiPageOverlayState extends State<MultiPageOverlay> {
|
|||
child: DecoratedThumbnail(
|
||||
entry: pageEntry,
|
||||
extent: extent,
|
||||
// the retrieval task queue can pile up for thumbnails of heavy pages
|
||||
// (e.g. thumbnails of 15MP HEIF images inside 100MB+ HEIC containers)
|
||||
// so we cancel these requests when possible
|
||||
cancellableNotifier: _cancellableNotifier,
|
||||
selectable: false,
|
||||
highlightable: false,
|
||||
),
|
||||
|
|
Loading…
Reference in a new issue