android原生拍照适配问题

    xiaoxiao2026-05-21  5

    拍照问题

    司项目里面需要拍照的地方很多,因为每次选取一张单张上传,所以并没有使用很多已经写好的第三方,反而选取了android原生的拍照和相册选择。 最先遇见的问题就是适配,找网上的帖子很多都有原生的拍照,但是在三星、华为、小米上面并不能完全适配,特别是华为和三星。花了我一段时间 终于找到一个靠谱点的方法,记录下来。 先贴代码吧。 public class MainActivity extends AppCompatActivity { private Button button; private static final int TAKE_PHOTO=1234; private static final int LOOK_PHOTO=4321; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); button = ((Button) findViewById(R.id.button)); button.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //弹出选择提示框 AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this); builder.setTitle("选择图片"); builder.setPositiveButton("相册", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.dismiss(); Intent intent = new Intent(Intent.ACTION_PICK); intent.setDataAndType(MediaStore.Images.Media.EXTERNAL_CONTENT_URI,"image/*"); startActivityForResult(intent,LOOK_PHOTO); } }); builder.setNegativeButton("拍照", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.dismiss(); Intent intent = new Intent(MainActivity.this, UseCameraActivity.class); startActivityForResult(intent,TAKE_PHOTO); } }); builder.show(); } }); } //接收返回数据 @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); //判断是否是选择图片或者拍照图片的成功返回 if(resultCode==RESULT_OK&&(requestCode==TAKE_PHOTO||requestCode==LOOK_PHOTO)){ Uri uri=null; String filePath=null; if(requestCode==TAKE_PHOTO){ filePath=data.getStringExtra(UseCameraActivity.IMAGE_PATH); }else{ uri=data.getData(); filePath = getRealFilePath(this, uri); } Toast.makeText(this,filePath,Toast.LENGTH_SHORT).show(); }else{ //进行失败处理 } } //选择相册后获得图片的真实路径 public static String getRealFilePath(final Context context, final Uri uri) { if (null == uri) return null; final String scheme = uri.getScheme(); String data = null; if (scheme == null) data = uri.getPath(); else if (ContentResolver.SCHEME_FILE.equals(scheme)) { data = uri.getPath(); } else if (ContentResolver.SCHEME_CONTENT.equals(scheme)) { Cursor cursor = context.getContentResolver().query(uri, new String[]{MediaStore.Images.ImageColumns.DATA}, null, null, null); if (null != cursor) { if (cursor.moveToFirst()) { int index = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA); if (index > -1) { data = cursor.getString(index); } } cursor.close(); } } return data; } }

    //这个主要的拍照处理的activity,由于这边出现了一种情况:有两个Activity,一个为A,一个为B,由A跳B,再由B跳向拍照,拍完照返回时发现B消失了,查了查原因可能是由于手机内存过于小,当跳转到拍照时,app相当于位于后台,在拍照的过程中,手机自动杀死了Activity导致返回时候Activity为空,app出错,这里进行的处理就是在Activity被杀死时候通过saveinstance保存拍照地址进行处理。

    public class UseCameraActivity extends AppCompatActivity { public final static String IMAGEFILEPATH = "ImageFilePath"; public final static String IMAGE_PATH = "image_path"; private String mImageFilePath; private final static String TAG ="UseCameraActivity"; static Activity mContext; private static Context applicationContext; public static final int TAKE_PHOTO=1111; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); //判断savedInstanceState是否保存的有数据 if (savedInstanceState != null) { //有数据,获取数据并返回 mImageFilePath = savedInstanceState.getString(IMAGEFILEPATH); File file = new File(mImageFilePath); if (file.exists()) { Intent intent = new Intent(); intent.putExtra(IMAGE_PATH, IMAGEFILEPATH); setResult(RESULT_OK, intent); Log.e(TAG,"拍摄成功"); finish(); }else{ Log.e(TAG,"拍摄失败"); } } //没有数据,前往拍照页面 mContext=this; applicationContext=getApplicationContext(); if(savedInstanceState==null){ takePhoto(); } } //这里获取系统时间给图片命名 public void takePhoto(){ long currentTimeMillis = System.currentTimeMillis(); mImageFilePath = getCameraPath() + currentTimeMillis+".jpg"; File file = new File(mImageFilePath); showCamera(file); } private void showCamera(File file){ Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(file)); startActivityForResult(intent,TAKE_PHOTO); } @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { if(requestCode==TAKE_PHOTO&&resultCode==RESULT_OK){ Intent intent = new Intent(); intent.putExtra(IMAGE_PATH,IMAGEFILEPATH); setResult(RESULT_OK,intent); finish(); }else{ finish(); } } @Override protected void onDestroy() { super.onDestroy(); } //Activity被杀死时候保存数据 @Override protected void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); outState.putString(IMAGEFILEPATH,mImageFilePath+""); } //下面这三个方法是为了创建file,华为的手机不会默认创建3级file,只能一层一层慢慢创建了, public static String getCameraPath() { String filePath = getImageRootPath() + "/camera/"; File file = new File(filePath); if (!file.isDirectory()) { file.mkdirs(); } file = null; return filePath; } public static String getImageRootPath() { String filePath = getAppRootPath() + "/image"; File file = new File(filePath); if (!file.exists()) { file.mkdirs(); } file = null; return filePath; } public static String getAppRootPath() { String filePath = "/a"; if (Environment.getExternalStorageState().equals( Environment.MEDIA_MOUNTED)) { filePath = Environment.getExternalStorageDirectory() + filePath; } else { filePath = applicationContext.getCacheDir() + filePath; } File file = new File(filePath); if (!file.exists()) { file.mkdirs(); } file = null; File nomedia = new File(filePath + "/.nomedia"); if (!nomedia.exists()) try { nomedia.createNewFile(); } catch (IOException e) { } return filePath; } }
    转载请注明原文地址: https://ju.6miu.com/read-1309907.html
    最新回复(0)