微信 H5 音樂項目總結

H5 音樂項目總結

剛剛完成了一個 H5 項目,途中使用 audio 的時候遇到很多坑,因此寫篇項目總結。

項目需求

要通過微信受權才能進入。因此只能在微信打開。javascript

流程:css

  1. 開場有個小的過渡效果,有 bgm
  2. 接着連續兩張圖片顯示,有各自的 bgmhtml

    1. 第二張圖片,有文字,文字的顯示要有打字的效果,附帶 bgm
  3. 主場面vue

    1. 擁有各個小物品,像時鐘、貓、電腦、手機、雜誌、durex 等等
    2. 點擊各個物品,對應的圖片會切換,而且播放聲音,最後顯示一個確認框。時鐘也會轉動
    3. 點擊關燈,進入下一個畫面
  4. 接着又是圖片的顯示。圖片會根據時鐘的時間,顯示不一樣的圖片。也是簡單的圖片漸變顯示、打字效果、彈幕和 bgm
  5. 最後是結果頁,結果頁有三個按鈕,從新來一次,生成截圖,外鏈

大概的需求就是這樣,挺簡單的。java

遇到的問題

微信 ios 沒法自動播放聲音

這個處理起來不難。ios

// 微信配置後
wx.ready(() => {
   audio.play()
})

// 或者
document.addEventListener("WeixinJSBridgeReady", () =>{  
  WeixinJSBridge.invoke('getNetworkType', {}, () => {
    audio.play()
  })
}, false)

這樣就會自動播放起來了。不過會等當前資源加載完畢的時候才播放。我這個項目由於資源挺多的,因此加載了至關一段時間,而後纔會播放音樂。vue-router

非微信 ios 如何自動播放聲音?

這個好像就處理不了了。只能經過用戶對應用觸發了交互,才能播放起音樂。vuex

好比有個開始按鈕,用戶點擊了這個按鈕後,你就能夠執行事件回調播放音樂。gulp

音樂播放,會有延遲的效果

好比資源還沒加載到,不能馬上播放。canvas

// html
<audio src='xxx' />

//js 
function play(dom) {
  const oAudio = document.querySelector(dom)
  oAudio.play()
  oAudio.muted = true
}

咱們能夠先讓它播放起來,這樣資源就會提早加載了,設置了靜音,這樣就能保證聲音不會被聽到。並且 DOM 節點是要一直存在的,除非你不須要再播放這個音樂。

至於在何時提早加載資源,就要看你的項目需求去判斷了。

ios 沒法設置音量大小

這個真的是蛋疼。。。項目一開始的 bgm 是要比較大聲的,後面的流程要下降音量

audio.volume = 0.5

安卓是沒問題的,可是 ios 是無效的,就算在 dom 設置 volume 也是無效的。

蘋果官網文檔

在上面有一句話是說到這個問題:The volume property is not settable in JavaScript. Reading the volume property always returns 1.

最後。。。只能用兩個相同的 bgm 可是不一樣音量的文件解決。可是這個 bgm 的文件大小有 500kb 。。。

圖片沒法快速加載

能夠在項目開始前,提早加載

const loadImg = (img) => {
  const isArray = Array.isArray(img)
  if (!isArray) {
    const oImg = new Image()
    oImg.src = img
    return new Promise(resolve => {
      oImg.onload = () => {
        resolve()
      }
    })
  }
  const arr = []
  img.forEach(v => {
    const oImg = new Image()
    oImg.src = v
    arr.push(new Promise(resolve => {
      oImg.onload = () => {
        resolve()
      }
    }))
  })
  return Promise.all(arr)
}

接受單個字符串或者數組參數,使用 promise 處理。

加載圖片後,再觸發動畫

讓圖片加載完了,再觸發動畫

this.loadImg([img, img_1, img_2_1, img_2_2]).then(() => {
  setTimeout(() => {
    this.playMusic()
    this.setOne()
  }, 500)
})

這樣就不會圖都沒有出來,動畫就播完了。

截圖功能

本來打算本身用 canvas 根據 dom 渲染到畫布上,再 toDataURL 生成圖片的,而後找到了一個比較好的庫, html2canvas,簡單快捷,一鍵生成。

html2canvas(document.querySelector('.app')).then(canvas => {
  // ...
})

裏面還有個坑,,截圖是不能有跨域的圖片存在,不然會空白一片。由於項目最後截圖的效果,只有一張圖片,因此我先把圖片轉成 base64,再截屏就能夠了。

createBase64() {
      const img = new Image()
      img.crossOrigin = true
      img.src = this.bg
      new Promise(resolve => {
        img.onload = () => {
          resolve()
        }
      }).then(() => {
        const oc = document.createElement('canvas')
        oc.width = img.width
        oc.height = img.height
        const ctx = oc.getContext('2d')
        ctx.drawImage(img, 0, 0)
        this.bg = oc.toDataURL()
      })
    }

頁面佈局

使用 rem 進行開發。

最外層 div 直接:

#app {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100vh;
  overflow: hidden;
}

不出現滾動條。

背景圖就用 background

.bg {
  background-size: cover;
  background-position: center center;
}

而後其餘一些比較散亂的,就用絕對定位

.cat {
  position: absolute;
  top: 50%;
  left: 50%;
}

先把對象定位到整個頁面的中間,再用 margin / transform 進行調整位置。水平位置同理。

這些單個對象的,定位的策略就是已中心點爲標準,進行定位。而不是以左上點或者左下點。

由於背景圖也是直接顯示中心部分的,因此單個對象的也要以中心點去定位。

限制資源大小

靜態資源是 css, js, image, audio。css 還好,沒用什麼 ui 庫。js 的話,只用了 vue 和 html2canvas。vue-router、vuex、mint-ui 這些都是通通去掉。

圖片就用 gulp 配合 tinypng 進行壓縮圖片

const gulp = require('gulp')
const tiny = require('gulp-tinypng-nokey')
const gulpLoadPlugins = require('gulp-load-plugins')
// 還要安裝 gulp-rename

const plugins = gulpLoadPlugins()

gulp.task('tinypng', function(cb) {
  gulp.src('src/assets/**/*.{jpg,jpeg,png,gif}')
    .pipe(tiny())
    .pipe(plugins.rename(function(path) {
      path.dirname = `/assets/${path.dirname}`
    }))
    .pipe(gulp.dest('./src'))
})

這樣是會把原文件給覆蓋掉的,若是你有必要的話,執行前要作好備份

音樂文件的話,由於是客戶那邊找的,能夠進行壓縮下,或者把不會播放到的部分給裁剪到。

裁剪的工具,我用的是 mac 的 QuickTime player.app 進行裁剪的。簡單地裁剪是沒問題的。若是像增長或者下降音樂的聲音大小,用的是 這個網站,挺好用的。最後就是格式的轉換,用的是 MediaHuman Audio Converter.app

最後再把稍微大點的資源扔到相似七牛這種雲服務器上,這樣既能加快加載速度,又能減低服務器的壓力。

總結

此次 H5 的開發,遇到比較麻煩的是 audio 這塊。特別大部分 audio 問題是出自 ios 的。。。幸虧有 iphone 進行開發測試,否則調試起來真的是麻煩大了。

靜態資源扔到七牛後,加載速度快了不少。

至於網頁和代碼就不放出來了,如今還沒上線,客戶那邊還在調細節~~

相關文章
相關標籤/搜索