HarmonyOS鸿蒙Next中组件截图分享

HarmonyOS鸿蒙Next中组件截图分享

需求描述背景

将鸿蒙布局内容截图分享到微信,但是不想初始化微信sdk,使用鸿蒙系统分享

实现步骤

2.1 组件截图获取PixelMap

核心api
getComponentSnapshot

@State pixmap: image.PixelMap | undefined = undefined
viewId = 'root';
build() {
...
  Column() {
    Text("分享内容1").fontSize(50).fontColor(Color.White)
  }
  .id(this.viewId)
...
 }

shareView() {
  // 获取组件截图
  this.getUIContext().getComponentSnapshot().get(this.viewId, async (error: Error, pixmap: image.PixelMap) => {
    if (error) {
      console.log("error: " + JSON.stringify(error))
      return;
    }
    this.pixmap = pixmap

  }, { scale: 1, waitUntilRenderFinished: true })
}

2.2 将PixelMap转图片保存到沙箱目录

保存图片或视频到沙箱指定目录

imagePath = getContext().filesDir + 'share.jpg';
// 将 pixelMap 转图片格式
transferPixelMap2Buffer(pixelMap: image.PixelMap): Promise<ArrayBuffer> {
  return new Promise((resolve, reject) => {
    let packOpts: image.PackingOption = { format: "image/jpeg", quality: 98 }
    // 创建ImagePacker实例
    const imagePackerApi = image.createImagePacker()
    imagePackerApi.packing(pixelMap, packOpts).then((buffer: ArrayBuffer) => {
      resolve(buffer)
    }).catch((err: BusinessError) => {
      reject()
    })
  })
}
// 保存图片到沙箱目录
async savePixmap2SystemFileManager() {
  if (!this.pixmap) {
    return
  }
  const imgBuffer = await this.transferPixelMap2Buffer(this.pixmap)
  const file = fs.openSync(this.imagePath, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);
  await fs.write(file.fd, imgBuffer)
  await fs.close(file.fd)
}

2.3 系统分享图片

分享图片api

await this.savePixmap2SystemFileManager()
let utdTypeId = utd.getUniformDataTypeByFilenameExtension('.jpg', utd.UniformDataType.IMAGE);
let shareData: systemShare.SharedData = new systemShare.SharedData({
  utd: utdTypeId,
  uri: fileUri.getUriFromPath(this.imagePath),
});
// 进行分享面板显示
let controller: systemShare.ShareController = new systemShare.ShareController(shareData);
let context = getContext(this) as common.UIAbilityContext;
controller.show(context, {
  selectionMode: systemShare.SelectionMode.SINGLE,
  previewMode: systemShare.SharePreviewMode.DETAIL,
}).then(() => {
  console.info('ShareController show success.');
}).catch((error: BusinessError) => {
  console.error(`ShareController show error. code: ${error.code}, message: ${error.message}`);
});

完整代码

// index.ets
import { image } from '@kit.ImageKit';
import { uniformTypeDescriptor as utd } from '@kit.ArkData';
import { systemShare } from '@kit.ShareKit';
import { common } from '@kit.AbilityKit';
import { fileUri } from '@kit.CoreFileKit';
import { BusinessError } from '@kit.BasicServicesKit';
import fs from '@ohos.file.fs';

@Entry
@Component
struct Index {
  @State pixmap: image.PixelMap | undefined = undefined
  imagePath = getContext().filesDir + 'share.jpg';
  viewId = 'root';

  build() {
    Column() {
      Column() {
        Text("分享内容1").fontSize(50).fontColor(Color.White)
        Text("分享内容2").fontSize(50).fontColor(Color.White)
        Text("分享内容3").fontSize(50).fontColor(Color.White)
        Text("分享内容4").fontSize(50).fontColor(Color.White)
        Text("分享内容5").fontSize(50).fontColor(Color.White)
        Text("分享内容6").fontSize(50).fontColor(Color.White)
        Text("分享内容7").fontSize(50).fontColor(Color.White)
      }
      .backgroundColor(Color.Green)
      .id(this.viewId)
      .margin(30)
      .padding(10)
      .borderRadius(10)

      Button("系统分享组件截图")
        .width('90%')
        .onClick(() =>{
          this.shareView()
        })
    }
    .height('100%')
    .width('100%')
  }

  // 保存图片到沙箱目录
  async savePixmap2SystemFileManager() {
    if (!this.pixmap) {
      return
    }
    const imgBuffer = await this.transferPixelMap2Buffer(this.pixmap)
    const file = fs.openSync(this.imagePath, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);
    await fs.write(file.fd, imgBuffer)
    await fs.close(file.fd)
  }

  // 将 pixelMap 转成图片格式
  transferPixelMap2Buffer(pixelMap: image.PixelMap): Promise<ArrayBuffer> {
    return new Promise((resolve, reject) => {
      let packOpts: image.PackingOption = { format: "image/jpeg", quality: 98 }
      // 创建ImagePacker实例
      const imagePackerApi = image.createImagePacker()
      imagePackerApi.packing(pixelMap, packOpts).then((buffer: ArrayBuffer) => {
        resolve(buffer)
      }).catch((err: BusinessError) => {
        reject()
      })
    })
  }

  shareView() {
    // 获取组件截图
    this.getUIContext().getComponentSnapshot().get(this.viewId, async (error: Error, pixmap: image.PixelMap) => {
      if (error) {
        console.log("error: " + JSON.stringify(error))
        return;
      }
      this.pixmap = pixmap
      await this.savePixmap2SystemFileManager()
      let utdTypeId = utd.getUniformDataTypeByFilenameExtension('.jpg', utd.UniformDataType.IMAGE);
      let shareData: systemShare.SharedData = new systemShare.SharedData({
        utd: utdTypeId,
        uri: fileUri.getUriFromPath(this.imagePath),
      });
      // 进行分享面板显示
      let controller: systemShare.ShareController = new systemShare.ShareController(shareData);
      let context = getContext(this) as common.UIAbilityContext;
      controller.show(context, {
        selectionMode: systemShare.SelectionMode.SINGLE,
        previewMode: systemShare.SharePreviewMode.DETAIL,
      }).then(() => {
        console.info('ShareController show success.');
      }).catch((error: BusinessError) => {
        console.error(`ShareController show error. code: ${error.code}, message: ${error.message}`);
      });
    }, { scale: 1, waitUntilRenderFinished: true })
  }
}

更多关于HarmonyOS鸿蒙Next中组件截图分享的实战教程也可以访问 https://www.itying.com/category-93-b0.html

2 回复

在HarmonyOS Next中,可通过调用CaptureControllercaptureToFilecaptureToMemory方法实现组件截图。需先获取目标组件的Surface对象,创建CaptureController实例并配置参数(如格式、质量)。调用截图方法后,结果将保存至指定路径或返回内存数据。注意需在UI线程操作并处理权限问题。

更多关于HarmonyOS鸿蒙Next中组件截图分享的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


在HarmonyOS Next中实现组件截图分享功能,代码实现思路清晰完整。主要流程包括:

  1. 使用getComponentSnapshot()获取组件截图PixelMap
  2. 通过ImagePacker将PixelMap转换为JPEG格式
  3. 保存图片到沙箱目录
  4. 调用系统分享接口分享图片

关键点说明:

  • getComponentSnapshot()需要指定组件id和参数(scale/waitUntilRenderFinished)
  • ImagePacker支持设置图片格式和质量参数
  • 分享时需通过UniformDataType指定文件类型为IMAGE
  • 使用ShareController调起系统分享面板

代码中已正确处理了错误情况和异步操作,可以直接参考使用。注意要添加相关权限声明(ohos.permission.READ_MEDIA等)。

回到顶部