当前位置: 首页 > news >正文

HarmonyOS 图片与 Base64 互转:ImageUtil pixelMapToBase64Str 实战

文章目录

    • 前言
      • packingFromPixelMap:PixelMap 打包成二进制
      • pixelMapToBase64Str:PixelMap 转 Base64 字符串
      • base64ToPixelMap:Base64 转回 PixelMap
      • packingFromImageSource:从 ImageSource 打包
      • 理解 PNG vs JPEG 的字节大小差异
      • 写在最后

前言

近期发现一款很有意思的HarmonyOS 三方库, 地址 @pura/harmony-utils(V1.4.0) , 作者是"桃花镇童长老", 我这里也是直接通过该作者公布的源码进行案例编写进行,写了到目前写了一部分demo ,感觉确实很有帮助,这里呢也是开始写一个系列的演示demo 供大家参考。如有帮助可以在OpenHarmony中进行下载安装进行使用哦

案例demo导航展示

↓↓↓↓↓↓接下来言归正传 ↓↓↓↓

图片和 Base64 互转是一个高频需求:上传图片到后台接口时可能需要传 Base64 字符串,从接口拿到 Base64 数据要在界面上显示时,需要先转回 PixelMap。

这篇把pixelMapToBase64Strbase64ToPixelMappackingFromPixelMap这几个方法讲清楚。

packingFromPixelMap:PixelMap 打包成二进制

在转 Base64 之前,先理解packingFromPixelMap——它是很多图片操作的基础步骤。

packingFromPixelMap把 PixelMap 编码成指定格式的图片二进制数据(ArrayBuffer):

// 打包成 PNGconstpm=awaitthis.makeTestPixelMap(180,100,220,80,80);constpackOpts:image.PackingOption={format:'image/png',quality:100};constbuf=awaitImageUtil.packingFromPixelMap(pm,packOpts);this.addLog(`packingFromPixelMap(png):${buf.byteLength}bytes`);
// 打包成 JPEG,质量 80constpm=awaitthis.makeTestPixelMap(50,100,200,80,80);constpackOpts:image.PackingOption={format:'image/jpeg',quality:80};constbuf=awaitImageUtil.packingFromPixelMap(pm,packOpts);this.addLog(`packingFromPixelMap(jpeg,q=80):${buf.byteLength}bytes`);

PackingOption的两个关键字段:

  • format:图片格式,'image/png'(无损)或'image/jpeg'(有损)
  • quality:质量(1-100),PNG 格式下这个值不影响文件大小,JPEG 下影响明显

一般规律:同样内容的图片,JPEG 文件比 PNG 小很多,但 JPEG 有压缩损失

pixelMapToBase64Str:PixelMap 转 Base64 字符串

这个方法封装了"打包 + Base64 编码"两步,直接给你一个 Base64 字符串:

// PNG 格式constpm=awaitthis.makeTestPixelMap(100,200,100,50,50);constb64=awaitImageUtil.pixelMapToBase64Str(pm,'image/png');this.previewBase64=b64.substring(0,60)+'...';this.addLog(`pixelMapToBase64Str(png):${b64.length}chars`);
// JPEG 格式constpm=awaitthis.makeTestPixelMap(200,150,50,60,60);constb64=awaitImageUtil.pixelMapToBase64Str(pm,'image/jpeg');this.addLog(`pixelMapToBase64Str(jpeg):${b64.length}chars`);

两个参数:

  1. PixelMap 对象
  2. 图片格式字符串('image/png''image/jpeg'

返回的是纯 Base64 字符串(不含data:image/png;base64,前缀)。

如果你要在 WebView 的 H5 页面里展示,需要自己拼接前缀:

constdataUrl=`data:image/png;base64,${b64}`;

base64ToPixelMap:Base64 转回 PixelMap

方向反过来,把 Base64 字符串解码成 PixelMap:

// 先把 PixelMap 转成 Base64constpm=awaitthis.makeTestPixelMap(255,128,0,40,40);constb64=awaitImageUtil.pixelMapToBase64Str(pm,'image/png');// 再把 Base64 转回 PixelMapconstrestored=awaitImageUtil.base64ToPixelMap(b64);this.previewPixelMap=restored;this.previewLabel='base64 → PixelMap (橙色40×40)';constinfo=restored.getImageInfoSync();this.addLog(`base64ToPixelMap:${info.size.width}×${info.size.height}`);

还原后的 PixelMap 尺寸信息应该和原来一致(40×40)。

这个方向的典型场景:后台接口返回 Base64 格式的图片,需要在Image组件里展示

packingFromImageSource:从 ImageSource 打包

packingFromImageSourcepackingFromPixelMap功能类似,区别是输入是ImageSource而不是PixelMap

// 先把 PixelMap 打包成 PNG,再创建 ImageSourceconstpm=awaitthis.makeTestPixelMap(200,200,50,60,60);constpngBuf=awaitImageUtil.packingFromPixelMap(pm,{format:'image/png',quality:100});constsrc=ImageUtil.createImageSource(pngBuf);// 再从 ImageSource 打包成 JPEGconstopts:image.PackingOption={format:'image/jpeg',quality:90};constbuf=awaitImageUtil.packingFromImageSource(src,opts);this.addLog(`packingFromImageSource:${buf.byteLength}bytes`);

这个用法的场景:从文件或网络得到了原始图片数据(非 PixelMap),需要转换格式。比如你有一个 PNG 文件的 ArrayBuffer,想转成 JPEG,就走这个流程:createImageSource(pngBuffer)packingFromImageSource(src, {format: 'image/jpeg'})

理解 PNG vs JPEG 的字节大小差异

演示代码展示了同一张图片打包成不同格式后的大小对比,这是理解图片压缩的直观方式。

一般来说:

  • PNG:无损压缩,文件较大,适合截图、图标、需要透明度的图
  • JPEG:有损压缩,文件较小,适合照片、自然图像
  • quality 参数:仅对 JPEG 有效,数值越低文件越小,画质越差

写在最后

图片和 Base64 互转就两个核心方法:

  • pixelMapToBase64Str(pm, format):PixelMap → Base64 字符串
  • base64ToPixelMap(b64):Base64 字符串 → PixelMap

packingFromPixelMap是它们的底层支撑,理解了打包过程,再看压缩相关的 API 就容易了。

下篇讲图片压缩:如何控制图片大小不超过目标体积。

http://www.jsqmd.com/news/905315/

相关文章:

  • 云南8日深度游导游排名2026:路线安排、近期评价和价格 - 随峰国旅
  • 观察使用 Taotoken Token Plan 后月度 API 开支的显著变化
  • GitHub访问慢到抓狂?这个免费插件让下载速度提升80倍的终极解决方案
  • 深入解析JoyAI-LLM-Flash-FP8的MoE架构:为什么480亿参数只激活30亿?
  • 2026云南五天四晚导游口碑榜:热门路线和价格透明度参考 - 随峰国旅
  • 打破华为健康数据壁垒:3步实现跨平台运动数据自由迁移
  • linux基础随心记三-四剑客
  • 排队免单为什么能让商家愿意主动参与?拆开看是这个逻辑
  • 别再只盯着储能了!聊聊虚拟电厂(VPP)如何用‘调度算法’盘活你家屋顶的光伏和充电桩
  • Obsidian与AI知识管理
  • 3分钟掌握:PowerShell自动化部署Microsoft Office完整指南
  • 从0到1精通InternLM2.5-7B-Chat-1M:新手必看的5个核心功能与实用技巧
  • BsMax:让Blender变成你最熟悉的3D创作伙伴
  • 高管求职渠道服务商实测:专业度与资源力对比评测 - 得赢
  • 5分钟掌握猫抓:浏览器资源嗅探工具完全使用指南
  • ppf-contact-solver并行计算优化:如何利用多GPU加速大规模物理模拟
  • BMRetriever-7B-openmind安全与隐私考量:医疗数据处理的7个最佳实践
  • 基于Micro:bit与PIR传感器的运动检测报警系统制作全攻略
  • Arduino综合实验:电位器同步控制直流电机与RGB LED
  • C++:构造函数,析构函数详解
  • 无损音乐下载神器:Qobuz-DL完整使用指南
  • 观察Taotoken平台旗舰模型更新速度与API服务稳定性的个人体验
  • 2026国产水质五参数在线监测仪十大品牌深度评测与选型实战指南 - 仪表品牌榜
  • 3分钟掌握免费AI图片高清修复:让模糊照片秒变清晰的专业工具
  • ThinkPad风扇终极控制指南:TPFanCtrl2让你的笔记本告别噪音烦恼
  • Relight项目核心技术剖析:LoRA微调在图像重照明中的应用
  • 基于Arduino与MAX7219的LED点阵时钟:从SPI驱动到3D打印外壳全解析
  • NPU加速实战:如何在华为昇腾平台上快速运行h2ogpt-gm-oasst1-en-2048-falcon-7b-v3模型
  • ControlNet-OpenPose-SDXL-1.0最佳实践:优化提示词与参数设置的7个秘诀
  • 干枯发质必入:高保湿发膜推荐TOP10 - 速递信息