首頁  >  文章  >  web前端  >  Angular中怎麼自訂影片播放器

Angular中怎麼自訂影片播放器

青灯夜游
青灯夜游原創
2022-04-28 10:39:562812瀏覽

怎麼自訂 Video 操作?自訂影片播放器?以下這篇文章跟大家介紹一下Angular 中自訂 Video 操作的方法,希望對大家有幫助!

Angular中怎麼自訂影片播放器

上一篇文章是 Angular 專案實作權限控制。最近自己在網路上看到別人使用 vue 進行自訂 video 的操作。加上不久前實現了 angular 自訂 video 的相關需求, 遂來記錄一下,作為交流思考。 【相關教學推薦:《angular教學》】

#實作的功能如下:

    ##播放/ 停止
  • 快退/ 快轉/ 倍速
  • 聲音開/ 聲音關
  • 進入全螢幕/ 退出全螢幕
  • 進入畫中畫/ 退出畫中畫【安卓平板不支持,不建議使用】
  • 經過時長/ 總長度
  • 播放進度條功能:支援點擊,拖曳進度
  • 聲音進度條功能:支援點擊,拖曳進度
#如圖:

Angular中怎麼自訂影片播放器

下面我們來一一實作:

這裡的重點不在佈局,我們簡單來定義一下:

<!-- app.component.html -->

<div class="video-page">
  <div class="video-tools">
    <button nz-button nzType="primary" (click)="play(&#39;btn&#39;)" style="margin-right: 12px;">播放 ✅</button>
    <button nz-button nzType="primary" (click)="pause(&#39;btn&#39;)">暂停 ✅</button>
    <ng-container>
      <button nz-button nz-dropdown [nzDropdownMenu]="menuForward" nzPlacement="bottomCenter" style="margin: 0 12px;">快进 ✅</button>
        <nz-dropdown-menu #menuForward="nzDropdownMenu">
          <ul nz-menu>
            <li nz-menu-item (click)="forwardSecond(10)">快进 10 s</li>
            <li nz-menu-item (click)="forwardSecond(20)">快进 20 s</li>
          </ul>
        </nz-dropdown-menu>
    </ng-container>
    <ng-container>
      <button nz-button nz-dropdown [nzDropdownMenu]="menuBack" nzPlacement="bottomCenter">快退 ✅</button>
        <nz-dropdown-menu #menuBack="nzDropdownMenu">
          <ul nz-menu>
            <li nz-menu-item (click)="retreatSecond(10)">快退 10 s</li>
            <li nz-menu-item (click)="retreatSecond(20)">快退 20 s</li>
          </ul>
        </nz-dropdown-menu>
    </ng-container>
    <ng-container>
      <button nz-button nz-dropdown [nzDropdownMenu]="speedUp" nzPlacement="bottomCenter" style="margin: 0 12px;">倍速 ✅</button>
        <nz-dropdown-menu #speedUp="nzDropdownMenu">
          <ul nz-menu>
            <li nz-menu-item (click)="speedUpVideo(1)">正常</li>
            <li nz-menu-item (click)="speedUpVideo(2)">2 倍</li>
            <li nz-menu-item (click)="speedUpVideo(4)">4 倍</li>
          </ul>
        </nz-dropdown-menu>
    </ng-container>
    <button nz-button nzType="primary" (click)="openOrCloseVoice()">声音开 / 声音关 ✅</button>
    <button nz-button nzType="primary" style="margin: 0 12px;" (click)="toFullScreen()">全屏 ✅</button>
    <br />
    <button nz-button nzType="primary" style="margin-top: 12px;" (click)="entryInPicture()">进入画中画 ⚠️ 安卓平板不支持</button>
    <button nz-button nzType="primary" style="margin: 12px 12px 0 12px;" (click)="exitInPicture()">退出画中画 ⚠️ 安卓平板不支持</button>
    <br />
    <div style="display: flex; justify-content: flex-start; align-items: center; margin: 12px 0;">
      经过时长 / 总时长 : ✅ {{ currentTime }}  / {{ totalTime }}
    </div>
    <!-- 进度条 -->
    <div style="display: flex; justify-content: flex-start; align-items: center; margin: 12px 0;">
      进度条:✅
      <div
        class="custom-video_control-bg"
        (mousedown)="handleProgressDown($event)"
        (mousemove)="handleProgressMove($event)"
        (mouseup)="handleProgressUp($event)"
      >
        <div
          class="custom-video_control-bg-outside"
          id="custom-video_control-bg-outside"
        >
          <span
            class="custom-video_control-bg-inside"
            id="custom-video_control-bg-inside"
          ></span>
          <span
            class="custom-video_control-bg-inside-point"
            id="custom-video_control-bg-inside-point"
          ></span>
        </div>
      </div>
    </div>
    <div style="display: flex; justify-content: flex-start; align-items: center; margin: 12px 0;">
      声音条:✅
      <div class="custom-video_control-voice">
        <span class="custom-video_control-voice-play">
          <i nz-icon nzType="sound" nzTheme="outline"></i>
        </span>
        <div
          class="custom-video_control-voice-bg"
          id="custom-video_control-voice-bg"
          (mousedown)="handleVolProgressDown($event)"
          (mousemove)="handleVolProgressMove($event)"
          (mouseup)="handleVolProgressUp($event)"
        >
          <div 
            class="custom-video_control-voice-bg-outside"
            id="custom-video_control-voice-bg-outside"
          >
            <span 
              class="custom-video_control-voice-bg-inside"
              id="custom-video_control-voice-bg-inside"
            ></span>
            <span 
              class="custom-video_control-voice-bg-point"
              id="custom-video_control-voice-bg-point"
            ></span>
          </div>
        </div>
      </div>
    </div>
  </div>
  <div class="video-content">
    <video id="video" class="video" style="width: 100%" poster="assets/poster.png">
      <source type="video/mp4" src="assets/demo.mp4">
      Sorry, your browser doesn&#39;t support.
    </video>
  </div>
</div>

這裡使用了

angular ant design,之前寫了一篇相關文章,還不熟悉的讀者可前往 Angular 結合NG-ZORRO 快速開發

#播放/ 停止

這裡直接呼叫

video 物件的方法play()pause():

// app.component.ts

// 播放按钮事件
play(flag: string | undefined) {
  if(flag) this.videoState.playState = true
  this.videoState.play = true
  this.video.play()
}
// 暂停按钮事件
pause(flag: string | undefined): void {
  if(flag) this.videoState.playState = false
  this.video.pause()
  this.videoState.play = false
}

這裡自訂的

playpause 方法加上了一個標誌,對下下面要講的進度條的控制有幫助,上面的程式碼可以更加簡潔,讀者可以簡寫下。

快退/ 快轉/ 倍速

這裡的

快退,快轉和倍速設定了不同的選項,透過參數傳遞:

// app.component.ts

// 快进指定的时间
forwardSecond(second: number): void {
  this.video.currentTime += second; // 定位到当前的播放时间 currentTime
}

// 后退指定的时间
retreatSecond(second: number): void {
  this.video.currentTime -= second
}

// 倍速
speedUpVideo(multiple: number): void {
  this.video.playbackRate = multiple; // 设定当前的倍速 playbackRate
}

Angular中怎麼自訂影片播放器

聲音開/ 聲音關

聲音的開關使用

videomuted 屬性即可:

// app.component.ts

// 开或关声音
openOrCloseVoice(): void {
  this.video.muted = !this.video.muted;
}

進入全螢幕/ 退出全螢幕

全螢幕的操作也是很簡單,使用

webkitRequestFullScreen

// app.component.ts

// 全屏操作
toFullScreen(): void {
  this.video.webkitRequestFullScreen()
}

全螢幕後,按

esc 可退出全螢幕

進入畫中畫/ 退出畫中畫

畫中畫相當於彈窗縮小影片~

// app.component.ts

// 进入画中画
entryInPicture(): void {
  this.video.requestPictureInPicture()
  this.video.style.display = "none"
}

// 退出画中画
exitInPicture(): void {
  if(this.document.pictureInPictureElement) {
    this.document.exitPictureInPicture()
    this.video.style.display = "block"
  }
}

設定

video 的樣式,是為了看起來不突兀...

經過長度/ 總時長

#記錄影片的總時長和影片目前的播放時長。我們已經來組件的時候就獲取視頻的元信息,得到總時長;在視頻播放的過程中,更新當前時長。

// app.component.ts

// 初始化 video 的相关的事件
initVideoData(): void {
  // 获取视频的总时长
  this.video.addEventListener(&#39;loadedmetadata&#39;, () => {
    this.totalTime = this.formatTime(this.video.duration)
  })
  // 监听时间发生更改
  this.video.addEventListener(&#39;timeupdate&#39;, () => {
    this.currentTime = this.formatTime(this.video.currentTime) // 当前播放的时间
  })
}

formatTime 是格式化函數

播放進度條功能

監聽滑鼠的

點擊,移動,放開的事件,將影片的播放時間和總事件相除,計算百分比。

// app.component.ts

// 进度条鼠标按下
handleProgressDown(event: any): void {
  this.videoState.downState = true
  this.pause(undefined);
  this.videoState.distance = event.clientX + document.documentElement.scrollLeft - this.videoState.leftInit;
}
// 进度条 滚动条移动
handleProgressMove(event: any): void {
  if(!this.videoState.downState) return
  let distanceX = (event.clientX + document.documentElement.scrollLeft) - this.videoState.leftInit
  if(distanceX > this.processWidth) { // 容错处理
    distanceX = this.processWidth;
  }
  if(distanceX < 0) { // 容错处理
    distanceX = 0
  }
  this.videoState.distance = distanceX
  this.video.currentTime = this.videoState.distance / this.processWidth * this.video.duration
}
// 进度条 鼠标抬起
handleProgressUp(event: any): void {
  this.videoState.downState = false
  // 视频播放
  this.video.currentTime = this.videoState.distance / this.processWidth * this.video.duration
  this.currentTime = this.formatTime(this.video.currentTime)
  if(this.videoState.playState) {
    this.play(undefined)
  }
}

這裡需要計算進度條的位置,來取得點擊進度條的百分比,之後更新影片的目前播放時間。當然,我們還得有容錯處理,例如進度條為負數時候,目前播放時間為0。

聲音進度條

我們實現了播放進度條的操作,對聲音進度條的實現就很容易上手了。聲音進度條也是監聽滑鼠的

點擊,移動,放開。不過,這次我們處理的是已知聲音 div 的高度。

// app.component.ts

// 声音条 鼠标按下
handleVolProgressDown(event: any) {
  this.voiceState.topInit = this.getOffset(this.voiceProOut, undefined).top
  this.volProcessHeight = this.voiceProOut.clientHeight
  this.voiceState.downState = true //按下鼠标标志
  this.voiceState.distance = this.volProcessHeight - (event.clientY + document.documentElement.scrollTop - this.voiceState.topInit) 
}
// 声音 滚动条移动
handleVolProgressMove(event: any) {
  if(!this.voiceState.downState) return
    let disY = this.voiceState.topInit + this.volProcessHeight - (event.clientY + document.documentElement.scrollTop)
    if(disY > this.volProcessHeight - 2) { // 容错处理
      disY = this.volProcessHeight - 2
    }
    if(disY < 0) { // 容错处理
      disY = 0
    }
    this.voiceState.distance = disY
    this.video.volume = this.voiceState.distance / this.volProcessHeight
    this.videoOption.volume = Math.round(this.video.volume * 100)
}
// 声音 鼠标抬起
handleVolProgressUp(event: any) {
  this.voiceState.downState = false //按下鼠标标志
  let voiceRate =  this.voiceState.distance / this.volProcessHeight
  if(voiceRate > 1) {
    voiceRate = 1
  }
  if(voiceRate < 0) {
    voiceRate = 0
  }
  this.video.volume = voiceRate
  this.videoOption.volume = Math.round(this.video.volume * 100); // 赋值给视频声音
}

如圖:

Angular中怎麼自訂影片播放器

效果示範

完成了上面的內容,我們以一個

gif 圖來展示效果:

Angular中怎麼自訂影片播放器

全屏,聲音和畫中畫比較難截圖,

Gif 上體現不來

詳細的程式碼,請前往 video-ng 取得。

【完】

更多程式相關知識,請造訪:程式設計入門! !

以上是Angular中怎麼自訂影片播放器的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn