Created
May 30, 2020 16:35
-
-
Save juliancruzsanchez/8394f6f79932affcf6c47bf063c8363d to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| (function(window, document, undefined) { | |
| "use strict"; | |
| var _Scrolleo = function(opts) { | |
| // Defaults | |
| this.acceleration = 0.08; //1 is fastest, 0 is slowest, 0.08 is default | |
| this.secondsPerScreen = null; //Set this to the length of the video. "1" is 1 second. | |
| this.additionalOffset = 0; //Add or subtract pixels to when the video will start. "10" means that the video will start 10px earlier. | |
| this.wrapperEl = null; | |
| // Override defaults | |
| if (opts) { | |
| for (var opt in opts) { | |
| this[opt] = opts[opt]; | |
| } | |
| } | |
| }; | |
| var targetScrollPos; | |
| _Scrolleo.prototype = { | |
| init: function() { | |
| var self = this; | |
| this.wrapper = document.querySelectorAll(this.wrapperEl); | |
| // get the location of the top of the page | |
| targetScrollPos = window.pageYOffset; | |
| Array.prototype.forEach.call(this.wrapper, function(wr) { | |
| // Set the pixelsPerSecond to the full duration of the video if nothing was set in the options | |
| if (self.secondsPerScreen === null) { | |
| self.wrapper[0].addEventListener("loadedmetadata", function() { | |
| self.secondsPerScreen = self.wrapper[0].duration; | |
| //recalculate values on video with new pixelsPerSecond | |
| self.distanceToTop = getElemDistanceToTop(elem); | |
| self.offsetFromTop = getOffsetFromTop(self.distanceToTop); | |
| self.pixelsPerSecond = getPixelsPerSecond(); | |
| }); | |
| } | |
| self.pixelsPerSecond = null; | |
| self.scrollPos = null; | |
| self.currentTime = null; | |
| self.offsetFromTop = null; | |
| self.distanceToTop = null; | |
| // http://paulirish.com/2011/requestanimationframe-for-smart-animating/ | |
| // requestAnimationFrame polyfill by Erik Möller. fixes from Paul Irish and Tino Zijdel | |
| (function() { | |
| var lastTime = 0; | |
| var vendors = ["ms", "moz", "webkit", "o"]; | |
| for (var x = 0; x < vendors.length && !window.requestAnimationFrame; ++x) { | |
| window.requestAnimationFrame = window[vendors[x] + "RequestAnimationFrame"]; | |
| window.cancelAnimationFrame = window[vendors[x] + "CancelAnimationFrame"] || window[vendors[x] + "CancelRequestAnimationFrame"]; | |
| } | |
| if (!window.requestAnimationFrame) | |
| window.requestAnimationFrame = function(callback, element) { | |
| var currTime = new Date().getTime(); | |
| var timeToCall = Math.max(0, 16 - (currTime - lastTime)); | |
| var id = window.setTimeout(function() { | |
| callback(currTime + timeToCall); | |
| }, timeToCall); | |
| lastTime = currTime + timeToCall; | |
| return id; | |
| }; | |
| if (!window.cancelAnimationFrame) | |
| window.cancelAnimationFrame = function(id) { | |
| clearTimeout(id); | |
| }; | |
| })(); | |
| // requestAnim shim layer by Paul Irish | |
| window.requestAnimFrame = (function() { | |
| return ( | |
| window.requestAnimationFrame || | |
| window.webkitRequestAnimationFrame || | |
| window.mozRequestAnimationFrame || | |
| window.oRequestAnimationFrame || | |
| window.msRequestAnimationFrame || | |
| function(/* function */ callback, /* DOMElement */ element) { | |
| window.setTimeout(callback, 1000 / 60); | |
| } | |
| ); | |
| })(); | |
| // Define functions to be used by Scrolleo | |
| var getElemDistanceToTop = function(elem) { | |
| //http://gomakethings.com/get-distances-to-the-top-of-the-document-with-native-javascript/ | |
| var location = 0; | |
| if (elem.offsetParent) { | |
| do { | |
| location += elem.offsetTop; | |
| elem = elem.offsetParent; | |
| } while (elem); | |
| } | |
| return location >= 0 ? location : 0; | |
| }, | |
| getOffsetFromTop = function(distanceToTop) { | |
| var offset = distanceToTop - window.innerHeight + self.additionalOffset; | |
| return offset >= 0 ? offset : 0; | |
| }, | |
| getPixelsPerSecond = function() { | |
| var pixelsPerSecond = (window.innerHeight + self.wrapper[0].clientHeight) / self.secondsPerScreen; | |
| return pixelsPerSecond >= 0 ? pixelsPerSecond : 0; | |
| }, | |
| scrollHandler = function() { | |
| targetScrollPos = window.pageYOffset; | |
| }, | |
| resizeHandler = function() { | |
| //recalculate values on resize | |
| self.distanceToTop = getElemDistanceToTop(elem); | |
| self.offsetFromTop = getOffsetFromTop(self.distanceToTop); | |
| self.pixelsPerSecond = getPixelsPerSecond(); | |
| }, | |
| scrollControl = function() { | |
| //what to do when scrolling | |
| self.scrollPos += (targetScrollPos - self.offsetFromTop - self.scrollPos) * self.acceleration; | |
| self.currentTime = self.scrollPos / self.pixelsPerSecond; //convert scrollPos from pixels to seconds to set self.currentTime | |
| self.wrapper[0].currentTime = self.currentTime; | |
| self.wrapper[0].pause(); | |
| }; | |
| // Get an element's distance from the top of the page | |
| var elem = self.wrapper[0]; | |
| // Calulate the initial size, distance, and offset of each scrolleo video | |
| self.distanceToTop = getElemDistanceToTop(elem); | |
| self.offsetFromTop = getOffsetFromTop(self.distanceToTop); | |
| self.pixelsPerSecond = getPixelsPerSecond(); | |
| self.scrollPos = targetScrollPos - self.offsetFromTop; | |
| wr.pause(); | |
| // Use requestAnimationFrame to ensure the video is updating when the browser is ready | |
| window.requestAnimFrame(function render() { | |
| window.requestAnimFrame(render); | |
| // Only kickoff scrollControl if the scrollPos of element hasn't reached targetScrollPos | |
| if (Math.round(self.scrollPos + self.offsetFromTop) != targetScrollPos) { | |
| scrollControl(); | |
| } | |
| }); | |
| window.addEventListener("scroll", scrollHandler, false); | |
| window.addEventListener("resize", resizeHandler, false); | |
| }); | |
| } | |
| }; | |
| window.Scrolleo = _Scrolleo; | |
| })(window, document); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment