como obter um uri de um recurso de imagem no android

96

Preciso abrir um intent para visualizar uma imagem da seguinte maneira:

Intent intent = new Intent(Intent.ACTION_VIEW);
Uri uri = Uri.parse("@drawable/sample_1.jpg");
intent.setData(uri);
startActivity(intent);

O problema é que isso Uri uri = Uri.parse("@drawable/sample_1.jpg");está incorreto.

user602874
fonte

Respostas:

138

O formato é:

"android.resource://[package]/[res id]"

[pacote] é o nome do seu pacote

[res id] é o valor do ID do recurso, por exemplo, R.drawable.sample_1

para costurá-lo, use

Uri path = Uri.parse("android.resource://your.package.name/" + R.drawable.sample_1);

Axarydax
fonte
3
Caminho do Uri = Uri.parse ("android.resource: //net.londatiga.android.twitpic/" + R.drawable.icon); String mpath = path.toString (); Não recebo esse arquivo ou erro de diretório quando estou fazendo isso
hemanth kumar
4
quando tento enviar a imagem como anexo de e-mail, ele está enviando o arquivo, mas sem a extensão .jpg. Portanto, a imagem não é válida no pc dos destinatários.
ruben
@hemanthkumar Veja esta resposta como referência: stackoverflow.com/a/8476930/62921 Ele explicou que não há pasta drawable exceto em sua máquina. É por isso que ele usa IDs e seu path.toString () não funciona.
ForceMagic
Isso não funciona para mim. Recebo ActivityNotFoundException. (android.content.ActivityNotFoundException: Nenhuma atividade encontrada para manipular o Intent {act = android.intent.action.VIEW dat = android.resource: //com.mypackage.myapp/2130837582}. LG E400 Android 2.3.6.
Lucio Crusca
@LucioCrusca - talvez você deva especificar o tipo de intenção - é uma imagem jpeg ou png?
Axarydax
65

Aqui está uma solução limpa que aproveita totalmente a android.net.Uriclasse por meio de seu Builderpadrão, evitando composição e decomposição repetidas da string URI, sem depender de strings codificadas ou ideias ad hoc sobre a sintaxe URI.

Resources resources = context.getResources();
Uri uri = new Uri.Builder()
    .scheme(ContentResolver.SCHEME_ANDROID_RESOURCE)
    .authority(resources.getResourcePackageName(resourceId))
    .appendPath(resources.getResourceTypeName(resourceId))
    .appendPath(resources.getResourceEntryName(resourceId))
    .build();
Uli
fonte
isso resolveu meu problema. Minha forma de uri era como "android.resource: //com.craiovadata.guessthecountry/drawable/sky"
Dan Alboteanu,
56
public static Uri resourceToUri(Context context, int resID) {
        return Uri.parse(ContentResolver.SCHEME_ANDROID_RESOURCE + "://" +
                context.getResources().getResourcePackageName(resID) + '/' +
                context.getResources().getResourceTypeName(resID) + '/' +
                context.getResources().getResourceEntryName(resID) );
    }
xnagyg
fonte
9

Para aqueles com erro, você pode estar inserindo o nome do pacote errado. Basta usar este método.

public static Uri resIdToUri(Context context, int resId) {
    return Uri.parse(Consts.ANDROID_RESOURCE + context.getPackageName()
                     + Consts.FORESLASH + resId);
}

Onde

public static final String ANDROID_RESOURCE = "android.resource://";
public static final String FORESLASH = "/";
sandalone
fonte
10
você realmente fez uma constante para um foreslash ??
Sartheris Stormhammer
@SartherisStormhammer Sim :), embora eu geralmente use a constante do sistema para a barra anterior;)
sandalone
4

Você quer o URI do recurso de imagem e R.drawable.goombé um recurso de imagem. A função Builder cria o URI que você está pedindo:

String resourceScheme = "res";
Uri uri = new Uri.Builder()
  .scheme(resourceScheme)
  .path(String.valueOf(intResourceId))
  .build();
Roide
fonte
Então você está passando algo como "18" para o caminho. Isso parece incorreto
Nick Cardoso
@NickCardoso R.drawable.goomba é o drawable que tenho em minha pasta de recursos. Se seu valor for 18, isso torna a atribuição incorreta?
roide
Claro que sim. developer.android.com/reference/android/net/… O ID no arquivo R precisa ser usado para resolver um caminho real.
Nick Cardoso
@NickCardoso obrigado, mas não funciona e funciona perfeitamente. O Scheme cuida desse caminho conforme a documentação que você apontou sugere.
roide de
3

Com base nas respostas acima, quero compartilhar um exemplo kotlin sobre como obter um Uri válido para qualquer recurso em seu projeto. Eu acho que é a melhor solução porque você não tem que digitar nenhuma string em seu código e correr o risco de digitá-lo incorretamente.

    val resourceId = R.raw.scannerbeep // r.mipmap.yourmipmap; R.drawable.yourdrawable
    val uriBeepSound = Uri.Builder()
        .scheme(ContentResolver.SCHEME_ANDROID_RESOURCE)
        .authority(resources.getResourcePackageName(resourceId))
        .appendPath(resources.getResourceTypeName(resourceId))
        .appendPath(resources.getResourceEntryName(resourceId))
        .build()
Sergio
fonte