Передача растрового изображения между двумя действиями
Я разрабатываю приложение для рисования, в котором я хочу передать образ растрового изображения из одной активности в другую, но проект не отвечает. Я преобразовал относительный макет скриншота в растровое изображение и передал его через Intent, но проблема не решена. Вот мой код....
DrawingActivity
package com.newdrawing;
public class DrawingActivity extends Activity {
private Bitmap mBitmap;
private Canvas mCanvas;
private Path mPath;
private Paint mBitmapPaint;
private Paint mPaint;
MyDrawView myDrawView;
RelativeLayout parent;
Bitmap bitmap;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_drawing);
parent = (RelativeLayout) findViewById(R.id.singleparent);
myDrawView = new MyDrawView(this);
parent.addView(myDrawView);
Activity context;
//RelativeLayout item = (RelativeLayout)findViewById(R.id.item);
View child = getLayoutInflater().inflate(R.layout.trans, null);
parent.addView(child);
}
public void color(View v) {
switch (v.getId()) {
case R.id.button3:
parent.setBackgroundColor(Color.RED);
break;
case R.id.button4:
parent.setBackgroundColor(Color.GREEN);
break;
case R.id.button5:
parent.setBackgroundColor(Color.BLUE);
break;
}
}
public void save(View v) {
parent.setDrawingCacheEnabled(true);
bitmap=parent.getDrawingCache();
parent.setDrawingCacheEnabled(false);
Log.e("Bitmap",String.valueOf(bitmap));
// send();
//Canvas c = new Canvas(bitmap);
//.draw(c);
// File outputFile; // Where to save it
//FileOutputStream out = new FileOutputStream(imageFile);
// boolean success = bitmap.compress(CompressFormat.PNG, 100, out);
// out.close();
Intent i = new Intent(this, ImageActivity.class);
ByteArrayOutputStream bs = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.PNG, 50, bs);
byte[] byteArray = bs.toByteArray();
i.putExtra("byteArray", byteArray);
startActivity(i);
}
private void send()
{
Intent i9=new Intent(DrawingActivity.this,ImageActivity.class);
i9.putExtra("Image",bitmap);
startActivity(i9);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.activity_drawing, menu);
return true;
}
public class MyDrawView extends View {
public MyDrawView(Context c) {
super(c);
mPath = new Path();
mBitmapPaint = new Paint(Paint.DITHER_FLAG);
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
mPaint.setColor(0xFF000000);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(3);
}
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
mBitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
mCanvas = new Canvas(mBitmap);
}
@Override
protected void onDraw(Canvas canvas) {
canvas.drawBitmap(mBitmap, 0, 0, mBitmapPaint);
canvas.drawColor(Color.TRANSPARENT);
canvas.drawPath(mPath, mPaint);
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 4;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX)/2, (y + mY)/2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath.reset();
}
@Override
public boolean onTouchEvent(MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
public void clear(){
mBitmap.eraseColor(Color.TRANSPARENT);
invalidate();
System.gc();
}
}
}
ImageActivity
package com.newdrawing;
public class ImageActivity extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_image);
Intent i = getIntent();
ImageView img=(ImageView)findViewById(R.id.image11);
/*
if(getIntent().hasExtra("byteArray"))
{
Bitmap b = BitmapFactory.decodeByteArray(
getIntent().getByteArrayExtra("byteArray"),0,getIntent().getByteArrayExtra("byteArray").length);
img.setImageBitmap(b);
Log.e("Bitmap",String.valueOf(b));
}*/
Bundle extras = getIntent().getExtras();
byte[] byteArray = extras.getByteArray("byteArray");
Bitmap bmp = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.length);
img.setImageBitmap(bmp);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.activity_image, menu);
return true;
}
}
Отчет Locat
10-16 10:39:22.653: E/AndroidRuntime(339): FATAL EXCEPTION: main
10-16 10:39:22.653: E/AndroidRuntime(339): java.lang.IllegalStateException: Could not execute method of the activity
10-16 10:39:22.653: E/AndroidRuntime(339): at android.view.View$1.onClick(View.java:2072)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.view.View.performClick(View.java:2408)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.view.View$PerformClick.run(View.java:8816)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.os.Handler.handleCallback(Handler.java:587)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.os.Handler.dispatchMessage(Handler.java:92)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.os.Looper.loop(Looper.java:123)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.app.ActivityThread.main(ActivityThread.java:4627)
10-16 10:39:22.653: E/AndroidRuntime(339): at java.lang.reflect.Method.invokeNative(Native Method)
10-16 10:39:22.653: E/AndroidRuntime(339): at java.lang.reflect.Method.invoke(Method.java:521)
10-16 10:39:22.653: E/AndroidRuntime(339): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868)
10-16 10:39:22.653: E/AndroidRuntime(339): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626)
10-16 10:39:22.653: E/AndroidRuntime(339): at dalvik.system.NativeStart.main(Native Method)
10-16 10:39:22.653: E/AndroidRuntime(339): Caused by: java.lang.reflect.InvocationTargetException
10-16 10:39:22.653: E/AndroidRuntime(339): at com.newdrawing.DrawingActivity.save(DrawingActivity.java:91)
10-16 10:39:22.653: E/AndroidRuntime(339): at java.lang.reflect.Method.invokeNative(Native Method)
10-16 10:39:22.653: E/AndroidRuntime(339): at java.lang.reflect.Method.invoke(Method.java:521)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.view.View$1.onClick(View.java:2067)
10-16 10:39:22.653: E/AndroidRuntime(339): ... 11 more
10-16 10:39:22.653: E/AndroidRuntime(339): Caused by: java.lang.IllegalStateException: Can't compress a recycled bitmap
10-16 10:39:22.653: E/AndroidRuntime(339): at android.graphics.Bitmap.checkRecycled(Bitmap.java:180)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.graphics.Bitmap.compress(Bitmap.java:572)
10-16 10:39:22.653: E/AndroidRuntime(339): ... 15 more
Ответы
Ответ 1
Вы можете просто попробовать ниже -
Intent i = new Intent(this, Second.class)
i.putExtra("Image", bitmap);
startActivity(i)
И, в Second.class
Bitmap bitmap = (Bitmap) intent.getParcelableExtra("Image");
Посмотрите здесь Если вы хотите сжать свой Bitmap
перед отправкой в следующую активность, просто посмотрите ниже -
Intent i = new Intent(this, NextActivity.class);
Bitmap b; // your bitmap
ByteArrayOutputStream bs = new ByteArrayOutputStream();
b.compress(Bitmap.CompressFormat.PNG, 50, bs);
i.putExtra("byteArray", bs.toByteArray());
startActivity(i);
в вашей следующей активности -
if(getIntent().hasExtra("byteArray")) {
ImageView previewThumbnail = new ImageView(this);
Bitmap b = BitmapFactory.decodeByteArray(
getIntent().getByteArrayExtra("byteArray"),0,getIntent()
.getByteArrayExtra("byteArray").length);
previewThumbnail.setImageBitmap(b);
}
Ответ 2
Я ответил на аналогичный вопрос в этом SO post. Мое решение сохранит изображение во внутренней памяти устройства, недоступное другим приложениям (на неработающих телефонах). Затем мы можем просто декодировать файл и показать его в imageview. Он предотвращает исключение TranscationTooLarge, поскольку вы не можете превышать предел 1mb проходящего пакета.
Ответ 3
Существует множество способов:
1)
Bitmap реализует Parcelable, поэтому вы всегда можете передать его в намерении:
Intent intent = new Intent(this, NewActivity.class);
intent.putExtra("BitmapImage", bitmap);
и извлеките его на другом конце:
Intent intent = getIntent();
Bitmap bitmap = (Bitmap) intent.getParcelableExtra("BitmapImage");
2)
Преобразуйте его в массив байтов, прежде чем добавлять его в намерение, отправлять и декодировать.
//Преобразование в байтовый массив
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);
Ответ 4
Я думаю, что для большинства случаев вполне нормально помещать растровое изображение на статическую ссылку, которая должна быть нулевой, если операция приема больше не нужна.
Таким образом, он очень быстро и не нуждается в преобразовании или кодировании и декодировании. Это также не оставляет следов.
Ответ 5
Если ваши изображения являются статическими и в папке с возможностью переноса и т.д. Поэтому отправьте растровое изображение с намерения на следующую операцию очень дорого (для машины:)). Итак, лучший способ - сначала создать string-array
в strings.xml
, как здесь.
<resources>
<string name="app_name">Gallery App</string>
<string-array name="images">
<item>@drawable/img1</item>
<item>@drawable/img2</item>
<item>@drawable/img3</item>
<item>@drawable/img4</item>
<item>@drawable/img5</item>
<item>@drawable/img6</item>
</string-array>
</resources>
Затем в вашей деятельности, чтобы получить список изображений, связанных с images
, этот массив, объявленный выше.
1: -Установите экземпляр TypeArray typeArray
2: -Assign typeArray = getResources().obtainTypedArray(R.array.images);
3: -Создайте свой список и добавьте каждый элемент по одному →
ArrayList list = new ArrayList();
for (int i = 0 ;i< typedArray.length() ; i++){
Bitmap bitmap = BitmapFactory.decodeResource(getResources(),typedArray.getResourceId(i ,-1));
list.add(bitmap);
}
4: - Конечно, теперь вы установите этот список в своем ArrayAdapter
view.setAdapter(new ArrayAdapter(this , R.layout.viewImages , list));
5: -Отправить кликированное битовое изображение для следующего действия
view.setOnItemClickedListener(new AdapterView.OnItemClickedListener(){
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Intent i = new Intent(MainActivity.this , DetailedImageActivity.class);
int imageId = typedArray.getResourceId(position , -1);
i.putExtra("imageId",imageId) ;
Log.i("ResourceId ","here");
startActivity(i);
}
});
6: -Повторить идентификатор растрового изображения и получить растровое изображение
public class DetailedImageActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_detailed_image);
ImageView imageView = (ImageView) findViewById(R.id.detailImageView);
String title = getIntent().getStringExtra("title");
int imageId = getIntent().getExtras().getInt("imageId") ;
Bitmap image = BitmapFactory.decodeResource(getResources() ,imageId);
imageView.setImageBitmap(image);
}
}
Ответ 6
Вы можете использовать пакет для передачи растрового изображения из одной активности в другую
Добавьте свое изображение в массив байтов:
ArrayList<byte[]> image=new ArrayList<byte[]>();
Bundle b = new Bundle();
Intent it=new Intent(getBaseContext(),your.class);
b.putByteArray("image", image.get(position));
it.putExtras(b);
startActivity(it);
И получите свое изображение для создания активности приемника из пакета
Ответ 7
В вашем логарифмическом состоянии он указывает
10-16 10:39:22.653: E/AndroidRuntime(339): Caused by: java.lang.IllegalStateException: Can't compress a recycled bitmap
10-16 10:39:22.653: E/AndroidRuntime(339): at android.graphics.Bitmap.checkRecycled(Bitmap.java:180)
10-16 10:39:22.653: E/AndroidRuntime(339): at android.graphics.Bitmap.compress(Bitmap.java:572)
Ваше растровое изображение было переработано до его передачи в ImageActivity. Вы можете сделать битмап статическим, чтобы он не перерабатывался.
Ответ 8
Я ищу его так много и, наконец, найду ответ в https://eazyprogramming.blogspot.com/2013/01/passing-image-between-activities.html#comment-form
в первом мероприятии
Intent intent=new Intent(FirstClass.this, SecondClass.class);
Bundle bundle=new Bundle();
bundle.putInt("image",R.drawable.ic_launcher);
intent.putExtras(bundle);
startActivity(intent);
в Second Acticity:
Bundle bundle=this.getIntent().getExtras();
int pic=bundle.getInt("image");
v.setImageResource(pic);
другой метод:
в первой операции:
Bundle extras = getIntent().getExtras();
byte[] b = extras.getByteArray("picture");
Bitmap bmp = BitmapFactory.decodeByteArray(b, 0, b.length);
ImageView image = (ImageView) findViewById(R.id.imageView1);
image.setImageBitmap(bmp);
в Second Acticity:
Bundle extras = getIntent().getExtras();byte[] b = extras.getByteArray("picture");Bitmap bmp = BitmapFactory.decodeByteArray(b, 0, b.length);ImageView image = (ImageView) findViewById(R.id.imageView1);