2010-02-03 4 views
20

Ich habe eine sehr einfache Anwendung mit einem ImageView und einem Button. Die erste Drawable-Ressource, die von meinem ImageView geladen wird, wird im XML-Layout mit dem Tag "android: src" angegeben. Zur Laufzeit möchte ich jedoch das von ihm angezeigte Bild ändern. Um dies zu tun, starte ich eine Aktivität für das Ergebnis, um ein Bild von der SD-Karte auszuwählen (Absicht, die an MediaStore.Images.Media.EXTERNAL_CONTENT_URI gesendet wurde). Jedoch, wenn das Bild ausgewählt ist, ich versuche, die Image mit dem ausgewählten Bild URI zu aktualisieren, aber ich bekomme die Meldung „java.lang.OutOfMemoryError: Bitmap-Größe überschreitet VM BudgetDas Ändern von ImageView-Inhalt verursacht OutOfMemoryError

Ich bin versucht, Bilder zu laden genommen mit der Kamera (Bildgröße sind etwa 1.1M) meines HTC-Hero aber kein Erfolg, scheint nur mit Bildern zu arbeiten, die weniger als 500KB sind. Jedoch muss ich Bilder laden, die mit der Kamera genommen werden. Wie kann ich das lösen? was mache ich falsch. Scheint mir, dass der Code sehr einfach ist und funktionieren sollte.

public void onClick(View v){ 
Intent selectImageIntent=new Intent(Intent.ACTION_PICK , 
    android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI); 
    startActivityForResult(selectImageIntent,1); 
} 

@Override 
protected void onActivityResult(int requestCode, int resultCode, Intent data){ 
super.onActivityResult(requestCode, resultCode, data); 
if(resultCode==Activity.RESULT_OK){ 
    Uri selectedImageUri = data.getData(); 
    Log.i(TAG,"chosen image: "+selectedImageUri.toString()); 
    ImageView imageView = (ImageView) this.findViewById(R.id.ImageView01); 
    imageView.setImageURI(selectedImageUri);//here I get the OutOfMemoryError 
    imageView.invalidate(); 

}else{ 
    //canceled 
} 

} 

P. S. das ist das einzige, was die App tun sollte, ich erschaffe keine anderen Objekte, daher möchte ich darauf hinweisen, dass ich neben dem Anzeigen des Bildes keinen Heap-Platz für andere Dinge verwende.

Antwort

43

Scheint wie vor dem Laden einer neuen Bitmap musste ich die Bitmap, die von der ImageView angezeigt wird, recyceln, jetzt funktioniert es ohne ein Problem. Hoffen Sie, dass dies jemand anderem hilft, rufen Sie einfach die folgende Methode auf, bevor Sie den Inhalt des neuen ImageViews festlegen.

((BitmapDrawable)imageView.getDrawable()).getBitmap().recycle();

so sieht der Code nun wie folgt aus:

@Override 
protected void onActivityResult(int requestCode, int resultCode, Intent data){ 
    super.onActivityResult(requestCode, resultCode, data); 
    switch(requestCode){ 
     case INTENT_REQUEST_SELECT_IMAGE: 
      if(resultCode==Activity.RESULT_OK){ 
       Uri selectedImageUri = data.getData(); 
       Log.i(TAG,"selectedImageUri.getPath()"+selectedImageUri.getPath()); 
       ImageView imageView = (ImageView) this.findViewById(R.id.ImageView_of_text); 
       ((BitmapDrawable)imageView.getDrawable()).getBitmap().recycle(); 
       imageView.setImageURI(selectedImageUri); 
       imageView.invalidate(); 

      }else{ 
       //TODO define what to do in case the user canceled OCR or any other event 
      } 
      break; 
     default: 
      break; 
    } 
} 

den Anruf Bitte beachten Sie auf der Bitmap des Image zu recyceln.

2

Das Problem wurde jetzt gelöst. anstatt nur eine Zeile:

((BitmapDrawable)imageView.getDrawable()).getBitmap().recycle(); 

diesen Code hinzufügen, bevor Image Inhalt Aktualisierung:

Drawable toRecycle= gallerypic.getDrawable(); 
if (toRecycle != null) { 
    ((BitmapDrawable)gallerypic.getDrawable()).getBitmap().recycle(); 
} 
gallerypic.setImageURI(selectedimage); 
6

Diese mich Nüsse fuhr.

Ich baue für ein Xoom mit sehr großen, hochauflösenden Vollbild-Bildern (800x1232).

Der folgende Code für mich gearbeitet:

public void onStop() 
{ 
    super.onStop(); 
    imageView.setImageBitmap(null); 
} 

Viel Glück !!!

+0

Diese Methode speichert Sie, wenn Sie einen FragmentStatePagerAdapter mit ImageViews verwenden, da das Zurückschreiben der Bitmap zu einem Fehler beim erneuten Aufblasen der Ansicht führt. –

1

Verwenden Sie dies nur vor dem Aktualisieren imageview: imageView1.setImageURI (null);

1

Ich habe jede Lösung dieses Beitrags und viele mehr, aber niemand gearbeitet. Schließlich habe ich android:largeHeap="true" in Manifest verwendet und das löst mein Problem.

Ich hoffe, das hilft jemandem.