zoukankan      html  css  js  c++  java
  • 基于 vue-element 组件实现音乐播放器功能

    效果:

    代码:

    <template>
      <div id='playMusic'>
        <audio ref='audio' :src='src'
         @pause="onPause"
         @play='onplay'
         @timeupdate="onTimeupdate"
         @loadedmetadata="onLoadedmetadata"></audio>
    
        <el-button type='text' @click='startPlayOrPause'>{{audio.playing | transPlayPause}}</el-button>
    
        <!-- 进度条 -->
        <el-slider v-model="sliderTime" :format-tooltip="formatProcessToolTip" @change="changeCurrentTime" class="slider"></el-slider>
    
        <span>{{audio.currentTime | formartSecond}} / </span>
    
        <span>{{audio.maxTime | formartSecond}}</span>
    
      </div>
    </template>

    js:

    <script>
    // 将整数转换成 时:分:秒的格式
    function realFormatSecond(second) {
      var secondType = typeof second
    
      if (secondType === 'number' || secondType === 'string') {
        second = parseInt(second)
    
        var hours = Math.floor(second / 3600)
        second = second - hours * 3600
        var mimute = Math.floor(second / 60)
        second = second - mimute * 60
    
        return hours + ':' + ('0' + mimute).slice(-2) + ':' + ('0' + second).slice(-2)
      } else {
        return '0:00:00'
      }
    }
    
    export default {
      name: 'playMusic',
      props: {
        src: {
          type: String,
          default: ''
        }
      },
      methods: {
        /* 进度条格式化toolTip */
        formatProcessToolTip (index = 0) {
          index = parseInt(this.audio.maxTime / 100 * index)
          return '时长:' + realFormatSecond(index)
        },
        /* 拖动进度条,改变当前时间 index是进度条改变时的回调函数的参数 值为0~100之间,需要换算成实际时间 */
        changeCurrentTime (index) {
          this.$refs.audio.currentTime = parseInt(index / 100 * this.audio.maxTime)
        },
        /* 音频加载完成后的回调函数 */
        onLoadedmetadata (res) {
          console.log(111)
          this.audio.maxTime = parseInt(res.target.duration)
        },
        /* 每秒触发一次 用来更新当前播放时间 */
        onTimeupdate (res) {
          this.audio.currentTime = res.target.currentTime
          /* 当音频播放时 进度条也要随之改变 */
          this.sliderTime = parseInt(this.audio.currentTime / this.audio.maxTime * 100)
        },
        /* 控制音频播放、暂停 */
        startPlayOrPause () {
          this.audio.playing ? this.pause() : this.play()
        },
        /* 播放音频 */
        play () {
          this.$refs.audio.play()
        },
        /* 暂停音频 */
        pause () {
          this.$refs.audio.pause()
        },
        /* 当音频播放 */
        onplay () {
          this.audio.playing = true
        },
        /* 当音频暂停 */
        onPause () {
          this.audio.playing = false
        }
      },
      data () {
        return {
          sliderTime: 0,
          audio: {
            maxTime: 0, /* 音频最大播放时长 */
            currentTime: 0, /* 当前播放时长 */
            playing: false /* 音频当前处于播放/暂停状态 */
          }
        }
      },
      filters: {
        /* 使用vue过滤器动态改变按钮的显示 */
        transPlayPause (value) {
          return value ? '暂停' : '播放'
        },
        /* 整数转换时分秒 */
        formartSecond (second = 0) {
          return realFormatSecond(second)
        }
      }
    }
    </script>

    less:

    <style lang="less">
    #playMusic {
      display: flex;
      align-items: center;
      .el-button {
        margin-right: 15px;
      }
      .slider {
        width: 150px;
        margin-right: 15px;
      }
      > span:nth-of-type(2) {
        margin-left: 5px;
      }
    }
    </style>

    参考: https://github.com/wangduanduan/element-audio

    另一个类似功能实现:

    效果:

    代码:

    <template>
      <div>
      <el-row>
       <el-col :span="4">
        <el-popover
        placement="top-start"
        trigger="hover">
         <div style="text-align: center">
          <el-progress 
          color="#67C23A"
          type="circle"
          :percentage="music.volume"></el-progress><br>
          <el-button 
          @click="changeVolume(-10)"
          icon="el-icon-minus"
          circle></el-button>
          <el-button 
          @click="changeVolume(10)"
          icon="el-icon-plus"
          circle></el-button>
         </div>
         <el-button 
         @click="play"
         id="play"
         slot="reference"
         :icon="music.isPlay?'el-icon-refresh':'el-icon-caret-right'"
         circle></el-button>
        </el-popover>
       </el-col>
       <el-col :span="14" style="padding-left: 20px">
        <el-slider
        @change="changeTime"
        :format-tooltip="formatTime"
        :max="music.maxTime"
        v-model="music.currentTime"
        style=" 100%;"></el-slider>
       </el-col>
       <el-col :span="6" style="padding: 9px 0px 0px 10px;color:#909399;font-size: 13px">
        {{formatTime(music.currentTime)}}/{{formatTime(music.maxTime)}}
       </el-col>
      </el-row>
      <audio ref="music" loop autoplay> 
       <source src="http://sc1.111ttt.cn:8282/2018/1/03m/13/396131232171.m4a?tflag=1519095601&pin=6cd414115fdb9a950d827487b16b5f97#.mp3" type="audio/mpeg">
      </audio>
     </div>
    </template>

    js:

    <script>
     export default{
      data(){
       return {
        music:{
         isPlay:false,
         currentTime:0,
         maxTime:0,
         volume:100
        }
       }
      },
      mounted(){
       this.$nextTick(()=>{
        setInterval(this.listenMusic,1000)
       })
      },
      methods:{
       listenMusic(){
        if(!this.$refs.music){
         return
        }
        if(this.$refs.music.readyState){
         this.music.maxTime = this.$refs.music.duration
        }
        this.music.isPlay=!this.$refs.music.paused
        this.music.currentTime = this.$refs.music.currentTime
       },
       play(){
        if(this.$refs.music.paused){
         this.$refs.music.play()
        }else{
         this.$refs.music.pause()
        }
        this.music.isPlay=!this.$refs.music.paused
        this.$nextTick(()=>{
         document.getElementById('play').blur()
        })
       },
       changeTime(time){
        this.$refs.music.currentTime = time
       },
       changeVolume(v){
        this.music.volume += v 
        if(this.music.volume>100){
         this.music.volume = 100
        }
        if(this.music.volume<0){
         this.music.volume = 0
        }
        this.$refs.music.volume = this.music.volume/100
       },
       formatTime(time){
        let it = parseInt(time)
        let m = parseInt(it/60)
        let s = parseInt(it%60)
        return (m<10?"0":"")+parseInt(it/60)+":"+(s<10?"0":"")+parseInt(it%60)
       }
      } 
     }
    </script>

    更详细的实现可以看 https://github.com/GitHub-Laziji/vblog

  • 相关阅读:
    MFC中ON_COMMAND,ON_MESSAGE,ON_NOTIFY的区别
    BIOS和CMOS的区别
    强大工具psexec工具用法简介
    Win10如何搭建FTP服务器以实现快速传输文件
    WPA-PSK无线网络破解原理及过程
    Wifi密码破解实战
    洋流.地球:四季只剩下冬天吗?
    天文.地球:最多的陨石有多大?
    德芙背后刻骨铭心的痛
    TTS
  • 原文地址:https://www.cnblogs.com/joe235/p/14754286.html
Copyright © 2011-2022 走看看