【问题标题】:java.io.FileNotFoundException: /storage/emulated/0/saved_images/grub.jpg: open failed: ENOENT (No such file or directory)java.io.FileNotFoundException:/storage/emulated/0/saved_images/grub.jpg:打开失败:ENOENT(没有这样的文件或目录)
【发布时间】:2014-12-09 06:37:50
【问题描述】:

我正在使用下面的代码将图像保存在 sd 卡中,但我不断收到以下异常

private void SaveImage(Bitmap finalBitmap,String filename) {

    String root = Environment.getExternalStorageDirectory().toString();
    File myDir = new File(root + "/saved_images");    
    myDir.mkdirs();

    String fname = filename;
    File file = new File (myDir, fname);
    if (file.exists ()) file.delete (); 
    try {
           FileOutputStream out = new FileOutputStream(file);
           finalBitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
           out.flush();
           out.close();

    } catch (Exception e) {
           e.printStackTrace();
    }
}

我错过了什么吗?

【问题讨论】:

  • 我通过请求用户许可修复了相同的错误消息。如果您使用的是 SDK > 22,则必须这样做。你可以在one of the answers here找到完整的代码。

标签: android


【解决方案1】:

如果您在 Android 版本 10 中遇到此问题,请打开清单文件并将此行添加到您的应用程序标签中。

<application android:requestLegacyExternalStorage="true" .....>

这个问题是因为在 Android 10 中引入了范围存储。请确保您在清单中添加权限请求并从用户那里获取运行时权限。在最新的 android 版本中,您需要用户的运行时权限。

【讨论】:

    【解决方案2】:

    修改你的代码,因为你没有创建目录:

     private void SaveImage(Bitmap finalBitmap,String filename) {
    
        String root = Environment.getExternalStorageDirectory().toString();
        File myDir = new File(root + "/saved_images");    
        myDir.mkdirs();
    
        String fname = filename;
        File file = new File (myDir, fname);
        if (file.exists ()) file.delete (); 
        file.createNewFile();
        try {
               FileOutputStream out = new FileOutputStream(file);
               finalBitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
               out.flush();
               out.close();
    
        } catch (Exception e) {
               e.printStackTrace();
        }
    }
    

    【讨论】:

    • 你怎么能不包围“file.createNewFile();”尝试并抓住?
    【解决方案3】:

    从 SDK 版本 30 开始,您不能扩展 android:requestLegacyExternalStorage="true"。而是稍微修改您的 ImageLoader 库。我看到你必须修改你的文件路径:File dir = new File(Environment.getExternalStorageDirectory().getAbsolutePath() + "saved_images"); 到类似File dir = new File(context.getExternalFilesDir(Environment.DIRECTORY_PICTURES), "saved_images"); 的东西。这应该可以解决问题。

    【讨论】:

    • 工作太棒了! @Vaidas
    【解决方案4】:

    这就是我在检查文本文件中的时间戳时从存储中读取文件的方式。第 2 行可能是您的最佳选择。

    File root = android.os.Environment.getExternalStorageDirectory();
    File dir = new File(root.getAbsolutePath() + "/path");
    dir.mkdirs();
    File file = new File(dir, ".storage.txt");
    Reader pr;
    String line = "";
    try {
        pr = new FileReader(file);
        int data = pr.read();
            while (data != -1) {
                line += (char) data;
                data = pr.read();
            }
        pr.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    //do stuff with line
    

    【讨论】:

      【解决方案5】:

      从 Android 6.0.0 你需要使用这个代码:

      if (ContextCompat.checkSelfPermission(thisActivity,
              Manifest.permission.WRITE_EXTERNAL_STORAGE)
      != PackageManager.PERMISSION_GRANTED)
      

      【讨论】:

        【解决方案6】:

        确保您在 Manifest 上设置了权限:

        <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
        <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
        

        【讨论】:

        • "android.permission.WRITE_EXTERNAL_STORAGE" 已在 android11(api 级别 30)上移除
        【解决方案7】:

        如果您在 Android 版本 10 中遇到此问题,请打开清单文件并将此行添加到您的应用程序标签中。

        <application android:requestLegacyExternalStorage="true" .....>
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多