2

I have some images stored in getExternalFilesDir() and i am trying to show those images in the android gallery (cooliris). Right now i have been doing this:

Intent intent = new Intent();
intent.setAction(android.content.Intent.ACTION_VIEW);
intent.setDataAndType(Uri.fromFile(imgPath,"image/*");
startActivity(intent);

But nothing happens. I have changed the setDataAndType to this:

intent.setDataAndType(Uri.fromFile(new File(imgPath)),"image/*");

This way it works, but it takes 5-10 seconds for the gallery to go from a black screen to showing my image.

Anyway to solve this or any better approach?

Filipe Batista
  • 1,862
  • 2
  • 24
  • 39

1 Answers1

1

By implementing a file content provider you will be able to avoid this 5-10 second delay

import java.io.File;
import java.io.FileNotFoundException;

import android.content.ContentProvider;
import android.content.ContentValues;
import android.database.Cursor;
import android.net.Uri;
import android.os.ParcelFileDescriptor;

public class FileContentProvider extends ContentProvider {
    private static final String AUTHORITY = "content://com.yourprojectinfo.fileprovider";

    public static Uri constructUri(String url) {
        Uri uri = Uri.parse(url);
        return uri.isAbsolute() ? uri : Uri.parse(AUTHORITY + url);
    }

    public static Uri constructUri(File file) {
        Uri uri = Uri.parse(file.getAbsolutePath());
        return uri.isAbsolute() ? uri : Uri.parse(AUTHORITY
                + file.getAbsolutePath());
    }

    @Override
    public ParcelFileDescriptor openFile(Uri uri, String mode)
            throws FileNotFoundException {
        File file = new File(uri.getPath());
        ParcelFileDescriptor parcel = ParcelFileDescriptor.open(file,
                ParcelFileDescriptor.MODE_READ_ONLY);
        return parcel;
    }

    @Override
    public boolean onCreate() {
        return true;
    }

    @Override
    public int delete(Uri uri, String s, String[] as) {
        throw new UnsupportedOperationException(
                "Not supported by this provider");
    }

    @Override
    public String getType(Uri uri) {
        return "image/jpeg";
    }

    @Override
    public Uri insert(Uri uri, ContentValues contentvalues) {
        throw new UnsupportedOperationException(
                "Not supported by this provider");
    }

    @Override
    public Cursor query(Uri uri, String[] as, String s, String[] as1, String s1) {
        throw new UnsupportedOperationException(
                "Not supported by this provider");
    }

    @Override
    public int update(Uri uri, ContentValues contentvalues, String s,
            String[] as) {
        throw new UnsupportedOperationException(
                "Not supported by this provider");
    }

}

Then you can call

Uri uri = FileContentProvider.constructUri(file);
Intent intent = new Intent();
intent.setAction(android.content.Intent.ACTION_VIEW);
intent.setDataAndType(uri,"image/*");
startActivity(intent);

This is a strange workaround but I think it has something to do with how android opens images using a URI. Their openFile(Uri uri, String mode) method is wrong / broken / can't resolve the URI properly.. I'm not really 100% sure though but I found this workaround to be effective.

don't forget to register to provider in the manifest

dymmeh
  • 22,247
  • 5
  • 53
  • 60
  • It's no working... I get the following error: `java.lang.UnsupportedOperationException: Not supported by this provider` 05-22 18:53:26.959: E/DatabaseUtils(26789): at com.mypackage.provider.FileContentProvider.query(FileContentProvider.java:58) – Filipe Batista May 22 '12 at 17:44
  • Well, something is querying on that URI which is wrong. Nothing should ever query that URI. Does it say what is calling query on it? – dymmeh May 22 '12 at 17:52
  • At the begging of the error says: `05-22 19:04:57.259: E/DatabaseUtils(26789): Writing exception to parcel` "Does it say what is calling query on it?" how can i see that? – Filipe Batista May 22 '12 at 17:56
  • Where it said "UnsupportedOperationException" there should be a bunch of lines underneath that showing the call stack (the methods that were called leading up to the error) – dymmeh May 22 '12 at 17:59
  • `at android.content.ContentProvider$Transport.bulkQuery(ContentProvider.java:174)` `at android.content.ContentProviderNative.onTransact(ContentProviderNative.java:111)` `at android.os.Binder.execTransact(Binder.java:320)` `at dalvik.system.NativeStart.run(Native Method) ` – Filipe Batista May 22 '12 at 18:04
  • Does your application call query on the image URI at all? I find it odd that anything is trying to query it. The gallery should just try to call openInputStream(Uri uri) which will then call openFile(Uri uri, String mode) within the content provider as I posted above. – dymmeh May 22 '12 at 18:09
  • i don't know why but `query` is being call before `openFile` – Filipe Batista May 22 '12 at 18:13