Vue使用js-audio-recorder實(shí)現(xiàn)錄制,播放與下載音頻功能
js-audio-recorder 簡(jiǎn)介
純 js 實(shí)現(xiàn)瀏覽器端錄音。
支持功能:
- 支持錄音,暫停,恢復(fù),和錄音播放。
- 支持音頻數(shù)據(jù)的壓縮,支持單雙通道錄音。
- 支持錄音時(shí)長(zhǎng)、錄音大小的顯示。
- 支持邊錄邊轉(zhuǎn)(播放) 后續(xù)支持。
- 支持導(dǎo)出錄音文件,格式為 pcm 或 wav。
- 支持錄音波形顯示,可自己定制。
項(xiàng)目地址:https://github.com/2fps/recorder
演示地址:https://recorder.zhuyuntao.cn/
Vue 項(xiàng)目創(chuàng)建
按下面的步驟創(chuàng)建 Vue 項(xiàng)目:

然后 cd 到 vue_recorder 下,終端輸入 npm run serve,出現(xiàn)下面輸出說(shuō)明成功了:

瀏覽器打開(kāi) http://localhost:8080/:

下載相關(guān)依賴
在項(xiàng)目中我們會(huì)用到 js-audio-plugin 以及 Element ,所以需要下載相關(guān)依賴并在 main.js 中引入。
安裝 js-audio-plugin 指令:npm i js-audio-recorder。
安裝 Element 指令:npm install element-ui。
安裝好以后,在 main.js 添加:
// 引入 element-ui import ElementUI from 'element-ui'; // element-ui 的 css 樣式要單獨(dú)引入 import 'element-ui/lib/theme-chalk/index.css'; Vue.use(ElementUI);
主界面設(shè)計(jì)
主頁(yè)面的設(shè)計(jì)在根組件 App.vue 中進(jìn)行,主要負(fù)責(zé)一些全局內(nèi)容的顯示。
<template>
<div id="app">
<!-- <nav>
<router-link to="/">Recorder</router-link> |
</nav> -->
<router-view />
</div>
</template>
<style lang="scss">
#app {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
}
nav {
padding: 30px;
a {
font-weight: bold;
color: #2c3e50;
&.router-link-exact-active {
color: #42b983;
}
}
}
</style>
設(shè)置路由
在 router 目錄下的 index.js 中設(shè)置路由:
import Vue from 'vue'
import VueRouter from 'vue-router'
import RecorderView from '../views/RecorderView.vue'
Vue.use(VueRouter)
const routes = [
{
path: '/',
name: 'recorder',
component: RecorderView
},
]
const router = new VueRouter({
routes
})
export default router
組件及頁(yè)面設(shè)計(jì)
在 compoments 文件夾下新建 MyRecorder.vue:
<template>
<div style="padding: 20px;">
<h1>{{ msg }}</h1>
<h3>錄音上傳</h3>
<div style="font-size:14px">
<h3>錄音時(shí)長(zhǎng):{{ recorder && recorder.duration.toFixed(4) }}</h3>
<br />
<el-button type="primary" @click="handleStart">開(kāi)始錄音</el-button>
<el-button type="info" @click="handlePause">暫停錄音</el-button>
<el-button type="success" @click="handleResume">繼續(xù)錄音</el-button>
<el-button type="warning" @click="handleStop">停止錄音</el-button>
<br />
<br />
<h3>
播放時(shí)長(zhǎng):{{ recorder && (playTime > recorder.duration ? recorder.duration.toFixed(4) : playTime.toFixed(4)) }}
</h3>
<br />
<el-button type="primary" @click="handlePlay">播放錄音</el-button>
<el-button type="info" @click="handlePausePlay">暫停播放</el-button>
<el-button type="success" @click="handleResumePlay">繼續(xù)播放</el-button>
<el-button type="warning" @click="handleStopPlay">停止播放</el-button>
<el-button type="error" @click="handleDestroy">銷毀錄音</el-button>
<el-button type="primary" @click="downloadPCM">下載PCM數(shù)據(jù)</el-button>
<el-button type="primary" @click="downloadWAV">下載WAV數(shù)據(jù)</el-button>
<el-button type="primary" @click="uploadRecord">上傳</el-button>
</div>
</div>
</template>
<script>
import Recorder from 'js-audio-recorder'
// import axios from 'axios'
export default {
name: 'MyRecorder',
props: {
msg: String
},
data() {
return {
recorder: null,
playTime: 0,
timer: null,
src: null
}
},
created() {
this.recorder = new Recorder({
sampleBits: 16, // 采樣位數(shù),支持 8 或 16,默認(rèn)是 16
sampleRate: 16000, // 采樣率,支持 11025、16000、22050、24000、44100、48000,根據(jù)瀏覽器默認(rèn)值,Chrome 是 48000
numChannels: 1, // 聲道數(shù),支持 1 或 2, 默認(rèn)是 1
})
},
methods: {
// 開(kāi)始錄音
handleStart() {
this.recorder = new Recorder()
Recorder.getPermission().then(() => {
console.log('開(kāi)始錄音')
this.recorder.start() // 開(kāi)始錄音
}, (error) => {
this.$message({
message: '請(qǐng)先允許該網(wǎng)頁(yè)使用麥克風(fēng)',
type: 'info'
})
console.log(`${error.name} : ${error.message}`)
})
},
handlePause() {
console.log('暫停錄音')
this.recorder.pause() // 暫停錄音
},
handleResume() {
console.log('恢復(fù)錄音')
this.recorder.resume() // 恢復(fù)錄音
},
handleStop() {
console.log('停止錄音')
this.recorder.stop() // 停止錄音
},
handlePlay() {
console.log('播放錄音')
console.log(this.recorder)
this.recorder.play() // 播放錄音
// 播放時(shí)長(zhǎng)
this.timer = setInterval(() => {
try {
this.playTime = this.recorder.getPlayTime()
} catch (error) {
this.timer = null
}
}, 100)
},
handlePausePlay() {
console.log('暫停播放')
this.recorder.pausePlay() // 暫停播放
// 播放時(shí)長(zhǎng)
this.playTime = this.recorder.getPlayTime()
this.time = null
},
handleResumePlay() {
console.log('恢復(fù)播放')
this.recorder.resumePlay() // 恢復(fù)播放
// 播放時(shí)長(zhǎng)
this.timer = setInterval(() => {
try {
this.playTime = this.recorder.getPlayTime()
} catch (error) {
this.timer = null
}
}, 100)
},
handleStopPlay() {
console.log('停止播放')
this.recorder.stopPlay() // 停止播放
// 播放時(shí)長(zhǎng)
this.playTime = this.recorder.getPlayTime()
this.timer = null
},
handleDestroy() {
console.log('銷毀實(shí)例')
this.recorder.destroy() // 銷毀實(shí)例
this.timer = null
},
downloadPCM() {
console.log('下載PCM格式數(shù)據(jù)')
// 注:使用該方法會(huì)默認(rèn)調(diào)用 stop() 方法
this.recorder.downloadPCM('record-pcm')
},
downloadWAV() {
console.log('下載WAV格式數(shù)據(jù)')
// 注:使用該方法會(huì)默認(rèn)調(diào)用 stop() 方法
this.recorder.downloadWAV('record-wav')
},
uploadRecord() {
if (this.recorder == null || this.recorder.duration === 0) {
this.$message({
message: '請(qǐng)先錄音',
type: 'error'
})
return false
}
this.recorder.pause() // 暫停錄音
this.timer = null
console.log('上傳錄音') // 上傳錄音
const formData = new FormData()
const blob = this.recorder.getPCMBlob() // 獲取 pcm 格式音頻數(shù)據(jù)
// 此處獲取到 blob 對(duì)象后需要設(shè)置 fileName 滿足項(xiàng)目上傳需求,這里選擇直接把 blob 作為 file 塞入 formData
const fileOfBlob = new File([blob], new Date().getTime() + '.pcm')
formData.append('file', fileOfBlob)
const url = window.URL.createObjectURL(fileOfBlob)
this.src = url
// const axios = require('axios')
// axios.post(url, formData).then(res => {
// console.log(res.data.data[0].url)
// })
}
}
}
</script>
在 views 文件夾下新建 RecorderView.vue:
<template>
<div class="home">
<!-- <img
alt="Vue logo"
src="../assets/logo.png"
> -->
<MyRecorder msg="Welcome to Vue Recorder" />
</div>
</template>
<script>
// @ is an alias to /src
import MyRecorder from '@/components/MyRecorder.vue'
export default {
name: 'RecorderView',
components: {
MyRecorder
}
}
</script>
項(xiàng)目啟動(dòng)
在終端中輸入指令:npm run serve。
可以看到如下界面,說(shuō)明項(xiàng)目成功運(yùn)行:

根據(jù)提示訪問(wèn)本地地址 http://localhost:8080/。

經(jīng)過(guò)測(cè)試,頁(yè)面正常排布,所有功能都正常使用(除了上傳功能)。
源碼下載
GitHub:https://github.com/UestcXiye/Vue-Recorder
到此這篇關(guān)于Vue使用js-audio-recorder實(shí)現(xiàn)錄制,播放與下載音頻功能的文章就介紹到這了,更多相關(guān)Vue js-audio-recorder內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Vue使用枚舉類型實(shí)現(xiàn)HTML下拉框步驟詳解
本文分步驟給大家介紹了Vue使用枚舉類型實(shí)現(xiàn)HTML下拉框的相關(guān)知識(shí),非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2018-02-02
vue在IIS服務(wù)器部署后路由無(wú)法跳轉(zhuǎn)
在IIS服務(wù)器上部署Vue項(xiàng)目時(shí),可能會(huì)遇到路由無(wú)法正常跳轉(zhuǎn)的問(wèn)題,解決方法有兩種,下面就來(lái)具體介紹一下解決方法,感興趣的可以了解一下2024-10-10
Vue引用Swiper4插件無(wú)法重寫(xiě)分頁(yè)器樣式的解決方法
今天小編就為大家分享一篇Vue引用Swiper4插件無(wú)法重寫(xiě)分頁(yè)器樣式的解決方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2018-09-09
Vue2安裝使用MonacoEditor方式(自定義語(yǔ)法,自定義高亮,自定義提示)
這篇文章主要介紹了Vue2安裝使用MonacoEditor方式(自定義語(yǔ)法,自定義高亮,自定義提示),具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-04-04
vue后臺(tái)項(xiàng)目如何使用router.addRoutes動(dòng)態(tài)加入路由的思路
這篇文章主要介紹了vue后臺(tái)項(xiàng)目如何使用router.addRoutes動(dòng)態(tài)加入路由的思路,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-06-06
vue cli3中eslint報(bào)錯(cuò)no-undef和eslint規(guī)則配置方式
這篇文章主要介紹了vue cli3中eslint報(bào)錯(cuò)no-undef和eslint規(guī)則配置方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-08-08
Vue3使用Vuex之mapState與mapGetters詳解
這篇文章主要為大家介紹了Vue3使用Vuex之mapState與mapGetters詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-03-03
在 Vue 中編寫(xiě) SVG 圖標(biāo)組件的方法
這篇文章主要介紹了在 Vue 中編寫(xiě) SVG 圖標(biāo)組件的方法,本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-02-02

