web-dev-qa-db-de.com

Übergeben von Android-Bitmap-Daten innerhalb von Aktivitäten mit der Absicht in Android

Ich habe eine Bitmap-Variable mit dem Namen bmp in Activity1, und ich möchte die Bitmap an Activity2 senden 

Nachfolgend ist der Code, den ich verwende, um ihn mit der Absicht zu übergeben.

Intent in1 = new Intent(this, Activity2.class);
in1.putExtra("image",bmp);
startActivity(in1);

In Activity2 versuche ich, mit dem folgenden Code auf die Bitmap zuzugreifen

Bundle ex = getIntent().getExtras();
Bitmap bmp2 = ex.getParceable("image");
ImageView result = (ImageView)findViewById(R.Id.imageView1);
result.setImageBitmap(bmp);

Die Anwendung wird ohne Ausnahme ausgeführt, liefert jedoch nicht das erwartete Ergebnis

57
adi.zean

Konvertieren Sie es in ein Byte-Array, bevor Sie es der Absicht hinzufügen, es versenden und dekodieren.

//Convert to byte array
ByteArrayOutputStream stream = new ByteArrayOutputStream();
bmp.compress(Bitmap.CompressFormat.PNG, 100, stream);
byte[] byteArray = stream.toByteArray();

Intent in1 = new Intent(this, Activity2.class);
in1.putExtra("image",byteArray);

Dann in Aktivität 2:

byte[] byteArray = getIntent().getByteArrayExtra("image");
Bitmap bmp = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.length);

bearbeiten

Ich dachte, ich sollte dies mit der besten Praxis aktualisieren:

In Ihrer ersten Aktivität sollten Sie die Bitmap auf der Festplatte speichern und dann in der nächsten Aktivität laden. Stellen Sie sicher, dass Sie Ihre Bitmap in der ersten Aktivität recyceln, um sie für die Garbage Collection zu verwenden:

Aktivität 1:

try {
    //Write file
    String filename = "bitmap.png";
    FileOutputStream stream = this.openFileOutput(filename, Context.MODE_PRIVATE);
    bmp.compress(Bitmap.CompressFormat.PNG, 100, stream);

    //Cleanup
    stream.close();
    bmp.recycle();

    //Pop intent
    Intent in1 = new Intent(this, Activity2.class);
    in1.putExtra("image", filename);
    startActivity(in1);
} catch (Exception e) {
    e.printStackTrace();
}

Laden Sie in Schritt 2 die Bitmap hoch:

Bitmap bmp = null;
String filename = getIntent().getStringExtra("image");
try {
    FileInputStream is = this.openFileInput(filename);
    bmp = BitmapFactory.decodeStream(is);
    is.close();
} catch (Exception e) {
    e.printStackTrace();
}

Prost!

168
Zaid Daghestani

Manchmal ist die Bitmap zu groß für das Kodieren und Dekodieren oder als Byte-Array in der Absicht. Dies kann entweder OOM oder eine schlechte Benutzeroberfläche verursachen.

Ich empfehle, die Bitmap in eine statische Variable der neuen Aktivität (die, in der sie verwendet wird) zu setzen, die sorgfältig null sein wird, wenn Sie sie nicht mehr benötigen (dh in onDestroy, aber nur, wenn "isChangingConfigurations" false zurückgibt).

5

Kotlin-Code zum Senden einer Bitmap an eine andere Aktivität aus Vorsatz:

1- in erste Aktivität:

          val i = Intent([email protected], Act2::class.Java)
           var bStream  =  ByteArrayOutputStream()
            bitmap.compress(Bitmap.CompressFormat.PNG, 50, bStream)
            val byteArray = bStream.toByteArray()
            i.putExtra("image", byteArray )
            startActivity(i)

2- In Aktivität zwei (Lesen Sie das Bitmap-Bild):

 var bitmap : Bitmap? =null
    if (intent.hasExtra("image")){
      //convert to bitmap          
        val byteArray = intent.getByteArrayExtra("image")
        bitmap = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.size)
    }

3-, wenn Sie es als Hintergrund für eine Ansicht festlegen möchten, wie ConstraintLayout oder ...:

 if (bitmap != null) {
     //Convert bitmap to BitmapDrawable
     var bitmapDrawable = BitmapDrawable( resources , bitmap)
      root_constraintLayout.backgroundDrawable = bitmapDrawable
   }
0
Hamed Jaliliani

Ich möchte auch eine Best Practices-Antwort für diejenigen posten, die dies tun möchten (aber möglicherweise die falsche Frage stellen).

Anstatt eine Bitmap herumzugeben (die Sie vermutlich aus dem Netzwerk heruntergeladen haben, andernfalls hätten Sie bereits einen Dateiverweis darauf), empfehle ich die Verwendung eines Image Loader wie Universal Image Loader , um ein Image in ein Bildansicht. Sie können es so konfigurieren, dass das Image anschließend auf die Festplatte zwischengespeichert wird:

 DisplayImageOptions defaultOptions = new DisplayImageOptions.Builder()
                .cacheInMemory(true)
                .cacheOnDisk(true)
                .considerExifParams(true)
                .bitmapConfig(Bitmap.Config.RGB_565)
                .build();
        ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(getApplicationContext())
                .defaultDisplayImageOptions(defaultOptions)
                .build();

        ImageLoader.getInstance().init(config);

Übergeben Sie nun einfach die Bild-URL in Ihrer Absicht und verwenden Sie die UIL, um das Bild zu laden. In Ihrer neu erstellten Aktivität wird das Bild beispielsweise sofort geladen, da es aus dem Cache geladen wird - auch wenn Ihre Bild-URL seit dem Herunterladen abgelaufen ist.

0
Micro

Wir können dieses Problem auch lösen, ohne dass Daten durch Vorsatz weitergegeben werden. Speichern Sie das Bild einfach in den Speicher und laden Sie das Bild in der nächsten Aktivität einfach von diesem Ort aus. Dies kann auch dazu führen, dass der App-Absturz keine großen Bitmap-Daten durchläuft. Hinweis: Sie müssen den Ortspfad nicht einmal an die Absicht übergeben den Pfad und benutze ihn.

0
murali krish

Wir können einfach nur Uri der Bitmap übergeben, anstatt ein Bitmap-Objekt zu übergeben. Wenn das Bitmap-Objekt "Big" ist, führt dies zu Speicherproblemen.

ErsteAktivität.

intent.putExtra("uri", Uri);

Von SecondActivity erhalten wir die Bitmap zurück.

Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(),Uri.parse(uri));
0
Vignesh Kumar