Come ottenere un oggetto Bitmap da un Uri (se riesco a memorizzarlo in
/data/data/MYFOLDER/myimage.pngo file///data/data/MYFOLDER/myimage.png) per usarlo nella mia applicazione?
Qualcuno ha un'idea su come realizzare questo?
Come ottenere un oggetto Bitmap da un Uri (se riesco a memorizzarlo in
/data/data/MYFOLDER/myimage.pngo file///data/data/MYFOLDER/myimage.png) per usarlo nella mia applicazione?
Qualcuno ha un'idea su come realizzare questo?
Risposte:
. . IMPORTANTE: vedere la risposta da @Mark Ingram di seguito e @pjv per una soluzione migliore. . .
Puoi provare questo:
public Bitmap loadBitmap(String url)
{
Bitmap bm = null;
InputStream is = null;
BufferedInputStream bis = null;
try
{
URLConnection conn = new URL(url).openConnection();
conn.connect();
is = conn.getInputStream();
bis = new BufferedInputStream(is, 8192);
bm = BitmapFactory.decodeStream(bis);
}
catch (Exception e)
{
e.printStackTrace();
}
finally {
if (bis != null)
{
try
{
bis.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
if (is != null)
{
try
{
is.close();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
return bm;
}
Ma ricorda, questo metodo dovrebbe essere chiamato solo da un thread (non dalla GUI -thread). Ho un AsyncTask.
Ecco il modo corretto di farlo:
protected void onActivityResult(int requestCode, int resultCode, Intent data)
{
super.onActivityResult(requestCode, resultCode, data);
if (resultCode == RESULT_OK)
{
Uri imageUri = data.getData();
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), imageUri);
}
}
Se è necessario caricare immagini molto grandi, il codice seguente lo caricherà in riquadri (evitando allocazioni di memoria di grandi dimensioni):
BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(myStream, false);
Bitmap region = decoder.decodeRegion(new Rect(10, 10, 50, 50), null);
Vedi la risposta qui
Ecco il modo corretto di farlo, tenendo sotto controllo anche l'utilizzo della memoria:
protected void onActivityResult(int requestCode, int resultCode, Intent data)
{
super.onActivityResult(requestCode, resultCode, data);
if (resultCode == RESULT_OK)
{
Uri imageUri = data.getData();
Bitmap bitmap = getThumbnail(imageUri);
}
}
public static Bitmap getThumbnail(Uri uri) throws FileNotFoundException, IOException{
InputStream input = this.getContentResolver().openInputStream(uri);
BitmapFactory.Options onlyBoundsOptions = new BitmapFactory.Options();
onlyBoundsOptions.inJustDecodeBounds = true;
onlyBoundsOptions.inDither=true;//optional
onlyBoundsOptions.inPreferredConfig=Bitmap.Config.ARGB_8888;//optional
BitmapFactory.decodeStream(input, null, onlyBoundsOptions);
input.close();
if ((onlyBoundsOptions.outWidth == -1) || (onlyBoundsOptions.outHeight == -1)) {
return null;
}
int originalSize = (onlyBoundsOptions.outHeight > onlyBoundsOptions.outWidth) ? onlyBoundsOptions.outHeight : onlyBoundsOptions.outWidth;
double ratio = (originalSize > THUMBNAIL_SIZE) ? (originalSize / THUMBNAIL_SIZE) : 1.0;
BitmapFactory.Options bitmapOptions = new BitmapFactory.Options();
bitmapOptions.inSampleSize = getPowerOfTwoForSampleRatio(ratio);
bitmapOptions.inDither = true; //optional
bitmapOptions.inPreferredConfig=Bitmap.Config.ARGB_8888;//
input = this.getContentResolver().openInputStream(uri);
Bitmap bitmap = BitmapFactory.decodeStream(input, null, bitmapOptions);
input.close();
return bitmap;
}
private static int getPowerOfTwoForSampleRatio(double ratio){
int k = Integer.highestOneBit((int)Math.floor(ratio));
if(k==0) return 1;
else return k;
}
La chiamata getBitmap () dal post di Mark Ingram chiama anche decodeStream (), quindi non perdi alcuna funzionalità.
Riferimenti:
getPowerOfTwoForSampleRatio()può essere ignorata. Vedi: developer.android.com/reference/android/graphics/…
try
{
Bitmap bitmap = MediaStore.Images.Media.getBitmap(c.getContentResolver() , Uri.parse(paths));
}
catch (Exception e)
{
//handle exception
}
e sì, il percorso deve essere in un formato simile a questo
file:///mnt/sdcard/filename.jpg
Questa è la soluzione più semplice:
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), uri);
private void uriToBitmap(Uri selectedFileUri) {
try {
ParcelFileDescriptor parcelFileDescriptor =
getContentResolver().openFileDescriptor(selectedFileUri, "r");
FileDescriptor fileDescriptor = parcelFileDescriptor.getFileDescriptor();
Bitmap image = BitmapFactory.decodeFileDescriptor(fileDescriptor);
parcelFileDescriptor.close();
} catch (IOException e) {
e.printStackTrace();
}
}
Bitmap bitmap = MediaStore.Images.Media.getBitmap(context.getContentResolver(), uri);
Sembra che sia MediaStore.Images.Media.getBitmapstato deprecato in API 29. Il modo consigliato è usare quello ImageDecoder.createSourceche è stato aggiunto API 28.
Ecco come sarebbe ottenere la bitmap:
val bitmap = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
ImageDecoder.decodeBitmap(ImageDecoder.createSource(requireContext().contentResolver, imageUri))
} else {
MediaStore.Images.Media.getBitmap(requireContext().contentResolver, imageUri)
}
Puoi recuperare bitmap da uri in questo modo
Bitmap bitmap = null;
try {
bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), imageUri);
} catch (IOException e) {
e.printStackTrace();
}
Uri imgUri = data.getData();
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), imgUri);
Utilizzare il metodo startActivityForResult come di seguito
startActivityForResult(new Intent(Intent.ACTION_PICK).setType("image/*"), PICK_IMAGE);
E puoi ottenere risultati in questo modo:
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode != RESULT_OK) {
return;
}
switch (requestCode) {
case PICK_IMAGE:
Uri imageUri = data.getData();
try {
Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(), imageUri);
} catch (IOException e) {
e.printStackTrace();
}
break;
}
}
Ho provato molti modi. questo lavoro per me perfettamente.
Se scegli pictrue dalla Galleria. Devi essere informato di ottenere Urida intent.clipdatao intent.data, perché uno di essi potrebbe essere nullo in una versione diversa.
private fun onChoosePicture(data: Intent?):Bitmap {
data?.let {
var fileUri:Uri? = null
data.clipData?.let {clip->
if(clip.itemCount>0){
fileUri = clip.getItemAt(0).uri
}
}
it.data?.let {uri->
fileUri = uri
}
return MediaStore.Images.Media.getBitmap(this.contentResolver, fileUri )
}
puoi fare questa struttura:
protected void onActivityResult(int requestCode, int resultCode, Intent imageReturnedIntent) {
super.onActivityResult(requestCode, resultCode, imageReturnedIntent);
switch(requestCode) {
case 0:
if(resultCode == RESULT_OK){
Uri selectedImage = imageReturnedIntent.getData();
Bundle extras = imageReturnedIntent.getExtras();
bitmap = extras.getParcelable("data");
}
break;
}
con questo puoi facilmente convertire un uri in bitmap. spero ti aiuti.
InputStream imageStream = null;
try {
imageStream = getContext().getContentResolver().openInputStream(uri);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
final Bitmap selectedImage = BitmapFactory.decodeStream(imageStream);
(KOTLIN) Quindi, dal 7 aprile 2020 nessuna delle opzioni sopra menzionate ha funzionato, ma ecco cosa ha funzionato per me:
Se si desidera archiviare la bitmap in un val e impostare un'immagine con essa, utilizzare questo:
val bitmap = BitmapFactory.decodeFile(currentPhotoPath).also { bitmap -> imageView.setImageBitmap(bitmap) }
Se vuoi solo impostare bitmap e imageView, usa questo:
BitmapFactory.decodeFile(currentPhotoPath).also { bitmap -> imageView.setImageBitmap(bitmap) }
Metodo completo per ottenere immagini uri dalla galleria mobile.
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == PICK_IMAGE_REQUEST && resultCode == RESULT_OK && data != null && data.getData() != null) {
Uri filePath = data.getData();
try { //Getting the Bitmap from Gallery
Bitmap bitmap = MediaStore.Images.Media.getBitmap(getContentResolver(), filePath);
rbitmap = getResizedBitmap(bitmap, 250);//Setting the Bitmap to ImageView
serImage = getStringImage(rbitmap);
imageViewUserImage.setImageBitmap(rbitmap);
} catch (IOException e) {
e.printStackTrace();
}
}
}