HarmonyOS 鸿蒙Next 现有一个网络地址的图片 怎么保存到相册

发布于 1周前 作者 yibo5220 来自 鸿蒙OS

HarmonyOS 鸿蒙Next 现有一个网络地址的图片 怎么保存到相册

现有一个网络地址的图片, 怎么保存到相册

2 回复

可以使用http模块下的request方法下载图片,并在该方法的回调函数中保存到相册,核心代码如下:

可以使用http模块下的request方法下载图片,并在该方法的回调函数中保存到相册,核心代码如下:
import { http } from '[@kit](/user/kit).NetworkKit'

import { BusinessError } from '[@kit](/user/kit).BasicServicesKit';

import ResponseCode from '[@ohos](/user/ohos).net.http';

import { photoAccessHelper } from '[@kit](/user/kit).MediaLibraryKit';

import fs from '[@ohos](/user/ohos).file.fs';

[@Entry](/user/Entry)
[@Component](/user/Component)
struct Index {
 loadImageWithUrl(url: string) {

   // 使用request下载图片并在回调函数中保存图片到相册

   http.createHttp().request(url,

     {

       method: http.RequestMethod.GET,

       connectTimeout: 60000,

       readTimeout: 60000

     },

     async (error: BusinessError, data: http.HttpResponse) => {

       if (error) {

         console.error(`http reqeust failed with. Code: ${error.code}, message: ${error.message}`);

       } else {

         if (ResponseCode.ResponseCode.OK === data.responseCode) {

           let imageBuffer: ArrayBuffer = data.result as ArrayBuffer;

           try {

             // 获取相册路径

             const context = getContext(this);

             let helper = photoAccessHelper.getPhotoAccessHelper(context);

             let uri = await helper.createAsset(photoAccessHelper.PhotoType.IMAGE, 'jpg')

             let file = await fs.open(uri, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE)

             // 写入文件

             await fs.write(file.fd, imageBuffer);

             // 关闭文件

             await fs.close(file.fd);

           } catch (error) {

             console.error("error is " + JSON.stringify(error))

           }

         } else {

           console.error("error occurred when image downloaded!")

         }

       }

     })

 }

 ......
}
复制

ohos.permission.INTERNET

ohos.permission.WRITE_IMAGEVIDEO

ohos.permission.WRITE_IMAGEVIDEO权限级别是system_basic,ACL使能是true,请按normal等级的应用申请权限。

申请权限步骤如下:

当前可通过DevEco Studio完成ACL方式跨级别申请权限,但该方法仅用于应用调试阶段使用,不可用于发布上架应用市场。如果需要开发商用版本的应用,请在对应的应用市场进行发布证书和Profile文件的申请。

参考链接:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/app-permission-mgmt-overview-V5

ACL权限需要申请,参考文档申请使用受限权限:

应用/元服务签名-DevEco Studio - 华为HarmonyOS开发者

也可以考虑通过安全控件savebutton创建媒体资源,不需要WRITE_IMAGEVIDEO权限。

参考链接:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/photoaccesshelper-savebutton-V5

SaveButton().onClick(async (event: ClickEvent, result: SaveButtonOnClickResult) => {

if (result == SaveButtonOnClickResult.SUCCESS) {

try {

  const context = getContext(this);

  let helper = photoAccessHelper.getPhotoAccessHelper(context); // onClick触发后5秒内通过createAsset接口创建图片文件,5秒后createAsset权限收回。

  let uri = await helper.createAsset(photoAccessHelper.PhotoType.IMAGE, 'jpg'); // 使用uri打开文件,可以持续写入内容,写入过程不受时间限制

  let file = await fs.open(uri, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);

  try {

    context.resourceManager.getMediaContent($r('app.media.app_icon').id, 0)

      .then(async value => {

        let media = value.buffer; // 写到媒体库文件中

        await fs.write(file.fd, media);

        await fs.close(file.fd);

        AlertDialog.show({ message: '已保存至相册!' });

      });

  } catch (err) {

    console.error("error is " + JSON.stringify(err))

  }

} catch (error) {

  console.error("error is " + JSON.stringify(error));

}

} else {

AlertDialog.show({ message: "设置权限失败" })

}

}) 复制 参考如下demo:

import { http } from ‘@kit.NetworkKit’;

import { promptAction } from ‘@kit.ArkUI’;

import { BusinessError } from ‘@kit.BasicServicesKit’;

import ResponseCode from ‘@ohos.net.http’;

import { image } from ‘@kit.ImageKit’;

import { photoAccessHelper } from ‘@kit.MediaLibraryKit’;

import { common } from ‘@kit.AbilityKit’;

import fs from ‘@ohos.file.fs’;

@Entry

@Component

struct Index {

@State imageBuffer: ArrayBuffer | undefined = undefined; // 图片ArrayBuffer

@State image: PixelMap | undefined = undefined;

@State photoAccessHelper: photoAccessHelper.PhotoAccessHelper | undefined = undefined; // 相册模块管理实例

async aboutToAppear(): Promise<void> {

this.getPicture();

}

build() {

Row() {

  Column() {

    Image(this.image)

      .objectFit(ImageFit.Contain)

      .width('50%')

    SaveButton()

      .onClick(async () => {

        if (this.imageBuffer !== undefined) {

          await this.saveImage(this.imageBuffer);

          promptAction.showToast({

            message: "成功",

            duration: 2000

          })

        }

      })

  }.width('100%')

}.height('100%')

}

/**

  • 通过http的request方法从网络下载图片资源

*/

async getPicture() {

http.createHttp()// 显示网络图片的地址

  .request('https://copyright.bdstatic.com/vcg/creative/cc9c744cf9f7c864889c563cbdeddce6.jpg',

    (error: BusinessError, data: http.HttpResponse) => {

      if (error) {

        // 下载失败时弹窗提示检查网络,不执行后续逻辑

        promptAction.showToast({

          message: "请求失败",

          duration: 2000

        })

        console.error('-----' + error.message)

        return;

      }

      this.transcodePixelMap(data);

      // 判断网络获取到的资源是否为ArrayBuffer类型

      if (data.result instanceof ArrayBuffer) {

        this.imageBuffer = data.result as ArrayBuffer;

      }

    }

  )

}

/**

  • 使用createPixelMap将ArrayBuffer类型的图片装换为PixelMap类型

  • @param data:网络获取到的资源

*/

transcodePixelMap(data: http.HttpResponse) {

if (ResponseCode.ResponseCode.OK === data.responseCode) {

  const imageData: ArrayBuffer = data.result as ArrayBuffer;

  // 通过ArrayBuffer创建图片源实例。

  const imageSource: image.ImageSource = image.createImageSource(imageData);

  const options: image.InitializationOptions = {

    'alphaType': 0, // 透明度

    'editable': false, // 是否可编辑

    'pixelFormat': 3, // 像素格式

    'scaleMode': 1, // 缩略值

    'size': { height: 100, width: 100 }

  }; // 创建图片大小

  // 通过属性创建PixelMap

  imageSource.createPixelMap(options).then((pixelMap: PixelMap) => {

    this.image = pixelMap;

  });

}

}

/**

  • 保存ArrayBuffer到图库

  • @param buffer:图片ArrayBuffer

  • @returns

*/

async saveImage(buffer: ArrayBuffer | string): Promise<void> {

const context = getContext(this) as common.UIAbilityContext; // 获取getPhotoAccessHelper需要的context

const helper = photoAccessHelper.getPhotoAccessHelper(context); // 获取相册管理模块的实例

const uri = await helper.createAsset(photoAccessHelper.PhotoType.IMAGE, 'jpg'); // 指定待创建的文件类型、后缀和创建选项,创建图片或视频资源

const file = await fs.open(uri, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);

await fs.write(file.fd, buffer);

await fs.close(file.fd);

}

}

更多关于HarmonyOS 鸿蒙Next 现有一个网络地址的图片 怎么保存到相册的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


在HarmonyOS鸿蒙Next系统中,要将网络地址的图片保存到相册,可以按照以下步骤操作:

  1. 获取图片数据: 使用网络请求库(如OkHttp或系统提供的网络请求API)获取网络地址的图片数据,通常是以字节数组(byte[])的形式存在。

  2. 创建Bitmap对象: 利用鸿蒙系统提供的图片处理类(如ImageProvider或相关API),将字节数组转换成Bitmap对象。

  3. 保存Bitmap到相册: 使用鸿蒙的媒体存储API,将Bitmap对象保存到设备的相册中。这通常涉及到申请存储权限,然后利用媒体存储的写入接口进行保存。

  4. 处理权限: 确保应用已获取存储权限,否则在保存图片时会失败。鸿蒙系统提供了动态权限申请的API,可以在运行时请求用户授权。

示例代码(伪代码,具体API需查阅鸿蒙开发文档):

// 伪代码示例,具体API需替换为鸿蒙系统提供的对应API
byte[] imageData = fetchImageDataFromUrl(imageUrl);
Bitmap bitmap = convertByteArrayToBitmap(imageData);
saveBitmapToAlbum(bitmap, context);

注意:以上步骤中的API名称和功能为示意性描述,实际开发时需参考鸿蒙系统的官方文档。

如果问题依旧没法解决请联系官网客服,官网地址是:https://www.itying.com/category-93-b0.html

回到顶部