草庐IT

Android 保存图片到相册

长满头发的程序猿 2023-08-09 原文

保存图片的方式分为两种

Android Q 以上

Android Q 以下

补充知识:

Android Q 以上的保存图片

1、保存到应用的内部存储空间 (内部存储

2、保存到 Android 系统设置的共享存储空间(外部储存

图片(包括照片和屏幕截图),存储在 DCIM/ 或 Pictures/ 目录

视频,存储在 DCIM/Movies/ 或 Pictures/ 目录

音频文件,存储在 Alarms/Audiobooks/Music/Notifications/Podcasts/ 或 Ringtones/ 目录中

下载的文件,存储在 Download/ 目录中

一、Android Q 以下保存文件方式

获取外部存储目录

函数使用:getExternalStorageDirectory()

获取外部存储公共目录

函数使用:getExternalStoragePublicDirectory()

二、Android Q 以上保存文件方式

获取外部存储目录

函数使用:getExternalFilesDir()

获取外部存储公共目录

函数使用:

Environment.DIRECTORY_DCIM  相机照片

Environment.DIRECTORY_MUSIC 音乐

Environment.DIRECTORY_PODCASTS 系统广播

Environment.DIRECTORY_RINGTONES 系统铃声

Environment.DIRECTORY_ALARMS 系统提醒铃声

Environment.DIRECTORY_NOTIFICATIONS 系统通知铃声

Environment.DIRECTORY_PICTURES 图片

Environment.DIRECTORY_MOVIES 电影

Environment.DIRECTORY_DOWNLOADS 下载

三、代码实现

Android Q 以下

            // Android Q 以下
            public void saveQNext(Bitmap image, Context context, String fileName, int quality) {
                String path = Environment.getExternalStorageDirectory().getAbsolutePath() + File.separator + "艾跳跳";
                Log.i("TAG", "saveQNext: >>> " + path);
                // 创建文件夹
                mkdir(path);
                // 文件名称
                Log.i("TAG", "saveQNext: " + fileName);
                File file = new File(path, fileName);
                try {
                    FileOutputStream fos = new FileOutputStream(file);
                    // 通过io流的方式来压缩保存图片
                    image.compress(Bitmap.CompressFormat.JPEG, quality, fos);
                    fos.flush();
                    fos.close();
                    // 保存图片后发送广播通知更新数据库
                    Uri uri = Uri.fromFile(file);
                    context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, uri));
                } catch (IOException e) {
                    e.printStackTrace();
                }

            }

Android Q 以上

          // Android Q 以上
            @RequiresApi(api = Build.VERSION_CODES.Q)
            public void saveQUp(Bitmap image, Context context, String fileName, int quality) {
                // 文件夹路径
                String imageSaveFilePath = Environment.DIRECTORY_DCIM + File.separator + "艾跳跳";
                Log.i("TAG", "文件夹目录 >>> " + imageSaveFilePath);
                mkdir(imageSaveFilePath);
                // 文件名字
                Log.d("TAG", "文件名字 >>> " + fileName);
                ContentValues contentValues = new ContentValues();
                contentValues.put(MediaStore.MediaColumns.TITLE, fileName);
                contentValues.put(MediaStore.MediaColumns.DISPLAY_NAME, fileName);
                contentValues.put(MediaStore.MediaColumns.MIME_TYPE, "image/jpeg");
                contentValues.put(MediaStore.MediaColumns.DATE_TAKEN, fileName);
                //该媒体项在存储设备中的相对路径,该媒体项将在其中保留
                contentValues.put(MediaStore.MediaColumns.RELATIVE_PATH, imageSaveFilePath);
                Uri uri = null;
                OutputStream outputStream = null;
                ContentResolver localContentResolver = context.getContentResolver();
                try {
                    uri = localContentResolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, contentValues);
                    outputStream = localContentResolver.openOutputStream(uri);
                    // Bitmap图片保存
                    // 1、宽高比例压缩
                    // 2、压缩参数
                    image.compress(Bitmap.CompressFormat.JPEG, quality, outputStream);
                    outputStream.flush();
                    outputStream.close();
                } catch (Exception e) {
                    e.printStackTrace();
                    if (uri != null) {
                        localContentResolver.delete(uri, null, null);
                    }
                } finally {
                    image.recycle();
                    try {
                        if (outputStream != null) {
                            outputStream.close();
                        }
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }

有关Android 保存图片到相册的更多相关文章

  1. ruby-on-rails - Ruby 检查日期时间是否为 iso8601 并保存 - 2

    我需要检查DateTime是否采用有效的ISO8601格式。喜欢:#iso8601?我检查了ruby​​是否有特定方法,但没有找到。目前我正在使用date.iso8601==date来检查这个。有什么好的方法吗?编辑解释我的环境,并改变问题的范围。因此,我的项目将使用jsapiFullCalendar,这就是我需要iso8601字符串格式的原因。我想知道更好或正确的方法是什么,以正确的格式将日期保存在数据库中,或者让ActiveRecord完成它们的工作并在我需要时间信息时对其进行操作。 最佳答案 我不太明白你的问题。我假设您想检查

  2. ruby-on-rails - Ruby on Rails - 为文本区域和图片生成列 - 2

    我是Rails的新手,所以请原谅简单的问题。我正在为一家公司创建一个网站。那家公司想在网站上展示它的客户。我想让客户自己管理这个。我正在为“客户”生成一个表格,我想要的三列是:公司名称、公司描述和Logo。对于名称,我使用的是name:string但不确定如何在脚本/生成脚手架终端命令中最好地创建描述列(因为我打算将其设置为文本区域)和图片。我怀疑描述(我想成为一个文本区域)应该仍然是描述:字符串,然后以实际形式进行调整。不确定如何处理图片字段。那么……说来话长:我在脚手架命令中输入什么来生成描述和图片列? 最佳答案 对于“文本”数

  3. 安卓apk修改(Android反编译apk) - 2

    最近因为项目需要,需要将Android手机系统自带的某个系统软件反编译并更改里面某个资源,并重新打包,签名生成新的自定义的apk,下面我来介绍一下我的实现过程。APK修改,分为以下几步:反编译解包,修改,重打包,修改签名等步骤。安卓apk修改准备工作1.系统配置好JavaJDK环境变量2.需要root权限的手机(针对系统自带apk,其他软件免root)3.Auto-Sign签名工具4.apktool工具安卓apk修改开始反编译本文拿Android系统里面的Settings.apk做demo,具体如何将apk获取出来在此就不过多介绍了,直接进入主题:按键win+R输入cmd,打开命令窗口,并将路

  4. ruby-on-rails - 有没有一种工具可以在编码时自动保存对文件的增量更改? - 2

    我最喜欢的Google文档功能之一是它会在我工作时不断自动保存我的文档版本。这意味着即使我在进行关键更改之前忘记在某个点进行保存,也很有可能会自动创建一个保存点。至少,我可以将文档恢复到错误更改之前的状态,并从该点继续工作。对于在MacOS(或UNIX)上运行的Ruby编码器,是否有具有等效功能的工具?例如,一个工具会每隔几分钟自动将Gitcheckin我的本地存储库以获取我正在处理的文件。也许我有点偏执,但这点小保险可以让我在日常工作中安心。 最佳答案 虚拟机有些人可能讨厌我对此的回应,但我在编码时经常使用VIM,它具有自动保存功

  5. ruby-on-rails - Rails 3.2 防止使用错误保存对象 - 2

    我有一个ActiveRecord对象,我想在不对模型进行永久验证的情况下阻止它被保存。您过去可以使用errors.add执行类似的操作,但它看起来不再有效了。user=User.lastuser.errors.add:name,"namedoesn'trhymewithorange"user.valid?#=>trueuser.save#=>true或user=User.lastuser.errors.add:base,"myuniqueerror"user.valid?#=>trueuser.save#=>true如何在不修改用户对象模型的情况下防止将用户对象保存在Rails3.2中

  6. ruby-on-rails - 将保存回调添加到单个 ActiveRecord 实例,可以吗? - 2

    是否可以为单个ActiveRecord实例添加回调?作为进一步的限制,这是继续使用库,所以我无法控制该类(除了对其进行猴子修补)。这或多或少是我想做的:defdo_something_creazymessage=Message.newmessage.on_save_call:do_even_more_crazy_stuffenddefdo_even_more_crazy_stuff(message)puts"Message#{message}hasbeensaved!Hallelujah!"end 最佳答案 你可以通过在创建对象后立

  7. ruby - 正则表达式 - 保存重复捕获的组 - 2

    这就是我做的a="%span.rockets#diamonds.ribbons.forever"a=a.match(/(^\%\w+)([\.|\#]\w+)+/)putsa.inspect这是我得到的#这就是我想要的#帮助?我尝试过但失败了:( 最佳答案 通常,您不能获得任意数量的捕获组,但如果您使用扫描,您可以为您想要捕获的每个标记获得一个匹配:a="%span.rockets#diamonds.ribbons.forever"a=a.scan(/^%\w+|\G[.|#]\w+/)putsa.inspect["%span","

  8. ruby-on-rails - Rails 3,在RAILS_ROOT上方显示来自本地文件系统的jpg图片 - 2

    我正在尝试找出一种方法来显示来自不在RAILS_ROOT下(在RedHat或Ubuntu环境中)的已安装文件系统的图像。我不想使用符号链接(symboliclink),因为这个应用程序实际上是通过Tomcat部署的,而当我关闭Tomcat时,Tomcat会尝试跟随符号链接(symboliclink)并删除挂载中的所有图像。由于这些文件的数量和大小,将图像放在public/images下也不是一种选择。我查看了send_file,但它只会显示一张图片。我需要在一个格式良好的页面中显示6个请求的图像。由于膨胀,我宁愿不使用Base64编码,但我不知道如何将图像数据与呈现的页面一起传递下去。

  9. ruby-on-rails - ActiveRecord:除非另有说明,否则在保存之前使所有文本字段都调用 strip - 2

    多年来,我在各种网站上遇到过各种问题,用户在字符串和文本字段的开头/结尾放置空格。有时这些会导致格式/布局问题,有时会导致搜索问题(即搜索顺序看起来不对,但实际上并非如此),有时它们实际上会使应用程序崩溃。我认为这会很有用,而不是像我过去所做的那样放入一堆before_save回调,向ActiveRecord添加一些功能以在保存之前自动调用任何字符串/文本字段上的.strip,除非我告诉它不是,例如do_not_strip:field_x,:field_y或类定义顶部的类似内容。在我去弄清楚如何做到这一点之前,有没有人看到更好的解决方案?明确一点,我已经知道我可以做到这一点:befor

  10. ruby-on-rails - 如何用 has_many 保存数据 :through - 2

    我在游戏和帐户模型之间存在多对多关系,如下所示:classAccount:destroyhas_many:games,:through=>:account_gamesendclassGame:destroyhas_many:accounts,:through=>:account_gamesendclassAccountGame现在我知道让我们说我想创建一个类似这样的记录:@account=Account.new(params[:user])@account.games但是我应该如何在执行此操作时更新AccountGame中的某些属性?假设AccountGame有一些名为score的字段

随机推荐