Execute javascript when all videos on page have been fully loaded - javascript

I have modified this script to accept videos instead of images:
http://www.catchmyfame.com/catchmyfame-jquery-plugins/jquery-beforeafter-plugin/
Locally, it works fine, but when I upload to a server, the videos are not synced. The first video starts earlier than the other one. Check it out:
http://amarsyla.com/sandbox/beforeafter/
HTML:
<div id="container">
<div>
<video alt="before" autoplay="true" loop="true" width="600" height="366">
<source src="before.mp4" type="video/mp4;">
</video>
</div>
<div>
<video alt="after" autoplay="true" loop="true" width="600" height="366">
<source src="after.mp4" type="video/mp4;">
</video>
</div>
</div>
I initialize the plugin using this code:
$(window).load(function() {
$('#container').beforeAfter();
});
Obviously, the window.load doesn't do the job. I need a JavaScript event or something similar which will be triggered that both of the videos have been loaded and they can start playing simultaneously with each other. I want the videos to be in perfect sync with each other, so each of them starts at the same time, and I thought this would be possible by initializing the plugin after both videos have been fully loaded. I've tried this:
var vid = document.getElementById("myVideo");
vid.oncanplaythrough = function() {
alert("Can play through video without stopping");
};
That doesn't work as I expected. It doesn't always fire. Any help would be appreciated.

The code in your question is different from the code at the link, so I'll go by the latter since that's the one actually running.
It looks like what's happening is that even once the videos are playing, they're losing synchronization a few seconds later when they have to wait for more data from the network. One might think that "oncanplaythrough" would be enough to assume that the videos are sufficiently buffered to play all the way through without pausing, it's not always the case.
In theory, "canplaythrough" fires when the browser guesses that data is coming in faster than you're playing it, as opposed to "canplay" which fires when there is just enough data to show one or two frames from the current time. But Chrome fires "canplaythrough" immediately after "canplay" so you can't count on it. Even on other better-behaved browsers, it's still possible that the data transfer starts fast and then slows down after the event fires.
So that means that you have to continuously watch for any "waiting" events on either video and pause them both until they catch up again.
Here's an example you can use as a reference to get you started:
http://code.chirls.com/whiteknuckles/
It's very old code and not my best work. I would do it differently if I wrote it today, but it seems to work reasonably well.

Related

html5 video poster gif to display until full video loaded

I would like to keep the poster gif displayed until the full video has loaded. It seems like this is not possible but does anyone else have a work around.`
<video id="wrVideo" controls poster="/images/busy.gif"
controlsList="nodownload" onerror="myFunction()" preload="auto" autoplay>
The gif loads but since chrome will start playing as soon as it thinks it has enough to play, I cannot manipulate this. I can check the buffered value at various times but not sure how I can implement this to only play the video when more than half of the video duration has buffered.
vid.oncanplaythrough = function() {
if(vid.buffered.end(0) < vid.duration){
vid.pause;
}
}
something like this but rather load the gif/spinner while the buffering reaches that point. Any ideas?
I finally figured this out and it involved a hack around chrome loading playable segments at a time. I forced the browser to download the entire video and then passed the blob url to the video source and voila, the preloader spins while the video is still loading which takes a while.

Displaying at least 100 videos on a single Web page

I would like to display a webpage with a wall of very short videos:
The videos are 1-2s long and all the same size (about 100px wide)
They are display in the form of a matrix (e.g. 10x10)
Playing the videos is triggered by user interaction (click or hover)
So far, I have tried inserting video tags using jQuery but when I reach about 60 videos, my browser (Chrome) hangs.
My question: is there a trick to display such a large quantity of videos on a single web page and what issue should I look out for to make sure the videos are ready to play before the user starts to interact.
EDIT: I understand this isn't common practice, but this project is an art installation and I need to be able to trigger all the videos (or moving images) on demand and without delay. On the other hand, the initial loading time doesn't matter so much, as the user will be made aware of the heavy load.
Thanks :)
IMO "videos are ready (...) before the user starts to interact" contradicts a leightweight DOM. You cannot have both. I'd try to show thumbnails and initialize the video with the interaction.
you could try to use the
use the
<video width="320" height="240" controls>
<source src="embed Link" type="video/mp4">
Your browser does not support the video tag.
</video>
tag inside of html. then you can acces every object by giving it a tag

Stop playing parent frame HTML5 audio from an iframe?

Quick question: I have an HTML document playing HTML5 Audio. Nothing fancy. Textbook really.
<audio id="audioclip" preload="auto" loop >
<source src="audio/music01.ogg" type="audio/ogg">
</audio>
The same HTML document features an iframe containing a few Images. Clicking on one of these images browses to a page containing an autostart HTML5 video clip.
Of course now the audio from the parent AND the audio from the iframe video play at the same time.
Is there an EASY way to stop the parent audio playback from inside the iframe automatically when the autoplay video triggers?
I found some pretty complicated stuff for parent/child communication. Far to sophisticated for me. But I also found this little snippet:
jQuery(function($) {
parent.$("#parent_element").trigger(event);
} (window.jQuery));
Could I put that to use in my case?
Or are there alternatives?
Just getting into JavaScript a little more, atm I'd consider myself a newbie. :-\
Many Thanks!
PS: On video end the iframe page automatically browses back to the previous page. It would be super-nifty if the audio would resume playing at the Point IF it was playing before. If not then...well...not. But I reckon that would be much more complex?

Firefox doesn't recognize if video src gets interrupted

i'm currently playing around with video.js to make video watching a bit more reliable. The current case if: while watching a video, the connection gets interrupted (loss of internet connectivity).
With chrome it was no big deal: I created a function, attached the function to the error event and voila, if an error occurred, my function was able to recover (in this case its just trying to reload the video and seek to the last known position).
On firefox nothing happened at all. The error is never raised.
I tried to work around this a bit and noticed that firefox seems to think the file is fully loaded in case of a network interruption. So the bufferedPercent jumps to 1 and the loadedalldata event is also triggered. For me this seems to be just broken, but i'm unable to nail it down to a firefox or a video.js problem.
Anyone else having such problems or knows a better way to handle such problems?
Background info: to test the case, i run a HAProxy infront of two webservers running nginx who deliver the video files. To trigger my problem, i just kill the nginx which is currently delivering the stream. So a reconnect should work fine (as long as the other one is still working of course ;)
Thanks and regards,
Darkman
Could it be that you are binding the error on the video tag and not the source tag?
As stated here:
Instead of the error event being dispatched to the media element itself, it now gets delivered to the child elements corresponding to the sources resulting in the error.
<video controls id="videoTag" width="640" height="360" preload="auto">
<source src="pathto.mp4" type='video/mp4; codecs="avc1.42E01E, mp4a.40.2"' id="mp4Source">
<source src="pathto.webm" type='video/webm; codecs="vp8.0, vorbis"' id="webmSource">
</video>
<script type="text/javascript">
document.getElementById('mp4Source').addEventListener('error', function(ev) {
alert('mp4Source error');
}, false);
document.getElementById('webmSource').addEventListener('error', function(ev) {
alert('webmSource error');
}, false);
document.getElementById('videoTag').addEventListener('error', function(ev) {
alert('videoTag error');
}, false);
document.getElementById('videoTag').addEventListener('stalled', function(ev) {
alert('videoTag stalled');
}, false);
</script>
EDIT: also check for the stalled event as it triggers when one disconnects the network while the media resource is downloading. Source.
When detecting playback/network errors on HTML5 video I normally use something that follows the code at end of this section.
Thanks

Javascript onloadedmetadata event not firing on iOS devices

Part of my current project involves loading external videos through HTML5's native video tag and then resizing them with Javascript to be the full height & width of the DOM.
My code seems to work perfectly on desktop browsers, but when I load up my project on my ipad the video doesn't get resized because the onloadedmetadata event never gets fired.
Here is a small code sample which reproduces the problem:
function init() {
var video = document.getElementById('viddy');
video.addEventListener('loadedmetadata', function(e){
var dimensions = [video.videoWidth, video.videoHeight];
alert(dimensions);
});
}
document.addEventListener("DOMContentLoaded", init, false);
<video id="viddy" autoplay>
<source src="http://media.w3.org/2010/05/sintel/trailer.webm" type='video/webm' />
<source src="http://www.w3schools.com/html/movie.mp4" type="video/mp4" />
</video>
http://jsfiddle.net/AUSNu/213/
I've even tried coding up a solution using jQuery, on the off-chance that the event may fire, but it still doesn't.
$('#viddy').on('loadedmetadata', function() {
alert('test');
});
I even went as far as enabling remote debugging through safari on my ipad, but still no output within the console.
Are there any workarounds to this? I couldn't find much info about this on the web / in documentation.
Unfortunately, there isn't really a way around this. Mobile Safari will not download any part of the video file until it gets a user interaction (i.e. some kind of touch event), not even the header, which is required to know the dimensions.
In your specific example, you need to enable controls on the video so the user can start it playing. (Or you can write your own code that starts it, but it has to be triggered by a touch or click event.) Once it starts playing, the loadedmetadata even will fire, and you can do what you want.
I recommend reading this other answer where someone else was trying to do pretty much the same thing. It discusses the problem in more detail along with a working link. Also, it addresses another problem with scaling the video that you will probably run into.
Safari on iPad (iOS6) does not scale HTML5 video to fill 100% of page width

Categories

Resources