Created
January 8, 2014 02:42
-
-
Save walidvb/8310900 to your computer and use it in GitHub Desktop.
This file contains 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
mod = angular.module('infinite-scroll', []) | |
mod.directive 'infiniteScroll', ['$rootScope', '$window', '$timeout', ($rootScope, $window, $timeout) -> | |
link: (scope, elem, attrs) -> | |
$window = angular.element($window) | |
# from jQuery UI (https://github.com/jquery/jquery-ui/blob/2f497023261a7400295f4dd64c45139232a0ea4f/ui/jquery.ui.core.js#L60) | |
$scrollParent = elem.parents() | |
.filter -> | |
console.log ($.css this, 'overflow') + ($.css this, 'overflow-y') + ($.css this, 'overflow-x') | |
(/(auto|scroll)/).test ($.css this, 'overflow') + ($.css this, 'overflow-y') + ($.css this, 'overflow-x') | |
.eq 0 | |
console.log $scrollParent | |
$scrollParent = $window if $scrollParent.length == 0 | |
# infinite-scroll-direction specifies whether the scroll is vertical or not. | |
scrollDirection = attrs.infiniteScrollDirection or 'vertical' | |
# infinite-scroll-distance specifies how close to the bottom of the page | |
# the window is allowed to be before we trigger a new scroll. The value | |
# provided is multiplied by the window height; for example, to load | |
# more when the bottom of the page is less than 3 window heights away, | |
# specify a value of 3. Defaults to 0. | |
scrollDistance = 0 | |
if attrs.infiniteScrollDistance? | |
scope.$watch attrs.infiniteScrollDistance, (value) -> | |
scrollDistance = parseInt(value, 10) | |
# infinite-scroll-disabled specifies a boolean that will keep the | |
# infnite scroll function from being called; this is useful for | |
# debouncing or throttling the function call. If an infinite | |
# scroll is triggered but this value evaluates to true, then | |
# once it switches back to false the infinite scroll function | |
# will be triggered again. | |
scrollEnabled = true | |
checkWhenEnabled = false | |
if attrs.infiniteScrollDisabled? | |
scope.$watch attrs.infiniteScrollDisabled, (value) -> | |
scrollEnabled = !value | |
if scrollEnabled && checkWhenEnabled | |
checkWhenEnabled = false | |
handler() | |
elementPos = elem.position() | |
# infinite-scroll specifies a function to call when the window | |
# is scrolled within a certain range from the bottom of the | |
# document. It is recommended to use infinite-scroll-disabled | |
# with a boolean that is set to true when the function is | |
# called in order to throttle the function call. | |
handler = -> | |
console.log "scrolling" | |
if scrollDirection is not 'vertical' | |
elementBottom = elementPos.top + elem.height() | |
scrollBottom = $scrollParent.height() + $scrollParent.scrollTop() | |
remaining = elementBottom - scrollBottom | |
shouldScroll = remaining <= $scrollParent.height() * scrollDistance | |
else | |
elementRight = elementPos.left + elem.width() | |
console.log $scrollParent.width() | |
scrollRight = $scrollParent.width() + $scrollParent.scrollTop() | |
remaining = elementRight - scrollRight | |
shouldScroll = remaining <= $scrollParent.width() * scrollDistance | |
if shouldScroll && scrollEnabled | |
if $rootScope.$$phase | |
scope.$eval attrs.infiniteScroll | |
else | |
scope.$apply attrs.infiniteScroll | |
else if shouldScroll | |
checkWhenEnabled = true | |
$scrollParent.on 'scroll', handler | |
scope.$on '$destroy', -> | |
$scrollParent.off 'scroll', handler | |
$timeout (-> | |
if attrs.infiniteScrollImmediateCheck | |
if scope.$eval(attrs.infiniteScrollImmediateCheck) | |
handler() | |
else | |
handler() | |
), 0 | |
] |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment