1. 背景
在开发小窗播放的时候遇到的问题,应用主页和详情页都有一个小窗播放,还有一个全屏的播放页,测试的时候发现两种小窗播放的场景不能播放,而全屏的页面却可以。
2. 报错
04-02 16:32:47.005 E/HttpProxyCacheDebuger( 8515): Error fetching info from 01.m3u8?..
...
04-02 16:32:47.006 W/System.err( 8515): java.net.MalformedURLException: Protocol not found: 01.m3u8?
...
04-02 16:32:47.014 E/HttpProxyCacheServer error( 8515): Error processing request. Version: 6.0.1
...
04-02 16:32:47.016 E/tv.danmaku.ijk.media.player.IjkMediaPlayer( 8515): Error (-10000,0)
3. 问题
经过测试发现两点:1. 拿到的播放链接是经过302重定向跳转的;2. 因为有小窗播放,在页面跳转回来的时候需要重新播放触发了onResume。
众所周知,GSYVideoPlayer最方便的点就在于可以切换系统内核、ijkplayer内核,exo2Player三种不同的内核,我开始使用的是ijk的内核,在进入小窗播放页面的时候会调用 startPlayLogic 开始播放,在等待播放的同时触发了Activity的onResume,在onResume中又重新调用了一遍 startPlayLogic,导致播放失败。
4. 解决
知道了问题之后,将其改为一次调用,发现ijkplayer内核会对重定向的视频链接做解析,得到真正的文件链接之后然后再去播放,整个过程大概用了20s左右,时间实在是太长了,不能忍受。
后来我将内核切换到系统内核,发现视频不能播了,原来系统内核不会对重定向的地址做解析,那就需要一个解析真正视频地址的操作如下:
new Thread(new Runnable() {
@Override
public void run() {
URL url = null;
try {
url = new URL(finalPlayUrl); // 原有的url
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.getResponseCode();
String realUrl = conn.getURL().toString(); // 真正的播放链接
conn.disconnect();
} catch (Exception e) {
e.printStackTrace();
}
}
}).start();
加上网络连接到真正播放,耗时5s以内,还是勉强可以接受的。
5. 总结
1. ijkplayer内核会对重定向的地址做解析,但是整体速度会非常慢。
2. 测试使用的链接是:http://devimages.apple.com/iphone/samples/bipbop/bipbopall.m3u8,因为需要模拟重定向的操作,就让服务端的同学帮忙做了一层转换。