鸿蒙HarmonyOS应用开发之Rawfile开发指导

场景介绍

开发者可以通过本指导了解在OpenHarmony应用中,如何使用Native Rawfile接口操作Rawfile目录和文件。功能包括文件列表遍历、文件打开、搜索、读取和关闭Rawfile。

接口说明

接口名描述
NativeResourceManager *OH_ResourceManager_InitNativeResourceManager(napi_env env, napi_value jsResMgr)初始化native resource manager。
RawDir *OH_ResourceManager_OpenRawDir(const NativeResourceManager *mgr, const char *dirName)打开指定rawfile目录。
int OH_ResourceManager_GetRawFileCount(RawDir *rawDir)获取指定rawfile目录下的rawfile文件数量。
const char *OH_ResourceManager_GetRawFileName(RawDir *rawDir, int index)获取rawfile名字。
RawFile *OH_ResourceManager_OpenRawFile(const NativeResourceManager *mgr, const char *fileName)打开指定rawfile文件。
long OH_ResourceManager_GetRawFileSize(RawFile *rawFile)获取rawfile文件大小。
int OH_ResourceManager_SeekRawFile(const RawFile *rawFile, long offset, int whence)指定rawfile内偏移量。
long OH_ResourceManager_GetRawFileOffset(const RawFile *rawFile)获取rawfile偏移量。
int OH_ResourceManager_ReadRawFile(const RawFile *rawFile, void *buf, size_t length)读取rawfile文件内容。
int64_t OH_ResourceManager_GetRawFileRemainingLength(const RawFile *rawFile)获取rawfile文件剩余长度。
void OH_ResourceManager_CloseRawFile(RawFile *rawFile)释放rawfile文件相关资源。
void OH_ResourceManager_CloseRawDir(RawDir *rawDir)释放rawfile目录相关资源。
bool OH_ResourceManager_GetRawFileDescriptor(const RawFile *rawFile, RawFileDescriptor &descriptor)获取rawfile的fd。
bool OH_ResourceManager_ReleaseRawFileDescriptor(const RawFileDescriptor &descriptor)释放rawfile的fd。
void OH_ResourceManager_ReleaseNativeResourceManager(NativeResourceManager *resMgr)释放native resource manager相关资源。

函数介绍

  1. 根据NativeResourceManager实例,使用OH_ResourceManager_OpenRawDir接口获取RawDir实例。
RawDir* rawDir = OH_ResourceManager_OpenRawDir(nativeResourceManager, path.c_str());
  1. 根据RawDir实例,使用OH_ResourceManager_GetRawFileCount接口获取对应目录下的rawfile文件总数 。
int count = OH_ResourceManager_GetRawFileCount(rawDir);
  1. 根据RawDir实例,使用OH_ResourceManager_GetRawFileName接口获取目录下对应index的rawfile文件名。
for (int index = 0; index < count; index++) {
    std::string fileName = OH_ResourceManager_GetRawFileName(rawDir, index);
}
  1. 根据NativeResourceManager实例,使用OH_ResourceManager_OpenRawFile接口获取指定文件名的RawFile实例
RawFile* rawFile = OH_ResourceManager_OpenRawFile(nativeResourceManager, fileName.c_str());
  1. 根据RawFile实例,使用OH_ResourceManager_GetRawFileSize接口获取对应rawfile文件大小。
long rawFileSize = OH_ResourceManager_GetRawFileSize(rawFile);
  1. 根据RawFile实例,使用OH_ResourceManager_SeekRawFile接口指定rawfile偏移量。
int position = OH_ResourceManager_SeekRawFile(rawFile, 10, 0);
int position = OH_ResourceManager_SeekRawFile(rawFile, 0 , 1);
int position = OH_ResourceManager_SeekRawFile(rawFile, -10, 2);
  1. 根据RawFile实例,使用OH_ResourceManager_GetRawFileOffset接口获取rawfile偏移量。
long rawFileOffset = OH_ResourceManager_GetRawFileOffset(rawFile)
  1. 根据RawFile实例,使用OH_ResourceManager_ReadRawFile接口读取rawfile文件内容。
std::unique_ptr<char[]> mediaData = std::make_unique<char[]>(rawFileSize);
long rawFileOffset = OH_ResourceManager_ReadRawFile(rawFile, mediaData.get(), rawFileSize);
  1. 根据RawFile实例,使用OH_ResourceManager_GetRawFileRemainingLength接口读取rawfile文件的剩余长度。
int64_t rawFileRemainingSize = OH_ResourceManager_GetRawFileRemainingLength(rawFile);
  1. 根据RawFile实例,使用OH_ResourceManager_CloseRawFile接口释放rawfile文件相关资源。
OH_ResourceManager_CloseRawFile(rawFile);
  1. 根据RawDir实例,使用OH_ResourceManager_CloseRawDir接口释放rawfile目录相关资源。
OH_ResourceManager_CloseRawDir(rawDir);
  1. 根据RawFile实例,使用OH_ResourceManager_GetRawFileDescriptor接口获取rawfile的RawFileDescriptor。
RawFileDescriptor descriptor;
bool result = OH_ResourceManager_GetRawFileDescriptor(rawFile, descriptor);
  1. 根据RawFileDescriptor实例,使用OH_ResourceManager_ReleaseRawFileDescriptor接口关闭rawfile的fd。
OH_ResourceManager_ReleaseRawFileDescriptor(descriptor);
  1. 根据NativeResourceManager实例,使用OH_ResourceManager_ReleaseNativeResourceManager接口释放native resource manager。
OH_ResourceManager_ReleaseNativeResourceManager(nativeResourceManager);

开发步骤

以ArkTS侧获取rawfile文件列表、rawfile文件内容、rawfile描述符{fd, offset, length}三种调用方式为例。

1. 创建工程

2. 添加依赖

创建完成后,IDE会在工程生成cpp目录,目录有libentry/index.d.ts、hello.cpp、CMakeLists.txt等文件。

  1. 打开src/main/cpp/CMakeLists.txt,在target_link_libraries依赖中添加资源的librawfile.z.so以及日志依赖libhilog_ndk.z.so。
target_link_libraries(entry PUBLIC libace_napi.z.so libhilog_ndk.z.so librawfile.z.so)
  1. 打开src/main/cpp/types/libentry/index.d.ts文件,此文件声明了应用侧函数getFileList、getRawFileContent、getRawFileDescriptor。
import resourceManager from '@ohos.resourceManager';
export const getFileList: (resmgr: resourceManager.ResourceManager, path: string) => Array<String>;
export const getRawFileContent: (resmgr: resourceManager.ResourceManager, path: string) => Uint8Array;
export const getRawFileDescriptor: (resmgr: resourceManager.ResourceManager, path: string) => resourceManager.RawFileDescriptor;  

3. 修改源文件

  1. 打开src/main/cpp/hello.cpp文件,文件Init会对当前方法进行初始化映射,这里定义对外接口为getFileList、getRawFileContent、getRawFileDescriptor,映射C++接口分别为GetFileList、GetRawFileContent、GetRawFileDescriptor。
EXTERN_C_START
static napi_value Init(napi_env env, napi_value exports)
{
    napi_property_descriptor desc[] = {
        { "getFileList", nullptr, GetFileList, nullptr, nullptr, nullptr, napi_default, nullptr },
        { "getRawFileContent", nullptr, GetRawFileContent, nullptr, nullptr, nullptr, napi_default, nullptr },
        { "getRawFileDescriptor", nullptr, GetRawFileDescriptor, nullptr, nullptr, nullptr, napi_default, nullptr }
    };

    napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
    return exports;
}
EXTERN_C_END
  1. 把src/main/cpp/hello.cpp文件中,增加对应的三个方法,如下所示
static napi_value GetFileList(napi_env env, napi_callback_info info)
static napi_value GetRawFileContent(napi_env env, napi_callback_info info)
static napi_value GetRawFileDescriptor(napi_env env, napi_callback_info info)
  1. 在hello.cpp文件中获取Js的资源对象,并转为Native的资源对象,即可调用资源的Native接口,获取rawfile列表、rawfile文件内容以及rawfile描述符{fd, offset, length}三种调用方式示例代码如下:
#include <rawfile/raw_file.h>
#include <rawfile/raw_dir.h>
#include <rawfile/raw_file_manager.h>

// 示例一:获取rawfile文件列表 GetFileList
static napi_value GetFileList(napi_env env, napi_callback_info info)
{
    OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "NDKTest Begin");
    size_t requireArgc = 3;
    size_t argc = 2;
    napi_value argv[2] = { nullptr };
    // 获取参数信息
    napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);

    // argv[0]即为函数第一个参数Js资源对象,OH_ResourceManager_InitNativeResourceManager转为Native对象。
    NativeResourceManager *mNativeResMgr = OH_ResourceManager_InitNativeResourceManager(env, argv[0]);

    // 获取函数argv[1],此为为rawfile相对路径
    size_t strSize;
    char strBuf[256];
    napi_get_value_string_utf8(env, argv[1], strBuf, sizeof(strBuf), &strSize);
    std::string dirName(strBuf, strSize);

    // 获取对应的rawDir指针对象
    RawDir* rawDir = OH_ResourceManager_OpenRawDir(mNativeResMgr, dirName.c_str());

    // 获取rawDir下文件及文件夹数量
    int count = OH_ResourceManager_GetRawFileCount(rawDir);

    // 遍历获取文件名称,并保存
    std::vector<std::string> tempArray;
    for(int i = 0; i < count; i++) {
        std::string filename = OH_ResourceManager_GetRawFileName(rawDir, i);
        tempArray.emplace_back(filename);
    }

    napi_value fileList;
    napi_create_array(env, &fileList);
    for (size_t i = 0; i < tempArray.size(); i++) {
        napi_value jsString;
        napi_create_string_utf8(env, tempArray[i].c_str(), NAPI_AUTO_LENGTH, &jsString);
        napi_set_element(env, fileList, i, jsString);
    }

    // 关闭打开的指针对象
    OH_ResourceManager_CloseRawDir(rawDir);
    OH_ResourceManager_ReleaseNativeResourceManager(mNativeResMgr);
    return fileList;
}

// 示例二:获取rawfile文件内容 GetRawFileContent
napi_value CreateJsArrayValue(napi_env env, std::unique_ptr<uint8_t[]> &data, long length)
{
    napi_value buffer;
    napi_status status = napi_create_external_arraybuffer(env, data.get(), length,
            [](napi_env env, void *data, void *hint) {
                delete[] static_cast<char*>(data);
            }, nullptr, &buffer);
    if (status != napi_ok) {
        OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "Failed to create external array buffer");
        return nullptr;
    }
    napi_value result = nullptr;
    status = napi_create_typedarray(env, napi_uint8_array, length, buffer, 0, &result);
    if (status != napi_ok) {
        OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "Failed to create media typed array");
        return nullptr;
    }
    data.release();
    return result;
}
static napi_value GetRawFileContent(napi_env env, napi_callback_info info)
{
    OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "GetFileContent Begin");
    size_t requireArgc = 3;
    size_t argc = 2;
    napi_value argv[2] = { nullptr };
    // 获取参数信息
    napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);

    // argv[0]即为函数第一个参数Js资源对象,OH_ResourceManager_InitNativeResourceManager转为Native对象。
    NativeResourceManager *mNativeResMgr = OH_ResourceManager_InitNativeResourceManager(env, argv[0]);
    size_t strSize;
    char strBuf[256];
    napi_get_value_string_utf8(env, argv[1], strBuf, sizeof(strBuf), &strSize);
    std::string filename(strBuf, strSize);

    // 获取rawfile指针对象
    RawFile *rawFile = OH_ResourceManager_OpenRawFile(mNativeResMgr, filename.c_str());
    if (rawFile != nullptr) {
        OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "OH_ResourceManager_OpenRawFile success");
    }
    // 获取rawfile大小并申请内存
    long len = OH_ResourceManager_GetRawFileSize(rawFile);
    std::unique_ptr<uint8_t[]> data= std::make_unique<uint8_t[]>(len);

    // 一次性读取rawfile全部内容
    int res = OH_ResourceManager_ReadRawFile(rawFile, data.get(), len);

    // 多次部分读取rawfile, 每次读取100 Byte。获取全部内容
    // long offset = 0;
    // while (OH_ResourceManager_GetRawFileRemainingLength(rawFile) > 0) {
    //     OH_ResourceManager_ReadRawFile(rawFile, data.get() + offset, 100);
    //     offset += 100;
    // }

    // 关闭打开的指针对象
    OH_ResourceManager_CloseRawFile(rawFile);
    OH_ResourceManager_ReleaseNativeResourceManager(mNativeResMgr);
    // 转为js对象
    return CreateJsArrayValue(env, data, len);
}

// 示例三:获取rawfile文件描述符 GetRawFileDescriptor
napi_value createJsFileDescriptor(napi_env env, RawFileDescriptor &descriptor)
{
    napi_value result;
    napi_status status = napi_create_object(env, &result);
    if (status != napi_ok) {
        return result;
    }

    napi_value fd;
    status = napi_create_int32(env, descriptor.fd, &fd);
    if (status != napi_ok) {
        return result;
    }
    status = napi_set_named_property(env, result, "fd", fd);
    if (status != napi_ok) {
        return result;
    }

    napi_value offset;
    status = napi_create_int64(env, descriptor.start, &offset);
    if (status != napi_ok) {
        return result;
    }
    status = napi_set_named_property(env, result, "offset", offset);
    if (status != napi_ok) {
        return result;
    }

    napi_value length;
    status = napi_create_int64(env, descriptor.length, &length);
    if (status != napi_ok) {
        return result;
    }
    status = napi_set_named_property(env, result, "length", length);
    if (status != napi_ok) {
        return result;
    }
    return result;
}
static napi_value GetRawFileDescriptor(napi_env env, napi_callback_info info)
{
    OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "NDKTest GetRawFileDescriptor Begin");
    size_t requireArgc = 3;
    size_t argc = 2;
    napi_value argv[2] = { nullptr };
    // 获取参数信息
    napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);
    
    napi_valuetype valueType;
    napi_typeof(env, argv[0], &valueType);
    // 获取native的resourceManager对象
    NativeResourceManager *mNativeResMgr = OH_ResourceManager_InitNativeResourceManager(env, argv[0]);
    size_t strSize;
    char strBuf[256];
    napi_get_value_string_utf8(env, argv[1], strBuf, sizeof(strBuf), &strSize);
    std::string filename(strBuf, strSize);
    // 获取rawfile指针对象
    RawFile *rawFile = OH_ResourceManager_OpenRawFile(mNativeResMgr, filename.c_str());
    if (rawFile != nullptr) {
        OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "OH_ResourceManager_OpenRawFile success");
    }
    // 获取rawfile的描述符RawFileDescriptor {fd, offset, length}
    RawFileDescriptor descriptor;
    OH_ResourceManager_GetRawFileDescriptor(rawFile, descriptor);
    // 关闭打开的指针对象
    OH_ResourceManager_CloseRawFile(rawFile);
    OH_ResourceManager_ReleaseNativeResourceManager(mNativeResMgr);
    // 转为js对象
    return createJsFileDescriptor(env,descriptor);
}

4. Js侧调用

  1. 打开src\main\ets\pages\index.ets, 导入"libentry.so";

  2. 资源获取包括获取本应用包资源、应用内跨包资源、跨应用包资源。
    获取本应用包resourceManager对象,通过.context().resourceManager方法。
    获取应用内跨包resourceManager对象,通过.context().createModuleContext().resourceManager 方法。
    获取跨应用包resourceManager对象,通过.context.createModuleContext(bundleName:‘bundleName name’,moduleName:‘module name’).resourceManager方法,该方法仅支持系统应用使用。
    Context的更多使用信息请参考应用上下文Context

  3. 调用Native接口getFileList即为src/main/cpp/types/libentry/index.d.ts中声明的接口,传入js的资源对象,以及rawfile文件夹的相对路径。

获取本应用包资源resourceManager对象的示例如下:

import hilog from '@ohos.hilog';
import testNapi from 'libentry.so'  // 导入so
@Entry
@Component
struct Index {
    @State message: string = 'Hello World'
    private resmgr = getContext().resourceManager;  // 获取本应用包的资源对象
    build() {
        Row() {
        Column() {
            Text(this.message)
            .fontSize(50)
            .fontWeight(FontWeight.Bold)
            .onClick(() => {
                hilog.isLoggable(0x0000, 'testTag', hilog.LogLevel.INFO);
                let rawfilelist = testNapi.getFileList(this.resmgr, ""); //传入资源对象,以及访问的rawfile文件夹名称
                console.log("rawfilelist" + rawfilelist);
                let rawfileContet = testNapi.getRawFileContent(this.resmgr, "rawfile1.txt");
                console.log("rawfileContet" + rawfileContet);
                let rawfileDescriptor = testNapi.getRawFileDescriptor(this.resmgr, "rawfile1.txt");
                console.log("getRawFileDescriptor" + rawfileDescriptor.fd, rawfileDescriptor.offset, rawfileDescriptor.length);
            })
        }
        .width('100%')
        }
        .height('100%')
    }
}

相关实例

针对资源管理Rawfile开发,有以下相关实例可供参考:

为了能让大家更好的学习鸿蒙(HarmonyOS NEXT)开发技术,这边特意整理了《鸿蒙开发学习手册》(共计890页),希望对大家有所帮助:https://qr21.cn/FV7h05

《鸿蒙开发学习手册》:

如何快速入门:https://qr21.cn/FV7h05

  1. 基本概念
  2. 构建第一个ArkTS应用
  3. ……

开发基础知识:https://qr21.cn/FV7h05

  1. 应用基础知识
  2. 配置文件
  3. 应用数据管理
  4. 应用安全管理
  5. 应用隐私保护
  6. 三方应用调用管控机制
  7. 资源分类与访问
  8. 学习ArkTS语言
  9. ……

基于ArkTS 开发:https://qr21.cn/FV7h05

  1. Ability开发
  2. UI开发
  3. 公共事件与通知
  4. 窗口管理
  5. 媒体
  6. 安全
  7. 网络与链接
  8. 电话服务
  9. 数据管理
  10. 后台任务(Background Task)管理
  11. 设备管理
  12. 设备使用信息统计
  13. DFX
  14. 国际化开发
  15. 折叠屏系列
  16. ……

鸿蒙开发面试真题(含参考答案):https://qr18.cn/F781PH

鸿蒙开发面试大盘集篇(共计319页):https://qr18.cn/F781PH

1.项目开发必备面试题
2.性能优化方向
3.架构方向
4.鸿蒙开发系统底层方向
5.鸿蒙音视频开发方向
6.鸿蒙车载开发方向
7.鸿蒙南向开发方向

<think>好的,用户现在在寻找关于鸿蒙应用开发中视频播放应用的实战项目教程或示例。我需要根据之前的对话历史和提供的引用内容来构建回答。首先,用户之前提到的引用[1]、[2]、[3]都涉及到鸿蒙的多媒体开发,特别是视频播放相关的组件和资源。所以,我应该重点参考这些内容,并结合用户的需求,提供一个结构清晰的实战步骤。 首先,用户需要的是完整的项目教程,所以回答应该分步骤讲解如何实现视频播放功能,可能包括环境准备、UI布局、权限设置、核心代码实现、功能扩展以及资源推荐。同时,用户提到了引用中的视频控件和组件库,我需要确保在步骤中涵盖这些点,比如使用VideoPlayer组件,引用提到的库可能是指提供的组件示例,需要指导用户如何获取和使用。 接下来,我需要确认用户可能遇到的问题,比如权限处理、本地与网络视频播放的区别、自定义控制栏等,这些应该在教程中提及。同时,引用[2]提到有学习资料和开发手册,应该在相关资源部分推荐,帮助用户深入学习。 还要注意用户希望回答真实可靠,所以需要确保代码示例正确,并符合鸿蒙最新的开发实践。例如,使用ArkTS进行声明式开发,这是鸿蒙推荐的方式。同时,引用[3]提到的仓颉社区,可以建议用户参考社区中的开源项目,但可能用户更需要直接的教程链接或示例代码,但由于引用中没有具体链接,可能需要引导用户到官方资源或提供的资料库。 最后,生成的相关问题需要围绕视频播放的深入开发,比如性能优化、多格式支持、直播功能等,确保问题与主题紧密相关,并帮助用户进一步探索。</think>### 鸿蒙视频播放应用开发实战指南(基于HarmonyOS 4.0) #### 一、开发环境准备 1. 安装**DevEco Studio 4.0**及以上版本 2. 创建项目时选择`Application > Empty Ability`模板 3. 配置`module.json5`添加视频权限: ```json "requestPermissions": [ { "name": "ohos.permission.INTERNET" // 网络视频需要 }, { "name": "ohos.permission.READ_MEDIA" // 本地视频需要 } ] ``` #### 二、UI布局实现 使用ArkTS声明式开发模式: ```typescript // VideoPage.ets @Entry @Component struct VideoPage { private controller: VideoController = new VideoController() build() { Column() { Video({ src: $rawfile('demo.mp4'), // 本地视频 controller: this.controller }) .width('100%') .height(400) .autoPlay(false) Button('播放/暂停') .onClick(() => { this.controller.start() // 播放控制 }) } } } ``` #### 三、核心功能实现 1. **网络视频播放**: ```typescript Video({ src: 'https://example.com/video.mp4', controller: this.controller }) ``` 2. **播放器控制栏定制**: ```typescript Video(...) .controls(false) // 关闭默认控制栏 .overlay(new CustomController()) // 自定义控制组件 ``` 3. **播放状态监听**: ```typescript this.controller.on('play', () => { console.log('视频开始播放') }) ``` #### 四、完整项目结构示例 ``` project/ ├── entry/ │ ├── src/main/ets/ │ │ ├── VideoPlayer/ │ │ │ ├── VideoPage.ets // 播放页 │ │ │ └── Controller.ets // 自定义控制器 │ ├── resources/ │ │ └── rawfile/ // 存放本地视频文件 ``` #### 五、进阶功能扩展 1. **视频列表管理**: ```typescript let videoList: VideoItem[] = [ { title: '宣传片', url: $rawfile('intro.mp4') }, { title: '教学视频', url: 'https://...' } ] ``` 2. **视频缓存机制**: ```typescript // 使用@ohos.file.fs实现本地缓存 import fs from '@ohos.file.fs' ``` #### 六、推荐学习资源 1. **鸿蒙官方组件库**(包含视频播放完整示例)[^1] 2. **《纯血版鸿蒙多媒体开发手册》**(含视频编解码优化方案)[^2] 3. **Gitee开源项目**:HarmonyOS-VideoPlayer-Demo(搜索可得)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值