35

Is there a way to use an asset image as a File. I need a File so it can be used for testing it over the internet using http. I've tried some answers from Stackoverflow.com (How to load images with image.file) but get an error 'Cannot open file, (OS Error: No such file or directory, errno = 2)'. The attached code line also gives an error.

File f = File('images/myImage.jpg');

RaisedButton(
   onPressed: ()=> showDialog(
     context: context,
     builder: (_) => Container(child: Image.file(f),)),
   child: Text('Show Image'),)

Using Image.memory widget(works)

Future<Null> myGetByte() async {
    _byteData = await rootBundle.load('images/myImage.jpg');
  }

  /// called inside build function
  Future<File> fileByte = myGetByte();

 /// Show Image
 Container(child: fileByte != null
 ? Image.memory(_byteData.buffer.asUint8List(_byteData.offsetInBytes, _ 
 byteData.lengthInBytes))
 : Text('No Image File'))),
1
  • 1
    Use AssetBundle to read it into memory and store it to a file. Commented Mar 22, 2019 at 8:35

3 Answers 3

66

You can access the byte data via rootBundle. Then, you can save it to the device's temporary directory which is obtained by path_provider (you need to add it as a dependency).

import 'dart:async';
import 'dart:io';

import 'package:flutter/services.dart' show rootBundle;
import 'package:path_provider/path_provider.dart';

Future<File> getImageFileFromAssets(String path) async {
  final byteData = await rootBundle.load('assets/$path');

  final file = File('${(await getTemporaryDirectory()).path}/$path');
  await file.create(recursive: true);
  await file.writeAsBytes(byteData.buffer.asUint8List(byteData.offsetInBytes, byteData.lengthInBytes));

  return file;
}

In your example, you would call this function like this:

File f = await getImageFileFromAssets('images/myImage.jpg');

For more information on writing the byte data, check out this answer.

You will need to await the Future and in order to do that, make the function async:

RaisedButton(
   onPressed: () async => showDialog(
     context: context,
     builder: (_) => Container(child: Image.file(await getImageFileFromAssets('images/myImage.jpg')))),
   child: Text('Show Image'));
Sign up to request clarification or add additional context in comments.

14 Comments

@ creativecreatorormaybenot now it really works. The problem I had was the function 'getImageFileFromAssets' was adding to it 'images/myImage.jpg' at getTemporaryDirectory(), instead of only '/myImage.jpg'. Finally I have a File! Thanks.
Hi, I follow the solution but I get the error about Unhandled Exception: FileSystemException: Cannot open file, path = '/data/user/0/com.example.myApp/cache/images/black.png' (OS Error: No such file or directory, errno = 2)
@creativecreatorormaybenot I think you should replace final file = File('${(await getTemporaryDirectory()).path}/$path'); with final file = File('${(await getTemporaryDirectory()).path}/image.png'); it will save time for future commers
I added await file.create(recursive: true); after creating the file. Because if your path includes directories that does not exist yet, writing to that file fails because by default create is with recursive false.
creativecreatorormaybenot, can you please edit your answer to include the line from @MustafaBerkayMutlu ?
|
3

Get File from Asset without providing a path.

import 'package:path_provider/path_provider.dart';


Future<File> getImageFileFromAssets(Asset asset) async {
    final byteData = await asset.getByteData();

    final tempFile =
        File("${(await getTemporaryDirectory()).path}/${asset.name}");
    final file = await tempFile.writeAsBytes(
      byteData.buffer
          .asUint8List(byteData.offsetInBytes, byteData.lengthInBytes),
    );

    return file;
  }

3 Comments

Thanks a lot man, you asked me alongside the next link. For people with problems with the image_picker in iOS 14.x
Asset class does not exist anywhere that I can find. Any insights?
The Asset class doesn't exist in your code as it is. For that matter you would need to install the multi_image_picker package and then to import it.
3

Make use of flutter_absolute_path package.

flutter_absolute_path: ^1.0.6

In pubspec.yaml

To convert file path from this format: "content://media/external/images/media/5275"

to "/storage/emulated/0/DCIM/Camera/IMG_00124.jpg"

List <File> fileImageArray = [];
assetArray.forEach((imageAsset) async {
  final filePath = await FlutterAbsolutePath.getAbsolutePath(imageAsset.identifier);

  File tempFile = File(filePath);
  if (tempFile.existsSync()) {
    fileImageArray.add(tempFile);
  }
}

1 Comment

you forget ")" in the last line edit it to make it easier for others

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.