前言

gsyVideoPlayer是一个很棒的播放器,也可以当成是对ijkPlayer的封装库。
在初始化时,可以写如下代码。当然这是默认的,可以不写。

PlayerFactory.setPlayManager(IjkPlayerManager.class);

默认选择ijkplayer播放,那么像使用其他播放器怎么办,gsyVideoPlayer提供了如下选择:

PlayerFactory.setPlayManager(IjkPlayerManager.class);//ijk内核,默认模式
PlayerFactory.setPlayManager(SystemPlayerManager.class);//系统内核模式
PlayerFactory.setPlayManager(Exo2PlayerManager.class);//EXOPlayer内核

但是这三种都不是自己想用的怎么办,如果使用腾讯播放器如何集成进去?
翻看PlayerFactory的源码,在 getPlayManager 方法会返回一个IPlayerManager对象,那么我只要写一个QQPlayerManager,然后在这样初始化就行了。

PlayerFactory.setPlayManager(QQPlayerManager.class);//使用腾讯播放器

集成腾讯播放器

在写QQPlayerManager前,需要去腾讯播放器网站 下载SDK。然后如下方式集成:

compile(name: 'LiteAVSDK_Player', ext: 'aar')
//compile(name: 'libsuperplayer', ext: 'aar')//使用gsyVideoPlayer,这个就可以不要了

接着就可以直接写了,QQPlayerManager要实现IPlayerManager,那么写起来只要将接口IPlayerManager的方法实现既可以,此处就直接贴代码了。
QQPlayerManager.java

package com.shopshops.cn.player;import android.content.Context;
import android.media.AudioManager;
import android.os.Message;
import android.view.Surface;import com.shopshops.cn.BuildConfig;
import com.shuyu.gsyvideoplayer.cache.ICacheManager;
import com.shuyu.gsyvideoplayer.model.GSYModel;
import com.shuyu.gsyvideoplayer.model.VideoOptionModel;
import com.shuyu.gsyvideoplayer.player.IPlayerManager;import java.util.List;import tv.danmaku.ijk.media.player.IMediaPlayer;public class QQPlayerManager implements IPlayerManager {private QQMediaPlayer mediaPlayer;private boolean release;private Surface surface;@Overridepublic IMediaPlayer getMediaPlayer() {return mediaPlayer;}@Overridepublic void initVideoPlayer(Context context, Message message, List<VideoOptionModel> optionModelList, ICacheManager cacheManager) {boolean enableHardware = true;/*GSYVideoManager videoManager = GSYVideoManager.instance();String playTag = videoManager.getPlayTag();if (!TextUtils.isEmpty(playTag))enableHardware = playTag.startsWith("m3u8Speed");*/mediaPlayer = new QQMediaPlayer(context, enableHardware);mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);release = false;GSYModel gsyModel = (GSYModel) message.obj;try {if (gsyModel.isCache() && cacheManager != null) {cacheManager.doCacheLogic(context, mediaPlayer, gsyModel.getUrl(), gsyModel.getMapHeadData(), gsyModel.getCachePath());} else mediaPlayer.setDataSource(gsyModel.getUrl());mediaPlayer.setLooping(gsyModel.isLooping());if (gsyModel.getSpeed() != 1 && gsyModel.getSpeed() > 0) {setSpeed(gsyModel.getSpeed());}} catch (Exception e) {if (BuildConfig.DEBUG) e.printStackTrace();}}@Overridepublic void showDisplay(Message msg) {Surface holder = (Surface) msg.obj;if (holder == null && mediaPlayer != null && !release) {mediaPlayer.setSurface(null);} else if (holder != null) {if (mediaPlayer != null && holder.isValid() && !release) {mediaPlayer.setSurface(holder);}//if (surface != null) surface.release();surface = holder;}}@Overridepublic void setNeedMute(boolean needMute) {//是否静音if (mediaPlayer != null && !release) {if (needMute) {mediaPlayer.setVolume(0, 0);} else mediaPlayer.setVolume(1, 1);}}@Overridepublic void releaseSurface() {if (surface != null) {surface.release();surface = null;}}@Overridepublic void release() {if (mediaPlayer != null) {release = true;mediaPlayer.release();}}@Overridepublic int getBufferedPercentage() {if (mediaPlayer == null) return -1;else return (int) mediaPlayer.getMediaPlayer().getBufferDuration();}@Overridepublic long getNetSpeed() {//if (mediaPlayer == null)return 0;}@Overridepublic void setSpeedPlaying(float speed, boolean soundTouch) {}@Overridepublic boolean isSurfaceSupportLockCanvas() {return false;}@Overridepublic void setSpeed(float speed, boolean soundTouch) {setSpeed(speed);}private void setSpeed(float speed) {if (release) {return;}if (mediaPlayer != null && mediaPlayer.getMediaPlayer() != null && mediaPlayer.isPlayable()) {mediaPlayer.getMediaPlayer().setRate(speed);}}@Overridepublic void start() {if (mediaPlayer != null) mediaPlayer.start();}@Overridepublic void stop() {if (mediaPlayer != null) mediaPlayer.stop();}@Overridepublic void pause() {if (mediaPlayer != null) mediaPlayer.pause();}@Overridepublic int getVideoWidth() {if (mediaPlayer == null) return 0;else return mediaPlayer.getVideoWidth();}@Overridepublic int getVideoHeight() {if (mediaPlayer == null) return 0;else return mediaPlayer.getVideoHeight();}@Overridepublic boolean isPlaying() {if (mediaPlayer == null) return false;else return mediaPlayer.isPlaying();}@Overridepublic void seekTo(long time) {if (mediaPlayer == null) return;else mediaPlayer.seekTo(time);}@Overridepublic long getCurrentPosition() {if (mediaPlayer == null) return 0;else return mediaPlayer.getCurrentPosition();}@Overridepublic long getDuration() {if (mediaPlayer == null) return 0;else return mediaPlayer.getDuration();}@Overridepublic int getVideoSarNum() {if (mediaPlayer == null) return 0;else return mediaPlayer.getVideoSarNum();}@Overridepublic int getVideoSarDen() {if (mediaPlayer == null) return 0;else return mediaPlayer.getVideoSarDen();}
}

initVideoPlayer用于初始化mediaPlayer ,mediaPlayer 是视频播放的核心,那么这儿也就少不了使用腾讯的mediaPlayer 。
QQMediaPlayer.java

package com.shopshops.cn.player;import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
import android.text.TextUtils;
import android.view.Surface;
import android.view.SurfaceHolder;import com.shopshops.cn.BuildConfig;
import com.shopshops.cn.base.AppConstant;
import com.shopshops.mylibrary.Logger;
import com.tencent.rtmp.ITXVodPlayListener;
import com.tencent.rtmp.TXLiveConstants;
import com.tencent.rtmp.TXVodPlayer;import java.io.FileDescriptor;
import java.io.IOException;
import java.util.Map;import tv.danmaku.ijk.media.player.AbstractMediaPlayer;
import tv.danmaku.ijk.media.player.MediaInfo;
import tv.danmaku.ijk.media.player.misc.ITrackInfo;public class QQMediaPlayer extends AbstractMediaPlayer {private TXVodPlayer txVodPlayer;private MediaInfo mediaInfo;private boolean mIsReleased;private boolean isPause;private String url;private Surface surface;private boolean canStart;private long progress_ms;//播放进度private long duration_ms_total;//视频总长private Context mContext;//notifyOnErrorpublic QQMediaPlayer(Context context, boolean enableHardware) {this.mContext = context;txVodPlayer = new TXVodPlayer(context);txVodPlayer.enableHardwareDecode(enableHardware);txVodPlayer.setVodListener(new ITXVodPlayListener() {@Overridepublic void onPlayEvent(TXVodPlayer txVodPlayer, int event, Bundle param) {if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "--event--" + event);if (event == TXLiveConstants.PLAY_EVT_PLAY_BEGIN) {//视频播放开始notifyOnPrepared();if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "视频播放开始");} else if (event == TXLiveConstants.PLAY_EVT_VOD_LOADING_END) {//loadingEndif (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "loadingEnd");//没有这个事件,发一个广播出去LocalBroadcastManager.getInstance(mContext).sendBroadcast(new Intent(AppConstant.PLAY_EVT_VOD_LOADING_END));} else if (event == TXLiveConstants.PLAY_EVT_PLAY_PROGRESS) {//视频播放进度// 加载进度, 单位是毫秒int duration_ms = param.getInt(TXLiveConstants.EVT_PLAYABLE_DURATION_MS);// 播放进度, 单位是毫秒progress_ms = param.getInt(TXLiveConstants.EVT_PLAY_PROGRESS_MS);// 视频总长, 单位是毫秒duration_ms_total = param.getInt(TXLiveConstants.EVT_PLAY_DURATION_MS);if (BuildConfig.DEBUG) {Logger.i("--xcc--QQMediaPlayer", "播放进度:" + param.getInt(TXLiveConstants.EVT_PLAY_PROGRESS_MS));}notifyOnBufferingUpdate(duration_ms);} else if (event == TXLiveConstants.PLAY_EVT_PLAY_END) {//视频播放结束notifyOnCompletion();if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "视频播放结束");} else if (event == TXLiveConstants.PLAY_ERR_NET_DISCONNECT || event == TXLiveConstants.PLAY_WARNING_RECONNECT) {//网络断连notifyOnError(event, 1);if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "网络断连");} else if (event == TXLiveConstants.PLAY_WARNING_VIDEO_DECODE_FAIL) {//当前视频帧解码失败notifyOnError(event, 1);if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "当前视频帧解码失败");} else if (event == TXLiveConstants.PLAY_WARNING_AUDIO_DECODE_FAIL) {//当前音频帧解码失败notifyOnError(event, 1);if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "当前音频帧解码失败");} else if (event == TXLiveConstants.PLAY_WARNING_HW_ACCELERATION_FAIL) {//硬解失败if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "硬解失败");} else if (event == TXLiveConstants.PLAY_EVT_CHANGE_RESOLUTION) {//视频分辨率改变notifyOnVideoSizeChanged(param.getInt(TXLiveConstants.EVT_PARAM1), param.getInt(TXLiveConstants.EVT_PARAM2), getVideoSarNum(), getVideoSarNum());if (BuildConfig.DEBUG) Logger.i("--xcc--QQMediaPlayer", "视频分辨率改变");}}@Overridepublic void onNetStatus(TXVodPlayer txVodPlayer, Bundle bundle) {}});}@Overridepublic void setDisplay(SurfaceHolder sh) {Surface surface = sh.getSurface();setSurface(surface);}@Overridepublic void setDataSource(Context context, Uri uri) throws IOException, IllegalArgumentException, SecurityException, IllegalStateException {this.url = uri.getPath();}@Overridepublic void setDataSource(Context context, Uri uri, Map<String, String> map) throws IOException, IllegalArgumentException, SecurityException, IllegalStateException {this.url = uri.toString();}@Overridepublic void setDataSource(FileDescriptor fileDescriptor) throws IOException, IllegalArgumentException, IllegalStateException {}@Overridepublic void setDataSource(String url) throws IOException, IllegalArgumentException, SecurityException, IllegalStateException {this.url = url;}@Overridepublic String getDataSource() {return url;}@Overridepublic void prepareAsync() throws IllegalStateException {notifyOnPrepared();}@Overridepublic void start() throws IllegalStateException {if (isPause) {//暂停后恢复播放isPause = false;txVodPlayer.resume();} else {if (TextUtils.isEmpty(url) || surface == null) {canStart = true;return;}this.txVodPlayer.startPlay(url);}}@Overridepublic void stop() throws IllegalStateException {isPause = false;this.txVodPlayer.stopPlay(false);}@Overridepublic void pause() throws IllegalStateException {isPause = true;this.txVodPlayer.pause();}@Overridepublic void setScreenOnWhilePlaying(boolean screenOn) {//txVodPlayer.setScreenOnWhilePlaying(screenOn);}@Overridepublic int getVideoWidth() {return txVodPlayer.getWidth();}@Overridepublic int getVideoHeight() {return txVodPlayer.getHeight();}@Overridepublic boolean isPlaying() {return txVodPlayer.isPlaying();}@Overridepublic void seekTo(long msec) throws IllegalStateException {float v = msec / 1000.0f;this.txVodPlayer.seek(v);//腾讯这儿是百分比}@Overridepublic long getCurrentPosition() {return progress_ms;//return (long) txVodPlayer.getCurrentPlaybackTime();}@Overridepublic long getDuration() {return duration_ms_total;//float duration = txVodPlayer.getDuration();//return (long) duration;}@Overridepublic void release() {txVodPlayer.stopPlay(true);this.mIsReleased = true;this.resetListeners();}@Overridepublic void reset() {//txVodPlayer.resume();//这个是恢复播放的this.resetListeners();}@Overridepublic void setVolume(float leftVolume, float rightVolume) {txVodPlayer.setMute(leftVolume + rightVolume == 0);}@Overridepublic int getAudioSessionId() {return 0;}@Overridepublic MediaInfo getMediaInfo() {if (mediaInfo == null) {MediaInfo module = new MediaInfo();module.mVideoDecoder = "QQMediaPlayer";module.mVideoDecoderImpl = "HW";module.mAudioDecoder = "QQMediaPlayer";module.mAudioDecoderImpl = "HW";mediaInfo = module;}return mediaInfo;}@Overridepublic void setLogEnabled(boolean b) {}@Overridepublic boolean isPlayable() {return true;}@Overridepublic void setAudioStreamType(int streamtype) {}@Overridepublic void setKeepInBackground(boolean keepInBackground) {}@Overridepublic int getVideoSarNum() {return 1;}@Overridepublic int getVideoSarDen() {return 1;}@Overridepublic void setWakeMode(Context context, int mode) {}@Overridepublic void setLooping(boolean b) {txVodPlayer.setLoop(b);}@Overridepublic boolean isLooping() {return txVodPlayer.isLoop();}@Overridepublic ITrackInfo[] getTrackInfo() {return new ITrackInfo[0];}@Overridepublic void setSurface(Surface surface) {if (surface == this.surface) return;this.surface = surface;/*if (surface == null) {if (!isPause) pause();}*/txVodPlayer.setSurface(surface);if (surface == null) return;if (TextUtils.isEmpty(url)) return;if (canStart) {canStart = false;start();/*} else if (isPause) {start();*/}}public TXVodPlayer getMediaPlayer() {return txVodPlayer;}
}

QQMediaPlayer需要继承AbstractMediaPlayer,实现里面抽象方法即可,同时TXVodPlayer是腾讯播放器的核心。这样做就可以让原先使用gsyVideoPlayer的项目,更快的切换到QQMediaPlayer。下一篇讲为什么要使用腾讯播放器,原先的播放器为什么不可以,以及如何同时使用两个播放器。

gsyVideoPlayer直播短视频回放,集成腾讯播放器相关推荐

  1. Android 基于GSYVideoPlayer实现短视频软件上下滑自动播放视频

    先放效果图 两个视频的地址: private final String mp4_a = "http://vfx.mtime.cn/Video/2019/03/19/mp4/190319212 ...

  2. 直播PK短视频?直播+短视频才是王道

    直播PK短视频?直播+短视频才是王道 复制代码 在这个快节奏的时代,短视频也成为了大众娱乐消遣的心头好.在排队,坐地铁,坐公交等等碎片时间里,我们经常可以看见大家抱着手机在看一些短视频打发时间. 7月 ...

  3. 强强联手,直播+短视频,碰撞出灿烂的烟火

    强强联手,直播+短视频,碰撞出灿烂的烟火 短视频究竟有多火? 当流量.宽带.资费.终端等都不再是问题,尤其是在视频移动化.资讯视频和视频社交化的趋势带动下,短视频营销正在成为新的品牌营销风向. 这几年 ...

  4. 泛娱乐市场如日中天,直播短视频黄金时代来临

    昨天中国泛娱乐赛道的重要玩家欢聚时代发布了一季度财报,该季度其总营收为32.489亿元,同比增长43.3%,非美国通用会计准则下,净利润达6.999亿元,同比增长31.1%,其总营收和利润还是高于市场 ...

  5. 实现网页直播源码的直播与视频回放功能

    流程介绍 网页直播源码直播.视频回放大致流程:获取视频流或本地音视频文件,将流推入到流媒体服务器当中,在 web 端使用合适的 js 拉流并播放音视频: 三种网页直播源码常见的流媒体协议介绍(RTMP ...

  6. 直播短视频手机APP应用下载页面静态html网页模板

    介绍: 直播短视频手机APP应用下载页面静态html网页模板,上传服务器即可使用 网盘下载地址: http://kekewl.cc/e7O1upV2sJR0 图片:

  7. 玩转直播+短视频 京东打造“史上最简单618”

    疫情之下,直播+短视频成为新时代的"弄潮儿",也成为本届"618"的最大看点之一! 与往年不同,本届"618"购物节,京东在站内站外联动布置 ...

  8. 超火网络直播短视频宣传海报PSD分层模板,新媒体互动

    这个年头如果你不懂直播间带货,你就真的"OUT"了 除了李佳琦薇娅们一些企业和品牌代言人,甚至还有村长县长们也都华丽丽转身纷纷走入直播 间,加入主播行列. 但以往直播带货都给人一种 ...

  9. 苹果/安卓直播短视频APP系统源码

    直播短视频产品价值 短视频能引流 直播能转化,将用户沉淀到自己的平台,流量获取途径打造. 直播短视频开发与执行 1.安卓app用Java语言面向对象,分布式处理,安全性更高,高性能 2.苹果app用O ...

  10. 数美科技直播短视频行业未成年人保护解决方案:全方位护航未成年人视听娱乐安全

    数字信息爆炸的时代,直播.短视频凭借趣味性.强互动.碎片化.陪伴性等特点,成为最受人们欢迎的娱乐方式之一,许多未成年人也沉浸在由一场场直播和一个个短视频构建出的虚拟世界中无法自拔. 直播.短视频平台为 ...

最新文章

  1. TBluetoothLE.OnDisconnectDevice
  2. lmbs PHP,PHP的GD2函数创建折线图源码示例
  3. python——类和对象之__dict__属性的使用
  4. linux nagios 检查udp端口,nagios插件之监控udp端口状态
  5. C和指针之函数之求最大公约数
  6. I-EIM分享一套局域网通讯源码
  7. 【OJ二分06】月度开销
  8. 液冷计算机组装,电脑水冷散热器原理解密及安装方法
  9. buildroot 编译问题
  10. WARN: Establishing SSL connection without server's identity verification is not recommended
  11. 提高搜索引擎结果页面排名的各种技术
  12. 【EXCEPTION_INIT】自定义错误名称并关联错误号
  13. Ajax.net中的Web服务
  14. Java—读取多层嵌套Json文件的内容并根据索引返回JsonObject
  15. 深度时空网络、记忆网络与特征表达学习在 CTR 预估中的应用
  16. 计算机系统保密检查整改情况函,民政局保密工作整改情况的报告
  17. python垃圾邮件识别_垃圾邮件过滤器 python简单实现
  18. 异常与调试之SEH、UEH、VEH、VCH以及SEH的区别总结——简单好理解
  19. C语言 输入今天的日期,显示明天的日期
  20. AI文件资源导出方法

热门文章

  1. RFID仓库管理系统解决方案有哪些功能模块
  2. 2019年外卖市场分析:本地外卖创业要注意哪些趋势?
  3. 逆流而上,整合阿里高频考点2023Java岗面试突击指南手册最新首发
  4. ADS1115的IIC通信
  5. Edge浏览器配置教程
  6. python爬虫使用指南_如何使用Python构建Web爬虫[分步指南]
  7. CVPR 2021 预讲 · 华为诺亚专场,5 篇精华报告,覆盖NAS、蒸馏、检测和降噪
  8. 从远程仓库获取最新代码合并到本地分支
  9. Electron“安装已中止,安装程序未成功地运行完成”
  10. Windows下打包安装程序