B 站在互动视频领域上的探索 李超然

Razor

2019/10/19 发布于 技术 分类

文字内容
1. B 站在互动视频领域上的探索 李李超然 bilibili 移动技术部 ⾼高级开发⼯工程师
2. 在此键⼊入姓名 在此键⼊入tittle
3. ⾃自我介绍 我,李李超然,哔哩哔哩,移动端,播放器器,弹幕内核,互动视频 兴趣,数学物理理,计算机图形学,游戏
4. ⽬目录 • 互动视频的业务特点 • 后端逻辑抽象⽅方式 • 前端引擎技术⽅方案 • 优化⼯工程结构
5. 挑战 1:需求⾛走向难以预估 ⿊黑镜:潘达斯奈奈基 隐形守护者 什什么是互动视频 ... ? ⽤用户操作可以影响视频内容
6. 性取向测♂试!av65760443 进来!由你抽卡! av59272883 B 站视频⽣生态 UGC 内容为主 视频作者的需求难以预估 …
7. 挑战 2:客户端升级率不不够⾼高 App 更更新后 7 天覆盖率 70%,之后增速缓慢 … 很多核⼼心⽤用户⾮非常抵触升级客户端 … 强制⽤用户升级,会引起⽤用户不不满 … 客户端技术⽅方案必须向前兼容!
8. 挑战 3:逻辑和样式需要在 4 端统⼀一 创作者需要所⻅见即所得的编辑器器 内容创作者 Web 编辑器器 预览界⾯面看到的效果和各终端⽤用户看到的效果⼀一致 观影⽤用户 Android 客户端 iOS 客户端 Web 播放端
9. ⽬目录 • 互动视频的业务特点 • 后端逻辑抽象⽅方式 • 前端引擎技术⽅方案 • 优化⼯工程结构
10. 数据结构:有向图 节点:视频⽚片段 边:选项按钮 暴暴露露,任务失败 开枪 遭遇敌⼈人 ⾛走正⻔门离开 暗中观察 获得绝密情报 从下⽔水道逃脱 任务成功
11. 数据结构:隐藏数值 选项按钮可以指定出现条件 被点击时可以改变隐藏数值 在⼀一起 告⽩白 出现条件:好感度 > 0 准备⼥女女友⽣生⽇日宴 准备礼物 好感度 = 好感度 + 5 告⽩白 暗中观察 好感度 = 好感度 - 5 相谈甚欢 出现条件:好感度 <= 0 你是⼀一个好⼈人
12. 图结构可能很复杂 … 剧本杀了了Ta av66384875
13. 服务端与客户端的协作⽅方式 谁处理理互动逻辑? 优势 劣势 客户端 低延迟 可离线游玩 难以快速响应新的需求 难以兼容历史版本 服务端 服务端发版⽅方便便 ⽤用户⽆无需升级客户端 ⾼高延迟 对客户端框架设计要求⾼高
14. 拥抱变化:客户端尽可能⽆无状态 需求不不稳定 需要快速迭代 服务端处理理所有逻辑 保持灵动 服务端 (2) 处理理互动逻辑 客户端尽可能⽆无状态 提交剧情树 下发逻辑(图,语义结构)? 下发 UI 和交互细节(样式)? (3) 下发展示内容 (1) 提交⽤用户选择 编辑器器 播放端
15. ⽬目录 • 互动视频的业务特点 • 后端逻辑抽象⽅方式 • 前端引擎技术⽅方案 • 优化⼯工程结构
16. UI 渲染⽅方案 直接使⽤用原⽣生控件 (eg. UIKit) 抽象双端原⽣生控件 (eg. Reactive Native) ⽆无法跨平台,代码复⽤用率低 ⽆无法⾃自由绘制,⾃自由度太受限 WebView (HTML / CSS) Direct UI (eg. Flutter) 性能不不佳 性能好,但复杂度⾼高,包体积⼤大 按实际需要⾃自研:降低复杂度和包体积
17. 跨平台 轻:~8,000 ⾏行行代码 JNI / GLES Android 播放端 跨平台:代码公⽤用率 70%+ OC++ / GLES 引擎 C++ 图形接⼝口 OpenGL ES WASM / WebGL WASM / WebGL 业务逻辑脚本化 JS JavaScriptCore iOS 播放端 Web 播放端 Web 编辑器器
18. 整体结构 业务逻辑——快速迭代 UI ⽪皮肤样式 各类选项逻辑 与外部代码互通 … 抽象图形接⼝口——简单的 2D 游戏引擎 Node Tree Animation RPC Script Engine 抽象基础能⼒力力——消除平台差异 Thread Pool File System Network Touch Event Surface GLES Context V-sync Signal Font Render
19. 设备⽆无关的坐标系 (1, 1) Y (1, 1) Y (0.3, 0.2) X O (0, 0) (0.3, 0.2) X O (0, 0)
20. Node Tree:空间 { } // sky x:'>x: 0.5, y:'>y: 0.5, width: 1, height: 1, background_color: "blue", children:'>children: [ { // body ... children:'>children: [ { // rotor ... }, { // missle ... x:'>x: 0, y:'>y: 0.2 } ] } ] 结构:树,节点-> 平移,旋转,缩放,透明度,shader,⼿手势
21. Node Tree:时间 { } start_time: 12.2, duration: 4.3, children: [ // ... ] 00:00 02:34 Root Layer Layer1 Sublayer1 Layer2 Sublayer2
22. Animation 直升⻜飞机的螺旋桨,从 02:34 开始,在接下来的 4 秒内,旋转⻆角度,线性地,从 45 度,变化到 90 度 Node { Start Time Duration Property Time Function From Value start_time: 0, duration:'>duration:'>duration:'>duration: 100, animations: [ // fade in { start:'>start: 0, duration:'>duration:'>duration:'>duration: 0.3, property:'>property: "alpha", from:'>from: 0, to:'>to: 1, time_func:'>func: “ease_in" }, ], } // fade out { start:'>start: 99.7, duration:'>duration:'>duration:'>duration: 0.3, property:'>property: "alpha", from:'>from: 1, to:'>to: 0, time_func:'>func: “ease_out" }, children: [ /* ... */ ] To Value
23. ⽬目录 • 互动视频的业务特点 • 后端逻辑抽象⽅方式 • 前端引擎技术⽅方案 • 优化⼯工程结构
24. 随视频时钟演化的渲染层 ⼴广告 弹幕 弹幕蒙版 视频画⾯面 字幕 + 关注
25. 随视频时钟演化的渲染层 播控⾯面板 随剧情出现的功能⼊入⼝口 gl context & threads game loop 弹幕 / CC 字幕 gl context & threads game loop 选项按钮 (互动视频) gl context & threads game loop 视频画⾯面 gl context & threads game loop all in one gl context & threads game loop ⼤大幅减少渲染⽬目标切换 ⼤大幅减少线程切换
26. 随视频时钟演化的渲染层 播控⾯面板 ⽤用户操作播控⾯面板影响时钟 播放 & 暂停 / 快进快退 / 倍速播放 / 缓冲 每⼀一帧:渲染层读取时钟当前时刻 随剧情出现的功能⼊入⼝口 弹幕 / CC 字幕 选项按钮 (互动视频) 视频画⾯面 根据获取的视频时钟时间,结算动画 class Clock { public: double GetCurrentTime() const; double GetPlaybackRate() const; 视频播放时钟 void SetCurrentTime(double time); void SetPlaybackRate(double rate); private: // … };
27. 动态化 服务端 逻辑向客户端迁移 低延迟 保持灵动 下发 JS 逻辑 客户端:JSBinding 客户端:C++ Engine JavaScriptCore
28. 动态化 C++ auto parent_node = std::make_shared'>std::make_shared(); parent_node->SetPosition(0.2, 0.3); auto child_node = std::make_shared'>std::make_shared("Hi From Cpp"); parent_node->AddChild(child_node); JavaScript parentNode = Node.Create(); parentNode.position = [0.2, 0.3]; childNode = TextNode.Create("Hi From JS"); parentNode.addChild(childNode);
29. 总结 挑战:需求⽅方向难以预估,需要快速迭代,需要多端统⼀一逻辑和样式 后端:有向图,节点->视频,边->逻辑 前端:基于 GLES 的跨端渲染,基于 JS 的跨端逻辑,时间轴元素统⼀一时钟