【鸿蒙】web 加载vue dist 包里的 html

下面给你「带进度条 + 判断 index.html 已存在则跳过解压」的完整可运行版本,直接替换即可通过 ArkTS 校验。

思路

  1. 先判断 www/dist/index.html 是否存在,存在就直接返回。
  2. 解压前把 unzipFileonProgress 回调接到 @State progress 上,实时刷新 Progress 组件。
  3. 解压完成后隐藏进度条,自动加载本地 html。
ts 复制代码
import web_webview from '@ohos.web.webview';
import fs from '@ohos.file.fs';
import zlib from '@ohos.zlib';
import { Context } from '@ohos.abilityAccessCtrl';

@Entry
@Component
struct WebLoadLocalHtml {
  private webCtrl = new web_webview.WebviewController();
  @State wwwPath: string = '';
  @State showProgress: boolean = false;
  @State progress: number = 0;          // 0~100

  /* 主逻辑:带进度解压 */
  private async copyAndUnzip(context: Context): Promise<string> {
    const wwwDir = context.filesDir + '/www';
    const targetHtml = wwwDir + '/dist/index.html';

    // 1. 已存在则直接返回
    try {
      fs.accessSync(targetHtml);
      console.info('index.html 已存在,跳过解压');
      return wwwDir;
    } catch { /* 不存在就继续 */ }

    // 2. 准备目录
    try { fs.mkdirSync(wwwDir); } catch {}

    // 3. 拷贝 zip
    const rawBytes = context.resourceManager.getRawFileContentSync('dist.zip');
    const zipPath = wwwDir + '/dist.zip';
    this.writeFileOnlyOne(zipPath, rawBytes);

    // 4. 带进度解压
    this.showProgress = true;
    this.progress = 0;

// 3. 解压(补齐第 3 个参数)
let options: zlib.Options = {
level: zlib.CompressLevel.COMPRESS_LEVEL_DEFAULT_COMPRESSION,
memLevel: zlib.MemLevel.MEM_LEVEL_DEFAULT,
strategy: zlib.CompressStrategy.COMPRESS_STRATEGY_DEFAULT_STRATEGY
};
zlib.unzipFile(destZip, wwwDir, options).then(()=>{
fs.unlinkSync(destZip);
this.wwwPath=wwwDir;
this.showProgress = false;
});

return wwwDir;
}

/* 写文件助手 */
private writeFileOnlyOne(filePath: string, data: Uint8Array) {
try { if (fs.accessSync(filePath)) return; } catch {}
const f = fs.openSync(filePath, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);
fs.writeSync(f.fd, data.buffer);
fs.closeSync(f);
}

/* 生命周期 */
async aboutToAppear() {
this.wwwPath = await this.copyAndUnzip(getContext());
}

build() {
Stack() {
Column() {
Button('加载 html')
.onClick(() => {
this.webCtrl.loadUrl(`file://${this.wwwPath}/dist/index.html`);
})

Web({ src: `file://${this.wwwPath}/dist/index.html`, controller: this.webCtrl })
.javaScriptAccess(true)
.fileAccess(true)
.onPageEnd(() => console.info('Vue 页面加载完成'))
.width('100%')
.height('100%')
}

/* 进度条遮罩 */
if (this.showProgress) {
Column() {
Progress({ value: this.progress, total: 100, type: ProgressType.Linear })
.width('80%')
Text(`解压中...${this.progress}%`)
}
.width('100%')
.height('100%')
.backgroundColor('#80000000')
.justifyContent(FlexAlign.Center)
}
}


}
}

使用要点

  • 判断的是 www/dist/index.html 而不是 www,避免目录存在但文件没写完的误判。
  • 进度条用 Stack 盖在 Web 组件上,解压完自动消失。
相关推荐
代码搬运媛8 小时前
Jest 测试框架详解与实现指南
前端
counterxing9 小时前
我把 Codex 里的 Skills 做成了一个 MCP,还支持分享
前端·agent·ai编程
wangqiaowq9 小时前
windows下nginx的安装
linux·服务器·前端
nashane9 小时前
HarmonyOS 6学习:CapsLock键失效诊断与长截图完整实现指南
学习·华为·harmonyos
之歆9 小时前
DAY_12JavaScript DOM 完全指南(二):实战与性能篇
开发语言·前端·javascript·ecmascript
发现一只大呆瓜9 小时前
Vite凭什么这么快?3分钟带你彻底搞懂 Vite 热更新的幕后黑手
前端·面试·vite
Maimai1080810 小时前
React如何用 @microsoft/fetch-event-source 落地 SSE:比原生 EventSource 更灵活的实时推送方案
前端·javascript·react.js·microsoft·前端框架·reactjs·webassembly
candyTong10 小时前
Claude Code 的 Edit 工具是怎么工作的
javascript·后端·架构
cen__y10 小时前
Linux12(Git01)
linux·运维·服务器·c语言·开发语言·git
richard_yuu11 小时前
鸿蒙心理测评模块实战|PHQ-9/GAD7双量表答题、实时计分与结果本地化存储
华为·harmonyos