微信小程序&&簡單的音樂播放器


z

博客班級 https://edu.cnblogs.com/campus/zjcsxy/SE2020
作業要求 https://edu.cnblogs.com/campus/zjcsxy/SE2020/homework/11334
作業目標
  • 編寫一個小程序,可以全新編寫,也可以學習別人的小程序進行修改
  • 熟悉git代碼管理流程,將源代碼上傳到到github
  • 在博客園班級中寫一篇相應的博文
作業源代碼  https://github.com/Saulger/music-player
學號 31801148-楊守概
院系 浙大城市學院計算機專業

 

·前言

第一次學習寫微信小程序,之前沒有一點基礎,連web也只是略懂皮毛,所以寫wxml和wxss的時候花了大量時間去學習布局以及樣式。JS也是讓我淚流滿面,也是讓我認識到自身的不足。拿到這個作業的時候,我第一反應就是我想做一個音樂的播放器,后來去網上查閱大量的樣例,一開始我根本無從下手,與其等死不如花時間從最基礎開始學起,主要參考網站是https://developers.weixin.qq.com/miniprogram/dev/framework/quickstart/。最后根據自己理想中的布局做了一個簡單的音樂播放器。

·頁面展示

 

 

 

 

 

 

 

 

 ·文件結構

 

 

 index為進入小程序的主頁,List為音樂列表頁,Play為音樂播放的效果頁,SongData.js為儲存的音樂信息。

·詳細介紹

index.wxml

<swiper class="top" indicator-dots="{{indicator_dots}}"
autoplay="{{autoplay}}" interval="{{interval}}" duration="{{duration}}" circular="{{circular}}">
    <block wx:for="{{imgurls}}" wx:key="{{index}}">
        <swiper-item>
            <image src="{{item}}" class="top_image"/>
        </swiper-item>
    </block>
</swiper>       //上方圖片輪播動畫實現
<view class="ownList"> <text class="ownlist">-----歌曲列表-----</text> </view>
<scroll-view scroll-y="true" > //下拉框的實現 <view class="songlist"> <block wx:for="{{songlist}}" wx:key="song_id"> <view class="songitem"> <view class="song-index">{{index+1}}</view> <navigator url="/pages/Play/Play?songid={{index}}" class="song-detail"> <view class="song-title">{{item.name}}</view> <view class="song-subtitle">{{item.singer}} - {{item.seconds}}</view> </navigator> <navigator url="/pages/Play/Play?songid={{index}}" class="song-play"><image src="/Images/play.png" /></navigator> </view> </block> </view> <loading hidden="{{!loading}}"> 正在加載音樂…… </loading> </scroll-view>

index.js

var config = require('../../utils/SongData.js'); 
Page({
  data: {
    imgurls:[
      'https://ss3.bdstatic.com/70cFv8Sh_Q1YnxGkpoWK1HF6hhy/it/u=47017426,376938455&fm=26&gp=0.jpg',
      'https://ss3.bdstatic.com/70cFv8Sh_Q1YnxGkpoWK1HF6hhy/it/u=2656019328,2056784029&fm=26&gp=0.jpg',
      'https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=2442328894,1339802770&fm=26&gp=0.jpg',
      'https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=3719062759,3237893044&fm=26&gp=0.jpg'
    ],
    indicator_dots:true,    //指示點
    autoplay:true,          //自動播放
    circular:true,          //是否采用銜接滑動
    interval:3000,          //自動切換時間間隔
    duration:1000,          //滑動動畫時長
    songlist: []            //音樂列表
  },
  //頁面加載事件
  onLoad: function (options) {
    this.setData({
      songlist: config.Data
    })
  }
})

最難的就是播放界面的實現了,進度條采用slider組件,value為進度條進度,activeColor為覆蓋的顏色,block-size和block-color分別為進度條上的點的大小與顏色。

<view class="container">
  <view class="background" style="background-image:url({{songImg}})"></view>
    <view class="rotate-disk-container">
      <view class="rotate-disk {{pauseStatus === false ? 'rotate-360' : 'rotate-360-paused'}}">      //中間圓形圖片旋轉的實現
        <image class="image" src="{{songImg}}"></image>
      </view>
    </view>
    <view class="title-container">
      <view class="text">
        <view><text class="name">{{songTitle}}----</text></view>
        <view><text class="singer">{{singerName}}</text></view>
      </view>
    </view>
    <view class="slider-container">
      <text class="slider-time">{{songState.currentPosition}}</text>
      <slider                                                    //下方時間條
          value="{{sliderValue}}"
          bindchange="bindSliderchange"
          activeColor="#13beec"
          style="width: 62%;margin: 0;"
          block-size="12"
          block-color="green"
        />
      <text class="slider-time">{{songTime}}</text>
    </view>
    <view class="operation-container">
      <image src="/Images/prev.png" class="icon-prev" bindtap="bindTapPrev"></image>
      <image
        src="{{pauseStatus === false ? '/Images/pause.png' : '/Images/start.png'}}"         //這里實現播放和暫停圖片的切換
        class="icon-play" bindtap="bindTapPlay"
        >
        </image>
      <image src="/Images/next.png" class="icon-next" bindtap="bindTapNext"></image>
    </view>
</view>
播放功能這里用的是wx.playBackgroundAudio()。這里面需要音樂外鏈dataUrl,音樂外鏈本人用的是騰訊雲,存入數據不需要錢但是讀取數據是要錢的,存入音樂文件生成音樂鏈接即可。

Play.js

 
         
var app = getApp();
var util = require('../../utils/SongData.js');
Page({
  data: {
    songIndex: 0,
    songTitle:'',
    songUrl: '',
    songImg: '',
    songTime: '',
    pauseStatus: false,
    silderValue: 0,
    duration: 0,
    currentPosition: 0
  },
  onLoad: function (options) {
    var that = this; 
    var index = options.songid;
    var hash = util.Data[index];
    that.setData({
      songIndex: index,
      songUrl: hash.play_url,
      songTime: hash.seconds,
      songImg: hash.img,
      songTitle: hash.name,
      singerName: hash.singer
    });
    const audio = wx.getBackgroundAudioManager()
    audio.onEnded(function(){                  //播放結束自動播放下一首
      that.bindTapNext()
    })
  },
  onReady:function(e){
    this.play()
  },
  bindTapPlay:function() {
    if(this.data.pauseStatus === true){
      this.play()
      this.setData({
        pauseStatus: false
      })
    }else{
      wx.pauseBackgroundAudio()
      this.setData({
        pauseStatus: true
      })
    }
  },

  bindTapPrev: function(){          //上一首
    var that = this
    var length = util.Data.length
    var index = parseInt(that.data.songIndex)
    if(index == 0 ){                      //如果是第一首歌,則跳到最后一首
      index = length - 1
    }else{
      index = index - 1
    }

    this.setData({
     pauseStatus:false,
     songIndex: index,
     songTime: util.Data[index].seconds,
     songImg: util.Data[index].img,
     songTitle: util.Data[index].name,
     singerName: util.Data[index].singer
    })
    setTimeout(() => {
      if (that.data.pauseStatus === false) {
        that.play()
      }
    }, 1000)
   
  },
  bindTapNext: function(){    //下一首
    var that = this
    var length = util.Data.length
    var index = parseInt(that.data.songIndex)
    if(index == length - 1 ){            //如果是一首,則跳到第一首
      index = 0
    }else{
      index = index + 1
    }
    this.setData({
     pauseStatus: false,
     songIndex: index,
     songTime: util.Data[index].seconds,
     songImg: util.Data[index].img,
     songTitle: util.Data[index].name,
     singerName: util.Data[index].singer
    })
    setTimeout(() => {
      if (that.data.pauseStatus === false) {
        that.play()
      }
    }, 1000)
  },
  bindSliderchange: function(e) {              //更新進度條
    let value = e.detail.value
    let that = this
    wx.getBackgroundAudioPlayerState({
      success: function (res) {
        let {status, duration} = res
        if (status === 1 || status === 0) {
          that.setData({
            sliderValue: value
          })
          wx.seekBackgroundAudio({              //通過進度條長度與總時間的百分比同步歌曲進程
              position: Math.floor(e.detail.value * duration / 100),
          })
        }
      }
    })
  },
  play() {
    let index = this.data.songIndex
    wx.playBackgroundAudio({
      dataUrl: util.Data[index].play_url,
      title: util.Data[index].singer,
      coverImgUrl: util.Data[index].img
    })
    let that = this
    let timer = setInterval(function() {
      that.setDuration(that)
    }, 0)
    this.setData({timer: timer})
  },
  setDuration(that) {
    wx.getBackgroundAudioPlayerState({
      success: function (res) {
        let {status, duration, currentPosition} = res
        if (status === 1 || status === 0) {
          that.setData({
            currentPosition: that.stotime(currentPosition),
            duration: that.stotime(duration),
            sliderValue: Math.floor(currentPosition * 100 / duration),
          })
        }
      }
    })
  },
  stotime(s) {                      //轉換時間的格式,將currentPosition和duration用時間的格式輸出
    let t = ''
    if (s > -1) {
      let min = Math.floor(s / 60) % 60;
      let sec = Math.floor(s) % 60
      if (min < 10) { t += '0' }
      t += min + ':'
      if (sec < 10) { t += '0' }
      t += sec
    }
    return t
  },
})
 

·個人總結

第一次做這種類型的作業,也是第一次使用微信開發者工具,剛拿到課題的時候也是無從下手,所以前面幾天主要是學習這類代碼,在半知半解的狀態下瀏覽借鑒了許多大佬的作品,根據自己心中布局完成了這次作業。過程也是被如何獲取頁面參數,切換上下首纏了很久,最后在同學的幫助下解決這個問題,才發現解決方法如此簡單,也是讓我意識到自己知識的薄弱。個人對這作品還是挺滿意的,瑕疵就是一些功能沒有實現吧,例如收藏,點贊,搜索這些功能,如果日后有時間還是會嘗試更新以下的。

這次作業也是讓我對前端UI的設計產生了極大的興趣,不僅是html還是軟件小程序的UI界面,都是我以后要去學習,畢竟計算機這個行業每秒都在迭代,每時每刻都有更好的替代,所以既然選了這個專業,便是要活到老,學到老。最后,希望大家能多指點!

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM