一。問題重述
有的公眾號消息點進去之後能夠自動播放音樂,不需要用戶手動觸發再 play,這是怎麼實現的?
二。方案嘗試
1.audio 設置 autoplay 屬性播放
給 audio 標籤設置 autoplay="autoplay"
結果:在某些Android 機上可以自動播放,IOS 不支持
2.setTimeout 播放
進入頁面後延遲執行 audio.play()
結果:Safari,IOS 微信不支持
3. 按鈕播放
通過點擊按鈕或者 touch 事件觸發播放
結果:某些 Android 微信不支持
4. 用舊微信 API 回調播放
通過獲取網絡狀態的接口回調播放(無論成功失敗,都執行 play)
var audio = document.getElementById('audio');
if (window.WeixinJSBridge) {
WeixinJSBridge.invoke('getNetworkType', {}, function(e) {
audio.play();
}, false);
}else{
document.addEventListener("WeixinJSBridgeReady", function() {
WeixinJSBridge.invoke('getNetworkType', {}, function(e) {
audio.play();
});
}, false);
}
結果:IOS 微信不支持,Safari 不支持(未做兼容性處理)
5. 用新微信 API 回調播放
原理同上,只是用了新的微信 API,詳細信息請查看 微信 JS-SDK 說明文檔
var audio = document.getElementById('audio');
if (window.WeixinJSBridge) {
wx.getNetworkType({
success: function (res) {
audio.play();
},
fail: function (res) {
audio.play();
}
});
}else{
document.addEventListener("WeixinJSBridgeReady", function() {
wx.getNetworkType({
success: function (res) {
audio.play();
},
fail: function (res) {
audio.play();
}
});
}, false);
}
結果:IOS 支持性未知
6. 微信 API 回調用 AudioAPI 播放
AudioAPI 無法打破 IOS 系統不讓自動下載音頻的限制(具體見後文),所以嘗試在回調中用 AudioAPI 播放音頻
注意:低版本 IOS 不支持 AudioAPI,Android 支持性未知
// 獲取 AudioContext
window.context = getAudiocontext();
// 獲取音頻數據
window.source = null;
window.bufs = [];
// 執行
getBufs();
/**
* 獲取 AudioContext
* @return {AudioContext} andio 元素相關的環境對象
*/
function getAudiocontext() {
window.AudioContext = (window.AudioContext || window.webkitAudioContext);
if(window.AudioContext) {
return new window.AudioContext();
} else {
console.log('not support web audio api');
}
}
/**
* 播放
* @param {Integer} 1: 多個 source 直接連接輸出設備 2: 多個 source 通過 GainNode 再連接輸出設備
* @return nth
*/
function getBufs() {
var audioURL = 'didi.mp3'; // 這裡替換為音頻文件 URL
var xhr1 = new XMLHttpRequest();
xhr1.open('GET', audioURL, true);
xhr1.responseType = 'arraybuffer'; // XMLHttpRequest 2 的新東西
xhr1.onload = function() {
// 音頻數據在 xhr.response 中,而不是 xhr.requestText
bufs.push(xhr1.response);
}
xhr1.send();
}
//////////
// 微信回調 //
//////////
var audio = document.getElementById('audio');
function runNow() {
context.decodeAudioData(bufs[0], function(buffer) {
source = context.createBufferSource();
source.buffer = buffer;
// 源直接連接到輸出設備
source.connect(context.destination);
source.start(0);
});
}
if (window.WeixinJSBridge) {
WeixinJSBridge.invoke('getNetworkType', {}, function(e) {
setTimeout(runNow, 3000);
}, false);
}else{
document.addEventListener("WeixinJSBridgeReady", function() {
WeixinJSBridge.invoke('getNetworkType', {}, function(e) {
setTimeout(runNow, 3000);
});
}, false);
}
結果:iPhnoe5 不支持,6p 未知,能觸發回調,但 play 代碼無效
7. 其他可能能實現的方法
- 模擬事件觸發(trigger)
手動觸發事件,在事件處理器中播放音頻,未經測試
- 新 API
官方公開的 1.0.0 版本 API 不支持播放音頻(僅僅支持播放錄音),後續可能會開放更多音頻 API,當然,都是後話
三。解決方案
沒有完美兼容的解決方案,經測試,iPhone 5S 及 6 上可以用 JS API 回調方式播放,Android 自動播放比較容易,但某些深度定制機型仍然無法播放
自動播放的難點主要來自 IOS,因為 IOS 系統限制不能自動下載音頻視頻,必須由用戶動作觸發播放:
In Safari on iOS (for all devices, including iPad), where the user may be on a cellular network and be charged per data unit, preload and autoplay are disabled. No data is loaded until the user initiates it. This means the JavaScript play() and load() methods are also inactive until the user initiates playback, unless the play() or load() method is triggered by user action. In other words, a user-initiated Play button works, but an onLoad="play()" event does not.
(引自 Safari HTML5 Audio and Video Guide)
關於 IOS 自動播放音頻的更多解決方案,請查看 Autoplay audio files on an iPad with HTML5
還看到一種解決方案:
if ("wView" in window) {
window.wView.allowsInlineMediaPlayback = "YES";
window.wView.mediaPlaybackRequiresUserAction = "NO";
}
據說添加上面代碼之後,直接 preload、autoplay 就可以了
注意:未經測試,效果未知
四。DEMO
http://www.ayqy.net/t/autoplay.html
參考資料
-
[黯羽輕揚:微信 API](/articles/微信 api/)
暫無評論,快來發表你的看法吧