加入白板房间
声网 Whiteboard HarmonyOS SDK 提供 ArkUI 白板组件。通过 WhiteboardOptions 初始化并加入房间,使用 WhiteboardController 操作房间,使用 WhiteboardCallbacks 接收事件。
前提条件
- DevEco Studio、HarmonyOS Stage 模型工程;本版仓库以 HarmonyOS 5.0.0 / API 12 为兼容基线。
- 已开启互动白板服务,获取 AppIdentifier。
- 业务服务端已创建房间,并下发匹配房间和数据中心的 Room Token。
获取 SDK
ohpm install @shengwang/whiteboard@0.2.11
添加权限
在模块 module.json5 的 module 中添加网络权限:
{
"requestPermissions": [
{ "name": "ohos.permission.INTERNET" }
]
}
实现步骤
1. 创建房间
由业务服务端调用创建房间,保存返回的房间 UUID 和数据中心。
2. 生成 Room Token
由业务服务端生成 Room Token,将房间 UUID、Room Token 和用户 uid 下发给客户端。SDK Token 保存在服务端。
3. 准备控制器和回调
创建 WhiteboardController 和 WhiteboardCallbacks,在组件显示前设置回调。onRoomReady 表示已成功入房,之后可调用房间与 App 接口。以下完整示例包含这两个对象。
4. 创建组件并加入房间
import {
Whiteboard, WhiteboardOptions, WhiteboardController,
WhiteboardCallbacks, Region, SDKError, WindowParams
} from '@shengwang/whiteboard';
@Entry
@Component
struct WhiteboardPage {
private controller: WhiteboardController = new WhiteboardController();
private callbacks: WhiteboardCallbacks = new WhiteboardCallbacks();
private options: WhiteboardOptions = {
appIdentifier: 'APP_IDENTIFIER',
roomUuid: 'ROOM_UUID',
roomToken: 'ROOM_TOKEN',
uid: 'CLIENT_UID',
region: Region.CN_HZ,
writable: true,
useMultiViews: true,
windowParams: new WindowParams(),
enableAppliancePlugin: true
};
aboutToAppear(): void {
this.callbacks.setOnRoomReady(() => {
// 已加入房间,可开始使用 controller 操作白板。
});
this.callbacks.sdkSetupFail = (error: SDKError) => {
console.error(error.message);
// 业务侧重新创建组件,完成 SDK 初始化和重新入房。
};
this.callbacks.setOnRoomPhaseChanged((phase) => {
console.info(`room phase: ${phase}`);
});
}
build() {
Column() {
Whiteboard({
options: this.options,
controller: this.controller,
callbacks: this.callbacks,
webDebug: false
}).width('100%').height('100%');
}.width('100%').height('100%');
}
}
appIdentifier、roomUuid、roomToken、uid、region 为必填字段。region 必须与创建房间的服务区域一致,writable 未传时映射为 true,useMultiViews/userCursor/enableAppliancePlugin 未显式提供时允许继承动态配置;未启用动态配置时使用内建默认。
必须把回调对象传给组件的 callbacks 参数;本版组件实际使用此参数,不能只填写 options.callbacks。组件加载后自动初始化 SDK 并入房,本版没有业务调用的 joinRoom() 方法。等待 onRoomReady 后再操作房间。
5. 接入多窗口
Window Manager 已通过内嵌 Bridge 集成。组件创建前设置 WhiteboardOptions.useMultiViews=true,窗口显示参数放在 windowParams。步骤 4 的示例已包含这两项:
// 在组件创建前配置,随后通过 Whiteboard 的 options 参数传入。
this.options.useMultiViews = true;
const windowParams = new WindowParams();
windowParams.setContainerSizeRatio(9 / 16);
this.options.windowParams = windowParams;
组件初始化并入房后自动挂载窗口管理器,业务通过 Controller 调用 App 和页面接口。详细配置见多窗口与统一课件控制。
6. 接入动态 PPT
内嵌 Bridge 已注册 app-slide。业务服务端完成转换后,在 onRoomReady 回调之后,通过 controller.addApp 创建动态 PPT 窗口:
import { WindowAppParam } from '@shengwang/whiteboard';
// 放在 WhiteboardPage 的业务方法中;入房成功后由按钮调用。
async openDynamicPpt(): Promise<void> {
const slide: WindowAppParam = {
kind: 'Slide',
options: {
title: '教学课件.pptx',
scenePath: '/slides/lesson-1'
},
attributes: {
taskId: 'CONVERSION_TASK_UUID',
url: 'https://convertcdn.netless.link/dynamicConvert'
}
};
try {
const appId = await this.controller.addApp(slide);
console.info(`动态 PPT 窗口 ID:${appId}`);
} catch (error) {
console.error(`创建课件窗口失败:${error}`);
}
}
taskId 使用已完成转换的任务 UUID,url 是资源地址前缀(末尾不带 /,不是 PPT 源文件地址)。options.scenePath 必须是以 / 开头的场景目录,同一房间内每个 App 使用不同目录。创建 App 需要可写权限;房间中已存在的课件会同步显示,不要在每次入房时重复插入。返回 ID 不表示课件资源与首帧全部加载完成。课件操作见新版 API 与多窗口课件控制。
7. 开启新教具
创建组件前同时启用多 View 与教具插件;步骤 4 的示例已开启:
this.options.useMultiViews = true;
this.options.enableAppliancePlugin = true;
SDK 已内嵌 Appliance Plugin 和 Worker,业务继续使用 Controller 的原生方法设置 Pencil、Selector、Eraser、Shape、Text 等教具,同一房间各端应一致开启。入房前的插件参数放在 WhiteboardOptions.appliancePluginOptions,自定义教具、背景图和 Auto Shape 见教具插件介绍与启用。
上述开关在组件初始化前配置;已入房后修改 options 不用于动态开启插件。
离开房间
在组件仍然挂载时调用并等待 controller.disconnect(),完成后再隐藏或销毁白板组件。组件消失时会解除 Controller 与 Bridge 的绑定。异步接口应处理 Promise rejection。
后续功能
0.2.11 没有公开的回放 Player、SyncedStore 或自定义 App 注册入口。业务应依据 Harmony 实际公开接口集成。
等待退出完成
调用 await controller.leaveRoom() 等待所属房间清理;disconnect() 保留为兼容入口并委托相同退出流程。重复退出复用清理结果。退出失败时先处理错误,避免立刻发起下一次入房;组件解绑不能当作房间已经退出的通知。动态配置接入和缺省规则见动态配置。