11
votes

I'm creating a series of video tutorials and would like to prevent users from seeking forward and skipping sections. I'll be using an HTML5 video player that will be used for desktop and iPad browsers. Ideally, I'd like this to work on the iPhone as well, but I realize you have no control over the video on the phone since it uses the iPhone video player.

How can I prevent users from seeking forward on an HTML5 video player?

6
"prevent users from seeking forward": a bad idea, IMO. What if a user watches half, closes his/her browser and then wants to watch the second half? S/He'll be forced to watch the first part again.Bart Kiers
I intend on placing checkpoints throughout the video that will save a user's progress to a DB as the video is playing. If the user returns to the page then they will start from their last checkpoint. The videos will be between 2 - 5 minutes. I realize that removing the ability to seek forward is not a good idea, though the project requires the user to watch the entire video before they can proceed to the next tutorial. Sure, people can view > source and download it, but the tutorial is to teach them a required skill that is a prerequisite for the next tutorial.jaysonp
Well, I can think of one example that forces you to watch the entire video - online driving courses.. they time everything even if you're done reading the text or video, they won't let you go to next section. That sucks. But they had to follow the requirements laid by the law.netrox
Any CBT (computer-based training) system that needs to ensure the user actually views the entire presentation would have requirements like this. If you've ever worked at a corporation that has annual legal training (like anti-corruption or anti-bribery, etc), they typically have similar requirements. This might be an "annoying" thing if you're making a YouTube-ish media site, but there are definitely solid use-cases where this sort of requirement would be vital. No reason to refuse his question on the grounds that you don't understand his use-case.Carnix

6 Answers

10
votes

Another example for Video.js:

videojs('example_video_1').ready(function(){
  var player = this;
  var previousTime = 0;
  var currentTime = 0;
  var seekStart = null;

  player.on('timeupdate', function(){
    previousTime = currentTime;
    currentTime = player.currentTime();
  });

  player.on('seeking', function(){
    if(seekStart === null) {
      seekStart = previousTime;
    }
  });

  player.on('seeked', function() {
    if(currentTime > seekStart) {
      player.currentTime(seekStart);
    }
    seekStart = null;
  });
});
6
votes

I only wanted to prevent seeking forward. I have more code in my system that allows them to pause and come back later. It records the current position and sets the video position on load.

I'm using video.js. I tried to use the timechange event, but it fires before seeking. So, I resorted to using an interval to grab the current position every second. If the seeking position is greater than the current position, then set it back. Works great.

var player = null;
var curpos = 0;
videojs('player').ready(function(){
  player = this;
});

player.on('seeking', function () {
  var ct = player.currentTime();
if(ct > curpos) {
  player.currentTime(curpos);
}
});

function getpos() {
  curpos = player.currentTime();
}
onesecond = setInterval(getpos, 1000);
2
votes

If you really want to do this amazingly user-hostile thing, then you can make use of the controls attribute. You will have to implement any controls you do want to allow using JS.

Of course, the user can always just view > source to get the URI of the video and download it.

1
votes

Thanks for your answer Rick.

I noticed that the user can drag and hold the seeker which allowed them to continue so I added where not seeking to the getPos function.HTML 5 and jQuery.

var video = document.getElementsByTagName('video')[0];

function allowMove() {
  $('input[id$="btnNext"]').removeAttr('disabled');
  $('input[id$="videoFlag"]').val("1");
}

function getpos() {
  if (!(video.seeking)) {
    curpos = video.currentTime;
  }
  console.log(curpos)
}
onesecond = setInterval('getpos()', 1000);

function setPos() {
  var ct = video.currentTime;
  if (ct > curpos) {
    video.currentTime = curpos;
  }
}
0
votes

I agree with @Bart Kiers that this is not a very good idea, but if you must do it, I can think of one way: hide the controls and provide your own play button that starts the video using JavaScript.

0
votes

Why not this way?

var video = document.getElementById("myVideo");
var counter = 0;

video.on('timeupdate', function() {
  if (video[0].paused == false) {
    counter = video[0].currentTime;
  }
}

video.on('seeking', function(e) {
  if ( parseInt(counter, 10) != parseInt(video[0].currentTime, 10) ) {
    video[0].currentTime = counter;
  }
});