简体   繁体   English

HTML5 Audio 对象无法在 Safari 中播放

[英]HTML5 Audio object doesn't play in Safari

On my page , I dynamically create an HTML5 Audio element in JavaScript:我的页面上,我用 JavaScript 动态创建了一个 HTML5 Audio 元素:

bell = new Audio("alarmclock.mp3");

Later on (in response to a jQuery Countdown object expiring), I play it:稍后(响应 jQuery Countdown 对象过期),我播放它:

bell.play();

Results:结果:

  • Chrome (6.0.472.55) for Mac: The audio plays fine. Mac 版 Chrome (6.0.472.55):音频播放正常。
  • OmniWeb (5.10.2): The audio plays fine. OmniWeb (5.10.2):音频播放正常。
  • Safari (5.0.1) for Mac: Mac 版 Safari (5.0.1): I hear nothing.我什么也听不到。 The audio plays fine.音频播放正常。 (I don't know why it didn't work earlier.) (我不知道为什么它没有更早地工作。)
  • MobileSafari (iOS 3.1.3—the latest version for my device): I hear nothing. MobileSafari(iOS 3.1.3——我设备的最新版本):我什么也没听到。

How would I go about troubleshooting this?我将如何解决这个问题? I'd really like to have it working in MobileSafari so my web app can be portable.我真的很想让它在 MobileSafari 中工作,这样我的网络应用程序就可以移植了。

About iPhone Safari: It seems play() work when launched by an onclick event.关于 iPhone Safari:似乎 play() 在由 onclick 事件启动时起作用。 See http://groups.google.com/group/iphonewebdev/browse_thread/thread/91e31ba7ae25e6d4?hl=en请参阅http://groups.google.com/group/iphonewebdev/browse_thread/thread/91e31ba7ae25e6d4?hl=en

Good question with "How would I go about troubleshooting this?". “我将如何解决这个问题?”的好问题。 Here would be my plan of attack...这将是我的攻击计划......

  • Debug with Safari on Mac;在 Mac 上使用 Safari 进行调试; if you get it working there, then go test with MobileSafari, since the latter is more of a pain.如果你让它在那里工作,然后用 MobileSafari 测试,因为后者更痛苦。
  • Start over with a blank page.从空白页重新开始。 Insert HTML5 audio element with this MP3 file statically (not via JavaScript).使用此 MP3 文件静态插入 HTML5 音频元素(不是通过 JavaScript)。
  • Keep working with your minimal page.继续使用您的最小页面。 Use jQuery's $(document).ready(function () { /* ... */ }) to load the audio on page load.使用 jQuery 的$(document).ready(function () { /* ... */ })在页面加载时加载音频。 Does it still work?它仍然有效吗?
  • OK, now try to add your countdown logic to the demo page---as little of it as possible.好的,现在尝试将倒计时逻辑添加到演示页面——尽可能少。 Did that cause the problem?这是否导致了问题?
  • If you've reached this point and it's still working on your demo page, you know that it's going to be something about all the other complicated things on your site, and not a problem with audio or even dynamically-loaded audio.如果您已经达到了这一点并且它仍在您的演示页面上工作,那么您知道这将涉及您网站上所有其他复杂的事情,而不是音频甚至动态加载的音频的问题。 In which case, good luck :-S.在这种情况下,祝你好运:-S。 Either add things to your blank page, testing each time, or temporarily remove them from your original page, until it works.要么将内容添加到您的空白页面,每次进行测试,要么从您的原始页面中暂时删除它们,直到它起作用为止。 Then you'll know what caused the problem.然后你就会知道是什么导致了这个问题。

Good news everybody大家好消息

I read somewhere that once you've played the sound once within a user interaction such as touch or click, you can then play it dynamically from your code.我在某处读到,一旦您在用户交互(例如触摸或点击)中播放了一次声音,您就可以从代码中动态播放它。

So set volume to zero and play all loaded sounds in one go.因此,将音量设置为零并一次性播放所有加载的声音。

I had a listener on 'touchstart' with a single instantiated function that played all the sounds once the user touches the screen.我在“touchstart”上有一个监听器,它有一个实例化的函数,一旦用户触摸屏幕,它就会播放所有的声音。

Here's how I did it in my REACT didMount()这是我在 REACT didMount() 中的做法

componentDidMount() 
{
    
    let that = this;
    document.body.addEventListener('touchstart', function(evt) //First touch event on the screen will trigger this
        { 
            console.log("Audio Setup for iOS:", that.state.allow_sound);
            if(!that.state.allow_sound) //False on initial load
            {
                var Audio1 = document.getElementById("ping");
                Audio1.load();  
                Audio1.volume = 0;
                Audio1.play();          
                
                var Audio2 = document.getElementById("boom");
                Audio2.load();  
                Audio2.volume = 0;
                Audio2.play();  
                        
                var Audio3 = document.getElementById("splash");
                Audio3.load();  
                Audio3.volume = 0;
                Audio3.play();          
                
                var Audio4 = document.getElementById("hit");
                Audio4.load();  
                Audio4.volume = 0;
                Audio4.play();                          

                that.setState({allow_sound : true})
            }
    });
}

Then you can call these sounds dynamically from within the code.

Use使用

bell = new Audio("alarmclock.mp3");
/*** The magical line ***/
bell.load()

bell.play()

Its preferable to use the new Audio() and load() on page load and play() it in some function call.最好在页面加载时使用 new Audio() 和 load() 并在某些函数调用中使用 play() 它。 Because load() takes some time.因为 load() 需要一些时间。 So better to load() the audio on page load to reduce latency.所以最好在页面加载时加载()音频以减少延迟。 Hope it works.希望它有效。 :) :)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM