Reputation: 31
I'm writing an application that needs to read two image files for various purposes.
One of the image files is received through an intent-filter, and I open it in this way (note: mIntent
is the result of getIntent()
):
mFileUri = (Uri) mIntent.getParcelableExtra(Intent.EXTRA_STREAM);
mInputStream = getContentResolver().openInputStream(mFileUri);
Then reading mInputStream works as expected.
The problem is reading the second image file: it's Uri
(converted using toString()
) is written in a shared preference, I get the value and use Uri.parse()
to restore it, as "default value" argument in the getString()
call I use the Uri
of a local resource located in the assets subdirectory (android.resource
scheme). The way I try to read it is the same, using getContentResolver().openInputStream()
, but something goes wrong: calling read()
on the returned InputStream
always return -1
. I've also tried getAssets().open()
, but it doesn't work, either with an android.resource
or a content
scheme Uri
.
Note: with the intent-received file I use read(byte[])
, while with the second one I use read()
.
So, here is my question: why does this happen and how can I solve this problem?
Upvotes: 2
Views: 337
Reputation: 24720
you can read assets using 'int read()' method, try:
AssetManager mgr = getAssets();
try {
InputStream is = mgr.open("test.txt");
Log.d(TAG, "onCreate 'is': " + is);
Log.d(TAG, "onCreate note 'is' is android.content.res.AssetManager$AssetInputStream");
int c;
while ((c = is.read()) != -1) {
Log.d(TAG, "onCreate " + (char) c);
}
} catch (IOException e) {
e.printStackTrace();
}
and the output (for a file assets/test.txt which contains bytes "qwertyuiop" is:
D/Test ( 872): onCreate 'is': android.content.res.AssetManager$AssetInputStream D/Test ( 872): onCreate note 'is' is android.content.res.AssetManager$AssetInputStream D/Test ( 872): onCreate q D/Test ( 872): onCreate w D/Test ( 872): onCreate e D/Test ( 872): onCreate r D/Test ( 872): onCreate t D/Test ( 872): onCreate y D/Test ( 872): onCreate u D/Test ( 872): onCreate i D/Test ( 872): onCreate o D/Test ( 872): onCreate p
but as you did not provide the Uri you are using to create your AssetInputStream i cannot reproduce your exact error.
Upvotes: 0
Reputation: 31
I was right: it is a bug in the AssetInputStream
implementation due to the lack of distinction between EOF and I/O errors in the native method _FileAsset::read(void *, size_t)
.
The result is that reading from AssetInputStream
is possible only by using read(byte[])
or read(byte[], int, int)
.
Upvotes: 1