写点什么

百家号在线视频编辑器的技术演进

用户头像
百度Geek说
关注
发布于: 2021 年 04 月 01 日
百家号在线视频编辑器的技术演进

导读:随着移动互联网的发展,视频化浪潮借着 5G 的东风扑面而来。然而众多用户在进行视频化创作的过程中,被传统视频编辑器复杂的功能和陡峭的学习曲线劝退。为此,百度百家号业务研发团队结合用户的实际创作需求,开发出一款简单易用的在线视频编辑和发布工具——百家号在线视频编辑器。本文将细致地介绍这一编辑器的技术原理,架构和演进方向,并从一角揭示百度内部的技术合作与创新机制。

*第四期百度架构师「周一见」活动进行中,本期赠送小度音箱,详细活动规则见二条推文~


前言


随着移动互联网的快速发展,人们越来越习惯于在手机上观看视频内容。百家号作为手百的内容生产平台,需要为作者提供简单易用的视频编辑和发布工具。在线视频编辑器正是在这种需求下应运而生。这篇内容将细致地介绍百家号视频编辑器所采用的技术。


名词解释

BOS: 百度对象存储 BOS (Baidu Object Storage) 提供稳定、安全、高效以及高扩展存储服务

VOD:视频点播服务,本文特指百度 VideoWorks(原 VOD 音视频点播服务)


一、一个在线视频编辑器都要实现哪些功能?

1.1 编辑器的基础功能

我们调查了本地视频编辑器,列举出一些视频编辑器必须要实现的功能:


素材源文件管理,加载和编辑

多轨道编辑器

拖拽操作(添加/删除素材, 添加/删除效果, 快速剪辑, 切换轨道 等)

音视频轨道分离

素材效果(浮雕、怀旧等),转场动画(淡入淡出、螺旋等),素材动画(单点缩放、模拟晃动等)

字幕编辑和嵌入

视频预览

多种格式渲染导出


1.2 在线编辑器的独特功能

一款在线视频编辑器,同样也要实现上述功能,只是具体实现上有所不同,例如:


  • 素材管理:要实现素材源文件的上传和删除

  • 视频预览:由前端 js 实现的简单预览

  • 导出:在线视频编辑器主要为百家号发布器服务,因此不导出视频文件,而是接入视频发布流程


此外,依托于百度和百家号技术体系,还可以实现音频转字幕,字幕合成音频,百家号图文内容转视频等额外功能。


二、如何实现一个在线视频编辑器?

2.1 后端技术选型


FFmpeg 是业界最常用的视频编解码集成框架,不仅功能强大,而且编解码效率很高。因此,后端服务采用 FFmpeg 作为视频编解码底层。


2.2 FFmpeg 介绍

FFmpeg 是一个自由软件,可以运行音频和视频多种格式的录影、转换、流功能。包含了 libavcodec——一个用于多个项目中音频和视频的解码器库,以及 libavformat——一个音频与视频格式转换库。


△图 1 ffmpeg


2.2.1 FFmpeg 特性

  • 自由软件,代码开源;

  • 自带众多滤镜(插件),能满足现阶段全部业务需求;

  • 支持第三方滤镜(插件),能满足未来业务需求;

  • 支持自定义编译,支持动态编译,尽可能降低内存占用;

  • 支持远程文件(http、ftp 等)作为输入,减少本地磁盘占用;

  • 支持 GPU 编解码,降低 CPU 占用,提升编解码速度(本业务咱时未使用 GPU 集群);

  • 语法简单,便于二次封装或组装。


2.2.2 命令行用法

△图 2 ffmpeg 命令行用法


例 1: ffmpeg -i in.wmv -vcodec libxvid out.mp4

例 2: ffmpeg -framerate 1 -t 1 -loop 1 -i "http://pic.rmb.bdstatic.com/2b18b480a1f2d15e3667e01c45dfc157.jpeg" -vcodec libx264 -pix_fmt yuv420p -y test.mp4

2.2.3 FFmpeg 滤镜基本规则

FFmpeg 中的 Filter(avfilter)通常翻译为过滤器/滤镜,滤镜的作用就是过滤(Filtering))。


任何对解码后的多媒体资源进行的编辑操作均可以称作广义上的 Filtering,而进行这些操作的组件和插件,就是滤镜。


例如,音频升降调/速、视频插帧/抽帧、剪裁/截取/合并/叠加等等。



△图 3 FFmpeg 转码和 Filter 过程


2.2.4 基础滤镜及其示意图

基础滤镜使用非常简单,只要在输入文件(及选项)和输出文件(及选项)之间,使用-vf 来添加需要的滤镜即可。例如:


  • 缩放 scale(静态)

ffmpeg -i video1080p.mp4 -vf scale=w=640:h=360 video360p.mp4


△图 4 scale 示意图


  • 缩放平移 zoompan(动态)

缩放平移 zoompan(动态):

ffmpeg -framerate 1 -t 1 -loop 1 -i "http://pic.rmb.bdstatic.com/2b18b480a1f2d15e3667e01c45dfc157.jpeg" -vf "zoompan=z='if(eq(on,0),1,if(lt(zoom,1.25),zoom+0.0005,1.25))':d=16.06*25:x='if(lt(zoom,1.25),0,(x-1))':y='if(lt(zoom,1.25),0,(y+1))':s='1024x720'" -y tmp.mp4


△图 5 zoompan 示意图


  • 模糊 boxblur:

ffmpeg -i tmp.mp4 -filter_complex "boxblur=luma_radius='min(h,w)/30':luma_power=2" -y boxblur.mp4  模糊虚化


△图 6 boxblur 示意图


  • 叠加 overlay:

ffmpeg -i tmp.mp4 -i watermark.png -filter_complex "[1:v]scale=-2:48[logo];[0:v][logo]overlay=48:48" -y watermark.mp4  左上 logo


△图 7 overlay 示意图


2.2.5 FFmpeg 管道式语法

规则:


  • 用[name] 来命名流

  • 滤镜之间用 , 分隔

  • 流之间用 ; 分隔

  • 第 i 个输入命为[i-1]

  • 第一个输入文件的视频流和音频流为[0:v] 和[0:a]

  • 最后一个流名可省略


举例:

-filter_complex "

    [0:v]split[front][back];  //复制并分离成 front 和 back 两条流

    [back] //背景流

            scale=1280:-2, //等比例缩放到输出宽度 1280

            boxblur=lumaradius='min(h,w)/30':lumapower=2, //模糊

            crop=iw:720[background]; //剪裁到 1280:720

    [front]scale=-2:720[foreground]; //等比例缩放到输出高度 720

    [background][foreground]overlay=(W-w)/2:(H-h)/2  //叠加

"


△图 8 管道化滤镜流示意图


实际效果:

△图 9 管道化滤镜流执行结果


2.3 前端技术选型

前端界面使用 React 框架实现,快速预览功能基于浏览器的 html5 音视频播放器实现,通过 html 标签传递调整参数给播放器,实现简单的负片、浮雕、黑白等播放效果,通过在视频上叠加动图的方式模拟转场效果。


受限于前端预览方案的性能和复杂度,前端快速预览只能展现部分编辑效果。


2.4 前后端功能边界及交互

2.4.1 前后端功能边界

进行具体的功能开发之前,需要根据需求和技术能力特点划分前后端功能边界,例如:


前端界面实现


  • 用户与视频编辑器的交互

  • 视频简单预览(受限于前后端技术栈差异和使用的资源差异,预览效果与最终结果可能不尽相同)

  • 将用户在编辑界面操作的结果转换成时间轴数据结构

  • ...


后端服务实现


  • 时间轴转译成 FFmpeg 命令

  • 视频产出后调用视频发布流程

  • ...


需要前后端共同实现

  • 字幕  <==> 音频

  • 素材上传

  • ...


根据我们的功能需求和前后端的功能划分,百家号在线视频编辑器的用户界面大致划分成 3 个区域:


  • 黄线内的功能区

  • 绿线内的多轨道编辑区

  • 红线内的快速预览区



2.4.2 时间轴数据结构

为了能在前后端之间进行交互,需要定义一种数据结构,这种数据结构要既便于前端多轨道编辑器的加载,修改和存储,又便于后端提取结构化数据。


我们定义了一种时间轴数据结构,时间轴中的轨道与多轨道编辑器中的轨道一一对应:


  1. {

  2. "timeline":{

  3. "video_track": [ //视频轨道

  4. {

  5. "start": 0.0, //开始时间

  6. "end": 1.5, //结束时间 = start + duration * speed

  7. "type": "video", //可以是视频video, 图片image, 转场动画transition, 黑屏blank

  8. "height": 720,

  9. "width": 1280,

  10. "in_effect": "fade_in", //入场效果

  11. "out_effect": "fade_out", //退出效果

  12. "style": "negative", // 效果: 负片,模糊,浮雕,黑白 等等

  13. "duration": 1.5, //时长

  14. "speed": 1, //播放速度

  15. "animation": "zoompan", //视频资源的动画效果, 如镜头晃动, 平移放大等

  16. "sourceUrl": "http://*.baidu.com/c20ad4d76fe97759aa27a0c99bff6710.mp4"

  17. }

  18. ],

  19. "audio_track": [ //音频轨道

  20. {

  21. "start": 0.0, //开始时间

  22. "end": 1.5, //结束时间 = start + duration * speed

  23. "type": "video", //可以是视频video(视频音轨), 音频audio, 空白静音slience

  24. "in_effect": "fade_in", //入场效果

  25. "out_effect": "fade_out", //退出效果

  26. "style": "jazz", // 效果: 爵士, 摇滚, 人声 等等平衡器效果

  27. "duration": 1.5, //时长

  28. "speed": 1, //播放速度

  29. "sourceUrl": "http://*.baidu.com/c20ad4d76fe97759aa27a0c99bff6710.mp3",

  30. "auto_subtitle": true, //语音转字幕

  31. }

  32. ],

  33. "subtitle": [ //字幕轨道

  34. {

  35. "start": 0.0, //开始时间

  36. "end": 1.5, //结束时间 = start + duration * speed

  37. "type": "video", //可以是视频video(视频音轨), 音频audio, 空白静音slience

  38. "style": "Arial,23,yellow,white", // 效果: 字体,大小,颜色,描边颜色

  39. "duration": 1.5, //时长

  40. "text": "这是一条字幕",

  41. "pos_x": 100, //字幕定位

  42. "pos_y": 200, //字幕定位

  43. "tts": true, //使用字幕合成语音

  44. }

  45. ],

  46. "watermark": [ //水印,特图

  47. {

  48. "start": 0.0, //开始时间

  49. "end": 1.5, //结束时间 = start + duration * speed

  50. "style": "transparent", //可以是透明transparent, 负片 等效果

  51. "style_params": "0.8", //效果的具体参数, 如透明度等

  52. "duration": 1.5, //时长

  53. "sourceUrl": "http://*.baidu.com/c20ad4d76fe97759aa27a0c99bff6710.png",

  54. "pos_x": 100, //贴图定位

  55. "pos_y": 200, //贴图定位

  56. "height": 100, //贴图高度

  57. "width": 100, //贴图宽度

  58. }

  59. ]

  60. },

  61. "author_info":{}, //作者信息

  62. "extra":{}, //其他信息

  63. }


2.4.3 异步调用和轮询

当用户在完成编辑工作后,需点击"保存"按钮提交。这时前端会将多轨道编辑器内所有资源要素封装成时间轴结构传递给后端服务。后端服务接到时间轴结构后会进行转译,并调用 FFmpeg 进行视频编解码。


后端这一阶段的工作是计算密集型的,通常需要消耗时间轴长度 2-5 倍的时间来完成视频最终合成。因此点击"保存"按钮后,前端采用异步调用 + 定期轮询状态的方式检查后端视频合成是否完成。


2.5 后端时间轴转译流程

前面提到后端服务要对前端传递来的时间轴进行转译,转写成 FFmpeg 命令。

这一步的主要流程如下图所示:



3. 百家号在线视频编辑器的具体实现

3.1 百家号视频编辑器整体架构


3.2 用户界面和服务接口

目前视频编辑器提供了两种使用方法:面向最终用户的图形界面和面向开发者的服务接口。


其中图形界面集成在百家号内容创作后台,现已对部分百家号作者开放,而通过接口提供的音频转码,视频合并等服务也已经应用到了百家号线上服务当中。


3.3 业务层: 时间轴转译

在业务层中,为了隔离内外部网络请求,添加了 UI 层模块,用于处理来自于图形界面的视频编辑请求。Service 模块是基于 PHP 开发的编辑器核心模块,主要作用是将图形界面和服务接口这两种类型的请求打平,将时间轴数据结构转译出能够直接执行的 FFmpeg 命令,并送给离线调度模块执行。


业务层 Service 模块在转译时主要完成了如下工作:


3.3.1 图片视频化

  • blur:传入视频/图片比例和尺寸可能与最终输出结果不一致,如手机竖屏拍摄的视频、网上下载的图片等等。之前业内对于不同比例的视频,要么留黑边,要么局部裁剪。随着手机短视频的兴起,现在流行的做法是如图 13 所示,,用模糊放大的背景图代替黑边。

  • zoompan:对于传入的静态图片,通常要将图片运动起来,使画面不至于太死板,获得更好的展现效果。


3.3.2 视频连接及转场

  • concat:将传入的个图片/视频流进行合并,连接成一条更长的视频轨。

  • overlay:在视频和视频相连接的时刻,添加一层转场动画,避免生硬的直接画面切换。


△图 13 overlay 添加过场动画


3.3.3 音频 

  • 将传入的多段视频伴音/配音/TTS 朗读接合成一条长音轨。

  • 根据用户选择添加 BGM,使视频更有氛围。

  • 处理淡入淡出,避免生硬切换。


3.3.4 字幕

  • 添加 ass 特效字幕头。

  • 根据时间轴中的文本,生成 ass 字幕文件。

  • 将 ass 字幕文件压制到视频流中。


3.3.5 组装

  • 将所有滤镜命令用管道式滤镜流方式组合,生成滤镜流脚本。

  • 将滤镜流脚本与生成的 ass 字幕同时分别上传到 BOS 上,便于后续 FFmpeg 命令直接读取和执行。


3.3.6 其他

  • 需要在空白位置添加特定长度的空白视频/音频,保证产出视频的时间轴与视频编辑器界面的时间轴一致。

  • 对较长的文本,需要精细拆分,以保证每段字幕都与 TTS 朗读同步(这一步骤在 UI 层进行计算)。


3.4 内部服务


在业务层中,涉及到用户信息、物料信息、语音合成等各种查询和调用,这些功能均由百家号和百度内部服务提供。


3.5 离线调度


Dispatch 是一个分布式的任务调度系统,负责在多个实例(或容器内)均衡地执行 FFmpeg 请求,将生成资源上传 BOS/VOD,回调 Service 层模块返回任务调度的执行结果。


FFmpeg 是一套开源的、完善的音视频流转编码自由软件,负责最终执行 FFmpeg 命令,生成音视频文件。


4. 离线调度框架:实现分布式 FFmpeg 调度

4.1 Dispatch 架构图


4.2 Dispatch 实现原理

实例启动时,Redis Hash 数据结构注册自己,member=ip,value = 当前队列长度:当前状态:更新时间戳;

任何一个接收到 Service 层模块的请求后,如果自己当前队列长度为 0,直接本地执行,否则将请求转发给队列最短的正常实例;

转发请求前先要从 Redis 获取所有 Dispatch 数据,解析所有实例的 ip、队列长度、状态、更新时间戳,根据规则选择一个最佳实例转发请求;

消费队列中的请求时,调用 FFmpeg 从 BOS 上获取输入文件,管道化滤镜流脚本,ass 字幕文件, 然后执行道化滤镜流脚本,在本地磁盘生成产出文件,并上传 BOS/VOD;

根据请求参数,回调 Service 层模块接口,更新任务状态。


5. 图文转视频技术项目:依托于视频编辑器后端服务的技术性尝试 

5.1 以场景为单元编辑视频


相比视频编辑器,图文转视频项目的用户界面取消了时间轴,转而采用"场景(Scene)"这一概念。即一张图+一段话便是一个场景,视频就是由场景串接起来的。


△图 16 以场景为单元创建视频(设计稿)


5.2 文章落地页 URL 转视频


得益于场景这一简单概念,可以将落地页 URL 简单地转成场景,从而让图文/图集作者可以一键开始视频内容的编辑和创作。


图 17 展示了这一创作过程的流程图。


△图 17 URL 转视频流程


当转成时间轴之后,即可调用视频编辑器的接口,生成和发布视频。


5.3 图文转视频 Demo


文末会附上几个图文转视频项目在技术验证时生成的视频,以展现实际效果。


请前往该链接观看:https://mp.weixin.qq.com/s/wHrQS9DXEKcszpiILt9Gmg


6. 总结与展望

6.1 组合创新,适应潮流

百家号的在线视频编辑器技术可以简单总结为:后端使用 PHP 将前端 JS 生成的时间轴格式数据转译成 FFmpeg 命令,并通过 Dispatch 调度调度框架来执行 FFmpeg 产出最终视频。从这一层面看,这一技术没有高深的技术门槛,没有复杂抽象的逻辑模型,我们的技术创新,主要是组合现有技术,形成一项适应潮流的新的技术方案。


伴随着视频化浪潮到来的,不仅是普通用户对视频内容的大量需求,还有创作者对视频编辑工具便利性的热切期待。百家号一直站创作者的角度,为创作者们提供更加优秀的视频编辑器。希望通过我们的努力,给视频化浪潮里的创作者们带去得力的船桨。


6.2 技术共享,合作共赢

随后,百度媒体云基于这一技术开发出了智能视频快编服务。得益于媒体云的长期技术积累和对视频编辑底层技术的深入挖掘,智能视频快编服务使用智能分片+GPU 编解码技术,将视频编辑合成的效率提升了数倍,同时也提供了更多新特性和新功能,使在线视频编辑技术更加实用化。


目前,百家号正在将视频编辑器及通用视频编辑能力的底层服务逐步迁移到媒体云的智能视频快编服务。百家号团队作为在线视频编辑器技术的输出方,已经开始享受技术合作带来的红利。

用户头像

百度Geek说

关注

百度官方技术账号 2021.01.22 加入

关注我们,带你了解更多百度技术干货。

评论

发布
暂无评论
百家号在线视频编辑器的技术演进