java - 如何在 Android 中为动态选择的图像创建 savedInstanceState?

标签 java android drawable android-savedstate

我创建了一个 android 应用程序。使用按钮从图库中选择图像并在 ImageView 中检索。图片获取成功。 现在我想保存所选图像的状态。我尝试修复。它使应用程序崩溃。当我更改水平方向时,应用程序崩溃了。请帮助我解决问题。

我的代码:

public class MainActivity extends ActionBarActivity {

ImageView imgBackground;
Button loadImgBtn;

String imgDecodableString;
Drawable drawable;

private static int RESULT_LOAD_IMG = 1;
private static final String IMAGE_DATA = "image_resource";


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    loadImgBtn = (Button)findViewById(R.id.btnSelectImage);
    imgBackground = (ImageView)findViewById(R.id.myImg);


    loadImgBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            /* Create intent to open Image Application like Gallery */
            Intent galleryIntent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
            /* start the Intent */
            startActivityForResult(galleryIntent,RESULT_LOAD_IMG);
        }
    });
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    try {
        if (requestCode == RESULT_LOAD_IMG && resultCode == RESULT_OK && null != data) {
            /* Get the Image from Data */
            Uri selectedImage = data.getData();
            String[] filePathColumn = { MediaStore.Images.Media.DATA };

            /* Get the Cursor */
            Cursor cursor = getContentResolver().query(selectedImage,filePathColumn,null,null,null);

            /* Move the first row */
            cursor.moveToFirst();

            int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
            imgDecodableString = cursor.getString(columnIndex);
            cursor.close();

            /* Rendering the Image */
            drawable =  new BitmapDrawable(imgDecodableString);
            imgBackground.setBackgroundDrawable(drawable);
        }
    } catch (Exception e) {
        message(getBaseContext()," Error : " + e.getMessage(),Toast.LENGTH_SHORT);
    }
}

public void message(Context ctx,String msg,int duration) {
    Toast.makeText(ctx,msg,duration).show();
}

@Override
protected void onSaveInstanceState(Bundle outState) {
     super.onSaveInstanceState(outState);
     outState.putParcelable(IMAGE_DATA, (android.os.Parcelable) drawable);
}

@Override
protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) {
    super.onRestoreInstanceState(savedInstanceState);
    drawable = (Drawable) savedInstanceState.getParcelable(IMAGE_DATA);
}
}

最佳答案

我没有测试过这个,所以我不知道它是否有效。希望是。

但是你应该知道这一点

...it might not be possible for you to completely restore your activity state with the Bundle that the system saves for you with the onSaveInstanceState() callback—it is not designed to carry large objects (such as bitmaps) and the data within it must be serialized then deserialized, which can consume a lot of memory and make the configuration change slow. In such a situation, you can alleviate the burden of reinitializing your activity by retaining a stateful Object when your activity is restarted due to a configuration change.

public class MainActivity extends ActionBarActivity {

        ImageView imgBackground;
        Button loadImgBtn;

        String imgDecodableString;
        BitmapDrawable drawable;

        private static int RESULT_LOAD_IMG = 1;
        private static final String IMAGE_DATA = "image_resource";


        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);

            loadImgBtn = (Button)findViewById(R.id.btnSelectImage);
            imgBackground = (ImageView)findViewById(R.id.myImg);


            loadImgBtn.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
            /* Create intent to open Image Application like Gallery */
                    Intent galleryIntent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
            /* start the Intent */
                    startActivityForResult(galleryIntent,RESULT_LOAD_IMG);
                }
            });

            if(savedInstanceState != null) {
                Bitmap tmp = savedInstanceState.getParcelable(IMAGE_DATA);
                if(tmp != null) {
                    drawable = new BitmapDrawable(getResources(), tmp);
                    imgBackground.setImageDrawable(drawable);
                }
            }
        }

        @Override
        protected void onActivityResult(int requestCode, int resultCode, Intent data) {
            super.onActivityResult(requestCode, resultCode, data);
            try {
                if (requestCode == RESULT_LOAD_IMG && resultCode == RESULT_OK && null != data) {
            /* Get the Image from Data */
                    Uri selectedImage = data.getData();
                    String[] filePathColumn = { MediaStore.Images.Media.DATA };

            /* Get the Cursor */
                    Cursor cursor = getContentResolver().query(selectedImage,filePathColumn,null,null,null);

            /* Move the first row */
                    cursor.moveToFirst();

                    int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
                    imgDecodableString = cursor.getString(columnIndex);
                    cursor.close();

            /* Rendering the Image */
                    drawable =  new BitmapDrawable(imgDecodableString);
                    imgBackground.setBackgroundDrawable(drawable);
                }
            } catch (Exception e) {
                message(getBaseContext()," Error : " + e.getMessage(), Toast.LENGTH_SHORT);
            }
        }

        public void message(Context ctx,String msg,int duration) {
            Toast.makeText(ctx,msg,duration).show();
        }

        @Override
        protected void onSaveInstanceState(Bundle outState) {
            super.onSaveInstanceState(outState);
            if(drawable != null && drawable.getBitmap() != null) {
                outState.putParcelable(IMAGE_DATA, drawable.getBitmap());
            }
        }

        @Override
        protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) {
            super.onRestoreInstanceState(savedInstanceState);
        }
    }

}

关于java - 如何在 Android 中为动态选择的图像创建 savedInstanceState?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29826979/

相关文章:

java - 在java中使用多个条件搜索书籍

java - 自定义自动对焦的算法或开源实现

java - 如何使用jsp在html中设置select的选定索引

java - 在服务器中更改样式后,Android 网页未更新

android - Android 中的自动化与仪器测试

android - 使用带有 MapView 的自定义绘图的奇怪绘图 Artifact

android - 带 NFC 的即时应用程序

android - 以编程方式更改 R.String 的值

android - 无法设置应用程序图标

android - 我怎样才能制作这种可绘制的形状,android?