欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

利用系统相机拍照,摄像,从系统相册中选择图片

程序员文章站 2024-03-23 10:01:58
...

简书地址:http://www.jianshu.com/p/4afa67766ea4

从系统相册中选择图片

利用系统相机拍照,摄像,从系统相册中选择图片

打开系统相册

    private void openAlbum() {
        Intent albumIntent = new Intent(Intent.ACTION_PICK);
        albumIntent.setType("image/*");
        startActivityForResult(albumIntent, REQUEST_OPEN_ALBUM);
    }

在onActivityResult中接收结果

case REQUEST_OPEN_ALBUM:
                if (resultCode == RESULT_OK) {
                    handleAlbumData(data);
                }
                break;
private void handleAlbumData(Intent data) {
        Uri uri = data.getData();
        String[] projection = new String[]{
                MediaStore.Images.Media.DATA
        };

        Cursor cursor = getContentResolver().query(
                uri,
                projection,
                null,
                null,
                null
        );
        if (cursor != null && cursor.moveToFirst()) {
            int dataIndex = cursor.getColumnIndex(MediaStore.Images.Media.DATA);
            String imagePath = cursor.getString(dataIndex);
            cursor.close();
            showBitmap(imagePath);
        }

    }

    private void showBitmap(String imagePath) {
        ToastUtils.showShortToast(imagePath);
        Bitmap bitmap = BitmapFactory.decodeFile(imagePath);
        showImgInDialog(bitmap);
    }

    private void showImgInDialog(Bitmap bitmap) {
        ImageView imageView = new ImageView(this);
        imageView.setImageBitmap(bitmap);
        new AlertDialog.Builder(this)
                .setView(imageView)
                .setNegativeButton("关闭", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        dialog.dismiss();
                    }
                })
                .show();
    }

打开系统相机,拍照,并返回结果

拍摄照片最常见的方法有两种:
1. 直接通过getExtras().get(“data”)获取Bitmap,这种方法返回的是一张经过压缩的图片,清晰度低,尺寸小。
2. 指定图片存储路径,需要的时候直接从路径中获取图片,优点就是图片清晰,不过得兼容一下Android 7.0系统
先看第一种方案:

效果图

利用系统相机拍照,摄像,从系统相册中选择图片

打开相机

private void openCamera() {
        Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        startActivityForResult(cameraIntent, REQUEST_IMAGE_CAPTURE);
    }

在onActivityResult中接收结果

            case REQUEST_IMAGE_CAPTURE:
                if (resultCode == RESULT_OK) {
                    handleImageCaptureData(data);
                }
                break;
   private void handleImageCaptureData(Intent data) {
        //这张图是经过压缩的,清晰度低
        Bitmap bitmap = (Bitmap) data.getExtras().get("data");
        showImgInDialog(bitmap);
    }

可以看到,接收到的图片尺寸太小了,完全是一个缩略图。

用第二种方案:

打开相机

    private void openCameraWithOutput() {
        String path = new File(Environment.getExternalStorageDirectory(), "ktools").getAbsolutePath();
        if (!new File(path).exists()) {
            new File(path).mkdirs();
        }
        outputImageFile = new File(path, System.currentTimeMillis() + ".png");
        if (!outputImageFile.exists()) {
            try {
                outputImageFile.createNewFile();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        //兼容7.0
        Uri contentUri = FileProvider.getUriForFile(
                this,
                BuildConfig.APPLICATION_ID,
                outputImageFile
        );
        Log.d(TAG, "openCameraWithOutput: uri = " + contentUri.toString());
        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        intent.putExtra(Intent.EXTRA_MIME_TYPES, MimeTypeMap.getSingleton().getMimeTypeFromExtension("png"));
        //指定输出路径
        intent.putExtra(MediaStore.EXTRA_OUTPUT, contentUri);
        startActivityForResult(intent, REQUEST_CODE_CAPTURE_IMAGE_WITHOUT_COMPRESS);
    }

在onActivityResult中接收结果

case REQUEST_CODE_CAPTURE_IMAGE_WITHOUT_COMPRESS:
                if (resultCode == RESULT_OK) {
                    handleImageCaptureWithoutCompress(data);
                }
                break;
    private void handleImageCaptureWithoutCompress(Intent data) {
        Bitmap bitmap = BitmapFactory.decodeFile(outputImageFile.getAbsolutePath());
        showImgInDialog(bitmap);
    }

拍摄视频的原理和拍照片的第二种方案是一样的

打开系统相机拍摄视频

效果图

利用系统相机拍照,摄像,从系统相册中选择图片

打开相机

    private void takeVideo() {
        File dirVideo = new File(Environment.getExternalStorageDirectory(), "ktools/videos/");
        if (!dirVideo.exists()) {
            dirVideo.mkdirs();
        }
        outputVideoFile = new File(dirVideo.getAbsolutePath() + System.currentTimeMillis() + ".mp4");
        if (!outputVideoFile.exists()) {
            try {
                outputVideoFile.createNewFile();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        //兼容7.0
        Uri videoUri = FileProvider.getUriForFile(
                this,
                BuildConfig.APPLICATION_ID,
                outputVideoFile
        );
        Intent intent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
        //指定输出
        intent.putExtra(MediaStore.EXTRA_OUTPUT, videoUri);
        intent.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 1);
        intent.putExtra(MediaStore.EXTRA_DURATION_LIMIT, 3000);
        startActivityForResult(intent, REQUEST_CODE_TAKE_VIDEO);
    }

在onActivityResult中接收结果

case REQUEST_CODE_TAKE_VIDEO:
                if (resultCode == RESULT_OK) {
                    handleVideoData(data);
                }
                break;
    private void handleVideoData(Intent data) {
        showVideoInDialog(outputVideoFile);
    }

    private void showVideoInDialog(File file) {
        final VideoView videoView = new VideoView(this);
        videoView.setVideoPath(file.getAbsolutePath());
        final AlertDialog dialog = new AlertDialog.Builder(this)
                .setView(videoView)
                .setPositiveButton("播放",null)
                .setNeutralButton("暂停",null)
                .setNegativeButton("关闭", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        dialog.dismiss();
                    }
                })
                .setCancelable(false)
                .show();

        dialog.getButton(AlertDialog.BUTTON_POSITIVE)
                .setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        videoView.start();
                    }
                });

        dialog.getButton(AlertDialog.BUTTON_NEUTRAL)
                .setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        videoView.pause();
                    }
                });
    }

权限声明与7.0具体兼容的步骤并不在上述代码中,完整代码可以去GitHub查看源代码。

源代码

Github地址