提交 7d6146aa 编写于 作者: D DCloud_LXH

feat(App): InnerAudioContext、BackgroundAudioManager支持倍速

上级 9dbf5080
...@@ -20,7 +20,7 @@ eventNames.forEach(name => { ...@@ -20,7 +20,7 @@ eventNames.forEach(name => {
callbacks[name] = [] callbacks[name] = []
}) })
const props = [ const props = [
{ {
name: 'duration', name: 'duration',
readonly: true readonly: true
...@@ -70,10 +70,15 @@ const props = [ ...@@ -70,10 +70,15 @@ const props = [
name: 'protocol', name: 'protocol',
readonly: true, readonly: true,
default: 'http' default: 'http'
},
{
name: 'playbackRate',
default: 1,
cache: true,
} }
] ]
const backgroundEvents = ['prev', 'next'] const backgroundEvents = ['prev', 'next']
class BackgroundAudioManager { class BackgroundAudioManager {
constructor () { constructor () {
...@@ -91,15 +96,15 @@ class BackgroundAudioManager { ...@@ -91,15 +96,15 @@ class BackgroundAudioManager {
} : {}) } : {})
} }
}) })
}) })
backgroundEvents.forEach((name) => { backgroundEvents.forEach((name) => {
onMethod(`onBackgroundAudio${name[0].toUpperCase() + name.substr(1)}`, () => { onMethod(`onBackgroundAudio${name[0].toUpperCase() + name.substr(1)}`, () => {
callbacks[name].forEach(callback => { callbacks[name].forEach(callback => {
if (typeof callback === 'function') { if (typeof callback === 'function') {
callback({}) callback({})
} }
}) })
}) })
}) })
props.forEach(item => { props.forEach(item => {
const name = item.name const name = item.name
...@@ -114,30 +119,30 @@ class BackgroundAudioManager { ...@@ -114,30 +119,30 @@ class BackgroundAudioManager {
this._options[name] = value this._options[name] = value
invokeMethod('setBackgroundAudioState', Object.assign({}, this._options, { invokeMethod('setBackgroundAudioState', Object.assign({}, this._options, {
audioId: this.id audioId: this.id
})) }), name)
} }
} }
Object.defineProperty(this, name, data) Object.defineProperty(this, name, data)
}) })
} }
play () { play () {
this._operate('play') this._operate('play')
} }
pause () { pause () {
this._operate('pause') this._operate('pause')
} }
stop () { stop () {
this._operate('stop') this._operate('stop')
} }
seek (position) { seek (position) {
this._operate('seek', { this._operate('seek', {
currentTime: position currentTime: position
}) })
} }
_operate (type, options) { _operate (type, options) {
invokeMethod('operateBackgroundAudio', Object.assign({}, options, { invokeMethod('operateBackgroundAudio', Object.assign({}, options, {
...@@ -157,4 +162,4 @@ let backgroundAudioManager ...@@ -157,4 +162,4 @@ let backgroundAudioManager
export function getBackgroundAudioManager () { export function getBackgroundAudioManager () {
return backgroundAudioManager || (backgroundAudioManager = new BackgroundAudioManager()) return backgroundAudioManager || (backgroundAudioManager = new BackgroundAudioManager())
} }
...@@ -60,9 +60,13 @@ const props = [ ...@@ -60,9 +60,13 @@ const props = [
}, },
{ {
name: 'volume' name: 'volume'
}, },
{ {
name: 'sessionCategory' name: 'sessionCategory'
},
{
name: 'playbackRate',
cache: true,
} }
] ]
...@@ -95,25 +99,25 @@ class InnerAudioContext { ...@@ -95,25 +99,25 @@ class InnerAudioContext {
} }
Object.defineProperty(this, name, data) Object.defineProperty(this, name, data)
}) })
} }
play () { play () {
this._operate('play') this._operate('play')
} }
pause () { pause () {
this._operate('pause') this._operate('pause')
} }
stop () { stop () {
this._operate('stop') this._operate('stop')
} }
seek (position) { seek (position) {
this._operate('seek', { this._operate('seek', {
currentTime: position * 1e3 currentTime: position * 1e3
}) })
} }
destroy () { destroy () {
clearInterval(this.__timing) clearInterval(this.__timing)
...@@ -121,7 +125,7 @@ class InnerAudioContext { ...@@ -121,7 +125,7 @@ class InnerAudioContext {
audioId: this.id audioId: this.id
}) })
delete innerAudioContexts[this.id] delete innerAudioContexts[this.id]
} }
_operate (type, options) { _operate (type, options) {
invokeMethod('operateAudio', Object.assign({}, options, { invokeMethod('operateAudio', Object.assign({}, options, {
......
...@@ -86,9 +86,16 @@ function stopTimeUpdateTimer () { ...@@ -86,9 +86,16 @@ function stopTimeUpdateTimer () {
} }
} }
function setMusicState (args) { function setMusicState (args, name) {
initMusic() initMusic()
const props = ['src', 'startTime', 'coverImgUrl', 'webUrl', 'singer', 'epname', 'title'] const props = ['src', 'startTime', 'coverImgUrl', 'webUrl', 'singer', 'epname', 'title']
if (name && name === 'playbackRate') {
let val = args[name]
audio.playbackRate && audio.playbackRate(parseFloat(val))
return
}
const style = {} const style = {}
Object.keys(args).forEach(key => { Object.keys(args).forEach(key => {
if (props.indexOf(key) >= 0) { if (props.indexOf(key) >= 0) {
...@@ -150,8 +157,8 @@ export function operateMusicPlayer ({ ...@@ -150,8 +157,8 @@ export function operateMusicPlayer ({
errMsg: `${api}:ok` errMsg: `${api}:ok`
} }
} }
export function setBackgroundAudioState (args) { export function setBackgroundAudioState (args, name) {
setMusicState(args) setMusicState(args, name)
return { return {
errMsg: 'setBackgroundAudioState:ok' errMsg: 'setBackgroundAudioState:ok'
} }
......
...@@ -5,7 +5,7 @@ import { ...@@ -5,7 +5,7 @@ import {
import { import {
publish publish
} from '../../bridge' } from '../../bridge'
const AUDIO_DEFAULT_SESSION_CATEGORY = 'playback' const AUDIO_DEFAULT_SESSION_CATEGORY = 'playback'
const audios = {} const audios = {}
...@@ -14,7 +14,7 @@ const evts = ['play', 'canplay', 'ended', 'stop', 'waiting', 'seeking', 'seeked' ...@@ -14,7 +14,7 @@ const evts = ['play', 'canplay', 'ended', 'stop', 'waiting', 'seeking', 'seeked'
const publishAudioStateChange = (state, res = {}) => publish('onAudioStateChange', Object.assign({ const publishAudioStateChange = (state, res = {}) => publish('onAudioStateChange', Object.assign({
state state
}, res)) }, res))
const initStateChage = audioId => { const initStateChage = audioId => {
const audio = audios[audioId] const audio = audios[audioId]
...@@ -48,12 +48,12 @@ const initStateChage = audioId => { ...@@ -48,12 +48,12 @@ const initStateChage = audioId => {
} }
} }
export function createAudioInstance () { export function createAudioInstance() {
const audioId = `${Date.now()}${Math.random()}` const audioId = `${Date.now()}${Math.random()}`
const audio = audios[audioId] = plus.audio.createPlayer('') const audio = audios[audioId] = plus.audio.createPlayer('')
audio.src = '' audio.src = ''
audio.volume = 1 audio.volume = 1
audio.startTime = 0 audio.startTime = 0
audio.setSessionCategory(AUDIO_DEFAULT_SESSION_CATEGORY) audio.setSessionCategory(AUDIO_DEFAULT_SESSION_CATEGORY)
return { return {
errMsg: 'createAudioInstance:ok', errMsg: 'createAudioInstance:ok',
...@@ -61,7 +61,7 @@ export function createAudioInstance () { ...@@ -61,7 +61,7 @@ export function createAudioInstance () {
} }
} }
export function destroyAudioInstance ({ export function destroyAudioInstance({
audioId audioId
}) { }) {
if (audios[audioId]) { if (audios[audioId]) {
...@@ -74,15 +74,16 @@ export function destroyAudioInstance ({ ...@@ -74,15 +74,16 @@ export function destroyAudioInstance ({
} }
} }
export function setAudioState ({ export function setAudioState({
audioId, audioId,
src, src,
startTime, startTime,
autoplay = false, autoplay = false,
loop = false, loop = false,
obeyMuteSwitch, obeyMuteSwitch,
volume, volume,
sessionCategory = AUDIO_DEFAULT_SESSION_CATEGORY sessionCategory = AUDIO_DEFAULT_SESSION_CATEGORY,
playbackRate
}) { }) {
const audio = audios[audioId] const audio = audios[audioId]
if (audio) { if (audio) {
...@@ -91,7 +92,9 @@ export function setAudioState ({ ...@@ -91,7 +92,9 @@ export function setAudioState ({
autoplay autoplay
} }
if (src) { if (src) {
audio.src = style.src = getRealPath(src) // iOS 设置 src 会重新播放
const realSrc = getRealPath(src)
if (audio.src !== realSrc) audio.src = style.src = realSrc
} }
if (startTime) { if (startTime) {
audio.startTime = style.startTime = startTime audio.startTime = style.startTime = startTime
...@@ -99,9 +102,12 @@ export function setAudioState ({ ...@@ -99,9 +102,12 @@ export function setAudioState ({
if (typeof volume === 'number') { if (typeof volume === 'number') {
audio.volume = style.volume = volume audio.volume = style.volume = volume
} }
audio.setStyles(style) audio.setStyles(style)
if (sessionCategory) { if (sessionCategory) {
audio.setSessionCategory(sessionCategory) audio.setSessionCategory(sessionCategory)
}
if (playbackRate && audio.playbackRate) {
audio.playbackRate(playbackRate)
} }
initStateChage(audioId) initStateChage(audioId)
} }
...@@ -110,7 +116,7 @@ export function setAudioState ({ ...@@ -110,7 +116,7 @@ export function setAudioState ({
} }
} }
export function getAudioState ({ export function getAudioState({
audioId audioId
}) { }) {
const audio = audios[audioId] const audio = audios[audioId]
...@@ -137,7 +143,7 @@ export function getAudioState ({ ...@@ -137,7 +143,7 @@ export function getAudioState ({
} }
} }
export function operateAudio ({ export function operateAudio({
operationType, operationType,
audioId, audioId,
currentTime currentTime
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册