Vimeo Froogaloop - Not detecting pause - javascript

I am using the old Vimeo API froogaloop for a project. I realise this is now out of date but this is a legacy project and does not support the new version.
I am trying to determine if a video is paused or not by doing this..
$lg.on('onAfterSlide.lg', function(event, prevIndex, index){
iframe = $('.inner .item').eq(index).find('.vimeo').get(0);
var player = $f(iframe);
player.addEvent('ready', function() {
player.addEvent('paused', function(paused) {
if (paused) {
console.log('Video is paused');
}
else {
console.log('Video is not paused');
}
});
});
});
For some reason the paused function never runs, can anyone see any obvious mistakes I am making?

Looks like you are listening to the wrong event. Update paused to pause.
player.addEvent('pause',...
That should ensure you are listening to the correct event.
Out of curiosity, what in your out of date project blocks you from updating to the latest Video Player API from Froogaloop?

Related

How to autoplay audio when the countdown timer is finished?

I want to play a sound after the countdown timer is done.
Normally I will do it using this peace of code
var audio = new Audio('path to file.mp3');
audio.play();
But I get the following error Unhandled Promise Rejection: NotAllowedError: The request is not allowed by the user agent or the platform in the current context, possibly because the user denied permission.
The thing is ... Google it self is doing it using a HTML5 audio tag
If you type countdown timer into google search field it should show you the widget that plays a sound after the countdown timer is finished.
Here is how Googles timer look like, if you guys don't know what I'm talking about :)
By making you click this "START" button, they ask for an user gesture and thus have marked their document as approved-by-user to play audio. This means they are not subject for chrome's autoplay policies anymore.
Now, Safari by default is even stricter than Chrome here, and a simple click on the document doesn't work: in this browser you need to start the playback from the user-event itself.
So in your case, it won't work, even if you did start the countdown from a click like Google.
The solution is then to start the playback from the click event, and to pause it immediately after. Doing so, your Element will be marked as approved-by-user and you will ave full control over it.
const audio = new Audio("https://dl.dropboxusercontent.com/s/1cdwpm3gca9mlo0/kick.mp3");
let time = 5;
btn.onclick = e => {
// mark our audio element as approved by the user
audio.play().then(() => { // pause directly
audio.pause();
audio.currentTime = 0;
});
countdown();
btn.disabled = true;
};
function countdown() {
pre.textContent = --time;
if(time === 0) return onend();
setTimeout(countdown, 1000);
}
function onend() {
audio.play(); // now we're safe to play it
time = 5;
btn.disabled = false;
}
<button id="btn">start countdown</button><br>
<pre id="pre"></pre>

HTML5 video - setting video.currentTime breaks the player

I am trying to interact with a 3rd-party html5 video player in Chrome. I am able to obtain a valid reference to it thusly:
document.getElementsByTagName("video")[1]
...and the readyState is 4, so it's all good.
I can successfully (and with expected result) call:
document.getElementsByTagName("video")[1].play();
document.getElementsByTagName("video")[1].pause();
BUT when I call:
document.getElementsByTagName("video")[1].currentTime = 500;
...the video freezes and it doesn't advance to the new currentTime. The video duration is much longer than 500 seconds, so it should be able to advance to that spot. I have tried other times besides 500, all with same result. If I examine currentTime, it is correct as to what I just set. But it doesn't actually go there. Also I can no longer interact with the video. It ignores any calls to play() or pause() after I try to set currentTime.
Before I call currentTime, when I call play() I get this valid promise back, and everything else still works:
After I call currentTime, when I call play(), I get this broken promise back, and now nothing works on that video object:
If you have a Hulu account you can easily observe this behavior on any video by simply trying it in the Chrome developer console.
EDIT: It was pointed out to me that skipping very much ahead breaks, but skipping a short distance actually works well. Could be related to commercials interspersed.
Try below code, it will first pause then set your position then again play
document.getElementsByTagName("video")[1].pause();
document.getElementsByTagName("video")[1].currentTime = 500;
document.getElementsByTagName("video")[1].play();
Why don't you try this code.
function setTime(tValue) {
// if no video is loaded, this throws an exception
try {
if (tValue == 0) {
video.currentTime = tValue;
}
else {
video.currentTime += tValue;
}
} catch (err) {
// errMessage(err) // show exception
errMessage("Video content might not be loaded");
}
}
Pls. try this:
hv = document.getElementsByTagName("video")[1];
hv.play();
hv.addEventListener('canplay', function() {
this.currentTime = 500;
});
var myVideo=document.getElementsByTagName("video")
if(myVideo[1] != undefind)
{
myVideo[1].currentTime=500;
}
/* or provide id to each video tag and use getElementById('id') */
var myVideo=document.getElementById("videoId")
if(myVideo != undefind)
{
myVideo.currentTime=500;
}

Can't avoid delay in javascript audio

I wonder whether this is an unresolved issue or not.
OK, so I have this very simple test code:
var audio = new Audio("0.mp3");
audio.oncanplay = function() {
audio.play();
setTimeout(function() {
audio.pause();
}, 30);
}
What I intend to do is to play my sound for a very short period of time.
I know for sure that the audio (a middle-C note) starts in 0:00:00.
Note that I use the oncanplay event to make sure the audio is loaded when I try to play it.
The problem I have is that I get unpredictable results. Sometimes (most of the times, really), audio is not heard at all. Other times, audio is heard but not always for the same period of time.
I know that Javascript can be slow, but I wonder, for example in the first case, why is the timeout set at all if the audio isn't playing yet.
Is this a known issue? It is possible to have a better control over Audio?
-Thanks
Avoid using setTimeout, which is not accurate and may result (as in your case) in a race condition. Use the 'timeupdate' event to keep track of the progress. Here the song will play and auto-pause after 7 seconds:
var audio = new Audio("0.mp3");
audio.oncanplay = function() {
audio.play();
audio.addEventListener('timeupdate', function() {
console.log(audio.currentTime.toFixed());
if ( audio.currentTime >= 7 ) audio.pause();
});
}
JSFiddle Demo

Tell whether video is loaded or not in Javascript

So, I've been using a listener on
document.getElementById("video").buffered.length
to see if it's greater than 0 for when a video's loaded or not. This works for a very small video, and only in Google Chrome. It doesn't work in Firefox at all. Any ideas for how to get this to work?
I essentially want to wait till 3 seperate videos are loaded to take a specific action, how do I go about this?
Try this:
var video = document.getElementById("video-id-name");
if ( video.readyState === 4 ) {
// it's loaded
}
Read here: https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/readyState
UPDATE:
As others have mentioned, my original solution below does work but it can lead to performance issues and some unpredictability in its behaviour.
Therefore I recommend listening to the loadeddata event.
Read more here: https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/loadeddata_event
const videoElement = document.getElementById("my_video");
videoElement.addEventListener('loadeddata', (e) => {
//Video should now be loaded but we can add a second check
if(videoElement.readyState >= 3){
//your code goes here
}
});
==================================
INFERIOR SOLUTION:
I find using setInterval works for actively listening to when the readyState of the video changes by checking every half-second until it loads in.
checkforVideo();
function checkforVideo() {
//Every 500ms, check if the video element has loaded
var b = setInterval(()=>{
if(VideoElement.readyState >= 3){
//This block of code is triggered when the video is loaded
//your code goes here
//stop checking every half second
clearInterval(b);
}
},500);
}
If you're not using ES6 just replace () => with function()
To make this into a listener, under normal circumstances, you'll want to listen to the suspend event. It's triggered when download is paused or stopped for any reason, including it's finished.
You'll also want to listen to playing for the cases when the content is already loaded (like, from cache)
video.addEventListener("playing", function() {
console.log("[Playing] loading of video");
if ( video.readyState == 4 ) {
console.log("[Finished] loading of video");
}
});
video.addEventListener("suspend", function(e) {
console.log("[Suspended] loading of video");
if ( video.readyState == 4 ) {
console.log("[Finished] loading of video");
}
});
Source: https://developer.mozilla.org/en/docs/Web/Guide/Events/Media_events
Use onloadeddata event on the video element. It checks whether the video is loaded or not. See this reference for more information.
The loadeddata event is fired when the frame at the current playback position of the media has finished loading; often the first frame.
var video = document.getElementById("video");
video.onloadeddata = function() {
// video is loaded
}
I find other way
const video = document.querySelector('video');
video.addEventListener('canplaythrough', (event) => {
console.log('I think I can play through the entire ' +
'video without ever having to stop to buffer.');
});
source - https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/canplaythrough_event

DOM Exception 11 when calling webkitEnterFullscreen()

What does the exception mean? How can I fix it? I am using the latest Google Chrome for Ubuntu.
INVALID_STATE_ERR: DOM Exception 11 can occur when a call to webkitEnterFullscreen is made before the video element has received its asset's metadata. The simplest solution is to defer the invocation of webkitEnterFullscreen by putting it in a callback function assigned to the video's loadedmetadata event.
In a mobile environment, you need to take things a step further by attaching that call to a touchable element so that it is user initiated since play and fullscreen actions must be driven by user interaction in mobile environments.
The code should look kind of like this:
var video, play, fullscreen;
video = document.createElement('video');
video.src = 'my_cool_video.mp4';
video.addEventListener('loadedmetadata', function () {
fullscreen.disabled = false;
}, false);
play = document.createElement('button');
play.innerHTML = 'PLAY';
play.addEventListener('click', function () {
video.play();
}, false);
fullscreen = document.createElement('button');
fullscreen.innerHTML = 'FULLSCREEN';
fullscreen.disabled = true;
fullscreen.addEventListener('click', function () {
video.webkitEnterFullscreen();
}, false);
document.body.appendChild(video);
document.body.appendChild(play);
documnet.body.appendChild(fullscreen);

Categories