马赛克切块提速 17.6×~38×:desiredRegion 重复读盘与一次解码管线(HarmonyOS)
现象: 马赛克切块 16×16=256 块耗时 31~43 秒;真机计时每块恒定 ~94-146ms,不随块尺寸缩小而下降(16×16 块只有 4×4 块 1/16 像素,每块却一样贵)。
原因:
source.createPixelMap({desiredRegion})每次调用都重新读盘 + 解析整个源文件------256 块 = 256 次 MB 级文件 IO;输出侧优化(desiredSize 缩放)只减输出像素,减不了输入读盘。解决: 一次整图解码(只读一次盘)→
readPixelsToBuffer→ JS 内存切块(Uint8Array 行拷贝)→image.createPixelMap静态函数逐块建小图 → 打包写盘;旧路径保留 try-catch 回退。16×16:43,546→1,140ms(38×)/ 31,372→1,780ms(17.6×)。
一、先采基线再动刀
优化前先采了五档基线,找到成本结构:"每块成本不随块尺寸缩小而下降" = 每次调用含整文件级固定开销的判别信号。这个信号当场推翻了原计划的输出侧优化------瓶颈是重复读盘而非小文件 IO,主攻方向改为"消除重复读盘"。
二、新管线:一次读盘,内存切块
typescript
// 1. 一次整图解码:只读一次盘(目标宽 = areaW × density × 2)
const full = await source.createPixelMap({ desiredSize: { width: targetW } })
// 2. 像素整读进 JS 内存
await full.readPixelsToBuffer(buffer)
// 3. JS 内存切块:Uint8Array 按行拷贝出每块的像素
// 4. image.createPixelMap 静态函数逐块建小图
// (@ohos.multimedia.image.d.ts :4468;srcPixelFormat: RGBA_8888 @since 12,:3872)
const tile = await image.createPixelMap(tileBuffer, {
size: { width: tw, height: th },
srcPixelFormat: image.PixelMapFormat.RGBA_8888
})
// 5. ImagePacker 打包写盘 → file:// URI → 发射器 config.src
旧 desiredRegion 逐块解码路径保留,新管线失败自动回退旧路径。
三、五档真机数据(ms,基线 → 优化)
| 档位 | 块数 | 动态照片 | 非动态 |
|---|---|---|---|
| 4×4 | 16 | 2,814 → 349 | 2,335 → 358 |
| 6×6 | 36 | 5,228 → 535 | 4,207 → 434 |
| 8×8 | 64 | 9,673 → 689 | 6,273 → 662 |
| 12×12 | 144 | 25,096 → 564 | 13,539 → 1,089 |
| 16×16 | 256 | 43,546 → 1,140(38×) | 31,372 → 1,780(17.6×) |
四、两个结构性前提
- 一发射器一图是结构下限(坑8) :
ImageParticleParameters.src是单值 ResourceStr 非数组(particle.d.ts :385);每发射器 config 仅一个(:602),count 只能复制同一 config(:628)。"每块 = 特定图 + 特定格位"在 Particle 架构内无解,N² 发射器是马赛克方案的结构下限------64×64=4096 发射器是压测档,512×512(26 万发射器)必死 - 精确拼合要 0,0 点发射(坑10) :size 随机出生区是错位之源,详见《emitter.size 是双刃剑》
运行时裁的块还必须先落沙箱:cacheDir 免权限可写(相册写入需授权、资源目录只读),IMAGE 粒子只收 URI 字符串不收 PixelMap------管线:解码 → 切块 → ImagePacker 编 JPEG → 写 cacheDir → file:// URI 喂发射器。
标签
#HarmonyOS #ArkUI #性能优化 #PixelMap #desiredRegion #马赛克 #image
📹 效果演示 :本文的「马赛克飞散」动态效果实录会发在抖音------号 581821159(天行健之初九),截图看不出的粒子细节,视频一眼就懂。
懿路向前 · AI辅助整理 · 2026-10-12