vevet 3.2.3 → 3.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (33) hide show
  1. package/lib/cjs/components/AnimationFrame/index.js +1 -1
  2. package/lib/cjs/components/Marquee/index.js +262 -0
  3. package/lib/cjs/components/Marquee/index.js.map +1 -0
  4. package/lib/cjs/components/Marquee/types.js +3 -0
  5. package/lib/cjs/components/Marquee/types.js.map +1 -0
  6. package/lib/cjs/components/index.js +1 -0
  7. package/lib/cjs/components/index.js.map +1 -1
  8. package/lib/cjs/version.js +1 -1
  9. package/lib/esm/components/AnimationFrame/index.js +1 -1
  10. package/lib/esm/components/Marquee/index.js +216 -0
  11. package/lib/esm/components/Marquee/index.js.map +1 -0
  12. package/lib/esm/components/Marquee/types.js +2 -0
  13. package/lib/esm/components/Marquee/types.js.map +1 -0
  14. package/lib/esm/components/index.js +1 -0
  15. package/lib/esm/components/index.js.map +1 -1
  16. package/lib/esm/version.js +1 -1
  17. package/lib/types/components/AnimationFrame/types.d.ts +1 -1
  18. package/lib/types/components/Marquee/index.d.ts +66 -0
  19. package/lib/types/components/Marquee/index.d.ts.map +1 -0
  20. package/lib/types/components/Marquee/types.d.ts +53 -0
  21. package/lib/types/components/Marquee/types.d.ts.map +1 -0
  22. package/lib/types/components/index.d.ts +1 -0
  23. package/lib/types/components/index.d.ts.map +1 -1
  24. package/lib/types/version.d.ts +1 -1
  25. package/package.json +2 -1
  26. package/src/components/AnimationFrame/index.ts +1 -1
  27. package/src/components/AnimationFrame/types.ts +1 -1
  28. package/src/components/Marquee/index.ts +319 -0
  29. package/src/components/Marquee/stories/index.stories.tsx +27 -0
  30. package/src/components/Marquee/stories/index.tsx +69 -0
  31. package/src/components/Marquee/types.ts +55 -0
  32. package/src/components/index.ts +1 -0
  33. package/src/version.ts +1 -1
@@ -49,7 +49,7 @@ var AnimationFrame = /** @class */ (function (_super) {
49
49
  return _this;
50
50
  }
51
51
  AnimationFrame.prototype._getDefaultProps = function () {
52
- return __assign(__assign({}, _super.prototype._getDefaultProps.call(this)), { fps: 'auto', autoFpsFrames: 50, isEnabled: false });
52
+ return __assign(__assign({}, _super.prototype._getDefaultProps.call(this)), { fps: 'auto', autoFpsFrames: 10, isEnabled: false });
53
53
  };
54
54
  Object.defineProperty(AnimationFrame.prototype, "isPlaying", {
55
55
  get: function () {
@@ -0,0 +1,262 @@
1
+ "use strict";
2
+ var __extends = (this && this.__extends) || (function () {
3
+ var extendStatics = function (d, b) {
4
+ extendStatics = Object.setPrototypeOf ||
5
+ ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
6
+ function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };
7
+ return extendStatics(d, b);
8
+ };
9
+ return function (d, b) {
10
+ if (typeof b !== "function" && b !== null)
11
+ throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
12
+ extendStatics(d, b);
13
+ function __() { this.constructor = d; }
14
+ d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
15
+ };
16
+ })();
17
+ var __assign = (this && this.__assign) || function () {
18
+ __assign = Object.assign || function(t) {
19
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
20
+ s = arguments[i];
21
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
22
+ t[p] = s[p];
23
+ }
24
+ return t;
25
+ };
26
+ return __assign.apply(this, arguments);
27
+ };
28
+ Object.defineProperty(exports, "__esModule", { value: true });
29
+ exports.Marquee = void 0;
30
+ var vevet_dom_1 = require("vevet-dom");
31
+ var Component_1 = require("../../base/Component");
32
+ var math_1 = require("../../utils/math");
33
+ var onResize_1 = require("../../utils/listeners/onResize");
34
+ var AnimationFrame_1 = require("../AnimationFrame");
35
+ /**
36
+ * Custom Marquee
37
+ */
38
+ var Marquee = /** @class */ (function (_super) {
39
+ __extends(Marquee, _super);
40
+ function Marquee(initialProps, canInit) {
41
+ if (canInit === void 0) { canInit = true; }
42
+ var _this = _super.call(this, initialProps, false) || this;
43
+ _this._container = (0, vevet_dom_1.selectOne)(_this.props.container);
44
+ if (!(_this._container instanceof HTMLElement)) {
45
+ throw new Error('No container');
46
+ }
47
+ _this.toggleClassName(_this._container, _this.className(''), true);
48
+ _this._initialHTML = _this._container.innerHTML;
49
+ _this._quantity = 0;
50
+ _this._items = [];
51
+ _this._itemWidth = 0;
52
+ _this._xCoord = 0;
53
+ _this._canPlay = true;
54
+ _this.resize();
55
+ if (canInit) {
56
+ _this.init();
57
+ }
58
+ return _this;
59
+ }
60
+ Marquee.prototype._getDefaultProps = function () {
61
+ return __assign(__assign({}, _super.prototype._getDefaultProps.call(this)), { container: "#".concat(this.prefix), viewportTarget: 'width', resizeDebounce: 0, speed: 1, isEnabled: true, pauseOnHover: false, prependWhitespace: true, isFpsNormalized: true });
62
+ };
63
+ Object.defineProperty(Marquee.prototype, "prefix", {
64
+ get: function () {
65
+ return "".concat(this.app.prefix, "marquee");
66
+ },
67
+ enumerable: false,
68
+ configurable: true
69
+ });
70
+ Object.defineProperty(Marquee.prototype, "container", {
71
+ /** Marquee container */
72
+ get: function () {
73
+ return this._container;
74
+ },
75
+ enumerable: false,
76
+ configurable: true
77
+ });
78
+ /** Init the class */
79
+ Marquee.prototype._init = function () {
80
+ _super.prototype._init.call(this);
81
+ this._setEvents();
82
+ };
83
+ /** Handle properties mutation */
84
+ Marquee.prototype._onPropsMutate = function () {
85
+ var _a, _b;
86
+ _super.prototype._onPropsMutate.call(this);
87
+ if (this.props.isEnabled) {
88
+ (_a = this._animationFrame) === null || _a === void 0 ? void 0 : _a.play();
89
+ }
90
+ else {
91
+ (_b = this._animationFrame) === null || _b === void 0 ? void 0 : _b.pause();
92
+ }
93
+ };
94
+ /** Set module event */
95
+ Marquee.prototype._setEvents = function () {
96
+ var _this = this;
97
+ var _a = this, container = _a.container, props = _a.props;
98
+ var hasPauseOnHover = props.pauseOnHover, viewportTarget = props.viewportTarget, resizeDebounce = props.resizeDebounce;
99
+ // create animation frame
100
+ this._animationFrame = new AnimationFrame_1.AnimationFrame();
101
+ this._animationFrame.addCallback('frame', function () { return _this._render(); });
102
+ this.addDestroyableAction(function () { var _a; return (_a = _this._animationFrame) === null || _a === void 0 ? void 0 : _a.destroy(); });
103
+ // initial play
104
+ if (this.props.isEnabled) {
105
+ this._animationFrame.play();
106
+ }
107
+ // pause on hover
108
+ this.addEventListener(container, 'mouseenter', function () {
109
+ if (hasPauseOnHover) {
110
+ _this._canPlay = false;
111
+ }
112
+ });
113
+ // play on mouseleave
114
+ this.addEventListener(container, 'mouseleave', function () {
115
+ _this._canPlay = true;
116
+ });
117
+ // resize the scene
118
+ var resizeHandler = (0, onResize_1.onResize)({
119
+ onResize: function () { return _this.resize(); },
120
+ element: this.container,
121
+ viewportTarget: viewportTarget,
122
+ resizeDebounce: resizeDebounce,
123
+ hasBothEvents: true,
124
+ });
125
+ this.addDestroyableAction(function () { return resizeHandler.remove(); });
126
+ };
127
+ Marquee.prototype.resize = function () {
128
+ this._createItems();
129
+ };
130
+ Marquee.prototype._createItems = function () {
131
+ this._disconnectMutations();
132
+ var container = this.container;
133
+ // clear
134
+ this._quantity = 0;
135
+ this._items = [];
136
+ this.container.innerHTML = '';
137
+ // apply styles to the container
138
+ container.style.position = 'relative';
139
+ container.style.display = 'block';
140
+ container.style.width = '100%';
141
+ container.style.overflow = 'hidden';
142
+ container.style.whiteSpace = 'nowrap';
143
+ // create the first item and get its sizes
144
+ // to calculate the further quantity of inner elements
145
+ var firstItem = this._createItem(true);
146
+ // get first item width
147
+ var itemWidth = firstItem.clientWidth;
148
+ if (itemWidth <= 0) {
149
+ itemWidth = window.innerWidth;
150
+ }
151
+ this._itemWidth = itemWidth;
152
+ // get items quantity
153
+ if (itemWidth < container.clientWidth) {
154
+ this._quantity = Math.ceil((container.clientWidth + itemWidth) / itemWidth);
155
+ }
156
+ this._quantity = Math.max(this._quantity, 4);
157
+ // now when we know the total quantity,
158
+ // we can create the rest of the items
159
+ for (var index = 1; index < this._quantity; index += 1) {
160
+ this._createItem(false);
161
+ }
162
+ // render for the first time
163
+ this._render(0);
164
+ // enable mutation observer
165
+ this._observeMutations();
166
+ };
167
+ /** Create a single item */
168
+ Marquee.prototype._createItem = function (isFirst) {
169
+ if (isFirst === void 0) { isFirst = false; }
170
+ var element = document.createElement('div');
171
+ element.classList.add(this.className('__element'));
172
+ if (!isFirst) {
173
+ element.setAttribute('aria-hidden', 'true');
174
+ }
175
+ var prefix = "".concat(this.props.prependWhitespace ? '&nbsp;' : '');
176
+ var body = this._initialHTML;
177
+ element.innerHTML = "".concat(prefix).concat(body);
178
+ // apply styles
179
+ if (!isFirst) {
180
+ element.style.position = 'absolute';
181
+ element.style.top = '0';
182
+ element.style.left = '0';
183
+ }
184
+ element.style.display = 'inline-block';
185
+ // append the element
186
+ this.container.appendChild(element);
187
+ this._items.push(element);
188
+ return element;
189
+ };
190
+ /**
191
+ * Observe DOM changes
192
+ * If a change happens inside the parent element,
193
+ * we recreate the marquee element
194
+ */
195
+ Marquee.prototype._observeMutations = function () {
196
+ var _this = this;
197
+ if (this._mutationObserver) {
198
+ return;
199
+ }
200
+ var config = {
201
+ childList: true,
202
+ };
203
+ var callback = function (mutationsList) {
204
+ mutationsList.forEach(function (mutation) {
205
+ if (mutation.type === 'childList') {
206
+ _this._initialHTML = _this.container.innerHTML;
207
+ _this._createItems();
208
+ }
209
+ });
210
+ };
211
+ this._mutationObserver = new MutationObserver(callback);
212
+ this._mutationObserver.observe(this.container, config);
213
+ };
214
+ /**
215
+ * Destroy mutation observer
216
+ */
217
+ Marquee.prototype._disconnectMutations = function () {
218
+ var _a;
219
+ (_a = this._mutationObserver) === null || _a === void 0 ? void 0 : _a.disconnect();
220
+ this._mutationObserver = undefined;
221
+ };
222
+ /** Render marquee */
223
+ Marquee.prototype.render = function (speed) {
224
+ if (speed === void 0) { speed = this.props.speed; }
225
+ this._render(speed);
226
+ };
227
+ /** Render marquee */
228
+ Marquee.prototype._render = function (speedProp) {
229
+ var _a, _b;
230
+ if (!this._canPlay) {
231
+ return;
232
+ }
233
+ var _c = this, qunantity = _c._quantity, itemWidth = _c._itemWidth, props = _c.props;
234
+ var isFpsNormalized = props.isFpsNormalized;
235
+ var fpsMultiplier = isFpsNormalized
236
+ ? (_b = (_a = this._animationFrame) === null || _a === void 0 ? void 0 : _a.easeMultiplier) !== null && _b !== void 0 ? _b : 1
237
+ : 1;
238
+ var defaultSpeed = props.speed * fpsMultiplier;
239
+ var speed = speedProp !== null && speedProp !== void 0 ? speedProp : defaultSpeed;
240
+ this._xCoord -= speed;
241
+ // get total width
242
+ var totalWidth = itemWidth * (qunantity - 1);
243
+ // render elements
244
+ for (var index = 0; index < qunantity; index += 1) {
245
+ var element = this._items[index];
246
+ // calulate transforms
247
+ var x = (0, math_1.wrap)(-itemWidth, totalWidth, this._xCoord + itemWidth * index);
248
+ // apply transforms
249
+ element.style.transform = "matrix3d(1,0,0.00,0,0.00,1,0.00,0,0,0,1,0, ".concat(x, ", 0, 0,1)");
250
+ }
251
+ // callbacks
252
+ this.callbacks.tbt('render', undefined);
253
+ };
254
+ Marquee.prototype._destroy = function () {
255
+ _super.prototype._destroy.call(this);
256
+ this._disconnectMutations();
257
+ this.container.innerHTML = this._initialHTML;
258
+ };
259
+ return Marquee;
260
+ }(Component_1.Component));
261
+ exports.Marquee = Marquee;
262
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/components/Marquee/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../../src/components/Marquee/types.ts"],"names":[],"mappings":""}
@@ -21,6 +21,7 @@ __exportStar(require("./Ctx2DPrerender"), exports);
21
21
  __exportStar(require("./CustomCursor"), exports);
22
22
  __exportStar(require("./DraggerDirection"), exports);
23
23
  __exportStar(require("./DraggerMove"), exports);
24
+ __exportStar(require("./Marquee"), exports);
24
25
  __exportStar(require("./Preloader"), exports);
25
26
  __exportStar(require("./ProgressPreloader"), exports);
26
27
  __exportStar(require("./ScrollBar"), exports);
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,mDAAiC;AACjC,iDAA+B;AAC/B,0CAAwB;AACxB,mDAAiC;AACjC,iDAA+B;AAC/B,qDAAmC;AACnC,gDAA8B;AAC9B,8CAA4B;AAC5B,sDAAoC;AACpC,8CAA4B;AAC5B,+CAA6B;AAC7B,0DAAwC;AACxC,iDAA+B;AAC/B,2DAAyC;AACzC,+DAA6C;AAC7C,8CAA4B;AAC5B,6CAA2B"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,mDAAiC;AACjC,iDAA+B;AAC/B,0CAAwB;AACxB,mDAAiC;AACjC,iDAA+B;AAC/B,qDAAmC;AACnC,gDAA8B;AAC9B,4CAA0B;AAC1B,8CAA4B;AAC5B,sDAAoC;AACpC,8CAA4B;AAC5B,+CAA6B;AAC7B,0DAAwC;AACxC,iDAA+B;AAC/B,2DAAyC;AACzC,+DAA6C;AAC7C,8CAA4B;AAC5B,6CAA2B"}
@@ -1,5 +1,5 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- var version = '3.2.3';
3
+ var version = '3.3.0';
4
4
  exports.default = version;
5
5
  //# sourceMappingURL=version.js.map
@@ -4,7 +4,7 @@ import { Component as ComponentClass } from '../../base/Component';
4
4
  */
5
5
  export class AnimationFrame extends ComponentClass {
6
6
  _getDefaultProps() {
7
- return Object.assign(Object.assign({}, super._getDefaultProps()), { fps: 'auto', autoFpsFrames: 50, isEnabled: false });
7
+ return Object.assign(Object.assign({}, super._getDefaultProps()), { fps: 'auto', autoFpsFrames: 10, isEnabled: false });
8
8
  }
9
9
  get isPlaying() {
10
10
  return this._isPlaying;
@@ -0,0 +1,216 @@
1
+ import { selectOne } from 'vevet-dom';
2
+ import { Component as ComponentClass } from '../../base/Component';
3
+ import { wrap } from '../../utils/math';
4
+ import { onResize } from '../../utils/listeners/onResize';
5
+ import { AnimationFrame } from '../AnimationFrame';
6
+ /**
7
+ * Custom Marquee
8
+ */
9
+ export class Marquee extends ComponentClass {
10
+ _getDefaultProps() {
11
+ return Object.assign(Object.assign({}, super._getDefaultProps()), { container: `#${this.prefix}`, viewportTarget: 'width', resizeDebounce: 0, speed: 1, isEnabled: true, pauseOnHover: false, prependWhitespace: true, isFpsNormalized: true });
12
+ }
13
+ get prefix() {
14
+ return `${this.app.prefix}marquee`;
15
+ }
16
+ /** Marquee container */
17
+ get container() {
18
+ return this._container;
19
+ }
20
+ constructor(initialProps, canInit = true) {
21
+ super(initialProps, false);
22
+ this._container = selectOne(this.props.container);
23
+ if (!(this._container instanceof HTMLElement)) {
24
+ throw new Error('No container');
25
+ }
26
+ this.toggleClassName(this._container, this.className(''), true);
27
+ this._initialHTML = this._container.innerHTML;
28
+ this._quantity = 0;
29
+ this._items = [];
30
+ this._itemWidth = 0;
31
+ this._xCoord = 0;
32
+ this._canPlay = true;
33
+ this.resize();
34
+ if (canInit) {
35
+ this.init();
36
+ }
37
+ }
38
+ /** Init the class */
39
+ _init() {
40
+ super._init();
41
+ this._setEvents();
42
+ }
43
+ /** Handle properties mutation */
44
+ _onPropsMutate() {
45
+ var _a, _b;
46
+ super._onPropsMutate();
47
+ if (this.props.isEnabled) {
48
+ (_a = this._animationFrame) === null || _a === void 0 ? void 0 : _a.play();
49
+ }
50
+ else {
51
+ (_b = this._animationFrame) === null || _b === void 0 ? void 0 : _b.pause();
52
+ }
53
+ }
54
+ /** Set module event */
55
+ _setEvents() {
56
+ const { container, props } = this;
57
+ const { pauseOnHover: hasPauseOnHover, viewportTarget, resizeDebounce, } = props;
58
+ // create animation frame
59
+ this._animationFrame = new AnimationFrame();
60
+ this._animationFrame.addCallback('frame', () => this._render());
61
+ this.addDestroyableAction(() => { var _a; return (_a = this._animationFrame) === null || _a === void 0 ? void 0 : _a.destroy(); });
62
+ // initial play
63
+ if (this.props.isEnabled) {
64
+ this._animationFrame.play();
65
+ }
66
+ // pause on hover
67
+ this.addEventListener(container, 'mouseenter', () => {
68
+ if (hasPauseOnHover) {
69
+ this._canPlay = false;
70
+ }
71
+ });
72
+ // play on mouseleave
73
+ this.addEventListener(container, 'mouseleave', () => {
74
+ this._canPlay = true;
75
+ });
76
+ // resize the scene
77
+ const resizeHandler = onResize({
78
+ onResize: () => this.resize(),
79
+ element: this.container,
80
+ viewportTarget,
81
+ resizeDebounce,
82
+ hasBothEvents: true,
83
+ });
84
+ this.addDestroyableAction(() => resizeHandler.remove());
85
+ }
86
+ resize() {
87
+ this._createItems();
88
+ }
89
+ _createItems() {
90
+ this._disconnectMutations();
91
+ const { container } = this;
92
+ // clear
93
+ this._quantity = 0;
94
+ this._items = [];
95
+ this.container.innerHTML = '';
96
+ // apply styles to the container
97
+ container.style.position = 'relative';
98
+ container.style.display = 'block';
99
+ container.style.width = '100%';
100
+ container.style.overflow = 'hidden';
101
+ container.style.whiteSpace = 'nowrap';
102
+ // create the first item and get its sizes
103
+ // to calculate the further quantity of inner elements
104
+ const firstItem = this._createItem(true);
105
+ // get first item width
106
+ let itemWidth = firstItem.clientWidth;
107
+ if (itemWidth <= 0) {
108
+ itemWidth = window.innerWidth;
109
+ }
110
+ this._itemWidth = itemWidth;
111
+ // get items quantity
112
+ if (itemWidth < container.clientWidth) {
113
+ this._quantity = Math.ceil((container.clientWidth + itemWidth) / itemWidth);
114
+ }
115
+ this._quantity = Math.max(this._quantity, 4);
116
+ // now when we know the total quantity,
117
+ // we can create the rest of the items
118
+ for (let index = 1; index < this._quantity; index += 1) {
119
+ this._createItem(false);
120
+ }
121
+ // render for the first time
122
+ this._render(0);
123
+ // enable mutation observer
124
+ this._observeMutations();
125
+ }
126
+ /** Create a single item */
127
+ _createItem(isFirst = false) {
128
+ const element = document.createElement('div');
129
+ element.classList.add(this.className('__element'));
130
+ if (!isFirst) {
131
+ element.setAttribute('aria-hidden', 'true');
132
+ }
133
+ const prefix = `${this.props.prependWhitespace ? '&nbsp;' : ''}`;
134
+ const body = this._initialHTML;
135
+ element.innerHTML = `${prefix}${body}`;
136
+ // apply styles
137
+ if (!isFirst) {
138
+ element.style.position = 'absolute';
139
+ element.style.top = '0';
140
+ element.style.left = '0';
141
+ }
142
+ element.style.display = 'inline-block';
143
+ // append the element
144
+ this.container.appendChild(element);
145
+ this._items.push(element);
146
+ return element;
147
+ }
148
+ /**
149
+ * Observe DOM changes
150
+ * If a change happens inside the parent element,
151
+ * we recreate the marquee element
152
+ */
153
+ _observeMutations() {
154
+ if (this._mutationObserver) {
155
+ return;
156
+ }
157
+ const config = {
158
+ childList: true,
159
+ };
160
+ const callback = (mutationsList) => {
161
+ mutationsList.forEach((mutation) => {
162
+ if (mutation.type === 'childList') {
163
+ this._initialHTML = this.container.innerHTML;
164
+ this._createItems();
165
+ }
166
+ });
167
+ };
168
+ this._mutationObserver = new MutationObserver(callback);
169
+ this._mutationObserver.observe(this.container, config);
170
+ }
171
+ /**
172
+ * Destroy mutation observer
173
+ */
174
+ _disconnectMutations() {
175
+ var _a;
176
+ (_a = this._mutationObserver) === null || _a === void 0 ? void 0 : _a.disconnect();
177
+ this._mutationObserver = undefined;
178
+ }
179
+ /** Render marquee */
180
+ render(speed = this.props.speed) {
181
+ this._render(speed);
182
+ }
183
+ /** Render marquee */
184
+ _render(speedProp) {
185
+ var _a, _b;
186
+ if (!this._canPlay) {
187
+ return;
188
+ }
189
+ const { _quantity: qunantity, _itemWidth: itemWidth, props } = this;
190
+ const { isFpsNormalized } = props;
191
+ const fpsMultiplier = isFpsNormalized
192
+ ? (_b = (_a = this._animationFrame) === null || _a === void 0 ? void 0 : _a.easeMultiplier) !== null && _b !== void 0 ? _b : 1
193
+ : 1;
194
+ const defaultSpeed = props.speed * fpsMultiplier;
195
+ const speed = speedProp !== null && speedProp !== void 0 ? speedProp : defaultSpeed;
196
+ this._xCoord -= speed;
197
+ // get total width
198
+ const totalWidth = itemWidth * (qunantity - 1);
199
+ // render elements
200
+ for (let index = 0; index < qunantity; index += 1) {
201
+ const element = this._items[index];
202
+ // calulate transforms
203
+ const x = wrap(-itemWidth, totalWidth, this._xCoord + itemWidth * index);
204
+ // apply transforms
205
+ element.style.transform = `matrix3d(1,0,0.00,0,0.00,1,0.00,0,0,0,1,0, ${x}, 0, 0,1)`;
206
+ }
207
+ // callbacks
208
+ this.callbacks.tbt('render', undefined);
209
+ }
210
+ _destroy() {
211
+ super._destroy();
212
+ this._disconnectMutations();
213
+ this.container.innerHTML = this._initialHTML;
214
+ }
215
+ }
216
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/components/Marquee/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../../src/components/Marquee/types.ts"],"names":[],"mappings":""}
@@ -5,6 +5,7 @@ export * from './Ctx2DPrerender';
5
5
  export * from './CustomCursor';
6
6
  export * from './DraggerDirection';
7
7
  export * from './DraggerMove';
8
+ export * from './Marquee';
8
9
  export * from './Preloader';
9
10
  export * from './ProgressPreloader';
10
11
  export * from './ScrollBar';
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,SAAS,CAAC;AACxB,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,oBAAoB,CAAC;AACnC,cAAc,eAAe,CAAC;AAC9B,cAAc,aAAa,CAAC;AAC5B,cAAc,qBAAqB,CAAC;AACpC,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,yBAAyB,CAAC;AACxC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,0BAA0B,CAAC;AACzC,cAAc,8BAA8B,CAAC;AAC7C,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,SAAS,CAAC;AACxB,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,oBAAoB,CAAC;AACnC,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,aAAa,CAAC;AAC5B,cAAc,qBAAqB,CAAC;AACpC,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,yBAAyB,CAAC;AACxC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,0BAA0B,CAAC;AACzC,cAAc,8BAA8B,CAAC;AAC7C,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC"}
@@ -1,3 +1,3 @@
1
- const version = '3.2.3';
1
+ const version = '3.3.0';
2
2
  export default version;
3
3
  //# sourceMappingURL=version.js.map
@@ -10,7 +10,7 @@ export declare namespace NAnimationFrame {
10
10
  fps?: 'auto' | number;
11
11
  /**
12
12
  * How many frames to be tested to detect real FPS
13
- * @default 50
13
+ * @default 10
14
14
  */
15
15
  autoFpsFrames?: number;
16
16
  /**
@@ -0,0 +1,66 @@
1
+ import { NMarquee } from './types';
2
+ import { Component as ComponentClass } from '../../base/Component';
3
+ export type { NMarquee };
4
+ /**
5
+ * Custom Marquee
6
+ */
7
+ export declare class Marquee<StaticProps extends NMarquee.IStaticProps = NMarquee.IStaticProps, ChangeableProps extends NMarquee.IChangeableProps = NMarquee.IChangeableProps, CallbacksTypes extends NMarquee.ICallbacksTypes = NMarquee.ICallbacksTypes> extends ComponentClass<StaticProps, ChangeableProps, CallbacksTypes> {
8
+ protected _getDefaultProps(): import("ts-essentials").DeepRequired<StaticProps & ChangeableProps> & {
9
+ container: string;
10
+ viewportTarget: string;
11
+ resizeDebounce: number;
12
+ speed: number;
13
+ isEnabled: boolean;
14
+ pauseOnHover: boolean;
15
+ prependWhitespace: boolean;
16
+ isFpsNormalized: boolean;
17
+ };
18
+ get prefix(): string;
19
+ /** Marquee container */
20
+ protected _container: HTMLElement;
21
+ /** Marquee container */
22
+ get container(): HTMLElement;
23
+ /** Initial html */
24
+ protected _initialHTML: string;
25
+ /** Mutation observer */
26
+ protected _mutationObserver?: MutationObserver;
27
+ /** Items quantity */
28
+ protected _quantity: number;
29
+ /** Items */
30
+ protected _items: HTMLElement[];
31
+ /** Single item width */
32
+ protected _itemWidth: number;
33
+ /** X Coordinate */
34
+ protected _xCoord: number;
35
+ /** Can play */
36
+ protected _canPlay: boolean;
37
+ /** Animation frame */
38
+ private _animationFrame?;
39
+ constructor(initialProps?: StaticProps & ChangeableProps, canInit?: boolean);
40
+ /** Init the class */
41
+ protected _init(): void;
42
+ /** Handle properties mutation */
43
+ protected _onPropsMutate(): void;
44
+ /** Set module event */
45
+ protected _setEvents(): void;
46
+ resize(): void;
47
+ protected _createItems(): void;
48
+ /** Create a single item */
49
+ protected _createItem(isFirst?: boolean): HTMLDivElement;
50
+ /**
51
+ * Observe DOM changes
52
+ * If a change happens inside the parent element,
53
+ * we recreate the marquee element
54
+ */
55
+ protected _observeMutations(): void;
56
+ /**
57
+ * Destroy mutation observer
58
+ */
59
+ protected _disconnectMutations(): void;
60
+ /** Render marquee */
61
+ render(speed?: number): void;
62
+ /** Render marquee */
63
+ protected _render(speedProp?: number): void;
64
+ protected _destroy(): void;
65
+ }
66
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/components/Marquee/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AACnC,OAAO,EAAE,SAAS,IAAI,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAK/D,YAAY,EAAE,QAAQ,EAAE,CAAC;AAEzB;;GAEG;AACH,qBAAa,OAAO,CAClB,WAAW,SAAS,QAAQ,CAAC,YAAY,GAAG,QAAQ,CAAC,YAAY,EACjE,eAAe,SAAS,QAAQ,CAAC,gBAAgB,GAAG,QAAQ,CAAC,gBAAgB,EAC7E,cAAc,SAAS,QAAQ,CAAC,eAAe,GAAG,QAAQ,CAAC,eAAe,CAC1E,SAAQ,cAAc,CAAC,WAAW,EAAE,eAAe,EAAE,cAAc,CAAC;IACpE,SAAS,CAAC,gBAAgB;;;;;;;;;;IAc1B,IAAI,MAAM,WAET;IAED,wBAAwB;IACxB,SAAS,CAAC,UAAU,EAAE,WAAW,CAAC;IAElC,wBAAwB;IACxB,IAAI,SAAS,gBAEZ;IAED,mBAAmB;IACnB,SAAS,CAAC,YAAY,EAAE,MAAM,CAAC;IAE/B,wBAAwB;IACxB,SAAS,CAAC,iBAAiB,CAAC,EAAE,gBAAgB,CAAC;IAE/C,qBAAqB;IACrB,SAAS,CAAC,SAAS,EAAE,MAAM,CAAC;IAE5B,YAAY;IACZ,SAAS,CAAC,MAAM,EAAE,WAAW,EAAE,CAAC;IAEhC,wBAAwB;IACxB,SAAS,CAAC,UAAU,EAAE,MAAM,CAAC;IAE7B,mBAAmB;IACnB,SAAS,CAAC,OAAO,EAAE,MAAM,CAAC;IAE1B,eAAe;IACf,SAAS,CAAC,QAAQ,EAAE,OAAO,CAAC;IAE5B,sBAAsB;IACtB,OAAO,CAAC,eAAe,CAAC,CAAiB;gBAE7B,YAAY,CAAC,EAAE,WAAW,GAAG,eAAe,EAAE,OAAO,UAAO;IAwBxE,qBAAqB;IACrB,SAAS,CAAC,KAAK;IAMf,iCAAiC;IACjC,SAAS,CAAC,cAAc;IAUxB,uBAAuB;IACvB,SAAS,CAAC,UAAU;IAyCb,MAAM;IAIb,SAAS,CAAC,YAAY;IAiDtB,2BAA2B;IAC3B,SAAS,CAAC,WAAW,CAAC,OAAO,UAAQ;IA6BrC;;;;OAIG;IACH,SAAS,CAAC,iBAAiB;IAuB3B;;OAEG;IACH,SAAS,CAAC,oBAAoB;IAK9B,qBAAqB;IACd,MAAM,CAAC,KAAK,SAAmB;IAItC,qBAAqB;IACrB,SAAS,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE,MAAM;IAmCpC,SAAS,CAAC,QAAQ;CAOnB"}
@@ -0,0 +1,53 @@
1
+ import { NComponent } from '../../base/Component/types';
2
+ import { TOnResizeTarget } from '../../utils/listeners/onResize';
3
+ export declare namespace NMarquee {
4
+ interface IStaticProps extends NComponent.IStaticProps {
5
+ /**
6
+ * Marquee container. You may use a CSS selector or the element itself.
7
+ * @default '#v-marquee'
8
+ */
9
+ container?: string | HTMLElement;
10
+ /**
11
+ * Viewport target
12
+ * @default 'width'
13
+ */
14
+ viewportTarget?: TOnResizeTarget;
15
+ /**
16
+ * Timeout of resize event
17
+ * @default 0
18
+ */
19
+ resizeDebounce?: number;
20
+ }
21
+ interface IChangeableProps extends NComponent.IChangeableProps {
22
+ /**
23
+ * Marquee speed
24
+ * @default 1
25
+ */
26
+ speed?: number;
27
+ /**
28
+ * Enable animation
29
+ * @default true
30
+ */
31
+ isEnabled?: boolean;
32
+ /**
33
+ * Pause on hover
34
+ * @default false
35
+ */
36
+ pauseOnHover?: boolean;
37
+ /**
38
+ * Prepend a whitespace
39
+ * @default true
40
+ */
41
+ prependWhitespace?: boolean;
42
+ /**
43
+ * On different screens with different FPS, animation may be slower or faster.
44
+ * This property is to normalize animation speed across different screens.
45
+ * @default true
46
+ */
47
+ isFpsNormalized?: boolean;
48
+ }
49
+ interface ICallbacksTypes extends NComponent.ICallbacksTypes {
50
+ render: undefined;
51
+ }
52
+ }
53
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../src/components/Marquee/types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AACpD,OAAO,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAC;AAE7D,yBAAiB,QAAQ,CAAC;IACxB,UAAiB,YAAa,SAAQ,UAAU,CAAC,YAAY;QAC3D;;;WAGG;QACH,SAAS,CAAC,EAAE,MAAM,GAAG,WAAW,CAAC;QACjC;;;WAGG;QACH,cAAc,CAAC,EAAE,eAAe,CAAC;QACjC;;;WAGG;QACH,cAAc,CAAC,EAAE,MAAM,CAAC;KACzB;IAED,UAAiB,gBAAiB,SAAQ,UAAU,CAAC,gBAAgB;QACnE;;;WAGG;QACH,KAAK,CAAC,EAAE,MAAM,CAAC;QACf;;;WAGG;QACH,SAAS,CAAC,EAAE,OAAO,CAAC;QACpB;;;WAGG;QACH,YAAY,CAAC,EAAE,OAAO,CAAC;QACvB;;;WAGG;QACH,iBAAiB,CAAC,EAAE,OAAO,CAAC;QAC5B;;;;WAIG;QACH,eAAe,CAAC,EAAE,OAAO,CAAC;KAC3B;IAED,UAAiB,eAAgB,SAAQ,UAAU,CAAC,eAAe;QACjE,MAAM,EAAE,SAAS,CAAC;KACnB;CACF"}
@@ -5,6 +5,7 @@ export * from './Ctx2DPrerender';
5
5
  export * from './CustomCursor';
6
6
  export * from './DraggerDirection';
7
7
  export * from './DraggerMove';
8
+ export * from './Marquee';
8
9
  export * from './Preloader';
9
10
  export * from './ProgressPreloader';
10
11
  export * from './ScrollBar';
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,SAAS,CAAC;AACxB,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,oBAAoB,CAAC;AACnC,cAAc,eAAe,CAAC;AAC9B,cAAc,aAAa,CAAC;AAC5B,cAAc,qBAAqB,CAAC;AACpC,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,yBAAyB,CAAC;AACxC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,0BAA0B,CAAC;AACzC,cAAc,8BAA8B,CAAC;AAC7C,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,SAAS,CAAC;AACxB,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,oBAAoB,CAAC;AACnC,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,aAAa,CAAC;AAC5B,cAAc,qBAAqB,CAAC;AACpC,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,yBAAyB,CAAC;AACxC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,0BAA0B,CAAC;AACzC,cAAc,8BAA8B,CAAC;AAC7C,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC"}
@@ -1,3 +1,3 @@
1
- declare const version = "3.2.3";
1
+ declare const version = "3.3.0";
2
2
  export default version;
3
3
  //# sourceMappingURL=version.d.ts.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vevet",
3
- "version": "3.2.3",
3
+ "version": "3.3.0",
4
4
  "description": "Vevet - a JavaScript library of ready-made solutions and helpers",
5
5
  "scripts": {
6
6
  "storybook": "storybook dev -p 6006",
@@ -44,6 +44,7 @@
44
44
  "cursor",
45
45
  "drag",
46
46
  "swipe",
47
+ "marquee",
47
48
  "preloader",
48
49
  "scrollbar",
49
50
  "smooth scroll",
@@ -15,7 +15,7 @@ export class AnimationFrame<
15
15
  return {
16
16
  ...super._getDefaultProps(),
17
17
  fps: 'auto',
18
- autoFpsFrames: 50,
18
+ autoFpsFrames: 10,
19
19
  isEnabled: false,
20
20
  };
21
21
  }
@@ -11,7 +11,7 @@ export namespace NAnimationFrame {
11
11
  fps?: 'auto' | number;
12
12
  /**
13
13
  * How many frames to be tested to detect real FPS
14
- * @default 50
14
+ * @default 10
15
15
  */
16
16
  autoFpsFrames?: number;
17
17
  /**
@@ -0,0 +1,319 @@
1
+ import { selectOne } from 'vevet-dom';
2
+ import { NMarquee } from './types';
3
+ import { Component as ComponentClass } from '@/base/Component';
4
+ import { wrap } from '@/utils/math';
5
+ import { onResize } from '@/utils/listeners/onResize';
6
+ import { AnimationFrame } from '../AnimationFrame';
7
+
8
+ export type { NMarquee };
9
+
10
+ /**
11
+ * Custom Marquee
12
+ */
13
+ export class Marquee<
14
+ StaticProps extends NMarquee.IStaticProps = NMarquee.IStaticProps,
15
+ ChangeableProps extends NMarquee.IChangeableProps = NMarquee.IChangeableProps,
16
+ CallbacksTypes extends NMarquee.ICallbacksTypes = NMarquee.ICallbacksTypes
17
+ > extends ComponentClass<StaticProps, ChangeableProps, CallbacksTypes> {
18
+ protected _getDefaultProps() {
19
+ return {
20
+ ...super._getDefaultProps(),
21
+ container: `#${this.prefix}`,
22
+ viewportTarget: 'width',
23
+ resizeDebounce: 0,
24
+ speed: 1,
25
+ isEnabled: true,
26
+ pauseOnHover: false,
27
+ prependWhitespace: true,
28
+ isFpsNormalized: true,
29
+ };
30
+ }
31
+
32
+ get prefix() {
33
+ return `${this.app.prefix}marquee`;
34
+ }
35
+
36
+ /** Marquee container */
37
+ protected _container: HTMLElement;
38
+
39
+ /** Marquee container */
40
+ get container() {
41
+ return this._container;
42
+ }
43
+
44
+ /** Initial html */
45
+ protected _initialHTML: string;
46
+
47
+ /** Mutation observer */
48
+ protected _mutationObserver?: MutationObserver;
49
+
50
+ /** Items quantity */
51
+ protected _quantity: number;
52
+
53
+ /** Items */
54
+ protected _items: HTMLElement[];
55
+
56
+ /** Single item width */
57
+ protected _itemWidth: number;
58
+
59
+ /** X Coordinate */
60
+ protected _xCoord: number;
61
+
62
+ /** Can play */
63
+ protected _canPlay: boolean;
64
+
65
+ /** Animation frame */
66
+ private _animationFrame?: AnimationFrame;
67
+
68
+ constructor(initialProps?: StaticProps & ChangeableProps, canInit = true) {
69
+ super(initialProps, false);
70
+
71
+ this._container = selectOne(this.props.container)! as HTMLElement;
72
+ if (!(this._container instanceof HTMLElement)) {
73
+ throw new Error('No container');
74
+ }
75
+
76
+ this.toggleClassName(this._container, this.className(''), true);
77
+
78
+ this._initialHTML = this._container.innerHTML;
79
+ this._quantity = 0;
80
+ this._items = [];
81
+ this._itemWidth = 0;
82
+ this._xCoord = 0;
83
+ this._canPlay = true;
84
+
85
+ this.resize();
86
+
87
+ if (canInit) {
88
+ this.init();
89
+ }
90
+ }
91
+
92
+ /** Init the class */
93
+ protected _init() {
94
+ super._init();
95
+
96
+ this._setEvents();
97
+ }
98
+
99
+ /** Handle properties mutation */
100
+ protected _onPropsMutate() {
101
+ super._onPropsMutate();
102
+
103
+ if (this.props.isEnabled) {
104
+ this._animationFrame?.play();
105
+ } else {
106
+ this._animationFrame?.pause();
107
+ }
108
+ }
109
+
110
+ /** Set module event */
111
+ protected _setEvents() {
112
+ const { container, props } = this;
113
+ const {
114
+ pauseOnHover: hasPauseOnHover,
115
+ viewportTarget,
116
+ resizeDebounce,
117
+ } = props;
118
+
119
+ // create animation frame
120
+ this._animationFrame = new AnimationFrame();
121
+ this._animationFrame.addCallback('frame', () => this._render());
122
+ this.addDestroyableAction(() => this._animationFrame?.destroy());
123
+
124
+ // initial play
125
+ if (this.props.isEnabled) {
126
+ this._animationFrame.play();
127
+ }
128
+
129
+ // pause on hover
130
+ this.addEventListener(container, 'mouseenter', () => {
131
+ if (hasPauseOnHover) {
132
+ this._canPlay = false;
133
+ }
134
+ });
135
+
136
+ // play on mouseleave
137
+ this.addEventListener(container, 'mouseleave', () => {
138
+ this._canPlay = true;
139
+ });
140
+
141
+ // resize the scene
142
+ const resizeHandler = onResize({
143
+ onResize: () => this.resize(),
144
+ element: this.container,
145
+ viewportTarget,
146
+ resizeDebounce,
147
+ hasBothEvents: true,
148
+ });
149
+ this.addDestroyableAction(() => resizeHandler.remove());
150
+ }
151
+
152
+ public resize() {
153
+ this._createItems();
154
+ }
155
+
156
+ protected _createItems() {
157
+ this._disconnectMutations();
158
+
159
+ const { container } = this;
160
+
161
+ // clear
162
+ this._quantity = 0;
163
+ this._items = [];
164
+ this.container.innerHTML = '';
165
+
166
+ // apply styles to the container
167
+ container.style.position = 'relative';
168
+ container.style.display = 'block';
169
+ container.style.width = '100%';
170
+ container.style.overflow = 'hidden';
171
+ container.style.whiteSpace = 'nowrap';
172
+
173
+ // create the first item and get its sizes
174
+ // to calculate the further quantity of inner elements
175
+ const firstItem = this._createItem(true);
176
+
177
+ // get first item width
178
+ let itemWidth = firstItem.clientWidth;
179
+ if (itemWidth <= 0) {
180
+ itemWidth = window.innerWidth;
181
+ }
182
+ this._itemWidth = itemWidth;
183
+
184
+ // get items quantity
185
+ if (itemWidth < container.clientWidth) {
186
+ this._quantity = Math.ceil(
187
+ (container.clientWidth + itemWidth) / itemWidth
188
+ );
189
+ }
190
+ this._quantity = Math.max(this._quantity, 4);
191
+
192
+ // now when we know the total quantity,
193
+ // we can create the rest of the items
194
+ for (let index = 1; index < this._quantity; index += 1) {
195
+ this._createItem(false);
196
+ }
197
+
198
+ // render for the first time
199
+ this._render(0);
200
+
201
+ // enable mutation observer
202
+ this._observeMutations();
203
+ }
204
+
205
+ /** Create a single item */
206
+ protected _createItem(isFirst = false) {
207
+ const element = document.createElement('div');
208
+ element.classList.add(this.className('__element'));
209
+
210
+ if (!isFirst) {
211
+ element.setAttribute('aria-hidden', 'true');
212
+ }
213
+
214
+ const prefix = `${this.props.prependWhitespace ? '&nbsp;' : ''}`;
215
+ const body = this._initialHTML;
216
+
217
+ element.innerHTML = `${prefix}${body}`;
218
+
219
+ // apply styles
220
+ if (!isFirst) {
221
+ element.style.position = 'absolute';
222
+ element.style.top = '0';
223
+ element.style.left = '0';
224
+ }
225
+
226
+ element.style.display = 'inline-block';
227
+
228
+ // append the element
229
+ this.container.appendChild(element);
230
+ this._items.push(element);
231
+
232
+ return element;
233
+ }
234
+
235
+ /**
236
+ * Observe DOM changes
237
+ * If a change happens inside the parent element,
238
+ * we recreate the marquee element
239
+ */
240
+ protected _observeMutations() {
241
+ if (this._mutationObserver) {
242
+ return;
243
+ }
244
+
245
+ const config: MutationObserverInit = {
246
+ childList: true,
247
+ };
248
+
249
+ const callback: MutationCallback = (mutationsList) => {
250
+ mutationsList.forEach((mutation) => {
251
+ if (mutation.type === 'childList') {
252
+ this._initialHTML = this.container.innerHTML;
253
+
254
+ this._createItems();
255
+ }
256
+ });
257
+ };
258
+
259
+ this._mutationObserver = new MutationObserver(callback);
260
+ this._mutationObserver.observe(this.container, config);
261
+ }
262
+
263
+ /**
264
+ * Destroy mutation observer
265
+ */
266
+ protected _disconnectMutations() {
267
+ this._mutationObserver?.disconnect();
268
+ this._mutationObserver = undefined;
269
+ }
270
+
271
+ /** Render marquee */
272
+ public render(speed = this.props.speed) {
273
+ this._render(speed);
274
+ }
275
+
276
+ /** Render marquee */
277
+ protected _render(speedProp?: number) {
278
+ if (!this._canPlay) {
279
+ return;
280
+ }
281
+
282
+ const { _quantity: qunantity, _itemWidth: itemWidth, props } = this;
283
+ const { isFpsNormalized } = props;
284
+
285
+ const fpsMultiplier = isFpsNormalized
286
+ ? this._animationFrame?.easeMultiplier ?? 1
287
+ : 1;
288
+
289
+ const defaultSpeed = props.speed * fpsMultiplier;
290
+ const speed = speedProp ?? defaultSpeed;
291
+
292
+ this._xCoord -= speed;
293
+
294
+ // get total width
295
+ const totalWidth = itemWidth * (qunantity - 1);
296
+
297
+ // render elements
298
+ for (let index = 0; index < qunantity; index += 1) {
299
+ const element = this._items[index];
300
+
301
+ // calulate transforms
302
+ const x = wrap(-itemWidth, totalWidth, this._xCoord + itemWidth * index);
303
+
304
+ // apply transforms
305
+ element.style.transform = `matrix3d(1,0,0.00,0,0.00,1,0.00,0,0,0,1,0, ${x}, 0, 0,1)`;
306
+ }
307
+
308
+ // callbacks
309
+ this.callbacks.tbt('render', undefined);
310
+ }
311
+
312
+ protected _destroy() {
313
+ super._destroy();
314
+
315
+ this._disconnectMutations();
316
+
317
+ this.container.innerHTML = this._initialHTML;
318
+ }
319
+ }
@@ -0,0 +1,27 @@
1
+ import type { StoryObj, Meta } from '@storybook/react';
2
+ import { Component } from '.';
3
+
4
+ type TComponent = typeof Component;
5
+
6
+ const meta: Meta<TComponent> = {
7
+ title: 'Components/Marquee',
8
+ component: Component,
9
+ };
10
+
11
+ export default meta;
12
+
13
+ export const Default: StoryObj<TComponent> = {
14
+ args: {},
15
+ };
16
+
17
+ export const WithPauseOnHover: StoryObj<TComponent> = {
18
+ args: {
19
+ pauseOnHover: true,
20
+ },
21
+ };
22
+
23
+ export const WithReverseSpeed: StoryObj<TComponent> = {
24
+ args: {
25
+ speed: -1,
26
+ },
27
+ };
@@ -0,0 +1,69 @@
1
+ import React, { FC, useEffect, useRef, useState } from 'react';
2
+ import { Marquee, NMarquee } from '..';
3
+
4
+ interface IProps extends NMarquee.IChangeableProps {}
5
+
6
+ export const Component: FC<IProps> = ({
7
+ speed,
8
+ isEnabled,
9
+ pauseOnHover,
10
+ prependWhitespace,
11
+ isFpsNormalized,
12
+ }) => {
13
+ const ref = useRef<HTMLDivElement>(null);
14
+
15
+ const [width, setWidth] = useState(400);
16
+ const [marquee, setMarquee] = useState<Marquee | undefined>();
17
+
18
+ useEffect(() => {
19
+ if (!ref.current) {
20
+ return undefined;
21
+ }
22
+
23
+ const instance = new Marquee({
24
+ container: ref.current,
25
+ speed,
26
+ isEnabled,
27
+ pauseOnHover,
28
+ prependWhitespace,
29
+ isFpsNormalized,
30
+ });
31
+
32
+ setMarquee(instance);
33
+
34
+ return () => instance.destroy();
35
+ }, [isEnabled, isFpsNormalized, pauseOnHover, prependWhitespace, speed]);
36
+
37
+ return (
38
+ <>
39
+ <button type="button" onClick={() => setWidth((val) => val + 20)}>
40
+ Rezize
41
+ </button>
42
+
43
+ <button
44
+ type="button"
45
+ onClick={() => marquee?.changeProps({ isEnabled: true })}
46
+ >
47
+ Play
48
+ </button>
49
+
50
+ <button
51
+ type="button"
52
+ onClick={() => marquee?.changeProps({ isEnabled: false })}
53
+ >
54
+ Pause
55
+ </button>
56
+
57
+ <button type="button" onClick={() => marquee?.render()}>
58
+ Manual render
59
+ </button>
60
+
61
+ <br />
62
+ <br />
63
+
64
+ <div style={{ background: '#ccc', width }}>
65
+ <span ref={ref}>Marquee</span>
66
+ </div>
67
+ </>
68
+ );
69
+ };
@@ -0,0 +1,55 @@
1
+ import { NComponent } from '@/base/Component/types';
2
+ import { TOnResizeTarget } from '@/utils/listeners/onResize';
3
+
4
+ export namespace NMarquee {
5
+ export interface IStaticProps extends NComponent.IStaticProps {
6
+ /**
7
+ * Marquee container. You may use a CSS selector or the element itself.
8
+ * @default '#v-marquee'
9
+ */
10
+ container?: string | HTMLElement;
11
+ /**
12
+ * Viewport target
13
+ * @default 'width'
14
+ */
15
+ viewportTarget?: TOnResizeTarget;
16
+ /**
17
+ * Timeout of resize event
18
+ * @default 0
19
+ */
20
+ resizeDebounce?: number;
21
+ }
22
+
23
+ export interface IChangeableProps extends NComponent.IChangeableProps {
24
+ /**
25
+ * Marquee speed
26
+ * @default 1
27
+ */
28
+ speed?: number;
29
+ /**
30
+ * Enable animation
31
+ * @default true
32
+ */
33
+ isEnabled?: boolean;
34
+ /**
35
+ * Pause on hover
36
+ * @default false
37
+ */
38
+ pauseOnHover?: boolean;
39
+ /**
40
+ * Prepend a whitespace
41
+ * @default true
42
+ */
43
+ prependWhitespace?: boolean;
44
+ /**
45
+ * On different screens with different FPS, animation may be slower or faster.
46
+ * This property is to normalize animation speed across different screens.
47
+ * @default true
48
+ */
49
+ isFpsNormalized?: boolean;
50
+ }
51
+
52
+ export interface ICallbacksTypes extends NComponent.ICallbacksTypes {
53
+ render: undefined;
54
+ }
55
+ }
@@ -5,6 +5,7 @@ export * from './Ctx2DPrerender';
5
5
  export * from './CustomCursor';
6
6
  export * from './DraggerDirection';
7
7
  export * from './DraggerMove';
8
+ export * from './Marquee';
8
9
  export * from './Preloader';
9
10
  export * from './ProgressPreloader';
10
11
  export * from './ScrollBar';
package/src/version.ts CHANGED
@@ -1,2 +1,2 @@
1
- const version = '3.2.3';
1
+ const version = '3.3.0';
2
2
  export default version;