微信小程序——音频播放器

先来个效果图韵下味:

需求:

  1. 音频的播放,暂停,中间按钮状态的变化,播放时实时更新播放进度;
  2. 前进15s,后退15s;
  3. 进度条拖动。

一开始想着这3个功能应该挺简单的。不就是播放,暂停,前进,后退么~呵~写的时候发现自己还是太年轻。当然,这跟自己的技术功底有关系。现在把我遇到的难点及要注意的点说一下~

  1. 需要设置一个名为seekPosition的全局变量,初始值为0。我们要在播放的时候实时记录播放的位置,存到该变量里,这是方便在前进15s 或 后退15s 时计算时间点。
  2. 前进15s时要判断剩余时间是否>15s,如果<15s,则返回到开始位置;
  3. 后退15s时要判断播放时间是否>15s,如果<15s,则返回到开始位置;
  4. 点击播放时,要先判断seekPisition是否>0,如果>0,则跳转到seekPosition的位置,并播放;
  5. 拖动时,要先让音频停止播放,拖动结束后,再播放音频。并且要计算拖动位置对应的时间。

完整代码:

wxml:

<view class=" audio-content">

  <image src="{{logo640x360}}" class="bg-blur"></image>
  <view class="bg-gray"></view>
  <view class="container-cover">
    <view class="cover">
      <image src="{{logo640x360}}" class="cover-image"></image>
      <view class="cover-tip">词不达意.mp3</view>

    </view>
  </view>
  <view class="audio-inner row item-center">
    <view class="audio-desc">{{currentProcess}}</view>
    <view class="audio-progress-wrap">
      <van-slider value="{{sliderValue}}" step="{{sliderStep}}" active-color="#09bb07" use-button-slot bind:change="onSliderChange" bind:drag="onSliderDrag">
        <view class="slider-button" slot="button"></view>
      </van-slider>
    </view>
    <view class="audio-desc">{{productDetail.duration}}</view>
  </view>

  <!-- 播放器控制条 -->
  <section class="speech-player js_control_bar">
    <view class="player-bar row  justify-center item-center">
      <view class="backward js_audio_backward" title="后退15s">
        <ss-icon name="back-15" size="32px" color="#fff" block="{{true}}" bind:click="backward" />
      </view>
      <view class="play" title="播放/暂停">
        <view class="circle-loading" wx:if="{{loading}}"></view>
        <ss-icon name="play-outline" size="50px" color="#fff" block="{{true}}" wx:if="{{pause}}" bind:click="audioPlay" />
        <ss-icon name="pause-outline" size="50px" color="#fff" block="{{true}}" wx:if="{{playing}}" bind:click="audioPause" />
      </view>
      <view class="forward js_audio_forward" title="前进15s">
        <ss-icon name="forward-15" size="32px" color="#fff" block="{{true}}" bind:click="forward" />
      </view>
    </view>
  </section>
</view>

这里面用到了有赞的小程序组件 icon组件 和 slider 组件。如果你要用的话把上面的 <ss-icon> 换成<van-icon>,并且需要自己找阿里矢量图标库查找对应的图标。

js:

// components/product/audio/index.js

let audioUrl = "",
  seekPosition = 0;
const audioContext = wx.createInnerAudioContext();

Component({
  options: {
    multipleSlots: true,
    addGlobalClass: true
  },

  /**
   * 组件的属性列表
   */
  properties: {
    productId: Number,
  },
  /**
   * 组件的初始数据
   */
  data: {
    pause: true,
    playing: false,
    loading: false,
    productDetail: {},
    audioDuration: 0,
    currentProcess: ‘00:00‘,
    sliderStep:1
  },

  /**
   * 组件的方法列表
   */
  methods: {
    //音频播放
    audioPlay(e) {
      const _this = this;
      let audioDuration = _this.data.audioDuration;
      if (audioUrl) {
        if (seekPosition) {
          //如果有指定位置,则跳转到指定位置
          audioContext.seek(seekPosition);
        }
        audioContext.play();
        _this.setData({
          pause: false,
          playing: true,
          loading: false,
        })
      } else {
       //getJSON是我自己封装的
        ss.getJSON(‘获取音频如果需要发送请求,这里面放请求地址‘, {
          放你自己的参数
        }, res => {
          audioUrl = res.t;
          audioContext.src = audioUrl;
          if (seekPosition) {
            audioContext.seek(seekPosition);
          }
          audioContext.play();
          audioContext.onPlay(() => {
            console.log(‘onPlay‘)
          })

          audioContext.onWaiting(() => {
            console.log(‘onWaiting‘)
            _this.setData({
              pause: false,
              playing: false,
              loading: true,
            })
          })

          audioContext.onCanplay(() => {
            console.log(‘onCanplay‘)
            _this.setData({
              pause: false,
              playing: true,
              loading: false
            })
            setTimeout(() => {
              audioContext.duration
            }, 500)

            _this.audioStatus();
          })

          audioContext.onError((res) => {
            console.log(res.errMsg)
          })
        })
      }

    },

    //播放暂停
    audioPause: function() {
      const _this = this;
      audioContext.pause();
      _this.setData({
        pause: true,
        playing: false,
        loading: false
      })
    },

    //记录播放状态
    audioStatus: function() {
      const _this = this;
      //音频播放进度更新事件
      audioContext.onTimeUpdate(() => {
        seekPosition = audioContext.currentTime;
        _this.setData({
          currentProcess: ss.formatSecToMin(audioContext.currentTime),
          sliderValue: audioContext.currentTime / _this.data.audioDuration * 100,
        })
      })
      //音频播放结束
      audioContext.onEnded(() => {
        seekPosition = 0;
        _this.setData({
          sliderValue: 0,
          currentProcess: ‘00:00‘,
          playing: false,
          pause: true
        })
      })
    },

    //开始拖动
    onSliderDrag(e) {
      const _this = this;
      if (_this.data.playing) {
        _this.audioPause()
      }
      let sliderValue = e.detail.value;
      seekPosition = _this.data.audioDuration / 100 * sliderValue;
      _this.setData({
        currentProcess: ss.formatSecToMin(seekPosition)
      })

    },

    //拖动结束
    onSliderChange(e) {
      const _this = this;
      _this.audioPlay()
    },

    //前进15s
    forward() {
      const _this = this,
        audioDuration = _this.data.audioDuration;
      let currentTime;
      if (_this.data.playing) {
        currentTime = audioContext.currentTime;
      }
      if (_this.data.pause) {
        currentTime = seekPosition;
      }

      if (audioDuration - currentTime > 15) {
        seekPosition = currentTime + 15;
        _this.setData({
          sliderValue: seekPosition / audioDuration * 100,
          currentProcess: ss.formatSecToMin(seekPosition)
        });
      } else {
        seekPosition = audioDuration;
        _this.setData({
          sliderValue: 0,
          currentProcess: ‘00:00‘
        });
      }
      if (audioUrl && _this.data.playing) {
        audioContext.seek(seekPosition);
      }
    },

    //后退15s
    backward() {
      const _this = this,
        audioDuration = _this.data.audioDuration;
      let currentTime;
      if (_this.data.playing) {
        currentTime = audioContext.currentTime;
      }
      if (_this.data.pause) {
        currentTime = seekPosition;
      }

      if (currentTime > 15) {
        seekPosition = currentTime - 15;
      } else {
        seekPosition = 0;
      }
      _this.setData({
        sliderValue: seekPosition / audioDuration * 100,
        currentProcess: ss.formatSecToMin(seekPosition)
      });
      if (audioUrl && _this.data.playing) {
        audioContext.seek(seekPosition);
      }
    }
  }
})

大概就是这些了~有更好解决方案的欢迎留言哈~~

原文地址:https://www.cnblogs.com/sese/p/11310806.html

时间: 2024-10-01 09:18:00

微信小程序——音频播放器的相关文章

微信小程序音频播放

小程序音频播放:不废话直接上代码: index.wxml <!--index.wxml--> <view class="mycontent"> <view class="swiper-tab"> <view class="swiper-tab-list {{currentTab==0 ? 'on' : ''}}" data-current="0" bindtap="swich

微信小程序api拦截器

微信小程序api拦截器 完美兼容原生小程序项目 完美兼用小程序api的原本调用方式,无痛迁移 小程序api全Promise化 和axios一样的请求方式 小程序api自定义拦截调用参数和返回结果 强大的async拦截 快速开始 安装 npm install wxapp-api-interceptors --save 详情 https://blog.csdn.net/rolan1993/article/details/80480341 原文地址:https://www.cnblogs.com/to

微信小程序如何播放腾讯视频?

1.背景 因为当时需要做视频播放,后台存放视频文件又不现实.所以,做了一个能解析腾讯视频地址的并播放视频的小程序. 2.介绍 小程序里的解析腾讯视频地址的代码是参考了一个开源项目you-get写的,把里面的腾讯视频下载的python代码写成了JS代码. 3.腾讯视频ID从哪获取 1.一般播放一个腾讯视频的时候播放地址为https://v.qq.com/x/page/w0647n5294g.html..html到最后一个/之间的字符串即为腾讯视频id.如https://v.qq.com/x/pag

微信小程序背景音频播放

需求描述:上一篇写到了  微信小程序音频播放的问题 我是应用了 一个播放的方法 wx.createAudioContext(audioId):这个方法不错 但是一旦锁频后就无法在继续播放 这次我们改进一下 当用户锁屏后仍然可以播放 ,那这里需要用的是小程序的 背景音乐的 api了 代码如下 wx.getBackgroundAudioManager() 这个是 音频背景播放方法 下面是实例化之后的可以操作的方法 示例代码: 如图所示 ,实例化 一个背景音频播放的代码 : 一下代码时我的业务逻辑,参

微信小程序实例源码大全

怎么本地测试微信小程序实例源码 1.下载源码 2.打开微信开发者工具 3.添加项目->选择本项目目录->编译执行 微信小程序实例源码大全 微信小程序游戏类demo:识色:从相似颜色中挑选不同的一个 源码链接:http://www.wxapp-union.com/forum.php?mod=viewthread&tid=1105 微信小程序精品demo:仿网易云音乐:歌单,FM,播放,评论 源码链接:http://www.wxapp-union.com/forum.php?mod=vie

微信小程序源码案例大全

微信小程序demo:足球,赛事分析 小程序简易导航 小程序demo:办公审批 小程序Demo:电魔方 小程序demo:借阅伴侣 微信小程序demo:投票 微信小程序demo:健康生活 小程序demo:文章列表demo 微商城(含微信小程序)完整源码+配置指南 微信小程序Demo:一个简单的工作系统 微信小程序Demo:用于聚会的小程序 微信小程序Demo:Growth 是一款专注于Web开发者成长的应用,- 微信小程序Demo: Music-Player 微信小程序Demo:团贷网(投资) 微信

微信小程序实例源码大全demo下载

怎么本地测试微信小程序实例源码 1.下载源码 2.打开微信开发者工具 3.添加项目->选择本项目目录->编译执行 微信小程序实例源码大全 微信小程序游戏类demo:识色:从相似颜色中挑选不同的一个 源码链接:http://www.wxapp-union.com/forum.php?mod=viewthread&tid=1105 微信小程序精品demo:仿网易云音乐:歌单,FM,播放,评论 源码链接:http://www.wxapp-union.com/forum.php?mod=vie

微信小程序源码下载(200多个)

微信小程序源码下载汇总,点击标题进入对应的微信小程序下载页面. 最新 demo源码(点击标题进入帖子下载) 描述 1 微信小程序 会议室预定小程序 微信小程序 会议室预定小程序**** 本内容被作者隐藏 **** 2 微信小程序-双人五子棋小游戏 微信小程序-双人五子棋小游戏**** 本内容被作者隐藏 **** 3 打卡签到小程序 用微信小程序实现的一个简单的打卡签到的小程序拒绝 4 微信小程序---左滑删除 微信小程序---左滑删除**** 本内容被作者隐藏 **** 5 一个借钱的记事本的微

微信小程序开发交流与推广

一.请加微信群: 请扫描下方的二维码加“微信小程序交流推广群”,由于微信群的限制,超过 100 人就不能扫码加群,大家可以先添加微信号:us9488 并备注“微信小程序”,然后拉你入群. 二.官方文档: 微信小程序介绍 微信小程序设计指南 微信小程序开发文档 微信小程序运营规范 微信小程序开发者社区 三.微信小程序解决方案: 微信小程序会话管理场景 微信小程序文件上传下载应用场景 微信小程序WebSocket长连接应用场景 微信小程序视频应用场景 四.代码: 会话管理场景 文件上传下载应用场景