Передача растровых данных android в рамках действия с помощью Intent в Android


у меня есть растровая переменная с именем bmp в Activity1, и я хочу отправить растровое изображение в Activity2

Ниже приведен код, который я использую, чтобы пройти его с намерением.

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

и в Activity2 я пытаюсь получить доступ к растровому изображению, используя следующий код

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

приложение работает без исключения, но это не дает ожидаемого результата

6 53

6 ответов:

преобразовать его в массив байтов, прежде чем добавить его в намерение, отправить его и декодировать.

//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);

затем в упражнении 2:

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

edit

думал, что я должен обновить это с лучшей практикой:

в первом задании, вы должны сохранить растровое изображение на диск, а затем загрузить его в следующем действии. Убедитесь, что вы переработали свое растровое изображение в первом действии, чтобы запустить его для сборки мусора:

действие 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();
}

в упражнении 2 Загрузите растровое изображение:

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();
}

Ура!

иногда растровое изображение может быть слишком большим для кодирования и декодирования или передачи в виде массива байтов в intent. Это может вызвать либо OOM, либо плохой пользовательский интерфейс.

Я предлагаю рассмотреть вопрос о том, чтобы поместить растровое изображение в статическую переменную новой активности (ту, которая ее использует), которая будет тщательно нулевой, когда она вам больше не нужна (что означает в onDestroy, но только если "isChangingConfigurations" возвращает false).

мы также можем решить эту проблему без передачи данных через intent. Просто сохраните изображение в памяти и в следующем действии просто загрузите изображение из этого места, что также может избежать сбоя приложения от передачи больших растровых данных. Примечание: вам даже не нужно передавать путь местоположения к намерению, запоминать путь и использовать его.

Я хотел бы также опубликовать ответ на лучшие практики для тех, кто хочет это сделать (но может задавать неправильный вопрос).

вместо передачи растрового изображения (которое я предполагаю, что вы загрузили из сети, иначе у вас уже была бы ссылка на файл), я рекомендую использовать загрузчик изображений, такой как Универсальный Загрузчик Изображений загрузить изображение в ImageView. Вы можете настроить его, чтобы затем кэшировать образ на диск:

 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);

теперь, просто передайте URL-адрес изображения в своем намерении и используйте UIL для загрузки изображения. Например, в Вашем новом действии изображение будет загружаться мгновенно, потому что оно загружается из кэша - даже если Ваш URL-адрес изображения истек с момента загрузки.

просто мы можем пройти только Ури растрового изображения, вместо того чтобы передать растровое изображение объекта. Если растровый объект большой, это вызовет проблему с памятью.

FirstActivity.

intent.putExtra("uri", Uri);

из SecondActivity мы получаем обратно растровое изображение.

Bitmap bitmap = MediaStore.Images.Media.getBitmap(this.getContentResolver(),Uri.parse(uri));
Bundle b = new Bundle();
b.putSerializable("Image", Bitmap);
mIntent.putExtras(b);
startActivity(mIntent);