iPad Bug Fix for Dynamically Created HTML5 Video

June 21st, 2010 by Mike Wilcox

I’m continuing my series on the iPad-targeted, BetterVideo HTML5 player which primarily targets the iPad which I first mentioned in a previous post. The player won’t be using the browser’s default controls — that would be sacrilegious for an AJAX developer who prides himself on UI design, and you can’t customize default player controls. Additionally, the HTML5 player will have the same functionality as the Flash player, so between the custom controls and this functionality, there will be a lot of JavaScript used. But even more importantly, the player is not placed on our own page; it’s designed to be used on our clients’ pages. Therefore, my preference is to provide the client with a simple bit of code and dynamically build everything that needs to be inserted into their page. This is where I ran into the iPad bug.

The Bug

I had created a prototype and it worked fine in Safari and Firefox, but when I went to test it in the iPad, the video didn’t play. Even stranger, there were no errors and certain video events were still triggered. I hard coded an HTML player, and that worked, but not the dynamic one. I tried building it with both with innerHTML and using createElement. document.write does work, but this is not much different than using straight markup. recreating the bug is quite simple and looks like this:

s +=	'<video width="480" height="270" controls>' +
            '<source src="myVideo.mp4" type="video/mp4" />' +
        '</video>';
node.innerHTML = s;

The Fix

I couldn’t find this fix on the web, I basically deduced it from a few other bug reports. There are issues with the video poster property when used with the child node objects. And if you have more than one source object, iPad ignores all but the first. As you can see in the example above, the latter bug didn’t apply. Those reports led me to believe that when I dynamically created the video object, the source/src wasn’t being set or read:

var video = p.node.getElementsByTagName("video")[0];
video.src = "myVideo.mp4";
video.load();

I tried it and it worked. This fix is only necessary for the iPad, and in my code, I have a conditional that only applies it if so. I’d like to use feature detection, but considering the iPad is my primary target, I don’t want to cripple it by adding a lag that checks if the video is playing. I also don’t expect this to be a bug that will last past the next iPad update or two.

Conclusion

HTML5 video is a very exciting new feature but it is still new. I’ve created a ticket for this on on the Webkit bug tracker. Bugs are to be expected, but so far they have been a minor hindrance to the development of our HTML5 Video Player. Stay tuned to this series for more updates.

Tags: , , , , , , ,

16 Responses to “iPad Bug Fix for Dynamically Created HTML5 Video”

  1. [...] iPad Bug Fix for Dynam­i­cally Cre­ated HTML5 Video | Club AJAX – Dal­las Ft. Worth Area AJAX … [...]

  2. Nielsenaa says:

    You’re Spot On ;

    Been scratching my head why ajax-loaded divs with single or multiple video tags in them would not work on ipad, while perfectly working on iphone or safari on desktop

    Thank you , you saved my sanity, and can now think about a workaround

  3. Nielsenaa says:

    Thank you very much ! coded that workaround, worked perfectly and even gave me the will to start getting playing with js video tag control , ha nice! :)

  4. Nielsenaa says:

    function getvid(divtarg,vidurl) {

    /* cleaning the div’s target content to avoid some slow or blocking UI behaviour, ifthere was already a video playing or at least in place */
    document.getElementById(divtarg).innerHTML = “”;

    /* inserting the video tag */
    document.getElementById(divtarg).innerHTML = “”;
    /* Mike ‘s code */
    var videotag = getElementsByTagName(“video”)[0];
    videotag.src = vidurl;
    videotag.load();
    }

    Where divtarg is the target div’s id where you want the video placed
    and vidurl, which is the complete absolute or relative url ;
    Thank you again Mike!

  5. Nielsenaa says:

    function getvid(divtarg,vidurl) {

    /* cleaning the div’s target content to avoid some slow or blocking UI behaviour, ifthere was already a video playing or at least in place */
    document.getElementById(divtarg).innerHTML = “”;

    /* inserting the video tag */
    document.getElementById(divtarg).innerHTML = “”;

    /* Mike ’s code */
    var videotag = getElementsByTagName(“video”)[0];
    videotag.src = vidurl;
    videotag.load();
    }

    Sorry, i forgot some backslashes that where automatically trimmed when i posted my initial message

  6. Nielsenaa says:

    sorry for the flood, my message keeps getting trimed; should read in second line (inserting the video tag):

    document.getElementById(divtarg).innerHTML = ”;

    (hope this message gets accepted, otherwise ill stop here trying :) )

  7. [...] many technical hurdles that had to be addressed, one of which was simply getting the darn thing to work on the iPad. But the main hurdle was the handling of fullscreen mode, which the specification does not allow [...]

  8. mtness says:

    Hi there! Just ran into this bug today, too. Many Thanx for sharing the fix.

    Kind regards, mtness.

  9. David says:

    Hi, you are the man!! ;) this bug made me go crazy…

    Thanks a lot.

    D

  10. Steve says:

    I tried this fix and while the video does play, it opened full screen even though I specified a width and height.

  11. [...] many technical hurdles that had to be addressed, one of which was simply getting the darn thing to work on the iPad. But the main hurdle was the handling of fullscreen mode, which the specification does not allow [...]

  12. Connor says:

    Thanks Mike – I am seeing the same issue. I came up with a similar workaround, but it’s good to know there are other people out there experiencing the same thing.

    Another issue I’ve seen is that two HTML5 videos won’t play at the same time on the iPad. I have two HTML5 videos on the same page. I click to play one, and then a few seconds later I click to play the other. The first one will stop playing when I click the second one. Even on desktop Safari when I set my user agent to iPad, both videos play fine. But on the actual iPad, both videos won’t play concurrently. Have you seen this issue before?

  13. Mike Wilcox says:

    @Connor, I haven’t. We only have one case where multiple videos are on a page and that doesn’t use the HTML5 player. Is that with the native controls? I wonder if it works better with JavaScript.

  14. Connor says:

    It was using JS, then I changed to use the native controls. I tried different video formats as well, but nothing seemed to work. Then I found this:

    “Multiple Simultaneous Audio or Video Streams

    Currently, all devices running iOS are limited to playback of a single audio or video stream at any time. Playing more than one video—side by side, partly overlapping, or completely overlaid—is not currently supported on iOS devices. Playing multiple simultaneous audio streams is also not supported. You can change the audio or video source dynamically, however. See “Replacing a Media Source Sequentially” for details.”

    http://developer.apple.com/library/safari/#documentation/AudioVideo/Conceptual/Using_HTML5_Audio_Video/Device-SpecificConsiderations/Device-SpecificConsiderations.html

    Unfortunately it doesn’t seem like there is any workaround here…

  15. Mike Wilcox says:

    @Connor, that’s excellent info that may have saved me and some readers a lot of pain and suffering. thanks!

  16. Tudor says:

    Thanks you so much for posting this, it saved my sanity after one day of unsuccessfully trying to get dynamically added audio to play :)