GSYVideoPlayer:Android 视频列表(RecyclerView)实现自动播放

在GitHub上面看了GSYVideoPlayer的demo代码,发现视频列表自动播放势必是不是很准确,然后结合了饺子播放器的demo代码整理了相关自动播放的代码

var linearLayoutManager = LinearLayoutManager(context, RecyclerView.VERTICAL, false)
recyclerView.layoutManager = linearLayoutManager


1/在这里注册RecyclerView的滑动监听
recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
    override fun onScrollStateChanged(recyclerView: RecyclerView, newState: Int) {
        super.onScrollStateChanged(recyclerView, newState)
        if (newState == RecyclerView.SCROLL_STATE_IDLE) {
            AutoPlayUtils.onScrollPlayVideo(
                recyclerView,
                R.id.player,
                linearLayoutManager!!.findFirstVisibleItemPosition(),
                linearLayoutManager!!.findLastVisibleItemPosition()
            )
        }
    }

    override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
        super.onScrolled(recyclerView, dx, dy)
        if (dy != 0) {
            AutoPlayUtils.onScrollReleaseAllVideos(
                linearLayoutManager!!.findFirstVisibleItemPosition(),
                linearLayoutManager!!.findLastVisibleItemPosition(),
                0.2f
            )
        }
    }
})

2/自定义CoverVideo View并继承GSYVideoPlayer

public class CoverVideo extends StandardGSYVideoPlayer {
    public static CoverVideo CURRENT_VIDEO;
    @Override
    public void startPlayLogic() {
        CURRENT_VIDEO = this;
        super.startPlayLogic();
    }
}

3/AutoPlayUtils具体滚动判断的类

/**
 * 列表自动播放工具类
 *
 * @author Liberations
 */
object AutoPlayUtils {
    var positionInList = -1 //记录当前播放列表位置

    /**
     * @param firstVisiblePosition 首个可见item位置
     * @param lastVisiblePosition  最后一个可见item位置
     */
    fun onScrollPlayVideo(
        recyclerView: RecyclerView,
        jzvdId: Int,
        firstVisiblePosition: Int,
        lastVisiblePosition: Int
    ) {
        for (i in 0..lastVisiblePosition - firstVisiblePosition) {
            val child = recyclerView.getChildAt(i)
            val view = child.findViewById<View>(jzvdId)
            if (view != null && view is CoverVideo) {
                if (getViewVisiblePercent(view) == 1f) {
                    if (positionInList != i + firstVisiblePosition) {
                        if (view.currentState != GSYVideoView.CURRENT_STATE_PLAYING) {
                            if (CoverVideo.CURRENT_VIDEO != null) {
                                //释放之前的view
                                CoverVideo.CURRENT_VIDEO.release()
                                CoverVideo.CURRENT_VIDEO = null
                            }
                            view.startPlayLogic()
                        }
                    }
                    break
                }
            }
        }
    }

    /**
     * @param firstVisiblePosition 首个可见item位置
     * @param lastVisiblePosition  最后一个可见item位置
     * @param percent              当item被遮挡percent/1时释放,percent取值0-1
     */
    fun onScrollReleaseAllVideos(
        firstVisiblePosition: Int,
        lastVisiblePosition: Int,
        percent: Float
    ) {
        if (CoverVideo.CURRENT_VIDEO == null) return
        if (positionInList >= 0) {
            if (positionInList <= firstVisiblePosition || positionInList >= lastVisiblePosition - 1) {
                if (getViewVisiblePercent(CoverVideo.CURRENT_VIDEO) < percent) {
                    CoverVideo.CURRENT_VIDEO.release()
                    CoverVideo.CURRENT_VIDEO = null
                }
            }
        }
    }

    /**
     * @param view
     * @return 当前视图可见比列
     */
    fun getViewVisiblePercent(view: View?): Float {
        if (view == null) {
            return 0f
        }
        val height = view.height.toFloat()
        val rect = Rect()
        if (!view.getLocalVisibleRect(rect)) {
            return 0f
        }
        val visibleHeight = (rect.bottom - rect.top).toFloat()
        return visibleHeight / height
    }
}

(在此感谢GSYVideoPlayer和饺子播放器的作者的无私分享)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值