innerSliderUtils.js 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777
  1. "use strict";
  2. var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
  3. Object.defineProperty(exports, "__esModule", {
  4. value: true
  5. });
  6. exports.checkSpecKeys = exports.checkNavigable = exports.changeSlide = exports.canUseDOM = exports.canGoNext = void 0;
  7. exports.clamp = clamp;
  8. exports.swipeStart = exports.swipeMove = exports.swipeEnd = exports.slidesOnRight = exports.slidesOnLeft = exports.slideHandler = exports.siblingDirection = exports.safePreventDefault = exports.lazyStartIndex = exports.lazySlidesOnRight = exports.lazySlidesOnLeft = exports.lazyEndIndex = exports.keyHandler = exports.initializedState = exports.getWidth = exports.getTrackLeft = exports.getTrackCSS = exports.getTrackAnimateCSS = exports.getTotalSlides = exports.getSwipeDirection = exports.getSlideCount = exports.getRequiredLazySlides = exports.getPreClones = exports.getPostClones = exports.getOnDemandLazySlides = exports.getNavigableIndexes = exports.getHeight = exports.extractObject = void 0;
  9. var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends"));
  10. // import supportsPassive from '../../../_util/supportsPassive';
  11. function clamp(number, lowerBound, upperBound) {
  12. return Math.max(lowerBound, Math.min(number, upperBound));
  13. }
  14. const safePreventDefault = event => {
  15. const passiveEvents = ['touchstart', 'touchmove', 'wheel'];
  16. if (!passiveEvents.includes(event.type)) {
  17. event.preventDefault();
  18. }
  19. };
  20. exports.safePreventDefault = safePreventDefault;
  21. const getOnDemandLazySlides = spec => {
  22. const onDemandSlides = [];
  23. const startIndex = lazyStartIndex(spec);
  24. const endIndex = lazyEndIndex(spec);
  25. for (let slideIndex = startIndex; slideIndex < endIndex; slideIndex++) {
  26. if (spec.lazyLoadedList.indexOf(slideIndex) < 0) {
  27. onDemandSlides.push(slideIndex);
  28. }
  29. }
  30. return onDemandSlides;
  31. };
  32. // return list of slides that need to be present
  33. exports.getOnDemandLazySlides = getOnDemandLazySlides;
  34. const getRequiredLazySlides = spec => {
  35. const requiredSlides = [];
  36. const startIndex = lazyStartIndex(spec);
  37. const endIndex = lazyEndIndex(spec);
  38. for (let slideIndex = startIndex; slideIndex < endIndex; slideIndex++) {
  39. requiredSlides.push(slideIndex);
  40. }
  41. return requiredSlides;
  42. };
  43. // startIndex that needs to be present
  44. exports.getRequiredLazySlides = getRequiredLazySlides;
  45. const lazyStartIndex = spec => spec.currentSlide - lazySlidesOnLeft(spec);
  46. exports.lazyStartIndex = lazyStartIndex;
  47. const lazyEndIndex = spec => spec.currentSlide + lazySlidesOnRight(spec);
  48. exports.lazyEndIndex = lazyEndIndex;
  49. const lazySlidesOnLeft = spec => spec.centerMode ? Math.floor(spec.slidesToShow / 2) + (parseInt(spec.centerPadding) > 0 ? 1 : 0) : 0;
  50. exports.lazySlidesOnLeft = lazySlidesOnLeft;
  51. const lazySlidesOnRight = spec => spec.centerMode ? Math.floor((spec.slidesToShow - 1) / 2) + 1 + (parseInt(spec.centerPadding) > 0 ? 1 : 0) : spec.slidesToShow;
  52. // get width of an element
  53. exports.lazySlidesOnRight = lazySlidesOnRight;
  54. const getWidth = elem => elem && elem.offsetWidth || 0;
  55. exports.getWidth = getWidth;
  56. const getHeight = elem => elem && elem.offsetHeight || 0;
  57. exports.getHeight = getHeight;
  58. const getSwipeDirection = function (touchObject) {
  59. let verticalSwiping = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
  60. let swipeAngle;
  61. const xDist = touchObject.startX - touchObject.curX;
  62. const yDist = touchObject.startY - touchObject.curY;
  63. const r = Math.atan2(yDist, xDist);
  64. swipeAngle = Math.round(r * 180 / Math.PI);
  65. if (swipeAngle < 0) {
  66. swipeAngle = 360 - Math.abs(swipeAngle);
  67. }
  68. if (swipeAngle <= 45 && swipeAngle >= 0 || swipeAngle <= 360 && swipeAngle >= 315) {
  69. return 'left';
  70. }
  71. if (swipeAngle >= 135 && swipeAngle <= 225) {
  72. return 'right';
  73. }
  74. if (verticalSwiping === true) {
  75. if (swipeAngle >= 35 && swipeAngle <= 135) {
  76. return 'up';
  77. } else {
  78. return 'down';
  79. }
  80. }
  81. return 'vertical';
  82. };
  83. // whether or not we can go next
  84. exports.getSwipeDirection = getSwipeDirection;
  85. const canGoNext = spec => {
  86. let canGo = true;
  87. if (!spec.infinite) {
  88. if (spec.centerMode && spec.currentSlide >= spec.slideCount - 1) {
  89. canGo = false;
  90. } else if (spec.slideCount <= spec.slidesToShow || spec.currentSlide >= spec.slideCount - spec.slidesToShow) {
  91. canGo = false;
  92. }
  93. }
  94. return canGo;
  95. };
  96. // given an object and a list of keys, return new object with given keys
  97. exports.canGoNext = canGoNext;
  98. const extractObject = (spec, keys) => {
  99. const newObject = {};
  100. keys.forEach(key => newObject[key] = spec[key]);
  101. return newObject;
  102. };
  103. // get initialized state
  104. exports.extractObject = extractObject;
  105. const initializedState = spec => {
  106. // spec also contains listRef, trackRef
  107. const slideCount = spec.children.length;
  108. const listNode = spec.listRef;
  109. const listWidth = Math.ceil(getWidth(listNode));
  110. const trackNode = spec.trackRef;
  111. const trackWidth = Math.ceil(getWidth(trackNode));
  112. let slideWidth;
  113. if (!spec.vertical) {
  114. let centerPaddingAdj = spec.centerMode && parseInt(spec.centerPadding) * 2;
  115. if (typeof spec.centerPadding === 'string' && spec.centerPadding.slice(-1) === '%') {
  116. centerPaddingAdj *= listWidth / 100;
  117. }
  118. slideWidth = Math.ceil((listWidth - centerPaddingAdj) / spec.slidesToShow);
  119. } else {
  120. slideWidth = listWidth;
  121. }
  122. const slideHeight = listNode && getHeight(listNode.querySelector('[data-index="0"]'));
  123. const listHeight = slideHeight * spec.slidesToShow;
  124. let currentSlide = spec.currentSlide === undefined ? spec.initialSlide : spec.currentSlide;
  125. if (spec.rtl && spec.currentSlide === undefined) {
  126. currentSlide = slideCount - 1 - spec.initialSlide;
  127. }
  128. let lazyLoadedList = spec.lazyLoadedList || [];
  129. const slidesToLoad = getOnDemandLazySlides((0, _extends2.default)((0, _extends2.default)({}, spec), {
  130. currentSlide,
  131. lazyLoadedList
  132. }), spec);
  133. lazyLoadedList = lazyLoadedList.concat(slidesToLoad);
  134. const state = {
  135. slideCount,
  136. slideWidth,
  137. listWidth,
  138. trackWidth,
  139. currentSlide,
  140. slideHeight,
  141. listHeight,
  142. lazyLoadedList
  143. };
  144. if (spec.autoplaying === null && spec.autoplay) {
  145. state['autoplaying'] = 'playing';
  146. }
  147. return state;
  148. };
  149. exports.initializedState = initializedState;
  150. const slideHandler = spec => {
  151. const {
  152. waitForAnimate,
  153. animating,
  154. fade,
  155. infinite,
  156. index,
  157. slideCount,
  158. lazyLoad,
  159. currentSlide,
  160. centerMode,
  161. slidesToScroll,
  162. slidesToShow,
  163. useCSS
  164. } = spec;
  165. let {
  166. lazyLoadedList
  167. } = spec;
  168. if (waitForAnimate && animating) return {};
  169. let animationSlide = index;
  170. let finalSlide;
  171. let animationLeft;
  172. let finalLeft;
  173. let state = {};
  174. let nextState = {};
  175. const targetSlide = infinite ? index : clamp(index, 0, slideCount - 1);
  176. if (fade) {
  177. if (!infinite && (index < 0 || index >= slideCount)) return {};
  178. if (index < 0) {
  179. animationSlide = index + slideCount;
  180. } else if (index >= slideCount) {
  181. animationSlide = index - slideCount;
  182. }
  183. if (lazyLoad && lazyLoadedList.indexOf(animationSlide) < 0) {
  184. lazyLoadedList = lazyLoadedList.concat(animationSlide);
  185. }
  186. state = {
  187. animating: true,
  188. currentSlide: animationSlide,
  189. lazyLoadedList,
  190. targetSlide: animationSlide
  191. };
  192. nextState = {
  193. animating: false,
  194. targetSlide: animationSlide
  195. };
  196. } else {
  197. finalSlide = animationSlide;
  198. if (animationSlide < 0) {
  199. finalSlide = animationSlide + slideCount;
  200. if (!infinite) finalSlide = 0;else if (slideCount % slidesToScroll !== 0) {
  201. finalSlide = slideCount - slideCount % slidesToScroll;
  202. }
  203. } else if (!canGoNext(spec) && animationSlide > currentSlide) {
  204. animationSlide = finalSlide = currentSlide;
  205. } else if (centerMode && animationSlide >= slideCount) {
  206. animationSlide = infinite ? slideCount : slideCount - 1;
  207. finalSlide = infinite ? 0 : slideCount - 1;
  208. } else if (animationSlide >= slideCount) {
  209. finalSlide = animationSlide - slideCount;
  210. if (!infinite) finalSlide = slideCount - slidesToShow;else if (slideCount % slidesToScroll !== 0) finalSlide = 0;
  211. }
  212. if (!infinite && animationSlide + slidesToShow >= slideCount) {
  213. finalSlide = slideCount - slidesToShow;
  214. }
  215. animationLeft = getTrackLeft((0, _extends2.default)((0, _extends2.default)({}, spec), {
  216. slideIndex: animationSlide
  217. }));
  218. finalLeft = getTrackLeft((0, _extends2.default)((0, _extends2.default)({}, spec), {
  219. slideIndex: finalSlide
  220. }));
  221. if (!infinite) {
  222. if (animationLeft === finalLeft) animationSlide = finalSlide;
  223. animationLeft = finalLeft;
  224. }
  225. if (lazyLoad) {
  226. lazyLoadedList = lazyLoadedList.concat(getOnDemandLazySlides((0, _extends2.default)((0, _extends2.default)({}, spec), {
  227. currentSlide: animationSlide
  228. })));
  229. }
  230. if (!useCSS) {
  231. state = {
  232. currentSlide: finalSlide,
  233. trackStyle: getTrackCSS((0, _extends2.default)((0, _extends2.default)({}, spec), {
  234. left: finalLeft
  235. })),
  236. lazyLoadedList,
  237. targetSlide
  238. };
  239. } else {
  240. state = {
  241. animating: true,
  242. currentSlide: finalSlide,
  243. trackStyle: getTrackAnimateCSS((0, _extends2.default)((0, _extends2.default)({}, spec), {
  244. left: animationLeft
  245. })),
  246. lazyLoadedList,
  247. targetSlide
  248. };
  249. nextState = {
  250. animating: false,
  251. currentSlide: finalSlide,
  252. trackStyle: getTrackCSS((0, _extends2.default)((0, _extends2.default)({}, spec), {
  253. left: finalLeft
  254. })),
  255. swipeLeft: null,
  256. targetSlide
  257. };
  258. }
  259. }
  260. return {
  261. state,
  262. nextState
  263. };
  264. };
  265. exports.slideHandler = slideHandler;
  266. const changeSlide = (spec, options) => {
  267. let previousInt, slideOffset, targetSlide;
  268. const {
  269. slidesToScroll,
  270. slidesToShow,
  271. slideCount,
  272. currentSlide,
  273. targetSlide: previousTargetSlide,
  274. lazyLoad,
  275. infinite
  276. } = spec;
  277. const unevenOffset = slideCount % slidesToScroll !== 0;
  278. const indexOffset = unevenOffset ? 0 : (slideCount - currentSlide) % slidesToScroll;
  279. if (options.message === 'previous') {
  280. slideOffset = indexOffset === 0 ? slidesToScroll : slidesToShow - indexOffset;
  281. targetSlide = currentSlide - slideOffset;
  282. if (lazyLoad && !infinite) {
  283. previousInt = currentSlide - slideOffset;
  284. targetSlide = previousInt === -1 ? slideCount - 1 : previousInt;
  285. }
  286. if (!infinite) {
  287. targetSlide = previousTargetSlide - slidesToScroll;
  288. }
  289. } else if (options.message === 'next') {
  290. slideOffset = indexOffset === 0 ? slidesToScroll : indexOffset;
  291. targetSlide = currentSlide + slideOffset;
  292. if (lazyLoad && !infinite) {
  293. targetSlide = (currentSlide + slidesToScroll) % slideCount + indexOffset;
  294. }
  295. if (!infinite) {
  296. targetSlide = previousTargetSlide + slidesToScroll;
  297. }
  298. } else if (options.message === 'dots') {
  299. // Click on dots
  300. targetSlide = options.index * options.slidesToScroll;
  301. } else if (options.message === 'children') {
  302. // Click on the slides
  303. targetSlide = options.index;
  304. if (infinite) {
  305. const direction = siblingDirection((0, _extends2.default)((0, _extends2.default)({}, spec), {
  306. targetSlide
  307. }));
  308. if (targetSlide > options.currentSlide && direction === 'left') {
  309. targetSlide = targetSlide - slideCount;
  310. } else if (targetSlide < options.currentSlide && direction === 'right') {
  311. targetSlide = targetSlide + slideCount;
  312. }
  313. }
  314. } else if (options.message === 'index') {
  315. targetSlide = Number(options.index);
  316. }
  317. return targetSlide;
  318. };
  319. exports.changeSlide = changeSlide;
  320. const keyHandler = (e, accessibility, rtl) => {
  321. if (e.target.tagName.match('TEXTAREA|INPUT|SELECT') || !accessibility) {
  322. return '';
  323. }
  324. if (e.keyCode === 37) return rtl ? 'next' : 'previous';
  325. if (e.keyCode === 39) return rtl ? 'previous' : 'next';
  326. return '';
  327. };
  328. exports.keyHandler = keyHandler;
  329. const swipeStart = (e, swipe, draggable) => {
  330. e.target.tagName === 'IMG' && safePreventDefault(e);
  331. if (!swipe || !draggable && e.type.indexOf('mouse') !== -1) return '';
  332. return {
  333. dragging: true,
  334. touchObject: {
  335. startX: e.touches ? e.touches[0].pageX : e.clientX,
  336. startY: e.touches ? e.touches[0].pageY : e.clientY,
  337. curX: e.touches ? e.touches[0].pageX : e.clientX,
  338. curY: e.touches ? e.touches[0].pageY : e.clientY
  339. }
  340. };
  341. };
  342. exports.swipeStart = swipeStart;
  343. const swipeMove = (e, spec) => {
  344. // spec also contains, trackRef and slideIndex
  345. const {
  346. scrolling,
  347. animating,
  348. vertical,
  349. swipeToSlide,
  350. verticalSwiping,
  351. rtl,
  352. currentSlide,
  353. edgeFriction,
  354. edgeDragged,
  355. onEdge,
  356. swiped,
  357. swiping,
  358. slideCount,
  359. slidesToScroll,
  360. infinite,
  361. touchObject,
  362. swipeEvent,
  363. listHeight,
  364. listWidth
  365. } = spec;
  366. if (scrolling) return;
  367. if (animating) return safePreventDefault(e);
  368. if (vertical && swipeToSlide && verticalSwiping) safePreventDefault(e);
  369. let swipeLeft;
  370. let state = {};
  371. const curLeft = getTrackLeft(spec);
  372. touchObject.curX = e.touches ? e.touches[0].pageX : e.clientX;
  373. touchObject.curY = e.touches ? e.touches[0].pageY : e.clientY;
  374. touchObject.swipeLength = Math.round(Math.sqrt(Math.pow(touchObject.curX - touchObject.startX, 2)));
  375. const verticalSwipeLength = Math.round(Math.sqrt(Math.pow(touchObject.curY - touchObject.startY, 2)));
  376. if (!verticalSwiping && !swiping && verticalSwipeLength > 10) {
  377. return {
  378. scrolling: true
  379. };
  380. }
  381. if (verticalSwiping) touchObject.swipeLength = verticalSwipeLength;
  382. let positionOffset = (!rtl ? 1 : -1) * (touchObject.curX > touchObject.startX ? 1 : -1);
  383. if (verticalSwiping) {
  384. positionOffset = touchObject.curY > touchObject.startY ? 1 : -1;
  385. }
  386. const dotCount = Math.ceil(slideCount / slidesToScroll);
  387. const swipeDirection = getSwipeDirection(spec.touchObject, verticalSwiping);
  388. let touchSwipeLength = touchObject.swipeLength;
  389. if (!infinite) {
  390. if (currentSlide === 0 && (swipeDirection === 'right' || swipeDirection === 'down') || currentSlide + 1 >= dotCount && (swipeDirection === 'left' || swipeDirection === 'up') || !canGoNext(spec) && (swipeDirection === 'left' || swipeDirection === 'up')) {
  391. touchSwipeLength = touchObject.swipeLength * edgeFriction;
  392. if (edgeDragged === false && onEdge) {
  393. onEdge(swipeDirection);
  394. state['edgeDragged'] = true;
  395. }
  396. }
  397. }
  398. if (!swiped && swipeEvent) {
  399. swipeEvent(swipeDirection);
  400. state['swiped'] = true;
  401. }
  402. if (!vertical) {
  403. if (!rtl) {
  404. swipeLeft = curLeft + touchSwipeLength * positionOffset;
  405. } else {
  406. swipeLeft = curLeft - touchSwipeLength * positionOffset;
  407. }
  408. } else {
  409. swipeLeft = curLeft + touchSwipeLength * (listHeight / listWidth) * positionOffset;
  410. }
  411. if (verticalSwiping) {
  412. swipeLeft = curLeft + touchSwipeLength * positionOffset;
  413. }
  414. state = (0, _extends2.default)((0, _extends2.default)({}, state), {
  415. touchObject,
  416. swipeLeft,
  417. trackStyle: getTrackCSS((0, _extends2.default)((0, _extends2.default)({}, spec), {
  418. left: swipeLeft
  419. }))
  420. });
  421. if (Math.abs(touchObject.curX - touchObject.startX) < Math.abs(touchObject.curY - touchObject.startY) * 0.8) {
  422. return state;
  423. }
  424. if (touchObject.swipeLength > 10) {
  425. state['swiping'] = true;
  426. safePreventDefault(e);
  427. }
  428. return state;
  429. };
  430. exports.swipeMove = swipeMove;
  431. const swipeEnd = (e, spec) => {
  432. const {
  433. dragging,
  434. swipe,
  435. touchObject,
  436. listWidth,
  437. touchThreshold,
  438. verticalSwiping,
  439. listHeight,
  440. swipeToSlide,
  441. scrolling,
  442. onSwipe,
  443. targetSlide,
  444. currentSlide,
  445. infinite
  446. } = spec;
  447. if (!dragging) {
  448. if (swipe) safePreventDefault(e);
  449. return {};
  450. }
  451. const minSwipe = verticalSwiping ? listHeight / touchThreshold : listWidth / touchThreshold;
  452. const swipeDirection = getSwipeDirection(touchObject, verticalSwiping);
  453. // reset the state of touch related state variables.
  454. const state = {
  455. dragging: false,
  456. edgeDragged: false,
  457. scrolling: false,
  458. swiping: false,
  459. swiped: false,
  460. swipeLeft: null,
  461. touchObject: {}
  462. };
  463. if (scrolling) {
  464. return state;
  465. }
  466. if (!touchObject.swipeLength) {
  467. return state;
  468. }
  469. if (touchObject.swipeLength > minSwipe) {
  470. safePreventDefault(e);
  471. if (onSwipe) {
  472. onSwipe(swipeDirection);
  473. }
  474. let slideCount, newSlide;
  475. const activeSlide = infinite ? currentSlide : targetSlide;
  476. switch (swipeDirection) {
  477. case 'left':
  478. case 'up':
  479. newSlide = activeSlide + getSlideCount(spec);
  480. slideCount = swipeToSlide ? checkNavigable(spec, newSlide) : newSlide;
  481. state['currentDirection'] = 0;
  482. break;
  483. case 'right':
  484. case 'down':
  485. newSlide = activeSlide - getSlideCount(spec);
  486. slideCount = swipeToSlide ? checkNavigable(spec, newSlide) : newSlide;
  487. state['currentDirection'] = 1;
  488. break;
  489. default:
  490. slideCount = activeSlide;
  491. }
  492. state['triggerSlideHandler'] = slideCount;
  493. } else {
  494. // Adjust the track back to it's original position.
  495. const currentLeft = getTrackLeft(spec);
  496. state['trackStyle'] = getTrackAnimateCSS((0, _extends2.default)((0, _extends2.default)({}, spec), {
  497. left: currentLeft
  498. }));
  499. }
  500. return state;
  501. };
  502. exports.swipeEnd = swipeEnd;
  503. const getNavigableIndexes = spec => {
  504. const max = spec.infinite ? spec.slideCount * 2 : spec.slideCount;
  505. let breakpoint = spec.infinite ? spec.slidesToShow * -1 : 0;
  506. let counter = spec.infinite ? spec.slidesToShow * -1 : 0;
  507. const indexes = [];
  508. while (breakpoint < max) {
  509. indexes.push(breakpoint);
  510. breakpoint = counter + spec.slidesToScroll;
  511. counter += Math.min(spec.slidesToScroll, spec.slidesToShow);
  512. }
  513. return indexes;
  514. };
  515. exports.getNavigableIndexes = getNavigableIndexes;
  516. const checkNavigable = (spec, index) => {
  517. const navigables = getNavigableIndexes(spec);
  518. let prevNavigable = 0;
  519. if (index > navigables[navigables.length - 1]) {
  520. index = navigables[navigables.length - 1];
  521. } else {
  522. for (const n in navigables) {
  523. if (index < navigables[n]) {
  524. index = prevNavigable;
  525. break;
  526. }
  527. prevNavigable = navigables[n];
  528. }
  529. }
  530. return index;
  531. };
  532. exports.checkNavigable = checkNavigable;
  533. const getSlideCount = spec => {
  534. const centerOffset = spec.centerMode ? spec.slideWidth * Math.floor(spec.slidesToShow / 2) : 0;
  535. if (spec.swipeToSlide) {
  536. let swipedSlide;
  537. const slickList = spec.listRef;
  538. const slides = slickList.querySelectorAll && slickList.querySelectorAll('.slick-slide') || [];
  539. Array.from(slides).every(slide => {
  540. if (!spec.vertical) {
  541. if (slide.offsetLeft - centerOffset + getWidth(slide) / 2 > spec.swipeLeft * -1) {
  542. swipedSlide = slide;
  543. return false;
  544. }
  545. } else {
  546. if (slide.offsetTop + getHeight(slide) / 2 > spec.swipeLeft * -1) {
  547. swipedSlide = slide;
  548. return false;
  549. }
  550. }
  551. return true;
  552. });
  553. if (!swipedSlide) {
  554. return 0;
  555. }
  556. const currentIndex = spec.rtl === true ? spec.slideCount - spec.currentSlide : spec.currentSlide;
  557. const slidesTraversed = Math.abs(swipedSlide.dataset.index - currentIndex) || 1;
  558. return slidesTraversed;
  559. } else {
  560. return spec.slidesToScroll;
  561. }
  562. };
  563. exports.getSlideCount = getSlideCount;
  564. const checkSpecKeys = (spec, keysArray) => keysArray.reduce((value, key) => value && spec.hasOwnProperty(key), true) ? null : console.error('Keys Missing:', spec);
  565. exports.checkSpecKeys = checkSpecKeys;
  566. const getTrackCSS = spec => {
  567. checkSpecKeys(spec, ['left', 'variableWidth', 'slideCount', 'slidesToShow', 'slideWidth']);
  568. let trackWidth, trackHeight;
  569. const trackChildren = spec.slideCount + 2 * spec.slidesToShow;
  570. if (!spec.vertical) {
  571. trackWidth = getTotalSlides(spec) * spec.slideWidth;
  572. } else {
  573. trackHeight = trackChildren * spec.slideHeight;
  574. }
  575. let style = {
  576. opacity: 1,
  577. transition: '',
  578. WebkitTransition: ''
  579. };
  580. if (spec.useTransform) {
  581. const WebkitTransform = !spec.vertical ? 'translate3d(' + spec.left + 'px, 0px, 0px)' : 'translate3d(0px, ' + spec.left + 'px, 0px)';
  582. const transform = !spec.vertical ? 'translate3d(' + spec.left + 'px, 0px, 0px)' : 'translate3d(0px, ' + spec.left + 'px, 0px)';
  583. const msTransform = !spec.vertical ? 'translateX(' + spec.left + 'px)' : 'translateY(' + spec.left + 'px)';
  584. style = (0, _extends2.default)((0, _extends2.default)({}, style), {
  585. WebkitTransform,
  586. transform,
  587. msTransform
  588. });
  589. } else {
  590. if (spec.vertical) {
  591. style['top'] = spec.left;
  592. } else {
  593. style['left'] = spec.left;
  594. }
  595. }
  596. if (spec.fade) style = {
  597. opacity: 1
  598. };
  599. if (trackWidth) style.width = trackWidth + 'px';
  600. if (trackHeight) style.height = trackHeight + 'px';
  601. // Fallback for IE8
  602. if (window && !window.addEventListener && window.attachEvent) {
  603. if (!spec.vertical) {
  604. style.marginLeft = spec.left + 'px';
  605. } else {
  606. style.marginTop = spec.left + 'px';
  607. }
  608. }
  609. return style;
  610. };
  611. exports.getTrackCSS = getTrackCSS;
  612. const getTrackAnimateCSS = spec => {
  613. checkSpecKeys(spec, ['left', 'variableWidth', 'slideCount', 'slidesToShow', 'slideWidth', 'speed', 'cssEase']);
  614. const style = getTrackCSS(spec);
  615. // useCSS is true by default so it can be undefined
  616. if (spec.useTransform) {
  617. style.WebkitTransition = '-webkit-transform ' + spec.speed + 'ms ' + spec.cssEase;
  618. style.transition = 'transform ' + spec.speed + 'ms ' + spec.cssEase;
  619. } else {
  620. if (spec.vertical) {
  621. style.transition = 'top ' + spec.speed + 'ms ' + spec.cssEase;
  622. } else {
  623. style.transition = 'left ' + spec.speed + 'ms ' + spec.cssEase;
  624. }
  625. }
  626. return style;
  627. };
  628. exports.getTrackAnimateCSS = getTrackAnimateCSS;
  629. const getTrackLeft = spec => {
  630. if (spec.unslick) {
  631. return 0;
  632. }
  633. checkSpecKeys(spec, ['slideIndex', 'trackRef', 'infinite', 'centerMode', 'slideCount', 'slidesToShow', 'slidesToScroll', 'slideWidth', 'listWidth', 'variableWidth', 'slideHeight']);
  634. const {
  635. slideIndex,
  636. trackRef,
  637. infinite,
  638. centerMode,
  639. slideCount,
  640. slidesToShow,
  641. slidesToScroll,
  642. slideWidth,
  643. listWidth,
  644. variableWidth,
  645. slideHeight,
  646. fade,
  647. vertical
  648. } = spec;
  649. let slideOffset = 0;
  650. let targetLeft;
  651. let targetSlide;
  652. let verticalOffset = 0;
  653. if (fade || spec.slideCount === 1) {
  654. return 0;
  655. }
  656. let slidesToOffset = 0;
  657. if (infinite) {
  658. slidesToOffset = -getPreClones(spec); // bring active slide to the beginning of visual area
  659. // if next scroll doesn't have enough children, just reach till the end of original slides instead of shifting slidesToScroll children
  660. if (slideCount % slidesToScroll !== 0 && slideIndex + slidesToScroll > slideCount) {
  661. slidesToOffset = -(slideIndex > slideCount ? slidesToShow - (slideIndex - slideCount) : slideCount % slidesToScroll);
  662. }
  663. // shift current slide to center of the frame
  664. if (centerMode) {
  665. slidesToOffset += parseInt(slidesToShow / 2);
  666. }
  667. } else {
  668. if (slideCount % slidesToScroll !== 0 && slideIndex + slidesToScroll > slideCount) {
  669. slidesToOffset = slidesToShow - slideCount % slidesToScroll;
  670. }
  671. if (centerMode) {
  672. slidesToOffset = parseInt(slidesToShow / 2);
  673. }
  674. }
  675. slideOffset = slidesToOffset * slideWidth;
  676. verticalOffset = slidesToOffset * slideHeight;
  677. if (!vertical) {
  678. targetLeft = slideIndex * slideWidth * -1 + slideOffset;
  679. } else {
  680. targetLeft = slideIndex * slideHeight * -1 + verticalOffset;
  681. }
  682. if (variableWidth === true) {
  683. let targetSlideIndex;
  684. const trackElem = trackRef;
  685. targetSlideIndex = slideIndex + getPreClones(spec);
  686. targetSlide = trackElem && trackElem.childNodes[targetSlideIndex];
  687. targetLeft = targetSlide ? targetSlide.offsetLeft * -1 : 0;
  688. if (centerMode === true) {
  689. targetSlideIndex = infinite ? slideIndex + getPreClones(spec) : slideIndex;
  690. targetSlide = trackElem && trackElem.children[targetSlideIndex];
  691. targetLeft = 0;
  692. for (let slide = 0; slide < targetSlideIndex; slide++) {
  693. targetLeft -= trackElem && trackElem.children[slide] && trackElem.children[slide].offsetWidth;
  694. }
  695. targetLeft -= parseInt(spec.centerPadding);
  696. targetLeft += targetSlide && (listWidth - targetSlide.offsetWidth) / 2;
  697. }
  698. }
  699. return targetLeft;
  700. };
  701. exports.getTrackLeft = getTrackLeft;
  702. const getPreClones = spec => {
  703. if (spec.unslick || !spec.infinite) {
  704. return 0;
  705. }
  706. if (spec.variableWidth) {
  707. return spec.slideCount;
  708. }
  709. return spec.slidesToShow + (spec.centerMode ? 1 : 0);
  710. };
  711. exports.getPreClones = getPreClones;
  712. const getPostClones = spec => {
  713. if (spec.unslick || !spec.infinite) {
  714. return 0;
  715. }
  716. return spec.slideCount;
  717. };
  718. exports.getPostClones = getPostClones;
  719. const getTotalSlides = spec => spec.slideCount === 1 ? 1 : getPreClones(spec) + spec.slideCount + getPostClones(spec);
  720. exports.getTotalSlides = getTotalSlides;
  721. const siblingDirection = spec => {
  722. if (spec.targetSlide > spec.currentSlide) {
  723. if (spec.targetSlide > spec.currentSlide + slidesOnRight(spec)) {
  724. return 'left';
  725. }
  726. return 'right';
  727. } else {
  728. if (spec.targetSlide < spec.currentSlide - slidesOnLeft(spec)) {
  729. return 'right';
  730. }
  731. return 'left';
  732. }
  733. };
  734. exports.siblingDirection = siblingDirection;
  735. const slidesOnRight = _ref => {
  736. let {
  737. slidesToShow,
  738. centerMode,
  739. rtl,
  740. centerPadding
  741. } = _ref;
  742. // returns no of slides on the right of active slide
  743. if (centerMode) {
  744. let right = (slidesToShow - 1) / 2 + 1;
  745. if (parseInt(centerPadding) > 0) right += 1;
  746. if (rtl && slidesToShow % 2 === 0) right += 1;
  747. return right;
  748. }
  749. if (rtl) {
  750. return 0;
  751. }
  752. return slidesToShow - 1;
  753. };
  754. exports.slidesOnRight = slidesOnRight;
  755. const slidesOnLeft = _ref2 => {
  756. let {
  757. slidesToShow,
  758. centerMode,
  759. rtl,
  760. centerPadding
  761. } = _ref2;
  762. // returns no of slides on the left of active slide
  763. if (centerMode) {
  764. let left = (slidesToShow - 1) / 2 + 1;
  765. if (parseInt(centerPadding) > 0) left += 1;
  766. if (!rtl && slidesToShow % 2 === 0) left += 1;
  767. return left;
  768. }
  769. if (rtl) {
  770. return slidesToShow - 1;
  771. }
  772. return 0;
  773. };
  774. exports.slidesOnLeft = slidesOnLeft;
  775. const canUseDOM = () => !!(typeof window !== 'undefined' && window.document && window.document.createElement);
  776. exports.canUseDOM = canUseDOM;