swipe.js 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. /**
  2. * DevExtreme (events/swipe.js)
  3. * Version: 19.1.16
  4. * Build date: Tue Oct 18 2022
  5. *
  6. * Copyright (c) 2012 - 2022 Developer Express Inc. ALL RIGHTS RESERVED
  7. * Read about DevExtreme licensing here: https://js.devexpress.com/Licensing/
  8. */
  9. "use strict";
  10. var eventUtils = require("./utils");
  11. var GestureEmitter = require("./gesture/emitter.gesture");
  12. var registerEmitter = require("./core/emitter_registrator");
  13. var SWIPE_START_EVENT = "dxswipestart";
  14. var SWIPE_EVENT = "dxswipe";
  15. var SWIPE_END_EVENT = "dxswipeend";
  16. var HorizontalStrategy = {
  17. defaultItemSizeFunc: function() {
  18. return this.getElement().width()
  19. },
  20. getBounds: function() {
  21. return [this._maxLeftOffset, this._maxRightOffset]
  22. },
  23. calcOffsetRatio: function(e) {
  24. var endEventData = eventUtils.eventData(e);
  25. return (endEventData.x - (this._savedEventData && this._savedEventData.x || 0)) / this._itemSizeFunc().call(this, e)
  26. },
  27. isFastSwipe: function(e) {
  28. var endEventData = eventUtils.eventData(e);
  29. return this.FAST_SWIPE_SPEED_LIMIT * Math.abs(endEventData.x - this._tickData.x) >= endEventData.time - this._tickData.time
  30. }
  31. };
  32. var VerticalStrategy = {
  33. defaultItemSizeFunc: function() {
  34. return this.getElement().height()
  35. },
  36. getBounds: function() {
  37. return [this._maxTopOffset, this._maxBottomOffset]
  38. },
  39. calcOffsetRatio: function(e) {
  40. var endEventData = eventUtils.eventData(e);
  41. return (endEventData.y - (this._savedEventData && this._savedEventData.y || 0)) / this._itemSizeFunc().call(this, e)
  42. },
  43. isFastSwipe: function(e) {
  44. var endEventData = eventUtils.eventData(e);
  45. return this.FAST_SWIPE_SPEED_LIMIT * Math.abs(endEventData.y - this._tickData.y) >= endEventData.time - this._tickData.time
  46. }
  47. };
  48. var STRATEGIES = {
  49. horizontal: HorizontalStrategy,
  50. vertical: VerticalStrategy
  51. };
  52. var SwipeEmitter = GestureEmitter.inherit({
  53. TICK_INTERVAL: 300,
  54. FAST_SWIPE_SPEED_LIMIT: 10,
  55. ctor: function(element) {
  56. this.callBase(element);
  57. this.direction = "horizontal";
  58. this.elastic = true
  59. },
  60. _getStrategy: function() {
  61. return STRATEGIES[this.direction]
  62. },
  63. _defaultItemSizeFunc: function() {
  64. return this._getStrategy().defaultItemSizeFunc.call(this)
  65. },
  66. _itemSizeFunc: function() {
  67. return this.itemSizeFunc || this._defaultItemSizeFunc
  68. },
  69. _init: function(e) {
  70. this._tickData = eventUtils.eventData(e)
  71. },
  72. _start: function(e) {
  73. this._savedEventData = eventUtils.eventData(e);
  74. e = this._fireEvent(SWIPE_START_EVENT, e);
  75. if (!e.cancel) {
  76. this._maxLeftOffset = e.maxLeftOffset;
  77. this._maxRightOffset = e.maxRightOffset;
  78. this._maxTopOffset = e.maxTopOffset;
  79. this._maxBottomOffset = e.maxBottomOffset
  80. }
  81. },
  82. _move: function(e) {
  83. var strategy = this._getStrategy();
  84. var moveEventData = eventUtils.eventData(e);
  85. var offset = strategy.calcOffsetRatio.call(this, e);
  86. offset = this._fitOffset(offset, this.elastic);
  87. if (moveEventData.time - this._tickData.time > this.TICK_INTERVAL) {
  88. this._tickData = moveEventData
  89. }
  90. this._fireEvent(SWIPE_EVENT, e, {
  91. offset: offset
  92. });
  93. e.preventDefault()
  94. },
  95. _end: function(e) {
  96. var strategy = this._getStrategy();
  97. var offsetRatio = strategy.calcOffsetRatio.call(this, e);
  98. var isFast = strategy.isFastSwipe.call(this, e);
  99. var startOffset = offsetRatio;
  100. var targetOffset = this._calcTargetOffset(offsetRatio, isFast);
  101. startOffset = this._fitOffset(startOffset, this.elastic);
  102. targetOffset = this._fitOffset(targetOffset, false);
  103. this._fireEvent(SWIPE_END_EVENT, e, {
  104. offset: startOffset,
  105. targetOffset: targetOffset
  106. })
  107. },
  108. _fitOffset: function(offset, elastic) {
  109. var strategy = this._getStrategy();
  110. var bounds = strategy.getBounds.call(this);
  111. if (offset < -bounds[0]) {
  112. return elastic ? (-2 * bounds[0] + offset) / 3 : -bounds[0]
  113. }
  114. if (offset > bounds[1]) {
  115. return elastic ? (2 * bounds[1] + offset) / 3 : bounds[1]
  116. }
  117. return offset
  118. },
  119. _calcTargetOffset: function(offsetRatio, isFast) {
  120. var result;
  121. if (isFast) {
  122. result = Math.ceil(Math.abs(offsetRatio));
  123. if (offsetRatio < 0) {
  124. result = -result
  125. }
  126. } else {
  127. result = Math.round(offsetRatio)
  128. }
  129. return result
  130. }
  131. });
  132. registerEmitter({
  133. emitter: SwipeEmitter,
  134. events: [SWIPE_START_EVENT, SWIPE_EVENT, SWIPE_END_EVENT]
  135. });
  136. exports.swipe = SWIPE_EVENT;
  137. exports.start = SWIPE_START_EVENT;
  138. exports.end = SWIPE_END_EVENT;