사용자가 이미지를 위해 카메라 또는 갤러리를 선택할 수 있도록 허용 그런 다음 ACTION_PICK_ACTIVITY사용자가 카메라 또는 갤러리를 선택할

내가하려고하는 것은 매우 간단 해 보이지만 며칠 동안 검색 한 후에는 이해할 수 없습니다.

사용자가 여러 (최대 5) 이미지를 선택할 수있는 응용 프로그램이 있습니다. 을 사용하고 ImageView있습니다. 사용자가를 클릭 ImageView하면 옵션을 허용하고 싶습니다.

  1. 갤러리에서 이미지를 선택하거나
  2. 카메라를 사용하여 이미지를 캡처하십시오.

나는 ACTION_GET_CONTENT의도 를 사용하여 시작했으며 갤러리에 도착하는 데 효과적입니다. 그런 다음 ACTION_PICK_ACTIVITY사용자가 카메라 또는 갤러리를 선택할 수 있도록 의도를 사용했습니다.

Intent pickIntent = new Intent(Intent.ACTION_PICK_ACTIVITY);
Intent gallIntent=new Intent(Intent.ACTION_GET_CONTENT);
gallIntent.setType("image/*");
Intent camIntent = new Intent("android.media.action.IMAGE_CAPTURE");
pickIntent.putExtra(Intent.EXTRA_INTENT, camIntent);
pickIntent.putExtra(Intent.EXTRA_INTENT, gallIntent)
pickIntent.putExtra(Intent.EXTRA_TITLE, "Select Source");
startActivityForResult(pickIntent, IMAGE_SELECTOR);

하지만 하나만 추가 할 수있는 것 같습니다 EXTRA_INTENT. 메뉴가 예상대로 표시되지만 갤러리 및 파일 …… 카메라 없음) 만 사용할 수 있습니다.

누락 된이 작업을 수행하는 더 좋고 쉬운 방법이 있습니까? 도움을 주셔서 감사합니다.



답변

의도 해결 결과를 병합하는 자체 선택기 대화 상자를 작성해야합니다.

이렇게하려면 원래 의도에 대해 PackageManager.queryIntentActivities () 를 사용하여 PackageManager를 쿼리하고 다음과 같이 검색된 각 활동에 대해 하나의 새로운 의도로 가능한 의도의 최종 목록을 작성해야합니다.

List<Intent> yourIntentsList = new ArrayList<Intent>();

List<ResolveInfo> listCam = packageManager.queryIntentActivities(camIntent, 0);
for (ResolveInfo res : listCam) {
    final Intent finalIntent = new Intent(camIntent);
    finalIntent.setComponent(new ComponentName(res.activityInfo.packageName, res.activityInfo.name));
    yourIntentsList.add(finalIntent);
}

List<ResolveInfo> listGall = packageManager.queryIntentActivities(gallIntent, 0);
for (ResolveInfo res : listGall) {
    final Intent finalIntent = new Intent(gallIntent);
    finalIntent.setComponent(new ComponentName(res.activityInfo.packageName, res.activityInfo.name));
    yourIntentsList.add(finalIntent);
}

(나는 이것을 컴파일하지 않을 수 있도록 여기에 직접 썼다)

그런 다음 목록에서 사용자 정의 대화 상자를 만드는 방법에 대한 자세한 내용은 https://developer.android.com/guide/topics/ui/dialogs.html#AlertDialog를 참조 하십시오.


답변

갤러리 나 카메라 또는 파일 시스템을 탐색하도록 등록 된 모든 응용 프로그램에서 이미지를 선택하려는 단일 의도를 시작하는 방법

Intent 옵션 목록으로 대화 상자를 만드는 것보다 Intent.createChooser를 사용하여 다양한 ‘카메라’, ‘갤러리’및 타사 파일 시스템 브라우저 앱의 그래픽 아이콘 및 짧은 이름에 액세스하는 것이 훨씬 좋습니다. ‘아스트로’등

표준 선택자 의도를 사용하고 그에 추가 의도를 추가하는 방법에 대해 설명합니다.

private Uri outputFileUri;

private void openImageIntent() {

    // Determine Uri of camera image to save.
    final File root = new File(Environment.getExternalStorageDirectory() + File.separator + "MyDir" + File.separator);
    root.mkdirs();
    final String fname = Utils.getUniqueImageFilename();
    final File sdImageMainDirectory = new File(root, fname);
    outputFileUri = Uri.fromFile(sdImageMainDirectory);

    // Camera.
    final List<Intent> cameraIntents = new ArrayList<Intent>();
    final Intent captureIntent = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
    final PackageManager packageManager = getPackageManager();
    final List<ResolveInfo> listCam = packageManager.queryIntentActivities(captureIntent, 0);
    for(ResolveInfo res : listCam) {
        final String packageName = res.activityInfo.packageName;
        final Intent intent = new Intent(captureIntent);
        intent.setComponent(new ComponentName(packageName, res.activityInfo.name));
        intent.setPackage(packageName);
        intent.putExtra(MediaStore.EXTRA_OUTPUT, outputFileUri);
        cameraIntents.add(intent);
    }

    // Filesystem.
    final Intent galleryIntent = new Intent();
    galleryIntent.setType("image/*");
    galleryIntent.setAction(Intent.ACTION_GET_CONTENT);

    // Chooser of filesystem options.
    final Intent chooserIntent = Intent.createChooser(galleryIntent, "Select Source");

    // Add the camera options.
    chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, cameraIntents.toArray(new Parcelable[cameraIntents.size()]));

    startActivityForResult(chooserIntent, YOUR_SELECT_PICTURE_REQUEST_CODE);
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (resultCode == RESULT_OK) {
        if (requestCode == YOUR_SELECT_PICTURE_REQUEST_CODE) {
            final boolean isCamera;
            if (data == null) {
                isCamera = true;
            } else {
                final String action = data.getAction();
                if (action == null) {
                    isCamera = false;
                } else {
                    isCamera = action.equals(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
                }
            }

            Uri selectedImageUri;
            if (isCamera) {
                selectedImageUri = outputFileUri;
            } else {
                selectedImageUri = data == null ? null : data.getData();
            }
        }
    }
}


답변

나는 이것을 발견 했다 . 사용 :

galleryIntent.setType("image/*");
galleryIntent.setAction(Intent.ACTION_GET_CONTENT);

의도 중 하나에 대해 사용자에게 Android 4에서 ‘문서’를 선택하는 옵션이 표시되어 매우 혼란 스럽습니다. 대신 이것을 사용하면 ‘갤러리’옵션이 표시됩니다.

Intent pickIntent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);


답변

또한이 문제가 있었고 AlertDialog를 만들고 DialogInterface 리스너와 함께 setItems () 메서드를 사용했습니다.

AlertDialog.Builder getImageFrom = new AlertDialog.Builder(Fotos.this);
getImageFrom.setTitle("Select:");
final CharSequence[] opsChars = {getResources().getString(R.string.takepic), getResources().getString(R.string.opengallery)};
getImageFrom.setItems(opsChars, new android.content.DialogInterface.OnClickListener(){

    @Override
    public void onClick(DialogInterface dialog, int which) {
        if(which == 0){
            Intent cameraIntent = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
            startActivityForResult(cameraIntent, CAMERA_PIC_REQUEST);
        }else
            if(which == 1){
                Intent intent = new Intent();
                intent.setType("image/*");
                intent.setAction(Intent.ACTION_GET_CONTENT);
                startActivityForResult(Intent.createChooser(intent,
                    getResources().getString(R.string.pickgallery)), SELECT_PICTURE);
            }
        dialog.dismiss();
    }
});


답변

갤러리 또는 카메라에서 이미지를 선택하기위한 완전한 유틸리티를 만들기 위해 몇 가지 솔루션을 병합했습니다. ImagePicker 유틸리티 의 기능은 다음과 같습니다 ( Github lib에도 있음 ).

  • 갤러리 및 카메라 요청에 대한 병합 의도.
  • 선택한 큰 이미지 크기 조정 (예 : 2500 x 1600)
  • 필요한 경우 이미지 회전

스크린 샷 :

ImagePicker 시작 의도

편집 : 다음은 갤러리 및 카메라 응용 프로그램에 대한 병합 된 의도를 얻는 코드 조각입니다. ImagePicker util ( Github lib ) 에서 전체 코드를 볼 수 있습니다 .

public static Intent getPickImageIntent(Context context) {
    Intent chooserIntent = null;

    List<Intent> intentList = new ArrayList<>();

    Intent pickIntent = new Intent(Intent.ACTION_PICK,
            android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
    Intent takePhotoIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    takePhotoIntent.putExtra("return-data", true);
    takePhotoIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(getTempFile(context)));
    intentList = addIntentsToList(context, intentList, pickIntent);
    intentList = addIntentsToList(context, intentList, takePhotoIntent);

    if (intentList.size() > 0) {
        chooserIntent = Intent.createChooser(intentList.remove(intentList.size() - 1),
                context.getString(R.string.pick_image_intent_text));
        chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, intentList.toArray(new Parcelable[]{}));
    }

    return chooserIntent;
}

private static List<Intent> addIntentsToList(Context context, List<Intent> list, Intent intent) {
    List<ResolveInfo> resInfo = context.getPackageManager().queryIntentActivities(intent, 0);
    for (ResolveInfo resolveInfo : resInfo) {
        String packageName = resolveInfo.activityInfo.packageName;
        Intent targetedIntent = new Intent(intent);
        targetedIntent.setPackage(packageName);
        list.add(targetedIntent);
    }
    return list;
}


답변

이 코드는 카메라 버튼 하나와 갤러리 버튼 하나가 있으며 이미지는 ImageView에 표시되므로 도움이됩니다.

https://github.com/siddhpuraamitr/Choose-Image-From-Gallery-Or-Camera


답변

이미지 선택을 사용하려고 할 때 4.4 이상에서 오류가 발생하는 경우 아래 코드를 사용할 수 있습니다.

Intent 옵션 목록으로 대화 상자를 만드는 것보다 Intent.createChooser를 사용하여 다양한 ‘카메라’, ‘갤러리’및 타사 파일 시스템 브라우저 앱의 그래픽 아이콘 및 짧은 이름에 액세스하는 것이 훨씬 좋습니다. ‘아스트로’등

표준 선택자 의도를 사용하고 그에 추가 의도를 추가하는 방법에 대해 설명합니다.

private void openImageIntent(){

    // Determine Uri of camera image to save.
    final File root = new File(Environment.getExternalStorageDirectory() + File.separator + "amfb" + File.separator);
    root.mkdir();
    final String fname = "img_" + System.currentTimeMillis() + ".jpg";
    final File sdImageMainDirectory = new File(root, fname);
    outputFileUri = Uri.fromFile(sdImageMainDirectory);

    // Camera.
    final List<Intent> cameraIntents = new ArrayList<Intent>();
    final Intent captureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    final PackageManager packageManager = getPackageManager();
    final List<ResolveInfo> listCam = packageManager.queryIntentActivities(captureIntent, 0);
    for (ResolveInfo res : listCam){
        final String packageName = res.activityInfo.packageName;
        final Intent intent = new Intent(captureIntent);
        intent.setComponent(new ComponentName(res.activityInfo.packageName, res.activityInfo.name));
        intent.setPackage(packageName);
        intent.putExtra(MediaStore.EXTRA_OUTPUT, outputFileUri);
        cameraIntents.add(intent);
    }

    //FileSystem
    final Intent galleryIntent = new Intent();
    galleryIntent.setType("image/");
    galleryIntent.setAction(Intent.ACTION_GET_CONTENT);

    // Chooser of filesystem options.
    final Intent chooserIntent = Intent.createChooser(galleryIntent, "Select Source");
    // Add the camera options.
    chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, cameraIntents.toArray(new Parcelable[]{}));
    startActivityForResult(chooserIntent, CAMERA_CAPTURE_IMAGE_REQUEST_CODE);

}


@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    //super.onActivityResult(requestCode, resultCode, data);
    if (resultCode == RESULT_OK) {
        if (requestCode == CAMERA_CAPTURE_IMAGE_REQUEST_CODE) {
            final boolean isCamera;
            if (data == null) {
                isCamera = true;
            } else {
                final String action = data.getAction();
                if (action == null) {
                    isCamera = false;
                } else {
                    isCamera = action.equals(MediaStore.ACTION_IMAGE_CAPTURE);
                }
            }

            Uri selectedImageUri;
            if (isCamera) {
                selectedImageUri = outputFileUri;
                //Bitmap factory
                BitmapFactory.Options options = new BitmapFactory.Options();
                // downsizing image as it throws OutOfMemory Exception for larger
                // images
                options.inSampleSize = 8;
                final Bitmap bitmap = BitmapFactory.decodeFile(selectedImageUri.getPath(), options);
                preview.setImageBitmap(bitmap);
            } else {
                selectedImageUri = data == null ? null : data.getData();
                Log.d("ImageURI", selectedImageUri.getLastPathSegment());
                // /Bitmap factory
                BitmapFactory.Options options = new BitmapFactory.Options();
                // downsizing image as it throws OutOfMemory Exception for larger
                // images
                options.inSampleSize = 8;
                try {//Using Input Stream to get uri did the trick
                    InputStream input = getContentResolver().openInputStream(selectedImageUri);
                    final Bitmap bitmap = BitmapFactory.decodeStream(input);
                    preview.setImageBitmap(bitmap);
                } catch (FileNotFoundException e) {
                    e.printStackTrace();
                }
            }
        }
    } else if (resultCode == RESULT_CANCELED){
        // user cancelled Image capture
        Toast.makeText(getApplicationContext(),
                "User cancelled image capture", Toast.LENGTH_SHORT)
                .show();
    } else {
        // failed to capture image
        Toast.makeText(getApplicationContext(),
                "Sorry! Failed to capture image", Toast.LENGTH_SHORT)
                .show();
    }
}