Reputation: 1885
So I'm trying to cache an image if an upload fails, due to the current limitations of flutter I think I will have to save it to shared preferences as a base64 file, then get it from shared preferences, convert it back to an image then upload that to firebase storage. My current code looks like so:
void saveImageToCache(File image) async {
List<int> imageBytes = image.readAsBytesSync();
String base64Image = base64Encode(imageBytes); //convert image ready to be cached as a string
var cachedImageName = "image $fileName";
instance.setString(cachedImageName, base64Image); // set image name in shared preferences
var retrievedImage = instance.getString(cachedImageName);// once a connection has been established again, get the image file from the cache and send it to firebase storage as an image
storageReference.putData(retrievedImage, StorageMetadata(contentType: 'base64'));
var prefix = "data:image/png;base64,";
var bStr = retrievedImage.substring(prefix.length);
var bs = Base64Codec.codec.decodeString(bStr);
var file = new File("image.png");
file.writeAsBytesSync(bs.codeUnits);
uploadTask = storageReference.child(fileName).putFile(file, const StorageMetadata(contentLanguage: "en"));
}
This is failing for me at var bStr = retrievedImage.substring(prefix.length);
with error type 'String' is not a subtype of type 'Uint8List' where
and im still not sure if im doing the right thing.
Any help would be great thanks.
Upvotes: 1
Views: 1569
Reputation: 5605
I wouldn't recommend storing binary files to shared preferences. Especially since you're building an image cache.
I'd just store them to a file.
Future<File> saveFile(File toBeSaved) async {
final filePath = '${(await getApplicationDocumentsDirectory()).path}/image_cache/image.jpg';
File(filePath)
..createSync(recursive: true)
..writeAsBytes(toBeSaved.readAsBytesSync());
}
This uses getApplicationDocumentsDirectory()
from the path provider package.
Upvotes: 3