2024-03-14 22:29:09 +02:00
import ' dart:async ' ;
import ' dart:ui ' as ui ;
import ' package:flutter/material.dart ' ;
import ' package:flutter_cache_manager/flutter_cache_manager.dart ' ;
2024-05-02 22:59:14 +02:00
import ' package:immich_mobile/providers/image/exceptions/image_loading_exception.dart ' ;
2024-05-01 04:36:40 +02:00
import ' package:immich_mobile/entities/store.entity.dart ' ;
2024-03-14 22:29:09 +02:00
/// Loads the codec from the URI and sends the events to the [chunkEvents] stream
///
/// Credit to [flutter_cached_network_image](https://github.com/Baseflow/flutter_cached_network_image/blob/develop/cached_network_image/lib/src/image_provider/_image_loader.dart)
/// for this wonderful implementation of their image loader
class ImageLoader {
static Future < ui . Codec > loadImageFromCache (
String uri , {
2024-04-25 06:30:32 +02:00
required CacheManager cache ,
2024-03-14 22:29:09 +02:00
required ImageDecoderCallback decode ,
StreamController < ImageChunkEvent > ? chunkEvents ,
} ) async {
final headers = {
' x-immich-user-token ' : Store . get ( StoreKey . accessToken ) ,
} ;
2024-04-25 06:30:32 +02:00
final stream = cache . getFileStream (
2024-03-14 22:29:09 +02:00
uri ,
2024-03-21 18:51:03 +02:00
withProgress: chunkEvents ! = null ,
2024-03-14 22:29:09 +02:00
headers: headers ,
) ;
await for ( final result in stream ) {
if ( result is DownloadProgress ) {
// We are downloading the file, so update the [chunkEvents]
chunkEvents ? . add (
ImageChunkEvent (
cumulativeBytesLoaded: result . downloaded ,
expectedTotalBytes: result . totalSize ,
) ,
) ;
2024-03-21 18:51:03 +02:00
} else if ( result is FileInfo ) {
2024-03-14 22:29:09 +02:00
// We have the file
2024-03-21 18:51:03 +02:00
final buffer = await ui . ImmutableBuffer . fromFilePath ( result . file . path ) ;
2024-03-14 22:29:09 +02:00
final decoded = await decode ( buffer ) ;
return decoded ;
}
}
// If we get here, the image failed to load from the cache stream
throw ImageLoadingException ( ' Could not load image from stream ' ) ;
}
}