概览:本文从Preview Kit的能力范围、使用约束讲起,逐步演示本地TXT文件预览流程,并重点剖析网络PDF文件的完整处理链路:配置网络权限 → 下载资源至沙箱(≤5MB)→ 构造PreviewInfo → 调用openPreview启动预览。
文件预览概述
Preview Kit(文件预览服务)为应用提供便捷的文件快速预览和文件打开加速能力。应用可以通过Preview Kit提供的预览API,对图片、视频、音频、文本、html进行预览查看,满足绝大多数办公开发的需求,包括:
go
1、预览展示:呈现文件的基本内容,如文本、图片等,支持选中多文件,在预览列表切换显示。
2、文件分享:将文件以分享的形式传给另一个软件。
3、使用其他软件打开:使用预览打开时,会获取到该文件类型的默认打开软件,然后点击"使用其他应用打开"进行跳转。
4、图片翻转放大:在非2in1设备时,预览能够对图片进行旋转放大等处理。
文件预览约束与限制:
bash
1、支持的国家和地区
➢ 当前Preview Kit仅支持中国境内(不包含中国香港、中国澳门、中国台湾)。
2、支持的设备
➢ 当前Preview Kit支持模拟器开发,但与真机存在部分能力差异。
➢ 模拟器不支持.pdf/.pptx/.xlsx/.docx文件格式预览。
文件预览模式
文件预览所支持的文件类型
| 类型 | 文件后缀 | mimeType类型 |
|---|---|---|
| 文本 | txt、cpp、c、h、java、xhtml、xml | text/plain、text/x-c++src、text/x-csrc、text/x-chdr、text/x-java、application/xhtml+xml、text/xml |
| 网页 | html、htm | text/html |
| 图片 | jpg、png、gif、webp、bmp、svg | image/jpeg、image/png、image/gif、image/webp,image/bmp、image/svg+xml |
| 音频 | m4a、aac、mp3、ogg、wav | audio/mp4a-latm、audio/aac、audio/mpeg、audio/ogg、audio/x-wav |
| 视频 | mp4、mkv、ts | video/mp4、video/x-matroska、video/mp2ts |
| 文件夹 | 无 | 无 |
| 文档 | application/pdf起始版本: 5.0.0(12) | |
| Office文档 | doc、docx、xls、xlsx、ppt、pptx、csv、ofd | application/msword、application/vnd.openxmlformats-officedocument.wordprocessingml.document、application/vnd.ms-excel、application/vnd.openxmlformats-officedocument.spreadsheetml.sheet、application/vnd.ms-powerpoint、application/vnd.openxmlformats-officedocument.presentationml.presentation、text/csv、general.ofd起始版本: 5.0.0(12) |
不同文件预览效果

不同设备类型的预览模式
模态窗:和父窗口绑定,模态窗存在时父窗口不可移动,不可操作,模态窗永远置于父窗口前面。
应用窗:应用窗口,可以通过AMS启动。
AMS:AbilityManagerService,用于协调各Ability运行关系、及对生命周期进行调度的系统服务。

文件预览基本流程实践
文件预览实践注意事项
1、当前Preview Kit仅支持跳出应用进行文件的预览,暂不支持应用内预览。
2、Office类型文档预览借助WPS提供的能力来实现,在预览文档类型文件时会存在"WPS提供技术支持"、"使用WPS Office打开"等相关字样。
3、当前Preview Kit暂不支持安全定制能力,包括禁止截录屏、屏蔽其他应用打开入口、屏蔽分享入口等安全预览能力。
4、当前Preview Kit需要调用方存在对应uri的转授权能力,从而让预览获得该文件的访问权限来正常读取文件。
创建待预览资源、预览目标文件资源
typescript
import { common } from '@kit.AbilityKit';
import { fileIo as fs, fileUri } from '@kit.CoreFileKit'
import { filePreview } from '@kit.PreviewKit';
@Entry
@Component
struct Index {
private context = this.getUIContext().getHostContext() as common.UIAbilityContext;
private fileName: string = 'preview_info.txt'
@State uri: string = ''
build() {
Column({ space: 10 }) {
Button('创建待预览资源')
.onClick(() => {
// 使用CoreFileKit提供的文件读写能力,在应用沙箱路径中生成及获取待预览文件资源。以txt文本文件预览流程为例。
let filesDir = this.context.filesDir
let filePath = filesDir + '/' + this.fileName
let file: fs.File = fs.openSync(filePath, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE)
let uri = fileUri.getUriFromPath(filePath)
this.uri = uri
let str: string = 'hello word'
let writeLen = fs.writeSync(file.fd, str)
fs.closeSync(file)
})
Button('预览目标文件资源')
.onClick(async () => {
// 1、使用canPreview判断资源是否可预览。
let result = await filePreview.canPreview(this.context, this.uri)
if (result) {
// 2、构造待预览文件资源的标准数据对象PreviewInfo。
let previewInfo: filePreview.PreviewInfo = {
title: this.fileName,
uri: this.uri,
mimeType: 'text/plain'
}
// 3、使用openPreview完成文件预览。
filePreview.openPreview(this.context, previewInfo)
} else {
this.getUIContext().getPromptAction().showToast({
message: 'File cannot be previewed'
})
}
})
}
.height('100%')
.width('100%')
}
}
案例:网络PDF文件预览
网络权限配置及资源限制条件
json
1、预览服务并不能直接预览在线PDF文件,需要将待预览PDF资源下载至本地沙箱。
2、需配置requestPermissions网络请求权限,否则会导致网络资源下载失败。
3、待预览PDF资源不能大于5M,否则可能报:2300023 向磁盘/应用程序写入接收数据失败。
"requestPermissions": [
{
"name": "ohos.permission.INTERNET"
},
]
封装网络资源下载方法、封装文件预览函数
typescript
import { fileIo as fs, fileUri } from '@kit.CoreFileKit';
import { common } from '@kit.AbilityKit';
import { filePreview } from '@kit.PreviewKit';
import { http } from '@kit.NetworkKit';
/**
* 下载PDF
* 1、基于http模块封装网络资源下载方法。
* 2、将下载到的PDF资源,写入本地沙箱路径。
*/
export async function downloadPdf(context: common.UIAbilityContext, url: string, fileName: string): Promise<string> {
const httpRequest = http.createHttp();
const filePath = `${context.filesDir}/${fileName}`;
try {
const response = await httpRequest.request(url, {
expectDataType: http.HttpDataType.ARRAY_BUFFER
});
if (response.responseCode === 200 && response.result instanceof ArrayBuffer) {
// 写入文件
const file = fs.openSync(filePath, fs.OpenMode.CREATE | fs.OpenMode.READ_WRITE);
fs.writeSync(file.fd, response.result);
fs.closeSync(file);
return filePath;
} else {
throw new Error('下载失败');
}
} catch (error) {
console.error('PDF下载出错:', JSON.stringify(error));
throw new Error('PDF下载出错');
} finally {
httpRequest.destroy();
}
}
/**
* 预览PDF
* 1、读取本地沙箱中的PDF资源,注意mimeType需要跟待预览文件保持一致。
* 2、使用canPreview判断可预览性,使用openPreview实现预览。
*/
export async function previewLocalPdf(context: common.UIAbilityContext, filePath: string) {
try {
if (context === undefined) {
return;
}
let file: fs.File = fs.openSync(filePath, fs.OpenMode.READ_WRITE | fs.OpenMode.CREATE);
let uri = fileUri.getUriFromPath(filePath);
fs.closeSync(file);
let result = await filePreview.canPreview(context, uri);
if (result) {
let previewInfo: filePreview.PreviewInfo = {
title: 'preview',
uri: uri,
mimeType: 'application/pdf'
};
filePreview.openPreview(context, previewInfo);
} else {
console.log('File cannot be previewed.');
}
} catch (err) {
console.error('openPreview error');
}
}
页面中调用预览方法
typescript
import { downloadPdf, previewLocalPdf } from '../utils/previewUtil';
import { common } from '@kit.AbilityKit';
@Entry
@Component
struct Index {
@State message: string = 'Hello World';
context = this.getUIContext().getHostContext() as common.UIAbilityContext;
url =
'https://communityfile-drcn.op.dbankcloud.cn/FileServer/getFile/cmtyPub/011/111/111/0000000000011111111.20250620163901.82504090472134057009843077544703:50001231000000:2800:74101FF0864D8F031151872AA510FA4891B78F9C47AF0398737645DD0CB57250.pdf?needInitFileName=true';
build() {
Column({ space: 20 }) {
Button("预览网络PDF")
.onClick(async () => {
let res = await downloadPdf(this.context, this.url, 'harmonyosBook.pdf');
previewLocalPdf(this.context, res);
});
}
.width('100%')
.height('100%')
.justifyContent(FlexAlign.Center);
}
}