從零實(shí)現(xiàn)一個(gè)自定義html5播放器

寫在最前

本次的分享是一個(gè)基于HTML5<vedio>標(biāo)簽實(shí)現(xiàn)的一個(gè)自定義視頻播放器掠兄。其中實(shí)現(xiàn)了播放暫停、進(jìn)度拖拽、音量控制及全屏等功能麦乞。
歡迎關(guān)注我的博客蕴茴,不定期更新中——

效果預(yù)覽

點(diǎn)我查看源碼倉庫

核心思路

我相信一定會有些沒有接觸過制作自定義播放器的童鞋對于<vedio>標(biāo)簽的認(rèn)識會停留在此姐直。

<video controls="controls" autoplay="autoplay">
  <source src="movie.ogg" type="video/ogg" />
</video>

其中controls屬性經(jīng)過設(shè)定倦淀,會在界面中顯示一個(gè)瀏覽器自帶的控制條。如果對于UI沒有要求的需求声畏,其內(nèi)置控制器已經(jīng)可以滿足大部分的需求撞叽。當(dāng)然了如果是這樣你們也不會看到這篇分享了=。=

隱藏控制條并模擬

那么實(shí)現(xiàn)一個(gè)自定義功能的播放器關(guān)鍵就在于插龄,我們不使用原生的控制器愿棋,將其隱藏掉之后,在下方同樣的位置通過html均牢、css來模擬所需樣式糠雨,同時(shí)通過js來調(diào)用vedio標(biāo)簽所暴露給我們的接口函數(shù)及屬性,以及檢測用戶的操作行為來同步的模擬UI與視頻播放數(shù)據(jù)的相應(yīng)變化徘跪。

幾個(gè)核心函數(shù)及屬性的用法

myVid=document.getElementById("video1");
//控制視頻開關(guān)
myVid.play() //播放
myVid.pause() //暫停
//模擬視頻進(jìn)度條
myVid.currentTime=5; //返回或設(shè)定當(dāng)前視頻播放位置
myVid.duration // 返回視頻總長度
//模擬視頻音量
myVid.volume //音量
//獲取視頻當(dāng)前狀態(tài)后判斷何時(shí)從loading切換為播放
myVid.readyState
//0 = HAVE_NOTHING - 沒有關(guān)于音頻/視頻是否就緒的信息
//1 = HAVE_METADATA - 關(guān)于音頻/視頻就緒的元數(shù)據(jù)
//2 = HAVE_CURRENT_DATA - 關(guān)于當(dāng)前播放位置的數(shù)據(jù)是可用的甘邀,但沒有足夠的數(shù)據(jù)來播放下一幀/毫秒
//3 = HAVE_FUTURE_DATA - 當(dāng)前及至少下一幀的數(shù)據(jù)是可用的
//4 = HAVE_ENOUGH_DATA - 可用數(shù)據(jù)足以開始播放

在所有實(shí)現(xiàn)中的關(guān)鍵點(diǎn),較為繁瑣的是對于進(jìn)度條的模擬真椿。其中使用了video標(biāo)簽中的currentTime以及duration屬性鹃答,通過當(dāng)前播放時(shí)間與總播放時(shí)間的比值,就可以計(jì)算出進(jìn)度條相對于總長的位置突硝。同時(shí)用戶通過拖拽進(jìn)度條所最后設(shè)置的長度也可以用來反向推算出此時(shí)視頻應(yīng)該播放的位置测摔。

拖拽代碼思路

//核心代碼示例
var dragDis = 0
var processWidth = xxx //拖拽條總長
$('body').mousedown(function(e) {
    startX = e.clientX
    dragDis = startX - leftInit //leftInit為拖拽條起始點(diǎn)距屏幕左側(cè)的距離
    dragTarget.css({ //拖拽按鈕
        left: dragDis
    })
    dragProcess.css({ //進(jìn)度條(藍(lán)色進(jìn)度條)
        width: dragDis
    }) // 令進(jìn)度條和拖拽按鈕渲染在同一位置
    videoSource.pause()
}).mousemove(function(e) {
    moveX = e.clientX
    disX = moveX - startX
    var left = dragDis + disX
    if(left > processWidth) {
        left = processWidth
    } else if(left < 0) {
        left = 0
    }
    dragTarget.css({
        left: left
    })
    dragProcess.css({
        width: left
    })
}).mouseup(function(e) {
    videoSource.play()
    videoSource.currentTime = $('藍(lán)色拖拽條').width() / processWidth * duration //拖拽后計(jì)算視頻的正確播放位置
})

同理音量的控制與其上行為基本一致,故在源碼中作者將音量與進(jìn)度部分通過不同元素進(jìn)行判斷是進(jìn)行進(jìn)度還是音量的拖拽控制解恰。

通過查詢視頻流狀態(tài)控制播放前的加載動畫

function ifState() {
    var state = videoSource.readyState
    if(state === 4) { //狀態(tài)為4即可播放
        videoPlayer()
    } else {
        $('.play-sym-wrapper').remove()
        $('body').append('<div class="play-sym-wrapper">![](./images/loading.gif)</div>')
        //添加loading動畫
        setTimeout(ifState, 10)
    }
}
setTimeout(ifState, 10)

核心的控制部分已經(jīng)說完了锋八,有興趣的同學(xué)可以去源碼的html中點(diǎn)擊播放,其中被迫有很多零碎的需求护盈,比如點(diǎn)擊暫停挟纱,保存音量等等。整個(gè)視頻播放器的基礎(chǔ)功能實(shí)現(xiàn)的還算完善腐宋。

最后

慣例po作者的博客紊服,不定時(shí)更新中——
有問題歡迎在issues下交流,捂臉求star=胸竞。=

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末欺嗤,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子卫枝,更是在濱河造成了極大的恐慌煎饼,老刑警劉巖,帶你破解...
    沈念sama閱讀 222,183評論 6 516
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件校赤,死亡現(xiàn)場離奇詭異吆玖,居然都是意外死亡筒溃,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,850評論 3 399
  • 文/潘曉璐 我一進(jìn)店門沾乘,熙熙樓的掌柜王于貴愁眉苦臉地迎上來怜奖,“玉大人,你說我怎么就攤上這事意鲸》持埽” “怎么了?”我有些...
    開封第一講書人閱讀 168,766評論 0 361
  • 文/不壞的土叔 我叫張陵怎顾,是天一觀的道長。 經(jīng)常有香客問我漱贱,道長槐雾,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 59,854評論 1 299
  • 正文 為了忘掉前任幅狮,我火速辦了婚禮募强,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘崇摄。我一直安慰自己擎值,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,871評論 6 398
  • 文/花漫 我一把揭開白布逐抑。 她就那樣靜靜地躺著鸠儿,像睡著了一般。 火紅的嫁衣襯著肌膚如雪厕氨。 梳的紋絲不亂的頭發(fā)上进每,一...
    開封第一講書人閱讀 52,457評論 1 311
  • 那天,我揣著相機(jī)與錄音命斧,去河邊找鬼田晚。 笑死,一個(gè)胖子當(dāng)著我的面吹牛国葬,可吹牛的內(nèi)容都是我干的贤徒。 我是一名探鬼主播,決...
    沈念sama閱讀 40,999評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼汇四,長吁一口氣:“原來是場噩夢啊……” “哼接奈!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起船殉,我...
    開封第一講書人閱讀 39,914評論 0 277
  • 序言:老撾萬榮一對情侶失蹤鲫趁,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后利虫,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體挨厚,經(jīng)...
    沈念sama閱讀 46,465評論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡堡僻,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,543評論 3 342
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了疫剃。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片钉疫。...
    茶點(diǎn)故事閱讀 40,675評論 1 353
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖巢价,靈堂內(nèi)的尸體忽然破棺而出牲阁,到底是詐尸還是另有隱情,我是刑警寧澤壤躲,帶...
    沈念sama閱讀 36,354評論 5 351
  • 正文 年R本政府宣布城菊,位于F島的核電站,受9級特大地震影響碉克,放射性物質(zhì)發(fā)生泄漏凌唬。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 42,029評論 3 335
  • 文/蒙蒙 一漏麦、第九天 我趴在偏房一處隱蔽的房頂上張望客税。 院中可真熱鬧,春花似錦撕贞、人聲如沸更耻。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,514評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽秧均。三九已至,卻和暖如春脊奋,著一層夾襖步出監(jiān)牢的瞬間熬北,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,616評論 1 274
  • 我被黑心中介騙來泰國打工诚隙, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留讶隐,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 49,091評論 3 378
  • 正文 我出身青樓久又,卻偏偏與公主長得像巫延,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子地消,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,685評論 2 360

推薦閱讀更多精彩內(nèi)容