保存图片EXTRA_OUPUT为空onActivityResult

Posted

技术标签:

【中文标题】保存图片EXTRA_OUPUT为空onActivityResult【英文标题】:Save picture EXTRA_OUPUT is empty onActivityResult 【发布时间】:2015-02-08 01:24:26 【问题描述】:

我在一个活动中加载了片段。

在这个片段中,我为按钮设置了一个 onClick 事件来拍照。我想将此图片保存在特定文件夹的内部存储中。

这是我的片段类,我尝试了很多不同的解决方案,但我不明白为什么创建了 mCurrentPhotoPath 但没有被拍摄的图片填充(SkImageDecoder::Factory 返回 null)。

这是我的片段类(我删除了部分代码)

public class Q3Fragment extends Fragment 

private OnFragmentInteractionListener mListener;
private Spinner field;
private int TAB_ID = 1;
private int Q_ID = 3;

private final static String DEBUG_TAG = "PHOTOMANAGER";
private String mCurrentPhotoPath;

private ImageView imagePreview;
private String filePath = "";
Intent takePictureIntent;
private PhotoManager pm;

public static Q3Fragment newInstance(String type) 
    Q3Fragment fragment = new Q3Fragment();
    Bundle args = new Bundle();
    args.putString("type", type);
    fragment.setArguments(args);
    return fragment;

public Q3Fragment() 

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) 

    final View view = inflater.inflate(R.layout.fragment_q3, container, false);


    /////////////

    imagePreview = (ImageView) view.findViewById(R.id.q4imgPreview);



    takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);

    Button buttonPhoto = (Button) view.findViewById(R.id.q4BtnPhoto);
    buttonPhoto.setOnClickListener(new View.OnClickListener() 
        @Override
        public void onClick(View v) 


            File photoFile = null;
            try 
                photoFile = createImageFile();
             catch (IOException ex) 

            
            // Continue only if the File was successfully created
            if (photoFile != null) 
                takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT,
                        Uri.fromFile(photoFile));
                startActivityForResult(takePictureIntent, 11);
            


        

    );

    /////////////

    return view;



@Override
public void onAttach(Activity activity) 
    super.onAttach(activity);
    try 
        mListener = (OnFragmentInteractionListener) activity;
     catch (ClassCastException e) 
        throw new ClassCastException(activity.toString()
                + " must implement OnFragmentInteractionListener");
    


@Override
public void onDetach() 
    super.onDetach();
    mListener = null;


public interface OnFragmentInteractionListener 
    // TODO: Update argument type and name
    public void onFragmentInteraction(Boolean valid,int qId);







@Override
public void onActivityResult(int requestCode, int resultCode,
                             Intent data) 
    Log.d("Fragment PHOTOMANAGER","onActivityResult");
    // lors du resultat de l'intent (lorsqu'on clique sur save la photo)

    try 
        handleSmallCameraPhoto();
     catch (IOException e) 
        e.printStackTrace();
    

    if(data != null) 
        getActivity().getContentResolver().delete(data.getData(), null, null);
    





// on enregistre la photo
private void handleSmallCameraPhoto() throws IOException 


    File f = new File(mCurrentPhotoPath);
    Uri contentUri = Uri.fromFile(f);

    if(f.exists())
        Log.d(DEBUG_TAG,"FILE EXISTS " + mCurrentPhotoPath);
    

    // here the bitmap not containing picture.
    Bitmap mBitmap = MediaStore.Images.Media.getBitmap(getActivity().getContentResolver(), contentUri);

    imagePreview.setImageBitmap(mBitmap);
    filePath = saveToInternalStorage(mBitmap);





// methode pour sauvegarder une photo (min ou full)
private String saveToInternalStorage(Bitmap bitmapImage)

    ContextWrapper cw = new ContextWrapper(getActivity().getApplicationContext());

    Log.d(DEBUG_TAG,"saveToInternalStorage");

    File directory = cw.getDir("imageDir_"+getArguments().getString("type"), Context.MODE_PRIVATE);

    String fileName;



    fileName = "q" + Q_ID + ".jpg";


    // Create imageDir
    File mypath = new File(directory, fileName);

    FileOutputStream fos = null;
    try 

        fos = new FileOutputStream(mypath);

        // Use the compress method on the BitMap object to write image to the OutputStream
        bitmapImage.compress(Bitmap.CompressFormat.JPEG, 80, fos);
        fos.close();
     catch (Exception e) 
        e.printStackTrace();
    
    Log.d(DEBUG_TAG,"FILE SAVED "+mypath.getAbsolutePath());
    return mypath.getAbsolutePath();


private File createImageFile() throws IOException 
    // Create an image file name
    String imageFileName = "q" + Q_ID +"photo";
    ContextWrapper cw = new ContextWrapper(getActivity().getApplicationContext());

    Log.d(DEBUG_TAG,"saveToInternalStorage");

    File directory = cw.getDir("imageDir_"+getArguments().getString("type"), Context.MODE_PRIVATE);
    File image = File.createTempFile(
            imageFileName,  /* prefix */
            ".jpg",         /* suffix */
            directory      /* directory */
    );

    // Save a file: path for use with ACTION_VIEW intents
    mCurrentPhotoPath = image.getAbsolutePath();
    Log.d(DEBUG_TAG," createcontainer file "+mCurrentPhotoPath);
    return image;




提前感谢您的帮助..

【问题讨论】:

这可能与***.com/questions/1910608/…有关 尝试使用BitmapFactory.decodeFile(mCurrentPhotoPath, bitmapOptions) 而不是MediaStore.Images.Media.getBitmap() 加载照片的位图。 【参考方案1】:

让我提一下 android 中的一个关键概念,这是理解您的代码为何不能按原样运行所必需的。 ACTION_IMAGE_CAPTURE 意图启动另一个应用。在这种情况下,相机应用程序可以完成工作。 EXTRA_OUTPUT 告诉被调用的应用程序(即相机应用程序)将拍摄的照片保存在文件系统中的哪个位置。

问题在于应用可能访问其自己的私有内部存储。因此,相机应用程序无法将图片保存在调用者的应用程序(即您的应用程序)私人存储中。

请注意,您调用的是ContextWrapper.getDir,它指向您应用的私有存储中的一个目录。

如果您想将图片存储在应用的私有存储中,则必须将图片临时存储在两个应用都可以访问的位置,然后onActivityResult 将图片复制到应用的私有存储中。

【讨论】:

哦,伙计..你救了我的一天!!!解决方案就在我附近,我想到了这个问题,但专注于其他无用的事情。非常感谢您的回答!

以上是关于保存图片EXTRA_OUPUT为空onActivityResult的主要内容,如果未能解决你的问题,请参考以下文章

Android Camera 拍照 三星BUG总结

如何将Java中的图片保存到多个blob中?

如果 UserDefaults 为空,如何检查一次

java怎样把一个byte数组保存成图片到硬盘上?

Ant design——message防抖优化——富文本的使用——富文本数据的收集——上传图片保存本地

尝试以编程方式删除文件夹时出现“目录不为空”错误