Skip to content

Commit ecb3bae

Browse files
updated iscroll
1 parent 8aa8799 commit ecb3bae

File tree

1 file changed

+149
-39
lines changed

1 file changed

+149
-39
lines changed

js/iscroll.js

Lines changed: 149 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/*! iScroll v5.1.3 ~ (c) 2008-2014 Matteo Spinelli ~ http://cubiq.org/license */
1+
/*! iScroll v5.2.0 ~ (c) 2008-2016 Matteo Spinelli ~ http://cubiq.org/license */
22
(function (window, document, Math) {
33
var rAF = window.requestAnimationFrame ||
44
window.webkitRequestAnimationFrame ||
@@ -48,8 +48,8 @@ var utils = (function () {
4848
};
4949

5050
me.prefixPointerEvent = function (pointerEvent) {
51-
return window.MSPointerEvent ?
52-
'MSPointer' + pointerEvent.charAt(9).toUpperCase() + pointerEvent.substr(10):
51+
return window.MSPointerEvent ?
52+
'MSPointer' + pointerEvent.charAt(7).toUpperCase() + pointerEvent.substr(8):
5353
pointerEvent;
5454
};
5555

@@ -86,12 +86,38 @@ var utils = (function () {
8686
hasTransform: _transform !== false,
8787
hasPerspective: _prefixStyle('perspective') in _elementStyle,
8888
hasTouch: 'ontouchstart' in window,
89-
hasPointer: window.PointerEvent || window.MSPointerEvent, // IE10 is prefixed
89+
hasPointer: !!(window.PointerEvent || window.MSPointerEvent), // IE10 is prefixed
9090
hasTransition: _prefixStyle('transition') in _elementStyle
9191
});
9292

93-
// This should find all Android browsers lower than build 535.19 (both stock browser and webview)
94-
me.isBadAndroid = /Android /.test(window.navigator.appVersion) && !(/Chrome\/\d/.test(window.navigator.appVersion));
93+
/*
94+
This should find all Android browsers lower than build 535.19 (both stock browser and webview)
95+
- galaxy S2 is ok
96+
- 2.3.6 : `AppleWebKit/533.1 (KHTML, like Gecko) Version/4.0 Mobile Safari/533.1`
97+
- 4.0.4 : `AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30`
98+
- galaxy S3 is badAndroid (stock brower, webview)
99+
`AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30`
100+
- galaxy S4 is badAndroid (stock brower, webview)
101+
`AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30`
102+
- galaxy S5 is OK
103+
`AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Mobile Safari/537.36 (Chrome/)`
104+
- galaxy S6 is OK
105+
`AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Mobile Safari/537.36 (Chrome/)`
106+
*/
107+
me.isBadAndroid = (function() {
108+
var appVersion = window.navigator.appVersion;
109+
// Android browser is not a chrome browser.
110+
if (/Android/.test(appVersion) && !(/Chrome\/\d/.test(appVersion))) {
111+
var safariVersion = appVersion.match(/Safari\/(\d+.\d)/);
112+
if(safariVersion && typeof safariVersion === "object" && safariVersion.length >= 2) {
113+
return parseFloat(safariVersion[1]) < 535.19;
114+
} else {
115+
return true;
116+
}
117+
} else {
118+
return false;
119+
}
120+
})();
95121

96122
me.extend(me.style = {}, {
97123
transform: _transform,
@@ -231,20 +257,29 @@ var utils = (function () {
231257
ev;
232258

233259
if ( !(/(SELECT|INPUT|TEXTAREA)/i).test(target.tagName) ) {
234-
ev = document.createEvent('MouseEvents');
235-
ev.initMouseEvent('click', true, true, e.view, 1,
236-
target.screenX, target.screenY, target.clientX, target.clientY,
237-
e.ctrlKey, e.altKey, e.shiftKey, e.metaKey,
238-
0, null);
239-
260+
// https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/initMouseEvent
261+
// initMouseEvent is deprecated.
262+
ev = document.createEvent(window.MouseEvent ? 'MouseEvents' : 'Event');
263+
ev.initEvent('click', true, true);
264+
ev.view = e.view || window;
265+
ev.detail = 1;
266+
ev.screenX = target.screenX || 0;
267+
ev.screenY = target.screenY || 0;
268+
ev.clientX = target.clientX || 0;
269+
ev.clientY = target.clientY || 0;
270+
ev.ctrlKey = !!e.ctrlKey;
271+
ev.altKey = !!e.altKey;
272+
ev.shiftKey = !!e.shiftKey;
273+
ev.metaKey = !!e.metaKey;
274+
ev.button = 0;
275+
ev.relatedTarget = null;
240276
ev._constructed = true;
241277
target.dispatchEvent(ev);
242278
}
243279
};
244280

245281
return me;
246282
})();
247-
248283
function IScroll (el, options) {
249284
this.wrapper = typeof el == 'string' ? document.querySelector(el) : el;
250285
this.scroller = this.wrapper.children[0];
@@ -258,8 +293,10 @@ function IScroll (el, options) {
258293

259294
snapThreshold: 0.334,
260295

261-
// INSERT POINT: OPTIONS
262-
296+
// INSERT POINT: OPTIONS
297+
disablePointer : !utils.hasPointer,
298+
disableTouch : utils.hasPointer || !utils.hasTouch,
299+
disableMouse : utils.hasPointer || utils.hasTouch,
263300
startX: 0,
264301
startY: 0,
265302
scrollY: true,
@@ -275,7 +312,8 @@ function IScroll (el, options) {
275312

276313
HWCompositing: true,
277314
useTransition: true,
278-
useTransform: true
315+
useTransform: true,
316+
bindToWrapper: typeof window.onmousedown === "undefined"
279317
};
280318

281319
for ( var i in options ) {
@@ -307,6 +345,13 @@ function IScroll (el, options) {
307345
this.options.tap = 'tap';
308346
}
309347

348+
// https://github.com/cubiq/iscroll/issues/1029
349+
if (!this.options.useTransition && !this.options.useTransform) {
350+
if(!(/relative|absolute/i).test(this.scrollerStyle.position)) {
351+
this.scrollerStyle.position = "relative";
352+
}
353+
}
354+
310355
if ( this.options.shrinkScrollbars == 'scale' ) {
311356
this.options.useTransition = false;
312357
}
@@ -315,7 +360,7 @@ function IScroll (el, options) {
315360

316361
// INSERT POINT: NORMALIZATION
317362

318-
// Some defaults
363+
// Some defaults
319364
this.x = 0;
320365
this.y = 0;
321366
this.directionX = 0;
@@ -332,7 +377,7 @@ function IScroll (el, options) {
332377
}
333378

334379
IScroll.prototype = {
335-
version: '5.1.3',
380+
version: '5.2.0',
336381

337382
_init: function () {
338383
this._initEvents();
@@ -359,7 +404,8 @@ IScroll.prototype = {
359404

360405
destroy: function () {
361406
this._initEvents(true);
362-
407+
clearTimeout(this.resizeTimeout);
408+
this.resizeTimeout = null;
363409
this._execEvent('destroy');
364410
},
365411

@@ -378,7 +424,18 @@ IScroll.prototype = {
378424
_start: function (e) {
379425
// React to left mouse button only
380426
if ( utils.eventType[e.type] != 1 ) {
381-
if ( e.button !== 0 ) {
427+
// for button property
428+
// http://unixpapa.com/js/mouse.html
429+
var button;
430+
if (!e.which) {
431+
/* IE case */
432+
button = (e.button < 2) ? 0 :
433+
((e.button == 4) ? 1 : 2);
434+
} else {
435+
/* All others */
436+
button = e.button;
437+
}
438+
if ( button !== 0 ) {
382439
return;
383440
}
384441
}
@@ -402,11 +459,10 @@ IScroll.prototype = {
402459
this.directionY = 0;
403460
this.directionLocked = 0;
404461

405-
this._transitionTime();
406-
407462
this.startTime = utils.getTime();
408463

409464
if ( this.options.useTransition && this.isInTransition ) {
465+
this._transitionTime();
410466
this.isInTransition = false;
411467
pos = this.getComputedPosition();
412468
this._translate(Math.round(pos.x), Math.round(pos.y));
@@ -548,7 +604,7 @@ IScroll.prototype = {
548604
this.endTime = utils.getTime();
549605

550606
// reset if we are outside of the boundaries
551-
if ( this.moved && this.resetPosition(this.options.bounceTime) ) {
607+
if ( this.resetPosition(this.options.bounceTime) ) {
552608
return;
553609
}
554610

@@ -752,10 +808,12 @@ IScroll.prototype = {
752808
easing = easing || utils.ease.circular;
753809

754810
this.isInTransition = this.options.useTransition && time > 0;
755-
756-
if ( !time || (this.options.useTransition && easing.style) ) {
757-
this._transitionTimingFunction(easing.style);
758-
this._transitionTime(time);
811+
var transitionType = this.options.useTransition && easing.style;
812+
if ( !time || transitionType ) {
813+
if(transitionType) {
814+
this._transitionTimingFunction(easing.style);
815+
this._transitionTime(time);
816+
}
759817
this._translate(x, y);
760818
} else {
761819
this._animate(x, y, time, easing.fn);
@@ -794,12 +852,26 @@ IScroll.prototype = {
794852
},
795853

796854
_transitionTime: function (time) {
855+
if (!this.options.useTransition) {
856+
return;
857+
}
797858
time = time || 0;
859+
var durationProp = utils.style.transitionDuration;
860+
if(!durationProp) {
861+
return;
862+
}
798863

799-
this.scrollerStyle[utils.style.transitionDuration] = time + 'ms';
864+
this.scrollerStyle[durationProp] = time + 'ms';
800865

801866
if ( !time && utils.isBadAndroid ) {
802-
this.scrollerStyle[utils.style.transitionDuration] = '0.001s';
867+
this.scrollerStyle[durationProp] = '0.0001ms';
868+
// remove 0.0001ms
869+
var self = this;
870+
rAF(function() {
871+
if(self.scrollerStyle[durationProp] === '0.0001ms') {
872+
self.scrollerStyle[durationProp] = '0s';
873+
}
874+
});
803875
}
804876

805877

@@ -913,7 +985,6 @@ IScroll.prototype = {
913985

914986
return { x: x, y: y };
915987
},
916-
917988
_initIndicators: function () {
918989
var interactive = this.options.interactiveScrollbars,
919990
customStyle = typeof this.options.scrollbars != 'string',
@@ -971,8 +1042,10 @@ IScroll.prototype = {
9711042

9721043
// TODO: check if we can use array.map (wide compatibility and performance issues)
9731044
function _indicatorsMap (fn) {
974-
for ( var i = that.indicators.length; i--; ) {
975-
fn.call(that.indicators[i]);
1045+
if (that.indicators) {
1046+
for ( var i = that.indicators.length; i--; ) {
1047+
fn.call(that.indicators[i]);
1048+
}
9761049
}
9771050
}
9781051

@@ -1024,6 +1097,8 @@ IScroll.prototype = {
10241097
utils.addEvent(this.wrapper, 'DOMMouseScroll', this);
10251098

10261099
this.on('destroy', function () {
1100+
clearTimeout(this.wheelTimeout);
1101+
this.wheelTimeout = null;
10271102
utils.removeEvent(this.wrapper, 'wheel', this);
10281103
utils.removeEvent(this.wrapper, 'mousewheel', this);
10291104
utils.removeEvent(this.wrapper, 'DOMMouseScroll', this);
@@ -1036,7 +1111,6 @@ IScroll.prototype = {
10361111
}
10371112

10381113
e.preventDefault();
1039-
e.stopPropagation();
10401114

10411115
var wheelDeltaX, wheelDeltaY,
10421116
newX, newY,
@@ -1049,7 +1123,9 @@ IScroll.prototype = {
10491123
// Execute the scrollEnd event after 400ms the wheel stopped scrolling
10501124
clearTimeout(this.wheelTimeout);
10511125
this.wheelTimeout = setTimeout(function () {
1052-
that._execEvent('scrollEnd');
1126+
if(!that.options.snap) {
1127+
that._execEvent('scrollEnd');
1128+
}
10531129
that.wheelTimeout = undefined;
10541130
}, 400);
10551131

@@ -1104,6 +1180,9 @@ IScroll.prototype = {
11041180
newX = this.x + Math.round(this.hasHorizontalScroll ? wheelDeltaX : 0);
11051181
newY = this.y + Math.round(this.hasVerticalScroll ? wheelDeltaY : 0);
11061182

1183+
this.directionX = wheelDeltaX > 0 ? -1 : wheelDeltaX < 0 ? 1 : 0;
1184+
this.directionY = wheelDeltaY > 0 ? -1 : wheelDeltaY < 0 ? 1 : 0;
1185+
11071186
if ( newX > 0 ) {
11081187
newX = 0;
11091188
} else if ( newX < this.maxScrollX ) {
@@ -1571,7 +1650,7 @@ IScroll.prototype = {
15711650
this._key(e);
15721651
break;
15731652
case 'click':
1574-
if ( !e._constructed ) {
1653+
if ( this.enabled && !e._constructed ) {
15751654
e.preventDefault();
15761655
e.stopPropagation();
15771656
}
@@ -1660,7 +1739,20 @@ function Indicator (scroller, options) {
16601739

16611740
if ( this.options.fade ) {
16621741
this.wrapperStyle[utils.style.transform] = this.scroller.translateZ;
1663-
this.wrapperStyle[utils.style.transitionDuration] = utils.isBadAndroid ? '0.001s' : '0ms';
1742+
var durationProp = utils.style.transitionDuration;
1743+
if(!durationProp) {
1744+
return;
1745+
}
1746+
this.wrapperStyle[durationProp] = utils.isBadAndroid ? '0.0001ms' : '0ms';
1747+
// remove 0.0001ms
1748+
var self = this;
1749+
if(utils.isBadAndroid) {
1750+
rAF(function() {
1751+
if(self.wrapperStyle[durationProp] === '0.0001ms') {
1752+
self.wrapperStyle[durationProp] = '0s';
1753+
}
1754+
});
1755+
}
16641756
this.wrapperStyle.opacity = '0';
16651757
}
16661758
}
@@ -1694,6 +1786,10 @@ Indicator.prototype = {
16941786
},
16951787

16961788
destroy: function () {
1789+
if ( this.options.fadeScrollbars ) {
1790+
clearTimeout(this.fadeTimeout);
1791+
this.fadeTimeout = null;
1792+
}
16971793
if ( this.options.interactive ) {
16981794
utils.removeEvent(this.indicator, 'touchstart', this);
16991795
utils.removeEvent(this.indicator, utils.prefixPointerEvent('pointerdown'), this);
@@ -1808,10 +1904,22 @@ Indicator.prototype = {
18081904

18091905
transitionTime: function (time) {
18101906
time = time || 0;
1811-
this.indicatorStyle[utils.style.transitionDuration] = time + 'ms';
1907+
var durationProp = utils.style.transitionDuration;
1908+
if(!durationProp) {
1909+
return;
1910+
}
1911+
1912+
this.indicatorStyle[durationProp] = time + 'ms';
18121913

18131914
if ( !time && utils.isBadAndroid ) {
1814-
this.indicatorStyle[utils.style.transitionDuration] = '0.001s';
1915+
this.indicatorStyle[durationProp] = '0.0001ms';
1916+
// remove 0.0001ms
1917+
var self = this;
1918+
rAF(function() {
1919+
if(self.indicatorStyle[durationProp] === '0.0001ms') {
1920+
self.indicatorStyle[durationProp] = '0s';
1921+
}
1922+
});
18151923
}
18161924
},
18171925

@@ -1875,7 +1983,7 @@ Indicator.prototype = {
18751983
this.maxBoundaryX = this.maxPosX;
18761984
}
18771985

1878-
this.sizeRatioX = this.options.speedRatioX || (this.scroller.maxScrollX && (this.maxPosX / this.scroller.maxScrollX));
1986+
this.sizeRatioX = this.options.speedRatioX || (this.scroller.maxScrollX && (this.maxPosX / this.scroller.maxScrollX));
18791987
}
18801988

18811989
if ( this.options.listenY ) {
@@ -2004,6 +2112,8 @@ IScroll.utils = utils;
20042112

20052113
if ( typeof module != 'undefined' && module.exports ) {
20062114
module.exports = IScroll;
2115+
} else if ( typeof define == 'function' && define.amd ) {
2116+
define( function () { return IScroll; } );
20072117
} else {
20082118
window.IScroll = IScroll;
20092119
}

0 commit comments

Comments
 (0)