componentSnapshot截图后保存到HarmonyOS 鸿蒙Next相册

componentSnapshot截图后保存到HarmonyOS 鸿蒙Next相册 【标题】componentSnapshot截图后保存到相册

【设备信息】

【API版本】Api14

【DevEco Studio版本】 5.0.5.315

【问题描述】如何实现componentSnapshot截图后保存到相册

【问题相关代码】

4 回复

总的流程是先使用截图组件截图,获取截图的PixelMap对象后再进行打包处理,写入沙箱,最后调showAssetsCreationDialog方法进行保存,可以看下这个demo:

import { componentSnapshot, promptAction } from '@kit.ArkUI';
import { image } from '@kit.ImageKit';
import { photoAccessHelper } from '@kit.MediaLibraryKit';
import { BusinessError } from '@kit.BasicServicesKit';
import { fileIo, fileUri } from '@kit.CoreFileKit';
import { common } from '@kit.AbilityKit';

@Entry
@Component
struct Index {
  @State pixmap: image.PixelMap | null = null
  private scrollerForScroll: Scroller = new Scroller()
  context = this.context as common.UIAbilityContext;
  combinePath = this.context.filesDir + '/combine' + Date.now() + '.jpeg';

  @Builder
  RandomBuilder() {
    Scroll(this.scrollerForScroll) {
      Text("这是截图区域")
        .width("100%")
        .height("40%")
        .fontSize(16)
        .textAlign(TextAlign.Center)
    }
    .id('hello')
    .backgroundColor("#ffffff")
  }

  build() {
    Column() {
      Button('截图').onClick(async () => {
        await this.snap()
      })
    }
  }

  //保存到相册
  async saveImageToAlbum() {
    try {
      let phAccessHelper = photoAccessHelper.getPhotoAccessHelper(this.context)
      let srcFileUri: Array<string> = [fileUri.getUriFromPath(this.combinePath)]
      let photoCreationConfigs: Array<photoAccessHelper.PhotoCreationConfig> = [
        {
          title: '保存图片',
          fileNameExtension: 'jpeg',
          photoType: photoAccessHelper.PhotoType.IMAGE,
          subtype: photoAccessHelper.PhotoSubtype.DEFAULT
        }
      ]
      let desFileUris: Array<string> = await phAccessHelper.showAssetsCreationDialog(srcFileUri, photoCreationConfigs)
      let imageFile = fileIo.openSync(desFileUris[0], fileIo.OpenMode.CREATE | fileIo.OpenMode.READ_WRITE);
      await fileIo.copyFile(this.combinePath, imageFile.fd, 0).then(() => {
        promptAction.showToast({
          message: "已保存到相册!"
        })
      })
      fileIo.closeSync(imageFile.fd)
    } catch (err) {
    }
  }

  /**
   * 截图方法
   */
  async snap() {
    componentSnapshot.createFromBuilder(() => {
      this.RandomBuilder()
    },
      (error: Error, pixmap: image.PixelMap) => {
        if (error) {
          console.log("error: " + JSON.stringify(error))
          return;
        }

        //图片打包参数
        let packOpts: image.PackingOption = { format: "image/jpeg", quality: 100 };
        const imagePackerApi = image.createImagePacker();

        let file = fileIo.openSync(this.combinePath, fileIo.OpenMode.READ_WRITE | fileIo.OpenMode.CREATE);

        imagePackerApi.packToFile(pixmap, file.fd, packOpts).then(() => {
          imagePackerApi.release(async (err: BusinessError) => {
            if (err) {
              console.error(`Failed to release the image source instance.code ${err.code},message is ${err.message}`);
            } else {
              console.info('Succeeded in releasing the image source instance.');
              fileIo.closeSync(file.fd);
              await this.saveImageToAlbum()
            }
          })
        }).catch((error: BusinessError) => {
          console.error(`Failed to pack the image to file.code ${error.code},message is ${error.message}`);
        })

      })
  }
}

更多关于componentSnapshot截图后保存到HarmonyOS 鸿蒙Next相册的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


有用,多谢!

很好!受学了,

在HarmonyOS中,componentSnapshot API可以用于截取当前组件的截图。要将截图保存到鸿蒙Next相册,可以使用MediaLibrary API。首先,通过componentSnapshot获取截图的PixelMap对象,然后将其转换为ImageSource,最后使用MediaLibrary将图像保存到相册中。

具体步骤如下:

  1. 使用componentSnapshot获取PixelMap对象。
  2. 使用ImageSource.createFromPixelMapPixelMap转换为ImageSource
  3. 使用MediaLibrarycreateAsset方法将ImageSource保存为图片文件到相册。

代码示例如下:

import mediaLibrary from '@ohos.multimedia.mediaLibrary';
import image from '@ohos.multimedia.image';

async function saveSnapshotToGallery(pixelMap) {
  const media = mediaLibrary.getMediaLibrary();
  const imageSource = image.createImageSource(pixelMap);
  const imagePacker = image.createImagePacker();
  const options = { format: 'image/jpeg', quality: 100 };
  const arrayBuffer = await imagePacker.packing(imageSource, options);
  const date = new Date();
  const displayName = \`snapshot_\${date.getTime()}.jpg\`;
  const publicPath = await media.getPublicDirectory(mediaLibrary.DirectoryType.DIR_IMAGE);
  const fileAsset = await media.createAsset(mediaLibrary.MediaType.IMAGE, displayName, publicPath);
  await fileAsset.open('w').then(fd => {
    fs.writeSync(fd, arrayBuffer);
    fs.closeSync(fd);
  });
}

此代码将截图保存到鸿蒙Next相册中。

回到顶部