IOException - Cannot load file

ⅰ亾dé卋堺 提交于 2019-12-04 03:29:48

问题


I have an app that shows GIF images. It all works fine if image is saved in drawable, and I access it like this

is=context.getResources().openRawResource(R.drawable.mygif);
movie = Movie.decodeStream(is);

But I need to download image from internet, so I'm saving it to CacheDir, that works fine. I tried the following to read it.

    try
    {
        is = new BufferedInputStream(new FileInputStream(new File(context.getCacheDir(), "mygif.gif")));
    }
    catch (FileNotFoundException e)
    {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    movie = Movie.decodeStream(is);

And this

movie = Movie.decodeFile(new File(context.getCacheDir(), "mygif.gif").getPath());

But no matter what, it ends with

java.io.IOException
at java.io.InputStream.reset(InputStream.java:218)
at android.graphics.Movie.decodeStream(Native Method)
at android.graphics.Movie.decodeTempStream(Movie.java:74)
at android.graphics.Movie.decodeFile(Movie.java:59)

or

java.io.IOException: Mark has been invalidated.
at java.io.BufferedInputStream.reset(BufferedInputStream.java:350)
at android.graphics.Movie.decodeStream(Native Method)

I think it's a very simple error, but I can't get over it. Manifest has:

<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

回答1:


suggestion:

1.try move the download location to another folder like: sdcard, or the app another folder except the cache.

2.when init the inputstream, try use: init with a buffer size

int buffersize = 16*1024;
InputStream  is = new BufferedInputStream(xxx,buffersize);

3.to check the file existed in your folder

update: change the code like this and dont use Movie.decodeFile

 InputStream is = null;
    try {
        is = new BufferedInputStream(new FileInputStream(new File(getCacheDir(), "mygif.gif")), 16 * 1024);
        is.mark(16 * 1024); 
    } catch (FileNotFoundException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
movie = Movie.decodeStream(is);

no exception throw, and the movie is not null.

Also, although your code will throw the exception, the movie is also not null.




回答2:


I know is a really old post, but I was having the same issue

Copying the InputStream to a byte array and calling Movie.decodeByteArray worked for me, even on Samsung Devices




回答3:


My answer is based on the BeNeXuS's answer.

The file size may not always be known, see:

File file = ...;
InputStream inputStream = new FileInputStream(file);

or

InputStream inputStream = getContext().getContentResolver().openInputStream(uri);

After getting the inputStream:

BufferedInputStream bis = new BufferedInputStream(inputStream);
ByteArrayOutputStream baos = new ByteArrayOutputStream();

byte buffer[] = new byte[1024];
int len;
while ((len = bis.read(buffer, 0, buffer.length)) > 0) {
    baos.write(buffer, 0, len);
}
bis.close();

byte[] imageData = baos.toByteArray();
baos.close();

Bitmap bitmap = BitmapFactory.decodeByteArray(imageData, 0, imageData.length);



回答4:


Android up to 4.4 fails to decode Movie from File and Stream in case of internal IOException in InputStream.reset() method. But decoding from bytes works well on all versions of Android. Here is quite minimal version of code to do this:

int size = (int) imageFile.length();
byte[] buffer = new byte[size];
FileInputStream inputStream = new FileInputStream(imageFile);
int readLength = inputStream.read(buffer);
inputStream.close();
Movie movie = Movie.decodeByteArray(buffer, 0, readLength);


来源:https://stackoverflow.com/questions/10240042/ioexception-cannot-load-file

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!