{"version":3,"sources":["ScrollWatch-2.0.1.min.js"],"names":["root","factory","define","amd","exports","module","ScrollWatch","this","instanceId","instanceData","config","container","window","document","documentElement","watch","watchOnce","inViewClass","ignoreClass","debounce","debounceTriggerLeading","scrollDebounce","resizeDebounce","scrollThrottle","resizeThrottle","watchOffsetXLeft","watchOffsetXRight","watchOffsetYTop","watchOffsetYBottom","infiniteScroll","infiniteOffset","onElementInView","onElementOutOfView","onInfiniteXInView","onInfiniteYInView","initEvent","extend","retObj","i","key","obj","len","arguments","length","hasOwnProperty","throttle","fn","threshhold","scope","last","deferTimer","context","now","Date","args","clearTimeout","setTimeout","apply","func","wait","immediate","timeout","timestamp","result","later","getTime","callNow","saveContainerElement","_id","querySelector","saveElements","elements","Array","prototype","slice","call","querySelectorAll","saveScrollPosition","lastScrollPosition","getScrollPosition","checkViewport","eventType","checkElements","checkInfinite","el","data","responseData","direction","getScrolledDirection","getScrolledAxis","isElementInView","classList","contains","add","splice","remove","axis","viewableRange","scrollSize","callback","isInfiniteScrollPaused","getViewableRange","scrollWidth","scrollHeight","hasScrollPositionChanged","end","addListeners","scrollingElement","getScrollingElement","addEventListener","scrollHandler","resizeHandler","removeListeners","removeEventListener","isContainerWindow","getViewportSize","size","w","clientWidth","h","clientHeight","pos","left","pageXOffset","top","pageYOffset","scrollLeft","scrollTop","range","x","y","scrollPos","viewportSize","start","getElementRange","containerCoords","coords","getBoundingClientRect","right","bottom","width","height","scrollDir","position","curScrollPosition","elRange","isElementInVerticalView","isElementInHorizontalView","mergeOptions","opts","handler","e","type","Object","defineProperty","value","bind","refresh","destroy","updateWatchOffsetXLeft","offset","updateWatchOffsetXRight","updateWatchOffsetYTop","updateWatchOffsetYBottom","pauseInfiniteScroll","resumeInfiniteScroll"],"mappings":"CAAC,SAASA,EAAMC,GACQ,kBAAXC,SAAyBA,OAAOC,IACzCD,UAAWD,GACiB,gBAAZG,SAChBC,OAAOD,QAAUH,IAEjBD,EAAKM,YAAcL,KAErBM,KAAM,WACR,YAGA,IAAIC,GAAa,EAGbC,KAEAC,GAEHC,UAAWC,OAAOC,SAASC,gBAC3BC,MAAO,sBACPC,WAAW,EACXC,YAAa,uBACbC,YAAa,sBACbC,UAAU,EACVC,wBAAwB,EACxBC,eAAgB,IAChBC,eAAgB,IAChBC,eAAgB,IAChBC,eAAgB,IAChBC,iBAAkB,EAClBC,kBAAmB,EACnBC,gBAAiB,EACjBC,mBAAoB,EACpBC,gBAAgB,EAChBC,eAAgB,EAChBC,gBAAiB,aACjBC,mBAAoB,aACpBC,kBAAmB,aACnBC,kBAAmB,cAGhBC,EAAY,kBAEZC,EAAS,SAASC,GAErB,GACIC,GACAC,EACAC,EAHAC,EAAMC,UAAUC,MAOpB,KAFAN,EAASA,MAEJC,EAAI,EAAOG,EAAJH,EAASA,IAIpB,GAFAE,EAAME,UAAUJ,GAQhB,IAAKC,IAAOC,GAEPA,EAAII,eAAeL,KAEtBF,EAAOE,GAAOC,EAAID,GAOrB,OAAOF,IAIJQ,EAAW,SAAUC,EAAIC,EAAYC,GAExC,GAAIC,GACAC,CAIJ,OAFAH,GAAaA,GAAc,IAEpB,WAEN,GAAII,GAAUH,GAASzC,KACnB6C,GAAO,GAAIC,MACXC,EAAOZ,SAEPO,IAAcA,EAAOF,EAAbK,GAEXxC,OAAO2C,aAAaL,GAEpBA,EAAaM,WAAW,WAEvBP,EAAOG,EAEPN,EAAGW,MAAMN,EAASG,IAEhBP,KAIHE,EAAOG,EAEPN,EAAGW,MAAMN,EAASG,MASjBnC,EAAW,SAASuC,EAAMC,EAAMC,GAEnC,GAAIC,GACAP,EACAH,EACAW,EACAC,EAEAC,EAAQ,WAEX,GAAIf,IAAO,GAAII,OAAOY,UAAYH,CAEvBH,GAAPV,GAAeA,GAAQ,EAE1BY,EAAUL,WAAWQ,EAAOL,EAAOV,IAInCY,EAAU,KAELD,IAEJG,EAASL,EAAKD,MAAMN,EAASG,GAExBO,IAEJV,EAAUG,EAAO,QAUrB,OAAO,YAEN,GAAIY,GAAUN,IAAcC,CAmB5B,OAjBAV,GAAU5C,KACV+C,EAAOZ,UACPoB,GAAY,GAAIT,OAAOY,UAElBJ,IAEJA,EAAUL,WAAWQ,EAAOL,IAIzBO,IAEHH,EAASL,EAAKD,MAAMN,EAASG,GAC7BH,EAAUG,EAAO,MAIXS,IAOLI,EAAuB,WAE1B,GAAIzD,GAASD,EAAaF,KAAK6D,KAAK1D,MAEJ,iBAArBA,GAAOC,YAGjBD,EAAOC,UAAYE,SAASwD,cAAc3D,EAAOC,aAO/C2D,EAAe,WAElB7D,EAAaF,KAAK6D,KAAKG,SAAWC,MAAMC,UAAUC,MAAMC,KAAK9D,SAAS+D,iBAAiBnE,EAAaF,KAAK6D,KAAK1D,OAAOK,MAAQ,SAAWN,EAAaF,KAAK6D,KAAK1D,OAAOQ,YAAc,OAKjL2D,EAAqB,WAExBpE,EAAaF,KAAK6D,KAAKU,mBAAqBC,EAAkBJ,KAAKpE,OAIhEyE,EAAgB,SAASC,GAE5BC,EAAcP,KAAKpE,KAAM0E,GACzBE,EAAcR,KAAKpE,KAAM0E,GAGrBA,IAAc9C,GAEjB0C,EAAmBF,KAAKpE,OAOtB2E,EAAgB,SAASD,GAE5B,GAOIG,GACA9C,EARA+C,EAAO5E,EAAaF,KAAK6D,KACzB3B,EAAM4C,EAAKd,SAAS5B,OACpBjC,EAAS2E,EAAK3E,OACdO,EAAcP,EAAOO,YACrBqE,GACHL,UAAWA,EAKZ,KAAK3C,EAAI,EAAOG,EAAJH,EAASA,IAEpB8C,EAAKC,EAAKd,SAASjC,GAGnBgD,EAAaF,GAAKA,EAEA,WAAdH,IAEHK,EAAaC,UAAYC,EAAqBb,KAAKpE,KAAMkF,EAAgBd,KAAKpE,QAI3EmF,EAAgBf,KAAKpE,KAAM6E,GAEzBA,EAAGO,UAAUC,SAAS3E,KAI1BmE,EAAGO,UAAUE,IAAI5E,GACjBP,EAAOqB,gBAAgB4C,KAAKpE,KAAM+E,GAE9B5E,EAAOM,YAIVqE,EAAKd,SAASuB,OAAOxD,EAAG,GACxBG,IACAH,IAIA8C,EAAGO,UAAUE,IAAInF,EAAOQ,gBAQtBkE,EAAGO,UAAUC,SAAS3E,IAAgBgE,IAAc9C,KAIvDiD,EAAGO,UAAUI,OAAO9E,GACpBP,EAAOsB,mBAAmB2C,KAAKpE,KAAM+E,KAWrCH,EAAgB,SAASF,GAE5B,GAEI3C,GACA0D,EACArF,EACAsF,EACAC,EACAC,EACAb,EARAD,EAAO5E,EAAaF,KAAK6D,KACzB1D,EAAS2E,EAAK3E,MASlB,IAAIA,EAAOmB,iBAAmBwD,EAAKe,uBASlC,IAPAJ,GAAQ,IAAK,KACbG,GAAY,oBAAqB,qBACjCxF,EAAYD,EAAOC,UACnBsF,EAAgBI,EAAiB1B,KAAKpE,MACtC2F,GAAcvF,EAAU2F,YAAa3F,EAAU4F,cAC/CjB,KAEKhD,EAAI,EAAO,EAAJA,EAAOA,KAIC,WAAd2C,GAA0BuB,EAAyB7B,KAAKpE,KAAMyF,EAAK1D,KAAqB,WAAd2C,GAAuC,YAAdA,GAA2BA,IAAc9C,IAAc8D,EAAcD,EAAK1D,IAAImE,IAAM/F,EAAOoB,gBAAkBoE,EAAW5D,KAI/NgD,EAAaL,UAAYA,EAEP,WAAdA,IAEHK,EAAaC,UAAYC,EAAqBb,KAAKpE,KAAMyF,EAAK1D,KAI/D5B,EAAOyF,EAAS7D,IAAIqC,KAAKpE,KAAM+E,KAW/BoB,EAAe,WAElB,GAAIrB,GAAO5E,EAAaF,KAAK6D,KACzBuC,EAAmBC,EAAoBjC,KAAKpE,KAEhDoG,GAAiBE,iBAAiB,SAAUxB,EAAKyB,eAAe,GAChEH,EAAiBE,iBAAiB,SAAUxB,EAAK0B,eAAe,IAI7DC,EAAkB,WAErB,GAAI3B,GAAO5E,EAAaF,KAAK6D,KACzBuC,EAAmBC,EAAoBjC,KAAKpE,KAEhDoG,GAAiBM,oBAAoB,SAAU5B,EAAKyB,eACpDH,EAAiBM,oBAAoB,SAAU5B,EAAK0B,gBAIjDH,EAAsB,WAEzB,MAAOM,GAAkBvC,KAAKpE,MAAQK,OAASH,EAAaF,KAAK6D,KAAK1D,OAAOC,WAK1EwG,EAAkB,WAErB,GAAIC,IACHC,EAAG5G,EAAaF,KAAK6D,KAAK1D,OAAOC,UAAU2G,YAC3CC,EAAG9G,EAAaF,KAAK6D,KAAK1D,OAAOC,UAAU6G,aAG5C,OAAOJ,IAKJrC,EAAoB,WAEvB,GACIpE,GADA8G,IAkBJ,OAfIP,GAAkBvC,KAAKpE,OAE1BkH,EAAIC,KAAO9G,OAAO+G,YAClBF,EAAIG,IAAMhH,OAAOiH,cAKjBlH,EAAYF,EAAaF,KAAK6D,KAAK1D,OAAOC,UAE1C8G,EAAIC,KAAO/G,EAAUmH,WACrBL,EAAIG,IAAMjH,EAAUoH,WAIdN,GAKJpB,EAAmB,WAEtB,GAAI2B,IACHC,KACAC,MAEGC,EAAYpD,EAAkBJ,KAAKpE,MACnC6H,EAAejB,EAAgBxC,KAAKpE,KAUxC,OARAyH,GAAMC,EAAEI,MAAQF,EAAUT,KAC1BM,EAAMC,EAAExB,IAAOuB,EAAMC,EAAEI,MAAQD,EAAaf,EAC5CW,EAAMC,EAAEb,KAAOY,EAAMC,EAAExB,IAAMuB,EAAMC,EAAEI,MAErCL,EAAME,EAAEG,MAAQF,EAAUP,IAC1BI,EAAME,EAAEzB,IAAMuB,EAAME,EAAEG,MAAQD,EAAab,EAC3CS,EAAME,EAAEd,KAAOY,EAAME,EAAEzB,IAAMuB,EAAME,EAAEG,MAE9BL,GAKJM,EAAkB,SAASlD,GAE9B,GAMImD,GANAP,GACHC,KACAC,MAEGjC,EAAgBI,EAAiB1B,KAAKpE,MACtCiI,EAASpD,EAAGqD,uBA2BhB,OAxBIvB,GAAkBvC,KAAKpE,OAE1ByH,EAAMC,EAAEI,MAAQG,EAAOd,KAAOzB,EAAcgC,EAAEI,MAC9CL,EAAMC,EAAExB,IAAM+B,EAAOE,MAAQzC,EAAcgC,EAAEI,MAG7CL,EAAME,EAAEG,MAAQG,EAAOZ,IAAM3B,EAAciC,EAAEG,MAC7CL,EAAME,EAAEzB,IAAM+B,EAAOG,OAAS1C,EAAciC,EAAEG,QAI9CE,EAAkB9H,EAAaF,KAAK6D,KAAK1D,OAAOC,UAAU8H,wBAE1DT,EAAMC,EAAEI,MAASG,EAAOd,KAAOa,EAAgBb,KAAQzB,EAAcgC,EAAEI,MACvEL,EAAMC,EAAExB,IAAMuB,EAAMC,EAAEI,MAAQG,EAAOI,MAErCZ,EAAME,EAAEG,MAASG,EAAOZ,IAAMW,EAAgBX,IAAO3B,EAAciC,EAAEG,MACrEL,EAAME,EAAEzB,IAAMuB,EAAME,EAAEG,MAAQG,EAAOK,QAItCb,EAAMC,EAAEb,KAAOY,EAAMC,EAAExB,IAAMuB,EAAMC,EAAEI,MACrCL,EAAME,EAAEd,KAAOY,EAAME,EAAEzB,IAAMuB,EAAME,EAAEG,MAE9BL,GAKJvC,EAAkB,WAErB,MAAIe,GAAyB7B,KAAKpE,KAAM,KAEhC,IAIJiG,EAAyB7B,KAAKpE,KAAM,KAEhC,IAFR,QAQGiF,EAAuB,SAASQ,GAEnC,GAAI8C,IAAab,GAAI,QAAS,QAASC,GAAI,OAAQ,OAC/Ca,GAAYd,EAAG,OAAQC,EAAG,OAC1BpD,EAAqBrE,EAAaF,KAAK6D,KAAKU,mBAC5CkE,EAAoBjE,EAAkBJ,KAAKpE,KAE/C,OAAOyI,GAAkBD,EAAS/C,IAASlB,EAAmBiE,EAAS/C,IAAS8C,EAAU9C,GAAM,GAAK8C,EAAU9C,GAAM,IAIlHQ,EAA2B,SAASR,GAEvC,GAAI+C,IAAYd,EAAG,OAAQC,EAAG,OAC1BpD,EAAqBrE,EAAaF,KAAK6D,KAAKU,mBAC5CkE,EAAoBjE,EAAkBJ,KAAKpE,KAE/C,OAAOyI,GAAkBD,EAAS/C,MAAWlB,EAAmBiE,EAAS/C,KAItEN,EAAkB,SAASN,GAE9B,GAAIa,GAAgBI,EAAiB1B,KAAKpE,MACtC0I,EAAUX,EAAgB3D,KAAKpE,KAAM6E,EAEzC,OAAO8D,GAAwBvE,KAAKpE,KAAM0I,EAAShD,IAAkBkD,EAA0BxE,KAAKpE,KAAM0I,EAAShD,IAIhHiD,EAA0B,SAASD,EAAShD,GAE/C,GAAIvF,GAASD,EAAaF,KAAK6D,KAAK1D,MAEpC,OAAOuI,GAAQf,EAAEG,MAAQpC,EAAciC,EAAEzB,IAAM/F,EAAOkB,oBAAsBqH,EAAQf,EAAEzB,IAAMR,EAAciC,EAAEG,MAAQ3H,EAAOiB,iBAIxHwH,EAA4B,SAASF,EAAShD,GAEjD,GAAIvF,GAASD,EAAaF,KAAK6D,KAAK1D,MAEpC,OAAOuI,GAAQhB,EAAEI,MAAQpC,EAAcgC,EAAExB,IAAM/F,EAAOgB,mBAAqBuH,EAAQhB,EAAExB,IAAMR,EAAcgC,EAAEI,MAAQ3H,EAAOe,kBAIvHyF,EAAoB,WAEvB,MAAOzG,GAAaF,KAAK6D,KAAK1D,OAAOC,YAAcC,OAAOC,SAASC,iBAIhEsI,EAAe,SAASC,GAE3BjH,EAAO3B,EAAaF,KAAK6D,KAAK1D,OAAQA,EAAQ2I,IAI3CC,EAAU,SAASC,GAEtB,GAAItE,GAAYsE,EAAEC,IAGb/I,GAAaF,KAAK6D,OAOL,WAAda,GAA0BuB,EAAyB7B,KAAKpE,KAAM,MAAQiG,EAAyB7B,KAAKpE,KAAM,OAE7GyE,EAAcL,KAAKpE,KAAM0E,IAMvB3E,EAAc,SAAS+I,GAE1B,GAAIhE,EAGJ,OAAI9E,gBAAgBD,IAEnBmJ,OAAOC,eAAenJ,KAAM,OAAQoJ,MAAOnJ,MAI3C6E,EAAO5E,EAAaF,KAAK6D,MAExB1D,UAEA6D,YACAO,oBAAqB8C,IAAK,EAAGF,KAAM,GACnCtB,wBAAwB,GAIzBgD,EAAazE,KAAKpE,KAAM8I,GAGpBhE,EAAK3E,OAAOS,UAEfkE,EAAKyB,cAAgB3F,EAASmI,EAAQM,KAAKrJ,MAAO8E,EAAK3E,OAAOW,eAAgBgE,EAAK3E,OAAOU,wBAC1FiE,EAAK0B,cAAgB5F,EAASmI,EAAQM,KAAKrJ,MAAO8E,EAAK3E,OAAOY,eAAgB+D,EAAK3E,OAAOU,0BAI1FiE,EAAKyB,cAAgBjE,EAASyG,EAAQM,KAAKrJ,MAAO8E,EAAK3E,OAAOa,eAAgBhB,MAC9E8E,EAAK0B,cAAgBlE,EAASyG,EAAQM,KAAKrJ,MAAO8E,EAAK3E,OAAOc,eAAgBjB,OAI/E4D,EAAqBQ,KAAKpE,MAC1BmG,EAAa/B,KAAKpE,MAClB+D,EAAaK,KAAKpE,MAClByE,EAAcL,KAAKpE,KAAM4B,GAhCzBsH,QAoCO,GAAInJ,GAAY+I,GA6DzB,OAvDA/I,GAAYmE,WAGXoF,QAAS,WAERvF,EAAaK,KAAKpE,MAClByE,EAAcL,KAAKpE,KAAM,YAI1BuJ,QAAS,WAER9C,EAAgBrC,KAAKpE,YACdE,GAAaF,KAAK6D,MAI1B2F,uBAAwB,SAASC,GAEhCvJ,EAAaF,KAAK6D,KAAK1D,OAAOe,iBAAmBuI,GAIlDC,wBAAyB,SAASD,GAEjCvJ,EAAaF,KAAK6D,KAAK1D,OAAOgB,kBAAoBsI,GAInDE,sBAAuB,SAASF,GAE/BvJ,EAAaF,KAAK6D,KAAK1D,OAAOiB,gBAAkBqI,GAIjDG,yBAA0B,SAASH,GAElCvJ,EAAaF,KAAK6D,KAAK1D,OAAOkB,mBAAqBoI,GAIpDI,oBAAqB,WAEpB3J,EAAaF,KAAK6D,KAAKgC,wBAAyB,GAIjDiE,qBAAsB,WAErB5J,EAAaF,KAAK6D,KAAKgC,wBAAyB,IAM3C9F","file":"ScrollWatch-2.0.1.min.js","sourcesContent":["(function(root, factory) {\n if (typeof define === 'function' && define.amd) {\n define([], factory);\n } else if (typeof exports === 'object') {\n module.exports = factory();\n } else {\n root.ScrollWatch = factory();\n }\n}(this, function() {\n'use strict';\n\n// Give each instance on the page a unique ID\nvar instanceId = 0;\n\n// Store instance data privately so it can't be accessed/modified\nvar instanceData = {};\n\nvar config = {\n\t// The default container is window, but we need the actual documentElement to determine positioning.\n\tcontainer: window.document.documentElement,\n\twatch: '[data-scroll-watch]',\n\twatchOnce: true,\n\tinViewClass: 'scroll-watch-in-view',\n\tignoreClass: 'scroll-watch-ignore',\n\tdebounce: false,\n\tdebounceTriggerLeading: false,\n\tscrollDebounce: 250,\n\tresizeDebounce: 250,\n\tscrollThrottle: 250,\n\tresizeThrottle: 250,\n\twatchOffsetXLeft: 0,\n\twatchOffsetXRight: 0,\n\twatchOffsetYTop: 0,\n\twatchOffsetYBottom: 0,\n\tinfiniteScroll: false,\n\tinfiniteOffset: 0,\n\tonElementInView: function(){},\n\tonElementOutOfView: function(){},\n\tonInfiniteXInView: function(){},\n\tonInfiniteYInView: function(){}\n};\n\nvar initEvent = 'scrollwatchinit';\n\nvar extend = function(retObj) {\n\n\tvar len = arguments.length;\n\tvar i;\n\tvar key;\n\tvar obj;\n\n\tretObj = retObj || {};\n\n\tfor (i = 1; i < len; i++) {\n\n\t\tobj = arguments[i];\n\n\t\tif (!obj) {\n\n\t\t\tcontinue;\n\n\t\t}\n\n\t\tfor (key in obj) {\n\n\t\t\tif (obj.hasOwnProperty(key)) {\n\n\t\t\t\tretObj[key] = obj[key];\n\n\t\t\t}\n\n\t\t}\n\t}\n\n\treturn retObj;\n\n};\n\nvar throttle = function (fn, threshhold, scope) {\n\n\tvar last;\n\tvar deferTimer;\n\n\tthreshhold = threshhold || 250;\n\n\treturn function () {\n\n\t\tvar context = scope || this;\n\t\tvar now = +new Date();\n\t\tvar args = arguments;\n\n\t\tif (last && now < last + threshhold) {\n\n\t\t\twindow.clearTimeout(deferTimer);\n\n\t\t\tdeferTimer = setTimeout(function () {\n\n\t\t\t\tlast = now;\n\n\t\t\t\tfn.apply(context, args);\n\n\t\t\t}, threshhold);\n\n\t\t} else {\n\n\t\t\tlast = now;\n\n\t\t\tfn.apply(context, args);\n\n\t\t}\n\n\t};\n\n};\n\n// http://underscorejs.org/#debounce\nvar debounce = function(func, wait, immediate) {\n\n\tvar timeout;\n\tvar args;\n\tvar context;\n\tvar timestamp;\n\tvar result;\n\n\tvar later = function() {\n\n\t\tvar last = new Date().getTime() - timestamp;\n\n\t\tif (last < wait && last >= 0) {\n\n\t\t\ttimeout = setTimeout(later, wait - last);\n\n\t\t} else {\n\n\t\t\ttimeout = null;\n\n\t\t\tif (!immediate) {\n\n\t\t\t\tresult = func.apply(context, args);\n\n\t\t\t\tif (!timeout) {\n\n\t\t\t\t\tcontext = args = null;\n\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t}\n\n\t};\n\n\treturn function() {\n\n\t\tvar callNow = immediate && !timeout;\n\n\t\tcontext = this;\n\t\targs = arguments;\n\t\ttimestamp = new Date().getTime();\n\n\t\tif (!timeout) {\n\n\t\t\ttimeout = setTimeout(later, wait);\n\n\t\t}\n\n\t\tif (callNow) {\n\n\t\t\tresult = func.apply(context, args);\n\t\t\tcontext = args = null;\n\n\t\t}\n\n\t\treturn result;\n\n\t};\n\n};\n\n// If a string was passed in as the container element, use it as a selector and query the DOM, otherwise we'll assume a DOM node was passed in\nvar saveContainerElement = function() {\n\n\tvar config = instanceData[this._id].config;\n\n\tif (typeof config.container === 'string') {\n\n\t\t// A selector was passed in for the container\n\t\tconfig.container = document.querySelector(config.container);\n\n\t}\n\n};\n\n// Save all elements to watch into an array\nvar saveElements = function() {\n\n\tinstanceData[this._id].elements = Array.prototype.slice.call(document.querySelectorAll(instanceData[this._id].config.watch + ':not(.' + instanceData[this._id].config.ignoreClass + ')'));\n\n};\n\n// Save the scroll position of the scrolling container so we can perform comparison checks\nvar saveScrollPosition = function() {\n\n\tinstanceData[this._id].lastScrollPosition = getScrollPosition.call(this);\n\n};\n\nvar checkViewport = function(eventType) {\n\n\tcheckElements.call(this, eventType);\n\tcheckInfinite.call(this, eventType);\n\n\t// Chrome does not return 0,0 for scroll position when reloading a page that was previously scrolled. To combat this, we will leave the scroll position at the default 0,0 when a page is first loaded.\n\tif (eventType !== initEvent) {\n\n\t\tsaveScrollPosition.call(this);\n\n\t}\n\n};\n\n// Determine if the watched elements are viewable within the scrolling container\nvar checkElements = function(eventType) {\n\n\tvar data = instanceData[this._id];\n\tvar len = data.elements.length;\n\tvar config = data.config;\n\tvar inViewClass = config.inViewClass;\n\tvar responseData = {\n\t\teventType: eventType\n\t};\n\tvar el;\n\tvar i;\n\n\tfor (i = 0; i < len; i++) {\n\n\t\tel = data.elements[i];\n\n\t\t// Prepare the data to pass to the callback\n\t\tresponseData.el = el;\n\n\t\tif (eventType === 'scroll') {\n\n\t\t\tresponseData.direction = getScrolledDirection.call(this, getScrolledAxis.call(this));\n\n\t\t}\n\n\t\tif (isElementInView.call(this, el)) {\n\n\t\t\tif (!el.classList.contains(inViewClass)) {\n\n\t\t\t\t// Add a class hook and fire a callback for every element that just came into view\n\n\t\t\t\tel.classList.add(inViewClass);\n\t\t\t\tconfig.onElementInView.call(this, responseData);\n\n\t\t\t\tif (config.watchOnce) {\n\n\t\t\t\t\t// Remove this element so we don't check it again next time\n\n\t\t\t\t\tdata.elements.splice(i, 1);\n\t\t\t\t\tlen--;\n\t\t\t\t\ti--;\n\n\t\t\t\t\t// Flag this element with the ignore class so we don't store it again if a refresh happens\n\n\t\t\t\t\tel.classList.add(config.ignoreClass);\n\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t} else {\n\n\t\t\tif (el.classList.contains(inViewClass) || eventType === initEvent) {\n\n\t\t\t\t// Remove the class hook and fire a callback for every element that just went out of view\n\n\t\t\t\tel.classList.remove(inViewClass);\n\t\t\t\tconfig.onElementOutOfView.call(this, responseData);\n\n\t\t\t}\n\n\t\t}\n\n\t}\n\n};\n\n// Determine if the infinite scroll zone is in view. This could come into view by scrolling or resizing. Initial load must also be accounted for.\nvar checkInfinite = function(eventType) {\n\n\tvar data = instanceData[this._id];\n\tvar config = data.config;\n\tvar i;\n\tvar axis;\n\tvar container;\n\tvar viewableRange;\n\tvar scrollSize;\n\tvar callback;\n\tvar responseData;\n\n\tif (config.infiniteScroll && !data.isInfiniteScrollPaused) {\n\n\t\taxis = ['x', 'y'];\n\t\tcallback = ['onInfiniteXInView', 'onInfiniteYInView'];\n\t\tcontainer = config.container;\n\t\tviewableRange = getViewableRange.call(this);\n\t\tscrollSize = [container.scrollWidth, container.scrollHeight];\n\t\tresponseData = {};\n\n\t\tfor (i = 0; i < 2; i++) {\n\n\t\t\t// If a scroll event triggered this check, verify the scroll position actually changed for each axis. This stops horizontal scrolls from triggering infiniteY callbacks and vice versa. In other words, only trigger an infinite callback if that axis was actually scrolled.\n\n\t\t\tif ((eventType === 'scroll' && hasScrollPositionChanged.call(this, axis[i]) || eventType === 'resize'|| eventType === 'refresh' || eventType === initEvent) && viewableRange[axis[i]].end + config.infiniteOffset >= scrollSize[i]) {\n\n\t\t\t\t// We've scrolled/resized all the way to the right/bottom\n\n\t\t\t\tresponseData.eventType = eventType;\n\n\t\t\t\tif (eventType === 'scroll') {\n\n\t\t\t\t\tresponseData.direction = getScrolledDirection.call(this, axis[i]);\n\n\t\t\t\t}\n\n\t\t\t\tconfig[callback[i]].call(this, responseData);\n\n\t\t\t}\n\n\t\t}\n\n\t}\n\n};\n\n// Add listeners to the scrolling container for each instance\nvar addListeners = function() {\n\n\tvar data = instanceData[this._id];\n\tvar scrollingElement = getScrollingElement.call(this);\n\n\tscrollingElement.addEventListener('scroll', data.scrollHandler, false);\n\tscrollingElement.addEventListener('resize', data.resizeHandler, false);\n\n};\n\nvar removeListeners = function() {\n\n\tvar data = instanceData[this._id];\n\tvar scrollingElement = getScrollingElement.call(this);\n\n\tscrollingElement.removeEventListener('scroll', data.scrollHandler);\n\tscrollingElement.removeEventListener('resize', data.resizeHandler);\n\n};\n\nvar getScrollingElement = function() {\n\n\treturn isContainerWindow.call(this) ? window : instanceData[this._id].config.container;\n\n};\n\n// Get the width and height of viewport/scrolling container\nvar getViewportSize = function() {\n\n\tvar size = {\n\t\tw: instanceData[this._id].config.container.clientWidth,\n\t\th: instanceData[this._id].config.container.clientHeight\n\t};\n\n\treturn size;\n\n};\n\n// Get the scrollbar position of the scrolling container\nvar getScrollPosition = function() {\n\n\tvar pos = {};\n\tvar container;\n\n\tif (isContainerWindow.call(this)) {\n\n\t\tpos.left = window.pageXOffset;\n\t\tpos.top = window.pageYOffset;\n\n\n\t} else {\n\n\t\tcontainer = instanceData[this._id].config.container;\n\n\t\tpos.left = container.scrollLeft;\n\t\tpos.top = container.scrollTop;\n\n\t}\n\n\treturn pos;\n\n};\n\n// Get the pixel range currently viewable within the scrolling container\nvar getViewableRange = function() {\n\n\tvar range = {\n\t\tx: {},\n\t\ty: {}\n\t};\n\tvar scrollPos = getScrollPosition.call(this);\n\tvar viewportSize = getViewportSize.call(this);\n\n\trange.x.start = scrollPos.left;\n\trange.x.end = range.x.start + viewportSize.w;\n\trange.x.size = range.x.end - range.x.start;\n\n\trange.y.start = scrollPos.top;\n\trange.y.end = range.y.start + viewportSize.h;\n\trange.y.size = range.y.end - range.y.start;\n\n\treturn range;\n\n};\n\n// Get the pixel range of where this element falls within the scrolling container\nvar getElementRange = function(el) {\n\n\tvar range = {\n\t\tx: {},\n\t\ty: {}\n\t};\n\tvar viewableRange = getViewableRange.call(this);\n\tvar coords = el.getBoundingClientRect();\n\tvar containerCoords;\n\n\tif (isContainerWindow.call(this)) {\n\n\t\trange.x.start = coords.left + viewableRange.x.start;\n\t\trange.x.end = coords.right + viewableRange.x.start;\n\n\n\t\trange.y.start = coords.top + viewableRange.y.start;\n\t\trange.y.end = coords.bottom + viewableRange.y.start;\n\n\t} else {\n\n\t\tcontainerCoords = instanceData[this._id].config.container.getBoundingClientRect();\n\n\t\trange.x.start = (coords.left - containerCoords.left) + viewableRange.x.start;\n\t\trange.x.end = range.x.start + coords.width;\n\n\t\trange.y.start = (coords.top - containerCoords.top) + viewableRange.y.start;\n\t\trange.y.end = range.y.start + coords.height;\n\n\t}\n\n\trange.x.size = range.x.end - range.x.start;\n\trange.y.size = range.y.end - range.y.start;\n\n\treturn range;\n\n};\n\n// Determines which axis was just scrolled (x/horizontal or y/vertical)\nvar getScrolledAxis = function() {\n\n\tif (hasScrollPositionChanged.call(this, 'x')) {\n\n\t\treturn 'x';\n\n\t}\n\n\tif (hasScrollPositionChanged.call(this, 'y')) {\n\n\t\treturn 'y';\n\n\t}\n\n};\n\nvar getScrolledDirection = function(axis) {\n\n\tvar scrollDir = {x: ['right', 'left'], y: ['down', 'up']};\n\tvar position = {x: 'left', y: 'top'};\n\tvar lastScrollPosition = instanceData[this._id].lastScrollPosition;\n\tvar curScrollPosition = getScrollPosition.call(this);\n\n\treturn curScrollPosition[position[axis]] > lastScrollPosition[position[axis]] ? scrollDir[axis][0] : scrollDir[axis][1];\n\n};\n\nvar hasScrollPositionChanged = function(axis) {\n\n\tvar position = {x: 'left', y: 'top'};\n\tvar lastScrollPosition = instanceData[this._id].lastScrollPosition;\n\tvar curScrollPosition = getScrollPosition.call(this);\n\n\treturn curScrollPosition[position[axis]] !== lastScrollPosition[position[axis]];\n\n};\n\nvar isElementInView = function(el) {\n\n\tvar viewableRange = getViewableRange.call(this);\n\tvar elRange = getElementRange.call(this, el);\n\n\treturn isElementInVerticalView.call(this, elRange, viewableRange) && isElementInHorizontalView.call(this, elRange, viewableRange);\n\n};\n\nvar isElementInVerticalView = function(elRange, viewableRange) {\n\n\tvar config = instanceData[this._id].config;\n\n\treturn elRange.y.start < viewableRange.y.end + config.watchOffsetYBottom && elRange.y.end > viewableRange.y.start - config.watchOffsetYTop;\n\n};\n\nvar isElementInHorizontalView = function(elRange, viewableRange) {\n\n\tvar config = instanceData[this._id].config;\n\n\treturn elRange.x.start < viewableRange.x.end + config.watchOffsetXRight && elRange.x.end > viewableRange.x.start - config.watchOffsetXLeft;\n\n};\n\nvar isContainerWindow = function() {\n\n\treturn instanceData[this._id].config.container === window.document.documentElement;\n\n};\n\nvar mergeOptions = function(opts) {\n\n\textend(instanceData[this._id].config, config, opts);\n\n};\n\nvar handler = function(e) {\n\n\tvar eventType = e.type;\n\n\t// Protect against the instance being destroyed while we still have queued or pending handler events (via @jsonk000)\n\tif (!instanceData[this._id]) {\n\n\t\treturn;\n\n\t}\n\n\t// For scroll events, only check the viewport if something has changed. Fixes issues when using gestures on a page that doesn't need to scroll. An event would still fire, but the position didn't change because the window/container \"bounced\" back into place.\n\tif (eventType === 'resize' || hasScrollPositionChanged.call(this, 'x') || hasScrollPositionChanged.call(this, 'y')) {\n\n\t\tcheckViewport.call(this, eventType);\n\n\t}\n\n};\n\nvar ScrollWatch = function(opts) {\n\n\tvar data;\n\n\t// Protect against missing new keyword\n\tif (this instanceof ScrollWatch) {\n\n\t\tObject.defineProperty(this, '_id', {value: instanceId++});\n\n\t\t// Keep all instance data private, except for the '_id', which will be the key to get the private data for a specific instance\n\n\t\tdata = instanceData[this._id] = {\n\n\t\t\tconfig: {},\n\t\t\t// The elements to watch for this instance\n\t\t\telements: [],\n\t\t\tlastScrollPosition: {top: 0, left: 0},\n\t\t\tisInfiniteScrollPaused: false\n\n\t\t};\n\n\t\tmergeOptions.call(this, opts);\n\n\t\t// In order to remove listeners later and keep a correct reference to 'this', give each instance it's own event handler\n\t\tif (data.config.debounce) {\n\n\t\t\tdata.scrollHandler = debounce(handler.bind(this), data.config.scrollDebounce, data.config.debounceTriggerLeading);\n\t\t\tdata.resizeHandler = debounce(handler.bind(this), data.config.resizeDebounce, data.config.debounceTriggerLeading);\n\n\t\t} else {\n\n\t\t\tdata.scrollHandler = throttle(handler.bind(this), data.config.scrollThrottle, this);\n\t\t\tdata.resizeHandler = throttle(handler.bind(this), data.config.resizeThrottle, this);\n\n\t\t}\n\n\t\tsaveContainerElement.call(this);\n\t\taddListeners.call(this);\n\t\tsaveElements.call(this);\n\t\tcheckViewport.call(this, initEvent);\n\n\t} else {\n\n\t\treturn new ScrollWatch(opts);\n\n\t}\n\n};\n\nScrollWatch.prototype = {\n\n\t// Should be manually called by user after loading in new content\n\trefresh: function() {\n\n\t\tsaveElements.call(this);\n\t\tcheckViewport.call(this, 'refresh');\n\n\t},\n\n\tdestroy: function() {\n\n\t\tremoveListeners.call(this);\n\t\tdelete instanceData[this._id];\n\n\t},\n\n\tupdateWatchOffsetXLeft: function(offset) {\n\n\t\tinstanceData[this._id].config.watchOffsetXLeft = offset;\n\n\t},\n\n\tupdateWatchOffsetXRight: function(offset) {\n\n\t\tinstanceData[this._id].config.watchOffsetXRight = offset;\n\n\t},\n\n\tupdateWatchOffsetYTop: function(offset) {\n\n\t\tinstanceData[this._id].config.watchOffsetYTop = offset;\n\n\t},\n\n\tupdateWatchOffsetYBottom: function(offset) {\n\n\t\tinstanceData[this._id].config.watchOffsetYBottom = offset;\n\n\t},\n\n\tpauseInfiniteScroll: function() {\n\n\t\tinstanceData[this._id].isInfiniteScrollPaused = true;\n\n\t},\n\n\tresumeInfiniteScroll: function() {\n\n\t\tinstanceData[this._id].isInfiniteScrollPaused = false;\n\n\t}\n\n};\n\nreturn ScrollWatch;\n}));\n"],"sourceRoot":"/source/"}