jsPsych: Audio fails to start in Safari 14.0.2

I’ve been battling with Safari and audio problems for a while, but that seems to be a new issue.

I understand that modern browsers only allow audio to play after there has been some interaction with the user (e.g. a click on a button). In a new experiment, the participants go through the instructions by hitting the spacebar or clicking on a piece of text. Then come some trials using the audio-keyboard-response plugin. In Firefox and Chrome, the sound plays just fine (whether the user clicks or presses the spacebar), but in Safari, nothing happens, and it just hangs silently.

To unlock it, I had to add an async call-function trial that displays a button with a callback that calls jsPsych.pluginAPI.audioContext():

    const is_Safari = /Version\/.*Safari\//.test(navigator.userAgent) && !window.MSStream;
    if(is_Safari){
        timeline.push({
            type: 'call-function',
            async: true,
            func: function(done){

                var display_element = document.getElementById('jspsych-content');

                display_element.innerHTML = "<p>Click on the screen to start...</p>";
                //var init_button = display_element.querySelector('#safari_audio_init');

                function init_audio_files(){
                    jsPsych.pluginAPI.audioContext();
                    done();
                }

                document.addEventListener('touchstart', init_audio_files, false);
                document.addEventListener('click', init_audio_files, false);
            }
        });
    }

It is a pain… but it works… I tried to have just a button without the jsPsych.pluginAPI.audioContext() callback, and it did not work. This is the only combination that worked, and with or without webAudio made no difference.

Honestly, I don’t think there is anything wrong with jsPsych. I don’t know why Safari makes it extra hard and quirky to get audio started… I’m going to make a plugin to deal with this automatically, but if there’s some more insight out there, that’d be great!

About this issue

  • Original URL
  • State: open
  • Created 3 years ago
  • Comments: 19 (10 by maintainers)

Most upvoted comments

Thanks @qbunt, after some research, we had indeed figured out that much. The issue boiled down to the fact that there is no clear documented definition of what Safari considers a “user gesture” and some cases were defying our intuition.

But this issue is a bit old, I haven’t had much time to look at it more in details (and jsPsych switching to TypeScript has spooked me a bit), and everything could be different by now. At the time, it seemed that, sometimes, clicks on JS generated buttons were not good enough for Safari to unlock playback (see above). It worked to use an HTML button as a workaround for cases where we wanted the test to be ran on iOS or iPad, despite the fact that the HTML button is there before the AudioContext is created… so definitely some unexpected behaviour. If you get to the bottom of this, it would be great to have some workarounds documented somewhere.

Oh boy. @becky-gilbert you’re right, they are two different issues. Turns out that firefox is a little dumber and let me record audio even without having a microphone, but Chrome(ium) does not.