效果图
![](http://file.zhishichong.com/images/article/20161028/005NFHyQgw1f5nt0cvpqjg308l0ftx6s.gif)
![](http://file.zhishichong.com/images/article/20161028/005NFHyQgw1f5nt137nbwg308l0fte89.gif)
由于
licecap
录制的GIF失帧太严重, 都模糊掉了, 再放两张高清截图前言
今年三月份,
斗鱼
获腾讯
领投的1亿美元融资的消息被各大平台报道转载,在电竞、泛娱乐已是热门投资的当下,网络直播平台自然也获得了各界的关注。盗用两张关于游戏直播的趋势图
这还仅仅是游戏直播这块的蛋糕.直播
行业的竞争会越来越激烈, 不管是主播还是直播平台都面临着激烈的竞争, 当然直播
行业也会越来越规范, 直播元素也越来越多.
视频直播初窥
视频直播,可以分为 采集,前处理,编码,传输, 服务器处理,解码,渲染
- 采集: iOS系统因为软硬件种类不多, 硬件适配性比较好, 所以比较简单. 而Android端市面上机型众多, 要做些机型的适配工作.PC端是最麻烦的, 各种奇葩摄像头驱动.所以现在很多的中小型直播平台, 都放弃了PC的直播, 更有一些直播平台只做iOS端的视频直播.
- 前处理: 美颜算法,视频的模糊效果, 水印等都是在这个环节做. 目前iOS端最著名开源框架的毫无疑问就是
GPUImage
.其中内置了125种渲染效果, 还支持各种脚本自定义. 我高仿的喵播
的美颜效果也是基于GPUImage
的. - 编码: 重难点在于要在分辨率,帧率,码率,GOP等参数设计上找到最佳平衡点。iOS8之后,
Apple
开放了VideoToolbox.framework
, 可以直接进行硬编解码, 这也是为什么现在大多数直播平台最低只支持到iOS8的原因之一. iOS端硬件兼容性比较好, 可以直接采取硬编码. 而Android得硬编码又是一大坑. - 传输: 这块一般都是交给
CDN
服务商.CDN
只提供带宽和服务器之间的传输, 发送端和接收端的网络连接抖动缓存还是要自己实现的.目前国内最大的CDN
服务商应该是网宿
. - 服务器处理: 需要在服务器做一些流处理工作, 让推送上来的流适配各个平台各种不同的协议, 比如:RTMP,HLS,FLV…
- 解码和渲染: 也就即音视频的播放. 解码毫无疑问也必须要硬解码. iOS端兼容较好, Android依然大坑.这块的难点在于音画同步, 目前很多直播平台这块是硬伤.国内比较好的开源项目应该是B站开源的ijkplayer .
斗鱼
就是基于ijkplayer 的, 本项目也是基于ijkplayer 的.
技术坑 : 降噪, 音频解码器, 蓝牙适配, 回声消除, 信令控制, 登录, 鉴权, 权限管理, 状态管理, 应用消息, 消息推送, 礼物系统, 即时聊天, 支付系统, 统计系统, 数据库, 缓存, 分布式文件存储, 消息队列, 运维系统等等大小不一的坑等你来填!!!
资金坑 : 以带宽为例, 2万人同时在线, 手机码率在600KB, 每个月的带宽费用至少在30万左右. 根据欢聚时代(YY)15年四季度财务报, 他们的带宽成本为人民币1.611亿元, 折合每月5000万+. 人力成本+渠道支出和其他支出就不详谈了.
社会坑: 还得每时每刻与各种黑暗势力斗争, 包括色情, 广告, 刷小号, 刷充值, 告侵权, DDos…(我反编译
喵播
的官方APP, 他们的项目名就叫Shehui
, O(∩_∩)O哈哈~)
项目下载地址
前期准备
项目主要是基于ijkplayer 的. 最好是打包成framework
. 原本我准备写一个打包教程, 不过后来在简书上发现了一篇特别详细的打包blog, 分享给大家: http://www.jianshu.com/p/1f06b27b3ac0.
如果你根据教程打包失败了(当然这种几率比较小), 我这还有一份我已经打包好的(Release版), 下载地址:
链接:http://pan.baidu.com/s/1eRVetdK 密码:2dc0
下载后, 直接解压即可.
项目文件结构
- Frameworks: 如果文件夹不存在, 点击
classes
选择Show in Finder
, 新建一个即可, 将你打包的或者下载的framework
拖入其中并拉进项目中. 你也可以自己建一个文件夹, 把这个Frameworks
直接delete
即可 - Profile : 个人中心, 这里面只有一个
ProfileController
. 因为总写重复代码, 都写吐了, 这儿有兴趣的自己写一下吧, So easy… - Network : 关于网络连接的工具类. 关于网络的实时监控, 网络状态的切换, 网络请求的工具类都在这里面.
- Other : 全局的常量. 当然你也可以在里面将文件结构更加细化.
- Home : 包含最新主播, 最热直播, 关注的直播, 礼物排行榜等模块. 还有最重要的视频直播也在这里面了.
- ShowTime :见名知意. 视频直播的前处理, 智能美颜和H264硬编码等都在这里面.
- Main :
UITabBarController
和UINavigationController
的配置 - Toos : 这儿命名有点不规范, 这里面放置的都是项目用到的分类
- Login : 登录模块
- Resource : 项目用到的资源文件
项目详解
- tip1: 判读网络类型.
在观看直播的时候, 我们通常都是用WiFi或者3/4G(土豪级别的), 一般用户在进行网络切换的时候, 我们都要给出友善的提示, 告诉TA: 您的网络状态切换到了XX状态. 假设用户从WiFi切换到4G, 你的应用也没个提醒, 导致TA的流量归零甚至欠了运营商一屁股的钱, 我想你的APP的用户体验也就归零或者为负了.
我们可以使用苹果的
Reachability
结合下面的代码实时监听网络状态的改变
1 2 3 4 5 6 7 |
typedef NS_ENUM(NSUInteger, NetworkStates) { NetworkStatesNone, // 没有网络 NetworkStates2G, // 2G NetworkStates3G, // 3G NetworkStates4G, // 4G NetworkStatesWIFI // WIFI }; |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
// 判断网络类型 + (NetworkStates)getNetworkStates { NSArray *subviews = [[[[UIApplication sharedApplication] valueForKeyPath:@"statusBar"] valueForKeyPath:@"foregroundView"] subviews]; // 保存网络状态 NetworkStates states = NetworkStatesNone; for (id child in subviews) { if ([child isKindOfClass:NSClassFromString(@"UIStatusBarDataNetworkItemView")]) { //获取到状态栏码 int networkType = [[child valueForKeyPath:@"dataNetworkType"] intValue]; switch (networkType) { case 0: //无网模式 states = NetworkStatesNone; break; case 1: states = NetworkStates2G; break; case 2: states = NetworkStates3G; break; case 3: states = NetworkStates4G; break; case 5: { states = NetworkStatesWIFI; } break; default: break; } } } //根据状态选择 return states; } |
- tip2: 登录模块
如果你多运行几次就会发现, 登录模块背景中播放的视频是2个视频每次随机播放一个的.并且是无限重复的, 也就是说只要你一直呆着登录界面, 就会单视频循环播放当前的视频. 这儿的登录只是几个按钮, 没有具体的登录逻辑, 随便点哪一个按钮都可以进入首页.
我们需要监听视频, 是否播放完成.
12// 监听视频是否播放完成[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didFinish) name:IJKMPMoviePlayerPlaybackDidFinishNotification object:nil];如果播放完成了, 让
IJKFFMoviePlayerController
再次play
即可