系统已经有的东西,如果我们没有新的需求的话,直接调用是最直接的。下面讲讲调用系统相机拍照并保存图片和如何调用系统相册的方法。
首先看看调用系统相机的核心方法:
代码如下 | 复制代码 |
Intent camera = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); startActivityForResult(camera, CAMERA); |
相机返回的数据通过下面的回调方法取得,并处理:
代码如下 | 复制代码 |
@Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); if(requestCode == CAMERA && resultCode == Activity.RESULT_OK && null != data){ String sdState=Environment.getExternalStorageState(); if(!sdState.equals(Environment.MEDIA_MOUNTED)){ GameLog.log(Tag, "sd card unmount"); return; } new DateFormat(); String name= DateFormat.format("yyyyMMdd_hhmmss", Calendar.getInstance(Locale.CHINA))+".jpg"; Bundle bundle = data.getExtras(); //获取相机返回的数据,并转换为图片格式 Bitmap bitmap = (Bitmap)bundle.get("data"); FileOutputStream fout = null; File file = new File("/sdcard/pintu/"); file.mkdirs(); String filename=file.getPath()+name; try { fout = new FileOutputStream(filename); bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fout); } catch (FileNotFoundException e) { e.printStackTrace(); }finally{ try { fout.flush(); fout.close(); } catch (IOException e) { e.printStackTrace(); } } //显示图片 } }
|
下面是调用系统相册并取得照片的方法:
代码如下 | 复制代码 |
Intent picture = new Intent(Intent.ACTION_PICK,android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI); startActivityForResult(picture, PICTURE); |
下面是相应的回调方法:
代码如下 | 复制代码 |
@Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); if(requestCode == CAMERA && resultCode == Activity.RESULT_OK && null != data){ Uri selectedImage = data.getData(); |
这样就完成了系统调用,很简单,但是有些朋友会碰到照片拍好了,在手机相册中发现照片不显示呀。
解决Android拍照保存在系统相册不显示的问题
MediaStore.Images.Media.insertImage(getContentResolver(), mBitmap, "", "");通过上面的那句代码就能插入到系统图库,这时候有一个问题,就是我们不能指定插入照片的名字,而是系统给了我们一个当前时间的毫秒数为名字,有一个问题郁闷了很久,我还是先把insertImage的源码贴出来吧
代码如下 | 复制代码 |
/** Uri url = null; try { if (source != null) { long id = ContentUris.parseId(url); if (url != null) { return stringUrl; |
上面方法里面有一个title,我刚以为是可以设置图片的名字,设置一下,原来不是,郁闷,哪位高手知道title这个字段是干嘛的,告诉下小弟,不胜感激!
当然Android还提供了一个插入系统相册的方法,可以指定保存图片的名字,我把源码贴出来吧
代码如下 | 复制代码 |
/** * Insert an image and create a thumbnail for it. * * @param cr The content resolver to use * @param imagePath The path to the image to insert * @param name The name of the image * @param description The description of the image * @return The URL to the newly created image * @throws FileNotFoundException */ public static final String insertImage(ContentResolver cr, String imagePath, String name, String description) throws FileNotFoundException { // Check if file exists with a FileInputStream FileInputStream stream = new FileInputStream(imagePath); try { Bitmap bm = BitmapFactory.decodeFile(imagePath); String ret = insertImage(cr, bm, name, description); bm.recycle(); return ret; } finally { try { stream.close(); } catch (IOException e) { } } } |
啊啊,贴完源码我才发现,这个方法调用了第一个方法,这个name就是上面方法的title,晕死,这下更加郁闷了,反正我设置title无效果,求高手为小弟解答,先不管了,我们继续往下说
上面那段代码插入到系统相册之后还需要发条广播
代码如下 | 复制代码 |
sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://"+ Environment.getExternalStorageDirectory()))); |
上面那条广播是扫描整个sd卡的广播,如果你sd卡里面东西很多会扫描很久,在扫描当中我们是不能访问sd卡,所以这样子用户体现很不好,用过微信的朋友都知道,微信保存图片到系统相册并没有扫描整个SD卡,所以我们用到下面的方法
代码如下 | 复制代码 |
Intent intent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE); Uri uri = Uri.fromFile(new File("/sdcard/image.jpg")); intent.setData(uri); mContext.sendBroadcast(intent); |
或者用MediaScannerConnection
代码如下 | 复制代码 |
final MediaScannerConnection msc = new MediaScannerConnection(mContext, new MediaScannerConnectionClient() { |
也行你会问我,怎么获取到我们刚刚插入的图片的路径?呵呵,这个自有方法获取,insertImage(ContentResolver cr, Bitmap source,String title, String description),这个方法给我们返回的就是插入图片的Uri,我们根据这个Uri就能获取到图片的绝对路径
代码如下 | 复制代码 |
private String getFilePathByContentResolver(Context context, Uri uri) { if (null == uri) { return null; } Cursor c = context.getContentResolver().query(uri, null, null, null, null); String filePath = null; if (null == c) { throw new IllegalArgumentException( "Query on " + uri + " returns null result."); } try { if ((c.getCount() != 1) || !c.moveToFirst()) { } else { filePath = c.getString( c.getColumnIndexOrThrow(MediaColumns.DATA)); } } finally { c.close(); } return filePath; } |
根据上面的那个方法获取到的就是图片的绝对路径