无Flash插件下利用js播放flv视频

2,281 阅读6分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

Flash插件想必大家都有所了解。曾经几乎所有的网站都需要加载Flash插件才能浏览完整内容。如今已经逐渐淡出了大众视野,但本期我们依然挖掘一些Flash遗留的技术问题,供大家参考。

盛行一时的Flash谢幕

Flash是一种多媒体创作和播放支持技术,在互联网技术史上曾经扮演过重要的地位。在20多年前,网络技术还不像今天一样发达的年代,人们曾经重度依赖Flash制作网页、广告、小软件、游戏等多种多样酷炫、可互动的在线内容。Flash一度达到98%的覆盖率,数以亿计的设备运行着Flash。即使到了2014年,依然有大约80%的Chrome浏览器用户会访问包含Flash内容的网站。

这就导致了一个问题,早期网络播放器大量依赖于Flash Player,自然而然地,流媒体文件格式flv(Flash Video)就成了网络最常用的流媒体格式。然而,随着时间推移,Flash的各种缺点暴露出来,耗电量大、运行缓慢、安全问题,兼容性问题(Flash原来只针对pc平台,移动端对Flash支持不友好)等,使得Flash日渐衰落。

2020年7月25日,Adobe 官方正式宣布,将在 2020 年底前正式停止 Flash Player 的开发、维护和更新。Adobe 强烈建议所有用户立即卸载 Flash Player 以避免后续漏洞攻击。这意味着宣告Adobe Flash Player时代终结 。

image.png

谷歌也早就宣布计划在2020年底(2020年12月31日),其下的Chrome浏览器将彻底移除Flash播放器,不再以任何方式支持Flash。随着谷歌带头,各大浏览器厂商会陆续不再支持Flash,最迟到2020年底。这是当时我收到的公告原文(截图):

ff2a5246c37a443b88303167855e6237.png

谷歌浏览器作为市场占有率最大的浏览器,他的公告几乎是宣判了Flash的死刑:

image.png

那么之前的flv格式视频媒体文件的播放就成为了一个问题。

B站与HTML5视频播放

进入Web2.0时代,新一代标记语言HTML5成为主流。很多网站开始向HTML5转移。比如我们广大青年喜爱的哔哩哔哩。HTML5中播放视频用的是video标签,仅支持Ogg、MPEG4、WebM三种格式。可是B站上依然有很多的flv格式的视频,如何处理呢?

这是一个历史遗留问题,前面也说了,由于早期网络上Flash盛行,很多视频格式都是方便传输的flv格式。这导致早期的哔哩哔哩上的视频都是flv格式的,所以B站上存储着大量的flv格式视频。然而Flash到了2020年底就不再支持,那么它是怎么播放的。B站想出了一个过渡的办法,可以看到B站同时支持Flash和H5播放(截图时间为2019年12月20日):

image.png

两年过去了,我们再看下B站的播放设置(截图与2021年12月7日):

image.png

可以看到,已经没有“播放器选择”这一设置了,彻底放弃了Flash播放器,全面拥抱了H5。

过渡时期解决方案

由于HTML5的video标签只支持mp4,要想支持flv,我们就要拆解flv了。由于flv容器封装的是H264+AAC,所以我们可以在网页端收到flv后,使用js代码解析flv,取出H264以及AAC,然后封装成mp4文件,再喂给video标签就可以了。这样我们就可以无插件播放flv了,由于mp4封装比flv复杂多了,所以这样可以减轻服务器压力,服务器不用再专门封装mp4文件。

优酷用的hls,跟flv类似,也需要一个js插件把hls转成mp4。于是哔哩哔哩自己开发了一套库用于格式转换,使哔哩哔哩网页端平滑过度到 HTML5 播放器,历史遗留不再是障碍。这个库便是flv.js,纯原生 JavaScript 开发。该库用的是ES6语法,然后通过 Babel Compiler 编译成 ECMAScript 5,使用 Browserify 打包。 我写了一个demo,仅供参考:

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8" />
		<title>播放flv</title>
		<script src="https://cdn.bootcss.com/flv.js/1.5.0/flv.min.js"></script>
	</head>
	<body>
		<video  id="videoElement" controls="controls"></video>
		<script>
			if (flvjs.isSupported()) {//检查flvjs能否正常使用
				var videoElement = document.getElementById('videoElement');//使用id选择器找到第二步设置的dom元素
				var flvPlayer = flvjs.createPlayer({//创建一个新的flv播放器对象
					type: 'flv',//类型flv
					url: 'http://localhost:8080/upload/av001.flv'//flv文件地址
				});
				flvPlayer.attachMediaElement(videoElement);//将flv视频装载进video元素内
				flvPlayer.load();//载入视频
				flvPlayer.play();//播放视频,如果不想要自动播放,去掉本行
			}
		</script>
	</body>
</html>

注意,代码中引入的flv.mim.js是由bootcss提供的,如果失效了,请更换其他的cdn源。此外,flv播放器对象,参数url必须是一个http地址,也就是说你至少要在本地搭建一个tomcat服务器,把flv放上去。

又遇Flash

当谷歌宣布不再支持Flash时我就在想,4399等还在使用flash的网站应该要进行大换血了,甚至关闭。后来也没有去关注和注意这件事,直到前几天我打开4399,发现还在运营,页面正常访问。然后我好奇的随便点开一个游戏想玩一玩,看看现在是使用什么技术来取代原来的Flash。按理说现在如果还在使用Flash,Chrome浏览器会出现如下提示:

image.png

结果发现居然还在使用Flash,我当时大为震撼:

image.png

从提示可以看到,Chrome浏览器确实不支持Flash了,所以他让你下载指定的浏览器,还提示你说如果仍无法开始游戏,下载安装Flash插件。这点可以看出,4399并没有进行技术迁移,没有大换血,依然沿用了Flash技术。这是我着实没有想到的,我原本预测要么关闭,要么像B站一样技术升级,没想到还有这波操作。

  于是我又打开了7k7k,结果和4399一样,如图:

image.png

于是我又看了看adobe官网,其首页有如下提示:

image.png

再翻一番Adobe的官方文档,有如下一段:

Adobe 先前宣布计划在 2020 年底停止在全球范围内更新和分发Adobe Flash Player。但是,Adobe先前还拓展了与互联网公司重庆重橙网络科技有限公司(以下简称重橙)的合作伙伴关系;

重橙是Adobe在游戏领域的全球战略合作伙伴,也是Adobe Flash Player在中国大陆的官方发行合作伙伴。Adobe将在2020年以后继续支持重橙仅在中国大陆地区独家发行和维护 Flash Player,以支持该地区市场所特有的的发行渠道、用户习惯以及广泛的开发商、企业和游戏社区。具体可参见中国大陆地区政策。

Adobe将继续与重橙紧密合作,以在整个中国大陆范围内提供最新、最安全的Adobe Flash Player版本。

然后有一则2020年底的公告:

主要内容如下:

2021年1月12日, Flash Player将进行版本更新。由于技术支持原因,本次及后续更新版本的Flash Player在Windows7以下(不包含Windows7)、Linux、Mac操作系统中不再支持视频格式内容的播放功能,其他原有功能可正常使用。

  也就是说国内还是有小部分用户还在使用Flash,国外已经全面废弃了。