gclass-anims 1.0.0-beta.21 → 1.0.0-beta.22

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.
@@ -0,0 +1,3208 @@
1
+ import { gsap } from "gsap";
2
+ import { DrawSVGPlugin, Flip, MotionPathPlugin, ScrambleTextPlugin, ScrollTrigger, SplitText, TextPlugin } from "gsap/all";
3
+ //#region Config.js
4
+ var defaults = {
5
+ orderDivide: 5,
6
+ spawnDelayMultiplier: .2,
7
+ spawnOffset: 20,
8
+ clickOffset: 10,
9
+ clickExpandOffset: 15,
10
+ clickDuration: .2,
11
+ ease: "back",
12
+ effectDelay: .5,
13
+ effectDuration: 1,
14
+ effectOffset: 20,
15
+ progressStart: "top bottom",
16
+ progressEnd: "center center",
17
+ textStagger: .03,
18
+ typewriterSplitCharDuration: .05,
19
+ minTextPartDuration: .3,
20
+ revealDelay: 0,
21
+ characterlist: "AaBbCcDdEeFfGgHhIiJjKkLlMmNnOoPpQqRrSsTtUuVvWwXxYyZz",
22
+ bootTime: 5,
23
+ breakpoints: {
24
+ xs: 475,
25
+ s: 640,
26
+ m: 768,
27
+ l: 1024,
28
+ xl: 1280
29
+ }
30
+ };
31
+ var animations = [
32
+ {
33
+ sel: ".spawn-down",
34
+ from: {
35
+ opacity: 0,
36
+ y: -defaults.spawnOffset
37
+ },
38
+ play: (el, delay, dur, ease) => SpawnV(el, delay, -defaults.spawnOffset, dur, ease)
39
+ },
40
+ {
41
+ sel: ".spawn-up",
42
+ from: {
43
+ opacity: 0,
44
+ y: defaults.spawnOffset
45
+ },
46
+ play: (el, delay, dur, ease) => SpawnV(el, delay, defaults.spawnOffset, dur, ease)
47
+ },
48
+ {
49
+ sel: ".spawn-left",
50
+ from: {
51
+ opacity: 0,
52
+ x: -defaults.spawnOffset
53
+ },
54
+ play: (el, delay, dur, ease) => SpawnH(el, delay, -defaults.spawnOffset, dur, ease)
55
+ },
56
+ {
57
+ sel: ".spawn-right",
58
+ from: {
59
+ opacity: 0,
60
+ x: defaults.spawnOffset
61
+ },
62
+ play: (el, delay, dur, ease) => SpawnH(el, delay, defaults.spawnOffset, dur, ease)
63
+ },
64
+ {
65
+ sel: ".spawn-cw",
66
+ from: {
67
+ scale: 0,
68
+ rotation: -360
69
+ },
70
+ play: (el, delay, dur, ease) => spawnSpinCW(el, delay, dur, ease)
71
+ },
72
+ {
73
+ sel: ".spawn-ccw",
74
+ from: {
75
+ scale: 0,
76
+ rotation: 360
77
+ },
78
+ play: (el, delay, dur, ease) => spawnSpinCCW(el, delay, dur, ease)
79
+ },
80
+ {
81
+ sel: ".spawn-fade",
82
+ from: { opacity: 0 },
83
+ play: (el, delay, dur, ease) => spawnFade(el, delay, dur, ease)
84
+ },
85
+ {
86
+ sel: ".spawn-blur",
87
+ from: {
88
+ opacity: 0,
89
+ filter: "blur(20px)"
90
+ },
91
+ play: (el, delay, dur, ease) => spawnBlur(el, delay, dur, ease)
92
+ },
93
+ {
94
+ sel: ".spawn-x-down",
95
+ from: {
96
+ scale: 0,
97
+ rotationX: -360
98
+ },
99
+ play: (el, delay, dur, ease) => spawnXDown(el, delay, dur, ease)
100
+ },
101
+ {
102
+ sel: ".spawn-x-up",
103
+ from: {
104
+ scale: 0,
105
+ rotationX: 360
106
+ },
107
+ play: (el, delay, dur, ease) => spawnXUp(el, delay, dur, ease)
108
+ },
109
+ {
110
+ sel: ".spawn-y-right",
111
+ from: {
112
+ scale: 0,
113
+ rotationY: -360
114
+ },
115
+ play: (el, delay, dur, ease) => spawnYRight(el, delay, dur, ease)
116
+ },
117
+ {
118
+ sel: ".spawn-y-left",
119
+ from: {
120
+ scale: 0,
121
+ rotationY: 360
122
+ },
123
+ play: (el, delay, dur, ease) => spawnYLeft(el, delay, dur, ease)
124
+ },
125
+ {
126
+ sel: ".expand-vertical",
127
+ from: {
128
+ opacity: 0,
129
+ scaleY: 0
130
+ },
131
+ play: (el, delay, dur, ease) => expandV(el, delay, dur, ease)
132
+ },
133
+ {
134
+ sel: ".expand-horizontal",
135
+ from: {
136
+ opacity: 0,
137
+ scaleX: 0
138
+ },
139
+ play: (el, delay, dur, ease) => expandH(el, delay, dur, ease)
140
+ },
141
+ {
142
+ sel: ".expand-right",
143
+ from: {
144
+ opacity: 0,
145
+ scaleX: 0
146
+ },
147
+ play: (el, delay, dur, ease) => expandRight(el, delay, dur, ease)
148
+ },
149
+ {
150
+ sel: ".expand-left",
151
+ from: {
152
+ opacity: 0,
153
+ scaleX: 0
154
+ },
155
+ play: (el, delay, dur, ease) => expandLeft(el, delay, dur, ease)
156
+ },
157
+ {
158
+ sel: ".expand-up",
159
+ from: {
160
+ opacity: 0,
161
+ scaleY: 0
162
+ },
163
+ play: (el, delay, dur, ease) => expandUp(el, delay, dur, ease)
164
+ },
165
+ {
166
+ sel: ".expand-down",
167
+ from: {
168
+ opacity: 0,
169
+ scaleY: 0
170
+ },
171
+ play: (el, delay, dur, ease) => expandDown(el, delay, dur, ease)
172
+ },
173
+ {
174
+ sel: ".expand-all",
175
+ from: {
176
+ opacity: 0,
177
+ scale: 0
178
+ },
179
+ play: (el, delay, dur, ease) => expandA(el, delay, dur, ease)
180
+ },
181
+ {
182
+ sel: ".typewriter",
183
+ typewriter: true,
184
+ from: { text: "" },
185
+ play: (el, delay, dur, ease) => typewriter(el, stashText(el), dur, delay, ease)
186
+ },
187
+ {
188
+ sel: ".typewriter-split",
189
+ typewriter: true,
190
+ typewriterSplit: true,
191
+ from: { opacity: 0 },
192
+ play: (el, delay, dur, ease) => null
193
+ },
194
+ {
195
+ sel: ".scramble",
196
+ scramble: true,
197
+ text: false,
198
+ play: (el, delay, dur, ease) => scramble(el, delay, dur, ease)
199
+ },
200
+ {
201
+ sel: ".scramble-all",
202
+ scramble: true,
203
+ text: false,
204
+ play: (el, delay, dur, ease) => scramble(el, delay, dur, ease)
205
+ },
206
+ {
207
+ sel: ".count",
208
+ count: true,
209
+ text: false,
210
+ from: { opacity: 0 },
211
+ play: (el, delay, dur, ease) => countUp(el, delay, dur, ease)
212
+ },
213
+ {
214
+ sel: ".clip-reveal-up",
215
+ text: false,
216
+ from: { clipPath: "inset(0% 0% 100% 0%)" },
217
+ play: (el, delay, dur, ease) => spawnClipReveal(el, delay, dur, ease, "up")
218
+ },
219
+ {
220
+ sel: ".clip-reveal-down",
221
+ text: false,
222
+ from: { clipPath: "inset(100% 0% 0% 0%)" },
223
+ play: (el, delay, dur, ease) => spawnClipReveal(el, delay, dur, ease, "down")
224
+ },
225
+ {
226
+ sel: ".clip-reveal-left",
227
+ text: false,
228
+ from: { clipPath: "inset(0% 0% 0% 100%)" },
229
+ play: (el, delay, dur, ease) => spawnClipReveal(el, delay, dur, ease, "left")
230
+ },
231
+ {
232
+ sel: ".clip-reveal-right",
233
+ text: false,
234
+ from: { clipPath: "inset(0% 100% 0% 0%)" },
235
+ play: (el, delay, dur, ease) => spawnClipReveal(el, delay, dur, ease, "right")
236
+ },
237
+ {
238
+ sel: ".clip-reveal",
239
+ text: false,
240
+ from: { clipPath: "inset(0% 0% 100% 0%)" },
241
+ play: (el, delay, dur, ease) => spawnClipReveal(el, delay, dur, ease, "up")
242
+ },
243
+ {
244
+ sel: ".curtain-horizontal",
245
+ text: false,
246
+ from: { clipPath: "inset(0% 50% 0% 50%)" },
247
+ play: (el, delay, dur, ease) => curtainHorizontal(el, delay, dur, ease)
248
+ },
249
+ {
250
+ sel: ".curtain-vertical",
251
+ text: false,
252
+ from: { clipPath: "inset(50% 0% 50% 0%)" },
253
+ play: (el, delay, dur, ease) => curtainVertical(el, delay, dur, ease)
254
+ },
255
+ {
256
+ sel: ".draw",
257
+ text: false,
258
+ from: { drawSVG: "0%" },
259
+ play: (el, delay, dur, ease) => drawsvg(el, delay, dur, ease)
260
+ },
261
+ {
262
+ sel: ".draw-split",
263
+ text: false,
264
+ from: { drawSVG: "0%" },
265
+ play: (el, delay, dur, ease) => drawsvgSplit(el, delay, dur, ease)
266
+ },
267
+ {
268
+ sel: ".shake",
269
+ build: (el, { edelay, amount, etime, ease }) => shake(edelay, el, amount, etime, ease),
270
+ key: "shakeanim"
271
+ },
272
+ {
273
+ sel: ".spin-cw",
274
+ build: (el, { edelay, etime, ease }) => spinCW(el, edelay, etime, ease),
275
+ key: "spinCW"
276
+ },
277
+ {
278
+ sel: ".spin-ccw",
279
+ build: (el, { edelay, etime, ease }) => spinCCW(el, edelay, etime, ease),
280
+ key: "spinCW"
281
+ },
282
+ {
283
+ sel: ".bounce",
284
+ build: (el, { edelay, amount, etime, ease }) => bounce(edelay, el, amount, etime, ease),
285
+ key: "bounce"
286
+ },
287
+ {
288
+ sel: ".bell",
289
+ build: (el, { edelay, amount, etime, ease }) => bell(edelay, el, amount, etime, ease),
290
+ key: "bell"
291
+ },
292
+ {
293
+ sel: ".pulse",
294
+ build: (el, { edelay, amount, etime, ease }) => pulse(edelay, el, amount, etime, ease),
295
+ key: "pulse"
296
+ },
297
+ {
298
+ sel: ".radiate",
299
+ build: (el, { edelay, amount, etime, ease, radiateZ }) => radiate(edelay, el, amount, etime, ease, radiateZ),
300
+ key: "radiate"
301
+ },
302
+ {
303
+ sel: ".float",
304
+ build: (el, { edelay, amount, etime, ease }) => hover(edelay, el, amount, etime, ease),
305
+ key: "float"
306
+ },
307
+ {
308
+ sel: ".marquee-left",
309
+ build: (el, ctx) => marquee(el, "left", ctx.time, ctx.mH, ctx.mV, el.classList.contains("marquee-no-repeat")),
310
+ key: "marquee"
311
+ },
312
+ {
313
+ sel: ".marquee-right",
314
+ build: (el, ctx) => marquee(el, "right", ctx.time, ctx.mH, ctx.mV, el.classList.contains("marquee-no-repeat")),
315
+ key: "marquee"
316
+ },
317
+ {
318
+ sel: ".marquee-up",
319
+ build: (el, ctx) => marquee(el, "up", ctx.time, ctx.mH, ctx.mV, el.classList.contains("marquee-no-repeat")),
320
+ key: "marquee"
321
+ },
322
+ {
323
+ sel: ".marquee-down",
324
+ build: (el, ctx) => marquee(el, "down", ctx.time, ctx.mH, ctx.mV, el.classList.contains("marquee-no-repeat")),
325
+ key: "marquee"
326
+ }
327
+ ];
328
+ function normalize(extra = []) {
329
+ const all = animations.concat(extra);
330
+ return {
331
+ all,
332
+ spawnConfigs: all.filter((a) => a.play).map((a) => ({
333
+ sel: a.sel,
334
+ from: a.from,
335
+ play: a.play,
336
+ typewriter: a.typewriter,
337
+ typewriterSplit: a.typewriterSplit,
338
+ text: a.text !== false,
339
+ count: a.count,
340
+ scramble: a.scramble
341
+ })),
342
+ loopConfigs: all.filter((a) => a.build).map((a) => ({
343
+ sel: a.sel,
344
+ build: a.build,
345
+ key: a.key || a.sel.slice(1),
346
+ loop: a.loop !== false
347
+ }))
348
+ };
349
+ }
350
+ //#endregion
351
+ //#region Animations.js
352
+ gsap.registerPlugin(Flip);
353
+ gsap.registerPlugin(SplitText);
354
+ gsap.registerPlugin(TextPlugin);
355
+ gsap.registerPlugin(DrawSVGPlugin);
356
+ gsap.registerPlugin(MotionPathPlugin);
357
+ gsap.registerPlugin(ScrambleTextPlugin);
358
+ var getBpDataMod = () => {
359
+ const entries = Object.entries(defaults.breakpoints || {}).sort((a, b) => a[1] - b[1]);
360
+ const names = entries.map(([k]) => k);
361
+ return {
362
+ entries,
363
+ names,
364
+ map: Object.fromEntries(entries),
365
+ re: names.length ? new RegExp(`^(${names.join("|")}):(.+)$`) : /^$^/
366
+ };
367
+ };
368
+ var isBreakpointActiveMod = (bp) => {
369
+ if (!bp) return true;
370
+ const { map } = getBpDataMod();
371
+ const px = map[bp];
372
+ if (px == null) return true;
373
+ if (typeof window === "undefined" || !window.matchMedia) return true;
374
+ return window.matchMedia(`(min-width: ${px}px)`).matches;
375
+ };
376
+ var hasGClassMod = (el, name) => {
377
+ if (el.classList.contains(name)) return true;
378
+ const { names } = getBpDataMod();
379
+ for (const bp of names) if (el.classList.contains(`${bp}:${name}`) && isBreakpointActiveMod(bp)) return true;
380
+ return false;
381
+ };
382
+ var getActivePrefixedClassMod = (el, prefix) => {
383
+ const { names, map, re } = getBpDataMod();
384
+ let best = null, bestPx = -2;
385
+ for (const c of el.classList) {
386
+ let bp = null, core = c;
387
+ const m = c.match(re);
388
+ if (m) {
389
+ bp = m[1];
390
+ core = m[2];
391
+ }
392
+ if (!core.startsWith(prefix)) continue;
393
+ if (bp && !isBreakpointActiveMod(bp)) continue;
394
+ const px = bp ? map[bp] : -1;
395
+ if (px > bestPx) {
396
+ best = c;
397
+ bestPx = px;
398
+ }
399
+ }
400
+ return best;
401
+ };
402
+ var DEFAULT_EASE = "power3.out";
403
+ var easeOf = (e) => e || DEFAULT_EASE;
404
+ var finalOpacity = (target) => {
405
+ const had = target.style.opacity;
406
+ target.style.removeProperty("opacity");
407
+ const v = parseFloat(getComputedStyle(target).opacity);
408
+ if (had !== "") target.style.opacity = had;
409
+ return isNaN(v) ? 1 : v;
410
+ };
411
+ var stashText = (el) => {
412
+ const busy = (el.typewriter || el._spawnTween || el._scrollTween)?.isActive?.();
413
+ const html = el.innerHTML;
414
+ if (!busy && html && html.trim()) el._gcText = html;
415
+ return el._gcText !== void 0 ? el._gcText : html;
416
+ };
417
+ function SpawnV(target, delay, dir, dur, ease) {
418
+ const e = easeOf(ease);
419
+ return gsap.fromTo(target, {
420
+ opacity: 0,
421
+ y: dir,
422
+ scale: .97
423
+ }, {
424
+ ease: e,
425
+ duration: dur,
426
+ delay,
427
+ y: 0,
428
+ opacity: finalOpacity(target),
429
+ scale: 1
430
+ });
431
+ }
432
+ function SpawnH(target, delay, dir, dur, ease) {
433
+ const e = easeOf(ease);
434
+ return gsap.fromTo(target, {
435
+ opacity: 0,
436
+ x: dir,
437
+ scale: .97
438
+ }, {
439
+ ease: e,
440
+ duration: dur,
441
+ delay,
442
+ x: 0,
443
+ opacity: finalOpacity(target),
444
+ scale: 1
445
+ });
446
+ }
447
+ function expandV(target, delay, dur, ease) {
448
+ const e = easeOf(ease);
449
+ return gsap.fromTo(target, {
450
+ opacity: 1,
451
+ scaleY: 0
452
+ }, {
453
+ ease: e,
454
+ duration: dur,
455
+ delay,
456
+ scaleY: 1,
457
+ opacity: finalOpacity(target),
458
+ transformOrigin: "50% 50%"
459
+ });
460
+ }
461
+ function expandH(target, delay, dur, ease) {
462
+ const e = easeOf(ease);
463
+ return gsap.fromTo(target, {
464
+ opacity: 1,
465
+ scaleX: 0
466
+ }, {
467
+ ease: e,
468
+ duration: dur,
469
+ delay,
470
+ scaleX: 1,
471
+ opacity: finalOpacity(target),
472
+ transformOrigin: "50% 50%"
473
+ });
474
+ }
475
+ function expandA(target, delay, dur, ease) {
476
+ const e = easeOf(ease);
477
+ return gsap.fromTo(target, {
478
+ opacity: 1,
479
+ scale: 0
480
+ }, {
481
+ ease: e,
482
+ duration: dur,
483
+ delay,
484
+ scale: 1,
485
+ opacity: finalOpacity(target),
486
+ transformOrigin: "50% 50%"
487
+ });
488
+ }
489
+ function typewriter(target, text, dur, delay, ease) {
490
+ gsap.utils.toArray(target).forEach((el) => {
491
+ if (el.style) el.style.whiteSpace = "pre-wrap";
492
+ });
493
+ const value = String(text).replace(/\n/g, "<br>");
494
+ return gsap.fromTo(target, { text: "" }, {
495
+ ease: easeOf(ease),
496
+ duration: dur,
497
+ delay,
498
+ text: { value }
499
+ });
500
+ }
501
+ function spawnSpinCCW(target, delay, dur, ease) {
502
+ const e = easeOf(ease);
503
+ return gsap.fromTo(target, {
504
+ scale: 0,
505
+ rotation: -90
506
+ }, {
507
+ ease: e,
508
+ duration: dur,
509
+ delay,
510
+ scale: 1,
511
+ rotation: 0,
512
+ transformOrigin: "50% 50%"
513
+ });
514
+ }
515
+ function spawnSpinCW(target, delay, dur, ease) {
516
+ const e = easeOf(ease);
517
+ return gsap.fromTo(target, {
518
+ scale: 0,
519
+ rotation: 90
520
+ }, {
521
+ ease: e,
522
+ duration: dur,
523
+ delay,
524
+ scale: 1,
525
+ rotation: 0,
526
+ transformOrigin: "50% 50%"
527
+ });
528
+ }
529
+ function spawnFade(target, delay, dur, ease) {
530
+ return gsap.fromTo(target, { opacity: 0 }, {
531
+ ease: easeOf(ease),
532
+ duration: dur,
533
+ delay,
534
+ opacity: finalOpacity(target)
535
+ });
536
+ }
537
+ function spawnBlur(target, delay, dur, ease) {
538
+ const e = easeOf(ease);
539
+ return gsap.fromTo(target, {
540
+ opacity: 0,
541
+ filter: "blur(20px)"
542
+ }, {
543
+ ease: e,
544
+ duration: dur,
545
+ delay,
546
+ opacity: finalOpacity(target),
547
+ filter: "blur(0px)"
548
+ });
549
+ }
550
+ var CLIP_FROM = {
551
+ up: "inset(0% 0% 100% 0%)",
552
+ down: "inset(100% 0% 0% 0%)",
553
+ left: "inset(0% 0% 0% 100%)",
554
+ right: "inset(0% 100% 0% 0%)"
555
+ };
556
+ function spawnClipReveal(target, delay, dur, ease, dir = "up") {
557
+ const from = CLIP_FROM[dir] || CLIP_FROM.up;
558
+ return gsap.fromTo(target, { clipPath: from }, {
559
+ clipPath: "inset(0% 0% 0% 0%)",
560
+ ease: easeOf(ease),
561
+ duration: dur,
562
+ delay
563
+ });
564
+ }
565
+ function curtainHorizontal(target, delay, dur, ease) {
566
+ return gsap.fromTo(target, { clipPath: "inset(0% 50% 0% 50%)" }, {
567
+ clipPath: "inset(0% 0% 0% 0%)",
568
+ ease: easeOf(ease),
569
+ duration: dur,
570
+ delay
571
+ });
572
+ }
573
+ function curtainVertical(target, delay, dur, ease) {
574
+ return gsap.fromTo(target, { clipPath: "inset(50% 0% 50% 0%)" }, {
575
+ clipPath: "inset(0% 0% 0% 0%)",
576
+ ease: easeOf(ease),
577
+ duration: dur,
578
+ delay
579
+ });
580
+ }
581
+ function spawnXUp(target, delay, dur, ease) {
582
+ const e = easeOf(ease);
583
+ return gsap.fromTo(target, {
584
+ scale: 0,
585
+ rotationX: 360,
586
+ opacity: 0
587
+ }, {
588
+ ease: e,
589
+ duration: dur,
590
+ delay,
591
+ scale: 1,
592
+ rotationX: 0,
593
+ opacity: finalOpacity(target),
594
+ transformOrigin: "50% 50%"
595
+ });
596
+ }
597
+ function spawnXDown(target, delay, dur, ease) {
598
+ const e = easeOf(ease);
599
+ return gsap.fromTo(target, {
600
+ scale: 0,
601
+ rotationX: -360,
602
+ opacity: 0
603
+ }, {
604
+ ease: e,
605
+ duration: dur,
606
+ delay,
607
+ scale: 1,
608
+ rotationX: 0,
609
+ opacity: finalOpacity(target),
610
+ transformOrigin: "50% 50%"
611
+ });
612
+ }
613
+ function spawnYRight(target, delay, dur, ease) {
614
+ const e = easeOf(ease);
615
+ return gsap.fromTo(target, {
616
+ scale: 0,
617
+ rotationY: 360,
618
+ opacity: 0
619
+ }, {
620
+ ease: e,
621
+ duration: dur,
622
+ delay,
623
+ scale: 1,
624
+ rotationY: 0,
625
+ opacity: finalOpacity(target),
626
+ transformOrigin: "50% 50%"
627
+ });
628
+ }
629
+ function spawnYLeft(target, delay, dur, ease) {
630
+ const e = easeOf(ease);
631
+ return gsap.fromTo(target, {
632
+ scale: 0,
633
+ rotationY: -360,
634
+ opacity: 0
635
+ }, {
636
+ ease: e,
637
+ duration: dur,
638
+ delay,
639
+ scale: 1,
640
+ rotationY: 0,
641
+ opacity: finalOpacity(target),
642
+ transformOrigin: "50% 50%"
643
+ });
644
+ }
645
+ function expandRight(target, delay, dur, ease) {
646
+ const e = easeOf(ease);
647
+ const tl = gsap.timeline();
648
+ tl.set(target, { transformOrigin: "100% 50%" }).fromTo(target, {
649
+ opacity: 1,
650
+ scaleX: 0
651
+ }, {
652
+ ease: e,
653
+ duration: dur,
654
+ delay,
655
+ scaleX: 1,
656
+ opacity: finalOpacity(target)
657
+ });
658
+ return tl;
659
+ }
660
+ function expandLeft(target, delay, dur, ease) {
661
+ const e = easeOf(ease);
662
+ const tl = gsap.timeline();
663
+ tl.set(target, { transformOrigin: "0% 50%" }).fromTo(target, {
664
+ opacity: 1,
665
+ scaleX: 0
666
+ }, {
667
+ ease: e,
668
+ duration: dur,
669
+ delay,
670
+ scaleX: 1,
671
+ opacity: finalOpacity(target)
672
+ });
673
+ return tl;
674
+ }
675
+ function expandUp(target, delay, dur, ease) {
676
+ const e = easeOf(ease);
677
+ const tl = gsap.timeline();
678
+ tl.set(target, { transformOrigin: "50% 100%" }).fromTo(target, {
679
+ opacity: 1,
680
+ scaleY: 0
681
+ }, {
682
+ ease: e,
683
+ duration: dur,
684
+ delay,
685
+ scaleY: 1,
686
+ opacity: finalOpacity(target)
687
+ });
688
+ return tl;
689
+ }
690
+ function expandDown(target, delay, dur, ease) {
691
+ const e = easeOf(ease);
692
+ const tl = gsap.timeline();
693
+ tl.set(target, { transformOrigin: "50% 0%" }).fromTo(target, {
694
+ opacity: 1,
695
+ scaleY: 0
696
+ }, {
697
+ ease: e,
698
+ duration: dur,
699
+ delay,
700
+ scaleY: 1,
701
+ opacity: finalOpacity(target)
702
+ });
703
+ return tl;
704
+ }
705
+ function countTargetVars(target) {
706
+ if (target._countTarget) return target._countTarget;
707
+ const match = (target.textContent || "0").replace(/,/g, "").match(/-?\d+(?:\.\d+)?/);
708
+ const end = match ? parseFloat(match[0]) : 0;
709
+ const decimals = match?.[0].includes(".") ? (match[0].split(".")[1] || "").length : 0;
710
+ const startCls = getActivePrefixedClassMod(target, "spawn-num-");
711
+ return target._countTarget = {
712
+ start: startCls ? parseFloat(startCls.slice(startCls.indexOf("spawn-num-") + 10)) : 0,
713
+ end,
714
+ decimals
715
+ };
716
+ }
717
+ function countUp(target, delay, dur, ease) {
718
+ const e = easeOf(ease);
719
+ const { start, end, decimals } = countTargetVars(target);
720
+ const obj = { n: start };
721
+ return gsap.timeline({ delay }).fromTo(obj, { n: start }, {
722
+ n: end,
723
+ duration: dur,
724
+ ease: e,
725
+ onUpdate: () => {
726
+ target.textContent = obj.n.toFixed(decimals);
727
+ }
728
+ }, 0);
729
+ }
730
+ var fillTimeOf = (el, fallback) => {
731
+ const m = getActivePrefixedClassMod(el, "fill-time-");
732
+ return m ? Number(m.slice(m.indexOf("fill-time-") + 10)) : fallback * .5;
733
+ };
734
+ var fillEaseOf = (el, fallbackEase) => {
735
+ const m = getActivePrefixedClassMod(el, "fill-ease-");
736
+ return m ? m.slice(m.indexOf("fill-ease-") + 10) : fallbackEase;
737
+ };
738
+ function drawsvg(target, delay, dur, ease) {
739
+ const e = easeOf(ease);
740
+ const first = gsap.utils.toArray(target)[0];
741
+ if (!(!!first && hasGClassMod(first, "fill-svg"))) return gsap.fromTo(target, { drawSVG: "0%" }, {
742
+ ease: e,
743
+ duration: dur,
744
+ delay,
745
+ drawSVG: "100%"
746
+ });
747
+ const fillDur = fillTimeOf(first, dur);
748
+ const fillEase = fillEaseOf(first, ease);
749
+ const fillTargets = gsap.utils.toArray(target).filter((el) => hasGClassMod(el, "fill-svg"));
750
+ const tl = gsap.timeline({ delay });
751
+ if (fillTargets.length) gsap.set(fillTargets, { fillOpacity: 0 });
752
+ tl.fromTo(target, { drawSVG: "0%" }, {
753
+ ease: e,
754
+ duration: dur,
755
+ drawSVG: "100%"
756
+ });
757
+ if (fillTargets.length) tl.fromTo(fillTargets, { fillOpacity: 0 }, {
758
+ ease: easeOf(fillEase),
759
+ duration: fillDur,
760
+ fillOpacity: 1
761
+ });
762
+ return tl;
763
+ }
764
+ function splitPaths(paths) {
765
+ const toSplit = gsap.utils.toArray(paths);
766
+ let newPaths = [];
767
+ if (toSplit.length > 1) {
768
+ toSplit.forEach((path) => newPaths.push(...splitPaths(path)));
769
+ return newPaths;
770
+ }
771
+ const path = toSplit[0];
772
+ if (!path) return newPaths;
773
+ if (path._gcSplitPaths?.[0]?.isConnected) return path._gcSplitPaths;
774
+ const rawPath = MotionPathPlugin.getRawPath(path);
775
+ const parent = path.parentNode;
776
+ const attributes = [...path.attributes];
777
+ newPaths = rawPath.map((segment) => {
778
+ const newPath = document.createElementNS("http://www.w3.org/2000/svg", "path");
779
+ let i = attributes.length;
780
+ while (i--) {
781
+ const attr = attributes[i];
782
+ if (attr.nodeName === "class") {
783
+ const filtered = attr.nodeValue.split(/\s+/).filter((c) => c && c !== "appear" && c !== "scroll" && c !== "scroll-progress" && c !== "draw" && c !== "draw-split").join(" ");
784
+ if (filtered) newPath.setAttributeNS(null, "class", filtered);
785
+ continue;
786
+ }
787
+ if (attr.nodeName.startsWith("data-gsap")) continue;
788
+ newPath.setAttributeNS(null, attr.nodeName, attr.nodeValue);
789
+ }
790
+ newPath.setAttributeNS(null, "d", "M" + segment[0] + "," + segment[1] + "C" + segment.slice(2).join(",") + (segment.closed ? "z" : ""));
791
+ newPath.dataset.gsapSplit = "1";
792
+ newPath.style.contain = "paint";
793
+ newPath.style.willChange = "transform";
794
+ parent.insertBefore(newPath, path);
795
+ return newPath;
796
+ });
797
+ parent.removeChild(path);
798
+ return path._gcSplitPaths = newPaths;
799
+ }
800
+ function drawsvgSplit(target, delay, dur, ease) {
801
+ const e = easeOf(ease);
802
+ const first = gsap.utils.toArray(target)[0];
803
+ const hasFill = !!first && hasGClassMod(first, "fill-svg");
804
+ const fillDur = hasFill ? fillTimeOf(first, dur) : 0;
805
+ const fillEase = hasFill ? fillEaseOf(first, ease) : ease;
806
+ const tl = gsap.timeline({ delay });
807
+ const paths = splitPaths(target);
808
+ let distance = 0;
809
+ paths.forEach((segment) => distance += segment.getTotalLength());
810
+ if (!distance) return tl;
811
+ if (hasFill && paths.length) gsap.set(paths, { fillOpacity: 0 });
812
+ paths.forEach((segment) => {
813
+ tl.fromTo(segment, { drawSVG: "0%" }, {
814
+ ease: e,
815
+ duration: dur * (segment.getTotalLength() / distance),
816
+ drawSVG: "100%"
817
+ });
818
+ });
819
+ if (hasFill && paths.length) tl.fromTo(paths, { fillOpacity: 0 }, {
820
+ ease: easeOf(fillEase),
821
+ duration: fillDur,
822
+ fillOpacity: 1
823
+ });
824
+ return tl;
825
+ }
826
+ var scrambleSegments = (target) => {
827
+ let wraps = target._gcScrambleSegs;
828
+ if (!wraps || !wraps.length || !wraps.every((w) => w.parentNode === target)) {
829
+ wraps = [];
830
+ [...target.childNodes].forEach((node) => {
831
+ if (node.nodeType !== 3 || !node.textContent.trim()) return;
832
+ const raw = node.textContent;
833
+ const core = raw.trim();
834
+ const leadIdx = raw.indexOf(core[0]);
835
+ const trailStart = leadIdx + core.length;
836
+ const frag = document.createDocumentFragment();
837
+ if (leadIdx > 0) frag.appendChild(document.createTextNode(raw.slice(0, leadIdx)));
838
+ const span = document.createElement("span");
839
+ span.textContent = core;
840
+ frag.appendChild(span);
841
+ if (trailStart < raw.length) frag.appendChild(document.createTextNode(raw.slice(trailStart)));
842
+ target.insertBefore(frag, node);
843
+ target.removeChild(node);
844
+ wraps.push(span);
845
+ });
846
+ target._gcScrambleSegs = wraps;
847
+ }
848
+ return wraps.map((w) => ({
849
+ t: w,
850
+ text: w.textContent
851
+ }));
852
+ };
853
+ function scrambleVars(target) {
854
+ const num = (prefix, fallback) => {
855
+ const c = getActivePrefixedClassMod(target, prefix);
856
+ if (!c) return fallback;
857
+ const idx = c.indexOf(prefix);
858
+ const n = Number(c.slice(idx + prefix.length));
859
+ return Number.isNaN(n) ? fallback : n;
860
+ };
861
+ let charsCls = null;
862
+ let bestPx = -2;
863
+ const { re: reChars, map: mapChars } = getBpDataMod();
864
+ for (const c of target.classList) {
865
+ let bp = null, core = c;
866
+ const m = c.match(reChars);
867
+ if (m) {
868
+ bp = m[1];
869
+ core = m[2];
870
+ }
871
+ if (!/^chars-\[(.*)\]$/.test(core)) continue;
872
+ if (bp && !isBreakpointActiveMod(bp)) continue;
873
+ const px = bp ? mapChars[bp] : -1;
874
+ if (px > bestPx) {
875
+ charsCls = core;
876
+ bestPx = px;
877
+ }
878
+ }
879
+ return {
880
+ segs: scrambleSegments(target),
881
+ chars: charsCls ? charsCls.slice(7, -1) : defaults.characterlist,
882
+ speed: num("amount-", 1),
883
+ revealDelay: num("reveal-delay-", defaults.revealDelay),
884
+ rtl: hasGClassMod(target, "scramble-rtl")
885
+ };
886
+ }
887
+ function scramble(target, delay, dur, ease) {
888
+ const e = getActivePrefixedClassMod(target, "ease-") ? easeOf(ease) : "none";
889
+ const { segs, chars, speed, revealDelay, rtl } = scrambleVars(target);
890
+ const all = hasGClassMod(target, "scramble-all");
891
+ const tl = gsap.timeline({ delay });
892
+ segs.forEach(({ t, text }) => {
893
+ if (all) tl.to(t, {
894
+ scrambleText: {
895
+ text,
896
+ chars,
897
+ speed,
898
+ revealDelay,
899
+ rightToLeft: rtl
900
+ },
901
+ ease: e,
902
+ duration: dur
903
+ }, 0);
904
+ else tl.fromTo(t, { scrambleText: {
905
+ text: "",
906
+ chars
907
+ } }, {
908
+ scrambleText: {
909
+ text,
910
+ chars,
911
+ speed,
912
+ revealDelay,
913
+ rightToLeft: rtl
914
+ },
915
+ ease: e,
916
+ duration: dur
917
+ }, 0);
918
+ });
919
+ return tl;
920
+ }
921
+ function verticalmove(target, amount, dur, ease) {
922
+ const e = easeOf(ease);
923
+ return gsap.to(target, {
924
+ y: amount,
925
+ scale: 1 + amount / 1e3,
926
+ duration: dur,
927
+ ease: e
928
+ });
929
+ }
930
+ function expandmove(target, amount, dur, ease) {
931
+ return gsap.to(target, {
932
+ scale: amount / 10,
933
+ duration: dur,
934
+ ease: easeOf(ease)
935
+ });
936
+ }
937
+ function magnet(target, x, y, scale, dur, ease) {
938
+ return gsap.to(target, {
939
+ x,
940
+ y,
941
+ scale,
942
+ duration: dur,
943
+ ease: easeOf(ease),
944
+ overwrite: "auto"
945
+ });
946
+ }
947
+ function magnet3d(target, x, y, scale, rotX, rotY, dur, ease) {
948
+ return gsap.to(target, {
949
+ x,
950
+ y,
951
+ scale,
952
+ rotationX: rotX,
953
+ rotationY: rotY,
954
+ transformOrigin: "50% 50%",
955
+ transformPerspective: 600,
956
+ duration: dur,
957
+ ease: easeOf(ease),
958
+ overwrite: "auto"
959
+ });
960
+ }
961
+ function reset(target, dur, ease) {
962
+ gsap.to(target, {
963
+ x: 0,
964
+ y: 0,
965
+ scale: 1,
966
+ duration: dur / 2,
967
+ ease
968
+ });
969
+ }
970
+ function spinCW(target, delay, dur, ease) {
971
+ const e = easeOf(ease);
972
+ const tl = gsap.timeline();
973
+ tl.fromTo(target, {
974
+ scale: 1,
975
+ rotation: 0
976
+ }, {
977
+ ease: e,
978
+ duration: dur,
979
+ delay,
980
+ rotation: 360
981
+ }).to(target, {
982
+ scale: 1,
983
+ duration: delay
984
+ });
985
+ return tl;
986
+ }
987
+ function spinCCW(target, delay, dur, ease) {
988
+ const e = easeOf(ease);
989
+ const tl = gsap.timeline();
990
+ tl.fromTo(target, {
991
+ scale: 1,
992
+ rotation: 0
993
+ }, {
994
+ ease: e,
995
+ duration: dur,
996
+ delay,
997
+ rotation: -360
998
+ }).to(target, {
999
+ scale: 1,
1000
+ duration: delay
1001
+ });
1002
+ return tl;
1003
+ }
1004
+ function bounce(delay, target, amount, dur, ease) {
1005
+ const e = easeOf(ease);
1006
+ const tl = gsap.timeline();
1007
+ tl.set(target, { transformOrigin: "50% 100%" }).to(target, {
1008
+ y: -amount - amount * .25,
1009
+ scaleX: .97,
1010
+ scaleY: 1.03,
1011
+ duration: dur * .48,
1012
+ ease: "power1.out"
1013
+ }).to(target, {
1014
+ y: 0,
1015
+ scaleX: 1.08,
1016
+ scaleY: .88,
1017
+ duration: dur * .3,
1018
+ ease: "power2.in"
1019
+ }).to(target, {
1020
+ y: 0,
1021
+ scaleX: 1,
1022
+ scaleY: 1,
1023
+ duration: dur * .12,
1024
+ ease: e
1025
+ }).to(target, {
1026
+ x: 0,
1027
+ duration: delay
1028
+ });
1029
+ return tl;
1030
+ }
1031
+ function shake(delay, target, amount, dur, ease) {
1032
+ const tl = gsap.timeline();
1033
+ tl.to(target, {
1034
+ x: amount,
1035
+ duration: dur * .1,
1036
+ ease: "power2.out"
1037
+ }).to(target, {
1038
+ x: -amount * .8,
1039
+ duration: dur * .15,
1040
+ ease: "power2.inOut"
1041
+ }).to(target, {
1042
+ x: amount * .5,
1043
+ duration: dur * .2,
1044
+ ease: "power2.inOut"
1045
+ }).to(target, {
1046
+ x: -amount * .25,
1047
+ duration: dur * .2,
1048
+ ease: "power2.inOut"
1049
+ }).to(target, {
1050
+ x: 0,
1051
+ duration: dur * .2,
1052
+ ease: easeOf(ease)
1053
+ }).to(target, {
1054
+ x: 0,
1055
+ duration: delay
1056
+ });
1057
+ return tl;
1058
+ }
1059
+ function bell(delay, target, amount, dur, ease) {
1060
+ const tl = gsap.timeline();
1061
+ tl.set(target, { transformOrigin: "50% 0%" }).to(target, {
1062
+ rotate: amount,
1063
+ duration: dur * .12,
1064
+ ease: "power2.out"
1065
+ }).to(target, {
1066
+ rotate: -amount * .7,
1067
+ duration: dur * .18,
1068
+ ease: "power2.inOut"
1069
+ }).to(target, {
1070
+ rotate: amount * .4,
1071
+ duration: dur * .22,
1072
+ ease: "power2.inOut"
1073
+ }).to(target, {
1074
+ rotate: -amount * .15,
1075
+ duration: dur * .22,
1076
+ ease: "power2.inOut"
1077
+ }).to(target, {
1078
+ rotate: 0,
1079
+ duration: dur * .2,
1080
+ ease: easeOf(ease)
1081
+ }).to(target, {
1082
+ rotate: 0,
1083
+ duration: delay
1084
+ });
1085
+ return tl;
1086
+ }
1087
+ function pulse(delay, target, amount, dur, ease) {
1088
+ const e = easeOf(ease);
1089
+ const tl = gsap.timeline();
1090
+ tl.to(target, {
1091
+ scale: amount / 10 * 1.05,
1092
+ duration: dur * .35,
1093
+ ease: "power2.out"
1094
+ }).to(target, {
1095
+ scale: 1,
1096
+ duration: dur * .45,
1097
+ ease: e
1098
+ }).to(target, {
1099
+ scale: 1,
1100
+ duration: delay
1101
+ });
1102
+ return tl;
1103
+ }
1104
+ function radiate(delay, target, amount, dur, ease, zIndex) {
1105
+ const clone = target.cloneNode(true);
1106
+ clone.setAttribute("data-gsap-radiate", "1");
1107
+ clone.style.cssText = `position:fixed;left:0;top:0;right:auto;bottom:auto;margin:0;pointer-events:none;transform-origin:50% 50%;${zIndex != null ? `z-index:${zIndex};` : ""}`;
1108
+ let tick = false;
1109
+ const applyRect = () => {
1110
+ const r = target.getBoundingClientRect();
1111
+ clone.style.left = `${r.left}px`;
1112
+ clone.style.top = `${r.top}px`;
1113
+ clone.style.width = `${r.width}px`;
1114
+ clone.style.height = `${r.height}px`;
1115
+ };
1116
+ const schedule = () => {
1117
+ if (tick) return;
1118
+ tick = true;
1119
+ requestAnimationFrame(() => {
1120
+ tick = false;
1121
+ applyRect();
1122
+ });
1123
+ };
1124
+ if (!target.isConnected) return gsap.fromTo(clone, {}, { duration: 0 });
1125
+ document.body.appendChild(clone);
1126
+ applyRect();
1127
+ window.addEventListener("scroll", schedule, { passive: true });
1128
+ window.addEventListener("resize", schedule, { passive: true });
1129
+ let tween = null;
1130
+ const cleanup = () => {
1131
+ clone.remove();
1132
+ window.removeEventListener("scroll", schedule);
1133
+ window.removeEventListener("resize", schedule);
1134
+ if (observer) observer.disconnect();
1135
+ };
1136
+ const observer = new MutationObserver(() => {
1137
+ if (!target.isConnected) {
1138
+ if (tween) tween.kill();
1139
+ cleanup();
1140
+ }
1141
+ });
1142
+ observer.observe(document.body, {
1143
+ childList: true,
1144
+ subtree: true
1145
+ });
1146
+ tween = gsap.fromTo(clone, {
1147
+ scale: 1,
1148
+ opacity: 1
1149
+ }, {
1150
+ scale: amount / 10,
1151
+ opacity: 0,
1152
+ duration: dur,
1153
+ delay,
1154
+ ease: easeOf(ease),
1155
+ onComplete: () => {
1156
+ observer.disconnect();
1157
+ cleanup();
1158
+ },
1159
+ onInterrupt: () => {
1160
+ observer.disconnect();
1161
+ cleanup();
1162
+ }
1163
+ });
1164
+ return tween;
1165
+ }
1166
+ function hover(delay, target, amount, dur, ease) {
1167
+ const tl = gsap.timeline();
1168
+ tl.set(target, { transformOrigin: "50% 50%" }).to(target, {
1169
+ y: -amount,
1170
+ scaleX: .98,
1171
+ scaleY: 1.02,
1172
+ duration: dur / 2,
1173
+ ease: "sine.inOut"
1174
+ }).to(target, {
1175
+ y: 0,
1176
+ scaleX: 1,
1177
+ scaleY: 1,
1178
+ duration: dur / 2,
1179
+ ease: "sine.inOut"
1180
+ });
1181
+ return tl;
1182
+ }
1183
+ function marquee(target, dir, duration, xOffset = 0, yOffset = 0, noRepeat = false) {
1184
+ const horizontal = dir === "left" || dir === "right";
1185
+ target.style.position = "relative";
1186
+ target.style.overflow = "hidden";
1187
+ let track = target._gcTrack;
1188
+ if (!track || !track.isConnected) {
1189
+ track = document.createElement("div");
1190
+ track.style.cssText = `position:absolute;top:${yOffset}px;left:${xOffset}px;display:flex;flex-direction:${horizontal ? "row" : "column"};width:max-content;will-change:transform;`;
1191
+ while (target.firstChild) track.appendChild(target.firstChild);
1192
+ target.appendChild(track);
1193
+ while (track.children.length && [...track.children].every((c) => c.style.position === "absolute" && c.style.display === "flex")) {
1194
+ const inner = track.firstElementChild;
1195
+ while (inner.firstChild) track.insertBefore(inner.firstChild, inner);
1196
+ track.removeChild(inner);
1197
+ }
1198
+ target._gcUnitHtml = track.innerHTML;
1199
+ }
1200
+ track.style.flexDirection = horizontal ? "row" : "column";
1201
+ const unitHtml = target._gcUnitHtml;
1202
+ const measurer = document.createElement("div");
1203
+ measurer.style.cssText = track.style.cssText + "visibility:hidden;";
1204
+ measurer.innerHTML = unitHtml;
1205
+ target.appendChild(measurer);
1206
+ const unitSize = horizontal ? measurer.scrollWidth : measurer.scrollHeight;
1207
+ measurer.remove();
1208
+ if (!unitSize) return gsap.fromTo(track, {}, { duration: 0 });
1209
+ if (target.offsetHeight === 0 && track.offsetHeight > 0) target.style.height = track.offsetHeight + "px";
1210
+ let copies;
1211
+ if (noRepeat) copies = 2;
1212
+ else {
1213
+ const viewport = horizontal ? target.offsetWidth : target.offsetHeight;
1214
+ copies = Math.max(2, Math.ceil(viewport / unitSize) + 1);
1215
+ }
1216
+ track.innerHTML = unitHtml.repeat(copies);
1217
+ const dist = unitSize;
1218
+ const vars = {
1219
+ duration,
1220
+ ease: "none"
1221
+ };
1222
+ if (dir === "right") return gsap.fromTo(track, { x: -dist }, {
1223
+ x: 0,
1224
+ ...vars
1225
+ });
1226
+ if (dir === "up") return gsap.fromTo(track, { y: 0 }, {
1227
+ y: -dist,
1228
+ ...vars
1229
+ });
1230
+ if (dir === "down") return gsap.fromTo(track, { y: -dist }, {
1231
+ y: 0,
1232
+ ...vars
1233
+ });
1234
+ return gsap.fromTo(track, { x: 0 }, {
1235
+ x: -dist,
1236
+ ...vars
1237
+ });
1238
+ }
1239
+ function flip(state, ease, dur) {
1240
+ Flip.from(state, {
1241
+ duration: dur,
1242
+ ease: ease || DEFAULT_EASE
1243
+ });
1244
+ }
1245
+ function animatecss(target, dur, delay, ease, propertyS, propertySValue, propertyE, propertyEValue) {
1246
+ return gsap.fromTo(target, { [propertyS]: propertySValue }, {
1247
+ [propertyE]: propertyEValue,
1248
+ ease,
1249
+ duration: dur,
1250
+ delay
1251
+ });
1252
+ }
1253
+ //#endregion
1254
+ //#region CustomAnims.js
1255
+ var customAnims = [{
1256
+ sel: ".whirl",
1257
+ from: {
1258
+ opacity: 0,
1259
+ rotation: 90,
1260
+ scale: .7
1261
+ },
1262
+ play: (el, delay, dur, ease) => gsap.fromTo(el, {
1263
+ opacity: 0,
1264
+ rotation: 90,
1265
+ scale: .7
1266
+ }, {
1267
+ ease,
1268
+ duration: dur,
1269
+ delay,
1270
+ rotation: 0,
1271
+ scale: 1,
1272
+ opacity: 1,
1273
+ transformOrigin: "center"
1274
+ })
1275
+ }, {
1276
+ sel: ".bounce-in",
1277
+ from: {
1278
+ opacity: 0,
1279
+ scale: 0
1280
+ },
1281
+ play: (el, delay, dur, ease) => {
1282
+ const tl = gsap.timeline({
1283
+ delay,
1284
+ defaults: {
1285
+ ease,
1286
+ duration: dur / 3
1287
+ }
1288
+ });
1289
+ tl.fromTo(el, {
1290
+ scale: 0,
1291
+ opacity: 0
1292
+ }, {
1293
+ scale: 1.1,
1294
+ opacity: 1
1295
+ }).to(el, { scale: .95 }).to(el, { scale: 1 });
1296
+ return tl;
1297
+ }
1298
+ }];
1299
+ //#endregion
1300
+ //#region Listeners.js
1301
+ var TEXT_PREFIX = "spawn-text-";
1302
+ var TEXT_PREFIX_LEN = 11;
1303
+ var bpEntries = Object.entries(defaults.breakpoints || {}).sort((a, b) => a[1] - b[1]);
1304
+ var bpNames = bpEntries.map(([k]) => k);
1305
+ var bpMap = Object.fromEntries(bpEntries);
1306
+ var bpPrefixRE = bpNames.length ? new RegExp(`^(${bpNames.join("|")}):(.+)$`) : /^$^/;
1307
+ var isBreakpointActive = (bp) => {
1308
+ if (!bp) return true;
1309
+ const px = bpMap[bp];
1310
+ if (px == null) return true;
1311
+ if (typeof window === "undefined" || !window.matchMedia) return true;
1312
+ return window.matchMedia(`(min-width: ${px}px)`).matches;
1313
+ };
1314
+ var mqForBp = (bp) => `(min-width: ${bpMap[bp]}px)`;
1315
+ var elementMatchesSel = (el, sel) => {
1316
+ const base = sel.slice(1);
1317
+ if (el.classList.contains(base)) return true;
1318
+ for (const bp of bpNames) if (el.classList.contains(`${bp}:${base}`) && isBreakpointActive(bp)) return true;
1319
+ return false;
1320
+ };
1321
+ var hasGClass = (el, name) => {
1322
+ if (el.classList.contains(name)) return true;
1323
+ for (const bp of bpNames) if (el.classList.contains(`${bp}:${name}`) && isBreakpointActive(bp)) return true;
1324
+ return false;
1325
+ };
1326
+ var wrapQAll = (qAll) => (sel) => {
1327
+ if (sel.includes(",")) {
1328
+ const parts = sel.split(",").map((s) => s.trim()).filter(Boolean);
1329
+ const set = /* @__PURE__ */ new Set();
1330
+ parts.forEach((p) => wrapQAll(qAll)(p).forEach((e) => set.add(e)));
1331
+ return [...set];
1332
+ }
1333
+ if (sel === "body *") return qAll(sel);
1334
+ if (bpNames.some((bp) => sel.includes(`${bp}:`))) return qAll("body *").filter((el) => sel.split(",").some((s) => elementMatchesSel(el, s.trim())));
1335
+ try {
1336
+ const baseEls = qAll(sel);
1337
+ const variantEls = qAll("body *").filter((el) => {
1338
+ for (const bp of bpNames) if (el.classList.contains(`${bp}:${sel.slice(1)}`) && isBreakpointActive(bp)) return true;
1339
+ return false;
1340
+ });
1341
+ return [.../* @__PURE__ */ new Set([...baseEls, ...variantEls])];
1342
+ } catch {
1343
+ return qAll(sel);
1344
+ }
1345
+ };
1346
+ var completeHandlers = /* @__PURE__ */ new Map();
1347
+ function registerComplete(name, fn) {
1348
+ if (typeof fn === "function") completeHandlers.set(name, fn);
1349
+ return fn;
1350
+ }
1351
+ function resolveHandler(name) {
1352
+ if (completeHandlers.has(name)) return completeHandlers.get(name);
1353
+ if (typeof window !== "undefined" && typeof window[name] === "function") return window[name];
1354
+ return null;
1355
+ }
1356
+ var RANDOMIZE_RE = /^randomize-(\w+)-\[(-?[\d.]+)\]-\[(-?[\d.]+)\]$/;
1357
+ var hasRandom = (el) => typeof el.className === "string" && /\brandomize-/.test(el.className);
1358
+ var randomVars = (el) => {
1359
+ const rnd = {};
1360
+ for (const c of el.classList) {
1361
+ const m = c.match(RANDOMIZE_RE);
1362
+ if (m) rnd[m[1]] = () => gsap.utils.random(Number(m[2]), Number(m[3]));
1363
+ }
1364
+ return rnd;
1365
+ };
1366
+ var randomEnds = (keys) => Object.fromEntries(keys.map((k) => [k, k === "opacity" ? 1 : k === "filter" ? "blur(0px)" : k === "clipPath" ? "inset(0% 0% 0% 0%)" : k === "drawSVG" ? "100%" : k.startsWith("scale") ? 1 : 0]));
1367
+ var invokePlay = (config, el, delay, dur, ease) => {
1368
+ if (!hasRandom(el)) return config.play(el, delay, dur, ease);
1369
+ const rnd = randomVars(el);
1370
+ const keys = Object.keys(rnd);
1371
+ if (!keys.length) return config.play(el, delay, dur, ease);
1372
+ const ends = randomEnds(keys);
1373
+ const origFromTo = gsap.fromTo;
1374
+ gsap.fromTo = (t, from, to) => origFromTo(t, {
1375
+ ...from,
1376
+ ...rnd
1377
+ }, {
1378
+ ...ends,
1379
+ ...to
1380
+ });
1381
+ try {
1382
+ return config.play(el, delay, dur, ease);
1383
+ } finally {
1384
+ gsap.fromTo = origFromTo;
1385
+ }
1386
+ };
1387
+ function initListeners(root = document, throttlePerFrame) {
1388
+ if (typeof root === "number") {
1389
+ throttlePerFrame = root;
1390
+ root = document;
1391
+ }
1392
+ throttlePerFrame = Number(throttlePerFrame) || 0;
1393
+ gsap.registerPlugin(TextPlugin, ScrollTrigger, SplitText);
1394
+ const { all: animAll, spawnConfigs, loopConfigs } = normalize(customAnims);
1395
+ const qAll = (sel) => {
1396
+ if (root === document || root === document.documentElement || root === document.body) return gsap.utils.toArray(sel);
1397
+ if (sel === "body *") return gsap.utils.toArray(root.querySelectorAll("*"));
1398
+ try {
1399
+ const els = [...root.querySelectorAll ? root.querySelectorAll(sel) : []];
1400
+ if (root.matches?.(sel)) els.unshift(root);
1401
+ return els;
1402
+ } catch {
1403
+ return gsap.utils.toArray(sel);
1404
+ }
1405
+ };
1406
+ const mm = gsap.matchMedia();
1407
+ const breakpointContexts = [];
1408
+ const getGateBpForSel = (el, sel) => {
1409
+ const base = sel.slice(1);
1410
+ for (const bp of bpNames) if (el.classList.contains(`${bp}:${base}`)) return bp;
1411
+ return null;
1412
+ };
1413
+ const getElGateBp = (el) => {
1414
+ for (const c of el.classList) {
1415
+ const m = c.match(bpPrefixRE);
1416
+ if (m) return m[1];
1417
+ }
1418
+ return null;
1419
+ };
1420
+ const runWithBreakpoint = (el, fn) => {
1421
+ const bp = getElGateBp(el);
1422
+ if (!bp) {
1423
+ fn();
1424
+ return;
1425
+ }
1426
+ const mq = mqForBp(bp);
1427
+ const ret = mm.add(mq, fn);
1428
+ breakpointContexts.push(ret);
1429
+ };
1430
+ const runWithBreakpointForSel = (el, sel, fn) => {
1431
+ const bp = getGateBpForSel(el, sel);
1432
+ if (!bp) {
1433
+ fn();
1434
+ return;
1435
+ }
1436
+ const mq = mqForBp(bp);
1437
+ const ret = mm.add(mq, fn);
1438
+ breakpointContexts.push(ret);
1439
+ };
1440
+ const qAllAllVariants = (sel) => {
1441
+ const base = sel.slice(1);
1442
+ return qAll("body *").filter((el) => el.classList.contains(base) || bpNames.some((bp) => el.classList.contains(`${bp}:${base}`)));
1443
+ };
1444
+ const qAllActive = wrapQAll(qAll);
1445
+ const registeredListeners = [];
1446
+ const onCompleteTweens = [];
1447
+ const addListener = (el, type, fn) => {
1448
+ el.addEventListener(type, fn);
1449
+ registeredListeners.push({
1450
+ el,
1451
+ type,
1452
+ fn
1453
+ });
1454
+ };
1455
+ const getActivePrefixedClass = (el, prefix) => {
1456
+ let best = null;
1457
+ let bestPx = -2;
1458
+ for (const c of el.classList) {
1459
+ let bp = null;
1460
+ let core = c;
1461
+ const m = c.match(bpPrefixRE);
1462
+ if (m) {
1463
+ bp = m[1];
1464
+ core = m[2];
1465
+ }
1466
+ if (!core.startsWith(prefix)) continue;
1467
+ if (bp && !isBreakpointActive(bp)) continue;
1468
+ const px = bp ? bpMap[bp] : -1;
1469
+ if (px > bestPx) {
1470
+ best = c;
1471
+ bestPx = px;
1472
+ }
1473
+ }
1474
+ return best;
1475
+ };
1476
+ const extractNumber = (cls, prefix) => {
1477
+ const idx = cls.indexOf(prefix);
1478
+ if (idx === -1) return NaN;
1479
+ return Number(cls.slice(idx + prefix.length));
1480
+ };
1481
+ const readClassNumber = (el, prefix, fallback) => {
1482
+ const match = getActivePrefixedClass(el, prefix);
1483
+ if (!match) return fallback;
1484
+ const n = extractNumber(match, prefix);
1485
+ return Number.isNaN(n) ? fallback : n;
1486
+ };
1487
+ const getEase = (el) => {
1488
+ const match = getActivePrefixedClass(el, "ease-");
1489
+ if (!match) return defaults.ease;
1490
+ const idx = match.indexOf("ease-");
1491
+ return match.slice(idx + 5) || defaults.ease;
1492
+ };
1493
+ const reducedMotion = () => (typeof window !== "undefined" && window.matchMedia?.(`(prefers-reduced-motion: reduce)`)?.matches) ?? false;
1494
+ const isReduced = (el) => reducedMotion() && hasGClass(el, "reduced");
1495
+ const isPreserved = (el) => {
1496
+ if (!el.dataset.gsapWired) return false;
1497
+ for (let node = el; node && node.nodeType === 1; node = node.parentElement) if (node.classList.contains("preserve") && node.dataset.gsapPreserved) return true;
1498
+ return false;
1499
+ };
1500
+ const markPreserved = (el) => {
1501
+ for (let node = el; node && node.nodeType === 1; node = node.parentElement) if (node.classList.contains("preserve")) node.dataset.gsapPreserved = "1";
1502
+ };
1503
+ const underPreservedRoot = (el) => {
1504
+ for (let node = el; node && node.nodeType === 1; node = node.parentElement) if (node.classList.contains("preserve") && node.dataset.gsapPreserved) return true;
1505
+ return false;
1506
+ };
1507
+ const findSpawn = (el) => {
1508
+ const direct = spawnConfigs.find(({ sel }) => elementMatchesSel(el, sel));
1509
+ if (direct) return direct;
1510
+ for (const c of el.classList) {
1511
+ let base = c;
1512
+ let bp = null;
1513
+ const m = c.match(bpPrefixRE);
1514
+ if (m) {
1515
+ bp = m[1];
1516
+ base = m[2];
1517
+ }
1518
+ if (!base.startsWith(TEXT_PREFIX)) continue;
1519
+ if (bp && !isBreakpointActive(bp)) continue;
1520
+ const found = spawnConfigs.find(({ sel }) => sel === "." + base.slice(TEXT_PREFIX_LEN));
1521
+ if (found) return found;
1522
+ }
1523
+ return null;
1524
+ };
1525
+ const leaveStates = /* @__PURE__ */ new WeakMap();
1526
+ const captureLeave = (node) => {
1527
+ if (!hasGClass(node, "leave")) return;
1528
+ const config = findSpawn(node);
1529
+ if (!config || config.typewriter) return;
1530
+ leaveStates.set(node, {
1531
+ html: node.outerHTML,
1532
+ rect: node.getBoundingClientRect(),
1533
+ tween: node._spawnTween || node._scrollTween,
1534
+ from: config.from,
1535
+ ease: getEase(node),
1536
+ parent: node.parentNode,
1537
+ next: node.nextElementSibling,
1538
+ margin: getComputedStyle(node).margin,
1539
+ zIndex: getComputedStyle(node).zIndex
1540
+ });
1541
+ };
1542
+ const flipStates = /* @__PURE__ */ new WeakMap();
1543
+ const flipping = /* @__PURE__ */ new WeakSet();
1544
+ const flipPos = (node) => {
1545
+ const r = node.getBoundingClientRect();
1546
+ return {
1547
+ x: r.x + window.scrollX,
1548
+ y: r.y + window.scrollY,
1549
+ w: r.width,
1550
+ h: r.height
1551
+ };
1552
+ };
1553
+ const captureFlip = (node) => {
1554
+ if (!hasGClass(node, "flip")) return;
1555
+ const config = findSpawn(node);
1556
+ if (!config || config.typewriter) return;
1557
+ if (flipping.has(node)) return;
1558
+ flipStates.set(node, flipPos(node));
1559
+ };
1560
+ const playFlip = (node) => {
1561
+ if (node._flipTween) {
1562
+ node._flipTween.kill();
1563
+ node._flipTween = null;
1564
+ gsap.set(node, { clearProps: "transform" });
1565
+ flipping.delete(node);
1566
+ }
1567
+ const old = flipStates.get(node);
1568
+ const cur = flipPos(node);
1569
+ flipStates.set(node, cur);
1570
+ if (!old) return;
1571
+ const dx = Math.round(old.x - cur.x);
1572
+ const dy = Math.round(old.y - cur.y);
1573
+ if (!dx && !dy) return;
1574
+ flipping.add(node);
1575
+ node._flipTween = gsap.fromTo(node, {
1576
+ x: dx,
1577
+ y: dy
1578
+ }, {
1579
+ x: 0,
1580
+ y: 0,
1581
+ duration: readClassNumber(node, "time-", defaults.effectDuration),
1582
+ ease: getEase(node),
1583
+ onComplete: () => {
1584
+ flipping.delete(node);
1585
+ node._flipTween = null;
1586
+ }
1587
+ });
1588
+ };
1589
+ const playLeave = (node) => {
1590
+ const snap = leaveStates.get(node);
1591
+ leaveStates.delete(node);
1592
+ if (!snap || node._leaving) return;
1593
+ node._leaving = true;
1594
+ const placeSpacer = (snap) => {
1595
+ if (!snap.parent || snap.parent.nodeType !== 1) return null;
1596
+ const spacer = document.createElement("div");
1597
+ spacer.style.cssText = `box-sizing:border-box;width:${snap.rect.width}px;height:${snap.rect.height}px;`;
1598
+ if (snap.margin) spacer.style.margin = snap.margin;
1599
+ const next = snap.next && snap.next.parentNode === snap.parent ? snap.next : null;
1600
+ snap.parent.insertBefore(spacer, next);
1601
+ return spacer;
1602
+ };
1603
+ if (snap.tween) {
1604
+ const reattached = !node.isConnected;
1605
+ const spacer = reattached ? placeSpacer(snap) : null;
1606
+ if (reattached) {
1607
+ node.classList.remove("leave", "appear", "scroll", "scroll-progress");
1608
+ node.style.cssText = `position:fixed;z-index:${snap.zIndex};left:${snap.rect.left}px;top:${snap.rect.top}px;
1609
+ width:${snap.rect.width}px;height:${snap.rect.height}px;margin:0;`;
1610
+ document.body.appendChild(node);
1611
+ }
1612
+ snap.tween.reverse();
1613
+ snap.tween.eventCallback("onReverseComplete", () => {
1614
+ if (reattached) node.remove();
1615
+ else node.style.display = "none";
1616
+ spacer?.remove();
1617
+ });
1618
+ return;
1619
+ }
1620
+ const ghost = document.createElement("div");
1621
+ ghost.innerHTML = snap.html;
1622
+ const g = ghost.firstElementChild;
1623
+ g.classList.remove("leave", "appear", "scroll", "scroll-progress");
1624
+ g.style.cssText = `position:fixed;z-index:${snap.zIndex};left:${snap.rect.left}px;top:${snap.rect.top}px;
1625
+ width:${snap.rect.width}px;height:${snap.rect.height}px;margin:0;`;
1626
+ document.body.appendChild(g);
1627
+ const spacer = placeSpacer(snap);
1628
+ gsap.to(g, {
1629
+ ...snap.from,
1630
+ duration: defaults.effectDuration,
1631
+ ease: snap.ease || defaults.ease,
1632
+ onComplete: () => {
1633
+ g.remove();
1634
+ spacer?.remove();
1635
+ }
1636
+ });
1637
+ };
1638
+ const collectLeave = (node) => {
1639
+ if (!node || node.nodeType !== 1) return [];
1640
+ if (node.classList && hasGClass(node, "leave")) return [node];
1641
+ const found = gsap.utils.toArray(node.querySelectorAll?.(".leave") || []);
1642
+ qAll("body *").filter((el) => hasGClass(el, "leave") && node.contains?.(el) && !found.includes(el)).forEach((el) => found.push(el));
1643
+ if (hasGClass(node, "leave") && !found.includes(node)) found.unshift(node);
1644
+ return found;
1645
+ };
1646
+ const refreshLeaveRect = (el) => {
1647
+ const s = leaveStates.get(el);
1648
+ if (s) {
1649
+ s.rect = el.getBoundingClientRect();
1650
+ s.tween = el._spawnTween || el._scrollTween || s.tween;
1651
+ }
1652
+ };
1653
+ const orderSelector = () => spawnConfigs.map(({ sel }) => sel).join(",") + "," + spawnConfigs.map(({ sel }) => ".spawn-text-" + sel.slice(1)).join(",");
1654
+ const getOrderDelay = (el, priority) => {
1655
+ const samepri = qAllActive(orderSelector()).filter((e) => {
1656
+ if (!hasGClass(e, "order")) return false;
1657
+ const match = [...e.classList].find((p) => p.startsWith("priority-"));
1658
+ return (match ? Number(match.split("-")[1]) : 0) === priority;
1659
+ });
1660
+ let order = samepri.indexOf(el);
1661
+ if (hasGClass(el, "reverse")) order = samepri.length - 1 - order;
1662
+ return order / defaults.orderDivide;
1663
+ };
1664
+ const readTiming = (el) => {
1665
+ const priority = readClassNumber(el, "priority-", 0);
1666
+ return {
1667
+ delay: hasGClass(el, "order") ? getOrderDelay(el, priority) : priority * defaults.spawnDelayMultiplier,
1668
+ duration: readClassNumber(el, "time-", 1),
1669
+ ease: getEase(el)
1670
+ };
1671
+ };
1672
+ const playNamed = (el, name) => {
1673
+ const entry = animAll.find((a) => a.sel === "." + name);
1674
+ if (!entry) return;
1675
+ const delay = readClassNumber(el, "complete-delay-", 0);
1676
+ const dur = readClassNumber(el, "complete-time-", 1);
1677
+ const tween = entry.play ? invokePlay(entry, el, delay, dur, getEase(el)) : entry.build(el, readLoopCtx(el));
1678
+ if (!tween) return;
1679
+ if (!entry.play) tween.delay(delay);
1680
+ el[name] = tween;
1681
+ onCompleteTweens.push(tween);
1682
+ };
1683
+ const fireOnComplete = (el, kind) => {
1684
+ const prefix = `on-${kind}-complete-`;
1685
+ const cls = [...el.classList].find((c) => c.startsWith(prefix));
1686
+ if (!cls) return;
1687
+ const val = cls.slice(prefix.length);
1688
+ if (val.startsWith("anim-")) playNamed(el, val.slice(5));
1689
+ else {
1690
+ const fn = resolveHandler(val);
1691
+ if (fn) fn(el);
1692
+ }
1693
+ };
1694
+ const scrollTriggers = [];
1695
+ const computeTo = (from) => {
1696
+ const to = {};
1697
+ for (const [key] of Object.entries(from || {})) if (key === "opacity") to[key] = 1;
1698
+ else if (key === "filter") to[key] = "blur(0px)";
1699
+ else if (key === "clipPath") to[key] = "inset(0% 0% 0% 0%)";
1700
+ else if (key === "drawSVG") to[key] = "100%";
1701
+ else to[key] = key.startsWith("scale") ? 1 : 0;
1702
+ return to;
1703
+ };
1704
+ const textSplits = [];
1705
+ const splitCache = /* @__PURE__ */ new WeakMap();
1706
+ const RTL_RE = /[\u0590-\u08FF\uFB50-\uFDFF\uFE70-\uFEFF]/;
1707
+ const isRTLText = (el) => RTL_RE.test(el.textContent || "");
1708
+ const getGranularity = (el) => {
1709
+ if (hasGClass(el, "lines")) return "lines";
1710
+ if (hasGClass(el, "words")) return "words";
1711
+ if (hasGClass(el, "letter")) return "chars";
1712
+ return "words";
1713
+ };
1714
+ const RTL_NON_JOINABLE = /[اأإآدذرزوؤءة]/;
1715
+ const RTL_DIACRITICS = /[\u064B-\u065F\u0670]/g;
1716
+ const RTL_JOIN_BREAK = /[\u200C\u200D\s]/;
1717
+ const RTL_LETTER = /[\u0621-\u064A\u066E-\u06D5\u0750-\u077F\u08A0-\u08FF\uFB50-\uFDFF\uFE70-\uFEFF]/;
1718
+ const getRTLCharSplit = (el) => new SplitText(el, {
1719
+ type: "words",
1720
+ linesClass: "gsap-line",
1721
+ wordsClass: "gsap-word",
1722
+ charsClass: "gsap-char",
1723
+ onSplit(self) {
1724
+ const ZWJ = "‍";
1725
+ const connects = (s) => !RTL_NON_JOINABLE.test(s.replace(RTL_DIACRITICS, "").slice(-1));
1726
+ self.chars.length = 0;
1727
+ self.words.forEach((wordEl) => {
1728
+ const chars = Array.from(wordEl.textContent);
1729
+ const segs = [];
1730
+ let i = 0;
1731
+ while (i < chars.length) {
1732
+ const c = chars[i];
1733
+ if (RTL_JOIN_BREAK.test(c)) {
1734
+ segs.push({
1735
+ text: c,
1736
+ brk: true
1737
+ });
1738
+ i++;
1739
+ continue;
1740
+ }
1741
+ if (!RTL_LETTER.test(c)) {
1742
+ segs.push({
1743
+ text: c,
1744
+ brk: false,
1745
+ letter: false
1746
+ });
1747
+ i++;
1748
+ continue;
1749
+ }
1750
+ let g = c;
1751
+ if (c === "ل" && i + 1 < chars.length) {
1752
+ let j = i + 1;
1753
+ let d = "";
1754
+ while (j < chars.length && RTL_DIACRITICS.test(chars[j])) d += chars[j++];
1755
+ if (j < chars.length && /[\u0622\u0623\u0625\u0627]/.test(chars[j])) {
1756
+ g += d + chars[j];
1757
+ i = j;
1758
+ }
1759
+ }
1760
+ while (i + 1 < chars.length && RTL_DIACRITICS.test(chars[i + 1])) {
1761
+ g += chars[i + 1];
1762
+ i++;
1763
+ }
1764
+ i++;
1765
+ segs.push({
1766
+ text: g,
1767
+ brk: false,
1768
+ letter: true
1769
+ });
1770
+ }
1771
+ wordEl.textContent = "";
1772
+ let prevConnectable = false;
1773
+ segs.forEach((seg, si) => {
1774
+ if (seg.brk) {
1775
+ wordEl.appendChild(document.createTextNode(seg.text));
1776
+ prevConnectable = false;
1777
+ return;
1778
+ }
1779
+ if (!seg.letter) {
1780
+ const pEl = document.createElement("div");
1781
+ pEl.style.display = "inline-block";
1782
+ pEl.className = "gsap-char";
1783
+ pEl.textContent = seg.text;
1784
+ wordEl.appendChild(pEl);
1785
+ self.chars.push(pEl);
1786
+ prevConnectable = false;
1787
+ return;
1788
+ }
1789
+ const connectable = connects(seg.text);
1790
+ let s = seg.text;
1791
+ if (prevConnectable) s = ZWJ + s;
1792
+ if (si + 1 < segs.length && segs[si + 1].letter && connectable) s += ZWJ;
1793
+ const charEl = document.createElement("div");
1794
+ charEl.style.display = "inline-block";
1795
+ charEl.className = "gsap-char";
1796
+ charEl.textContent = s;
1797
+ wordEl.appendChild(charEl);
1798
+ self.chars.push(charEl);
1799
+ prevConnectable = connectable;
1800
+ });
1801
+ });
1802
+ self.words.forEach((w) => w.replaceWith(...w.childNodes));
1803
+ self.words.length = 0;
1804
+ }
1805
+ });
1806
+ const wrapFlexTarget = (el) => {
1807
+ if (!/^(inline-)?flex$/.test(getComputedStyle(el).display)) return null;
1808
+ const wrappers = [];
1809
+ let run = [];
1810
+ const flush = () => {
1811
+ if (!run.length) return;
1812
+ const w = document.createElement("div");
1813
+ el.insertBefore(w, run[0]);
1814
+ run.forEach((n) => w.appendChild(n));
1815
+ wrappers.push(w);
1816
+ run = [];
1817
+ };
1818
+ [...el.childNodes].forEach((n) => {
1819
+ if (n.nodeType === 3 && n.textContent.trim()) run.push(n);
1820
+ else flush();
1821
+ });
1822
+ flush();
1823
+ if (!wrappers.length) return null;
1824
+ return () => wrappers.forEach((w) => {
1825
+ while (w.firstChild) el.insertBefore(w.firstChild, w);
1826
+ w.remove();
1827
+ });
1828
+ };
1829
+ const revertSplitInstance = (s) => {
1830
+ s.revert();
1831
+ s._gcFlexUnwrap?.();
1832
+ };
1833
+ const getSplit = (el, gran) => {
1834
+ let s = splitCache.get(el);
1835
+ const rtlChars = gran === "chars" && isRTLText(el);
1836
+ const key = rtlChars ? "rtl-chars" : gran;
1837
+ if (!s || s.granularity !== key) {
1838
+ if (s) revertSplitInstance(s);
1839
+ const hasN = el.textContent.includes("\n");
1840
+ if (hasN && el.style) el.style.whiteSpace = "pre-wrap";
1841
+ s = rtlChars ? getRTLCharSplit(el) : new SplitText(el, {
1842
+ type: gran,
1843
+ reduceWhiteSpace: hasN ? false : void 0,
1844
+ linesClass: "gsap-line",
1845
+ wordsClass: "gsap-word",
1846
+ charsClass: "gsap-char",
1847
+ onSplit(self) {
1848
+ for (const c of self.chars || []) if (c.textContent === "\n") {
1849
+ c.textContent = "";
1850
+ c.style.display = "block";
1851
+ c.style.width = "100%";
1852
+ c.style.height = "0";
1853
+ }
1854
+ for (const w of self.words || []) if (w.textContent.includes("\n")) w.style.whiteSpace = "pre-wrap";
1855
+ }
1856
+ });
1857
+ s._gcFlexUnwrap = wrapFlexTarget(el);
1858
+ s.granularity = key;
1859
+ splitCache.set(el, s);
1860
+ textSplits.push(s);
1861
+ }
1862
+ return s;
1863
+ };
1864
+ const getParts = (el, gran) => {
1865
+ const s = getSplit(el, gran);
1866
+ const parts = gran === "chars" && isRTLText(el) ? s.chars || [] : s[gran] || [];
1867
+ for (let i = 0; i < parts.length; i++) {
1868
+ parts[i].style.willChange = "transform, opacity";
1869
+ if (gran === "chars" || gran === "words") parts[i].style.display = "inline-block";
1870
+ }
1871
+ return parts;
1872
+ };
1873
+ const revertSplit = (el) => {
1874
+ if (hasGClass(el, "no-revert")) return;
1875
+ const s = splitCache.get(el);
1876
+ if (!s) return;
1877
+ splitCache.delete(el);
1878
+ const idx = textSplits.indexOf(s);
1879
+ if (idx !== -1) textSplits.splice(idx, 1);
1880
+ revertSplitInstance(s);
1881
+ };
1882
+ const playText = (el, from, delay, dur, ease) => {
1883
+ const gran = getGranularity(el);
1884
+ const parts = getParts(el, gran);
1885
+ if (!parts.length) return;
1886
+ const requestedStagger = readClassNumber(el, "stagger-", null);
1887
+ let stagger, duration;
1888
+ if (requestedStagger != null) {
1889
+ stagger = requestedStagger;
1890
+ duration = Math.max(dur - stagger * (parts.length - 1), defaults.minTextPartDuration);
1891
+ } else {
1892
+ duration = Math.min(dur, Math.max(dur / 3, defaults.minTextPartDuration));
1893
+ stagger = parts.length > 1 ? (dur - duration) / (parts.length - 1) : 0;
1894
+ }
1895
+ let rnd = null;
1896
+ if (hasRandom(el)) {
1897
+ rnd = randomVars(el);
1898
+ if (!Object.keys(rnd).length) rnd = null;
1899
+ }
1900
+ const effFrom = {
1901
+ ...from,
1902
+ ...rnd
1903
+ };
1904
+ return gsap.fromTo(parts, effFrom, {
1905
+ ...computeTo(effFrom),
1906
+ ease,
1907
+ duration,
1908
+ delay,
1909
+ stagger,
1910
+ onComplete: () => {
1911
+ if (hasGClass(el, "leave")) refreshLeaveRect(el);
1912
+ revertSplit(el);
1913
+ fireOnComplete(el, "spawn");
1914
+ }
1915
+ });
1916
+ };
1917
+ const playTypewriterSplit = (el, delay, dur, ease) => {
1918
+ const gran = getGranularity(el);
1919
+ const parts = getParts(el, gran);
1920
+ if (!parts.length) return;
1921
+ const perChar = dur / Math.max(parts.length, 1);
1922
+ return gsap.fromTo(parts, { opacity: 0 }, {
1923
+ opacity: 1,
1924
+ ease,
1925
+ duration: Math.min(defaults.typewriterSplitCharDuration, perChar),
1926
+ delay,
1927
+ stagger: perChar,
1928
+ onComplete: () => revertSplit(el)
1929
+ });
1930
+ };
1931
+ const textClsFor = (el) => [...el.classList].find((c) => c.startsWith(TEXT_PREFIX));
1932
+ const isTextElement = (el) => {
1933
+ const cls = textClsFor(el);
1934
+ if (!cls) return false;
1935
+ return !!spawnConfigs.find(({ sel }) => sel === "." + cls.slice(TEXT_PREFIX_LEN));
1936
+ };
1937
+ const setupPin = (el) => {
1938
+ if (!hasGClass(el, "pin") || el.dataset.gsapPinned) return;
1939
+ const clamp = (n) => Math.min(100, Math.max(0, n));
1940
+ const startClass = readClassNumber(el, "progress-start-", null);
1941
+ const endClass = readClassNumber(el, "progress-end-", null);
1942
+ const start = startClass != null ? `top ${clamp(100 - startClass)}%` : "top top";
1943
+ const end = endClass != null ? `top ${clamp(100 - endClass)}%` : "bottom top";
1944
+ const t = ScrollTrigger.create({
1945
+ trigger: el,
1946
+ start,
1947
+ end,
1948
+ pin: true,
1949
+ pinSpacing: true,
1950
+ anticipatePin: 1
1951
+ });
1952
+ el.dataset.gsapPinned = "1";
1953
+ scrollTriggers.push(t);
1954
+ };
1955
+ qAllAllVariants(".pin").forEach((el) => runWithBreakpointForSel(el, ".pin", () => setupPin(el)));
1956
+ const setupScrollDriven = (el) => {
1957
+ if (el.dataset?.gsapScrollDriven) return;
1958
+ el.dataset.gsapScrollDriven = "1";
1959
+ if (isReduced(el)) return;
1960
+ [...el.classList];
1961
+ const clamp = (n) => Math.min(100, Math.max(0, n));
1962
+ const parallaxCls = getActivePrefixedClass(el, "parallax-");
1963
+ if (parallaxCls) {
1964
+ const factor = parseFloat(parallaxCls.slice(parallaxCls.indexOf("parallax-") + 9)) || 1;
1965
+ if (factor === 1) return;
1966
+ const amt = (factor - 1) * 50;
1967
+ const t = gsap.fromTo(el, { yPercent: -amt }, {
1968
+ yPercent: amt,
1969
+ ease: "none",
1970
+ scrollTrigger: {
1971
+ trigger: el,
1972
+ start: "top bottom",
1973
+ end: "bottom top",
1974
+ scrub: true
1975
+ }
1976
+ });
1977
+ scrollTriggers.push(t.scrollTrigger);
1978
+ return;
1979
+ }
1980
+ if (hasGClass(el, "progress-bar") || hasGClass(el, "scroll-fill")) {
1981
+ const startClass = readClassNumber(el, "progress-start-", null);
1982
+ const endClass = readClassNumber(el, "progress-end-", null);
1983
+ const reverse = hasGClass(el, "progress-reverse");
1984
+ const t = gsap.fromTo(el, { scaleX: reverse ? 1 : 0 }, {
1985
+ scaleX: reverse ? 0 : 1,
1986
+ ease: "none",
1987
+ transformOrigin: "left center",
1988
+ scrollTrigger: {
1989
+ trigger: el,
1990
+ start: startClass != null ? `top ${clamp(100 - startClass)}%` : "top bottom",
1991
+ end: endClass != null ? `top ${clamp(100 - endClass)}%` : "bottom top",
1992
+ scrub: true
1993
+ }
1994
+ });
1995
+ scrollTriggers.push(t.scrollTrigger);
1996
+ return;
1997
+ }
1998
+ if (hasGClass(el, "scroll-fade-bg")) {
1999
+ const t = gsap.fromTo(el, { backgroundPosition: "0% 0%" }, {
2000
+ backgroundPosition: "100% 100%",
2001
+ ease: "none",
2002
+ scrollTrigger: {
2003
+ trigger: el,
2004
+ start: "top bottom",
2005
+ end: "bottom top",
2006
+ scrub: true
2007
+ }
2008
+ });
2009
+ scrollTriggers.push(t.scrollTrigger);
2010
+ return;
2011
+ }
2012
+ if (hasGClass(el, "scroll-horizontal")) {
2013
+ const track = el.querySelector(".scroll-track");
2014
+ if (!track) return;
2015
+ const getAmount = () => track.scrollWidth - el.clientWidth;
2016
+ const t = gsap.to(track, {
2017
+ x: () => -getAmount(),
2018
+ ease: "none",
2019
+ scrollTrigger: {
2020
+ trigger: el,
2021
+ start: "top top",
2022
+ end: () => `+=${getAmount()}`,
2023
+ pin: true,
2024
+ scrub: 1,
2025
+ anticipatePin: 1,
2026
+ invalidateOnRefresh: true
2027
+ }
2028
+ });
2029
+ scrollTriggers.push(t.scrollTrigger);
2030
+ }
2031
+ };
2032
+ qAll("body *").filter((el) => hasGClass(el, "progress-bar") || hasGClass(el, "scroll-fill") || hasGClass(el, "scroll-fade-bg") || hasGClass(el, "scroll-horizontal") || [...el.classList].some((c) => c.startsWith("parallax-") || bpNames.some((bp) => c.startsWith(`${bp}:parallax-`)))).forEach((el) => setupScrollDriven(el));
2033
+ const getScroller = (el) => {
2034
+ const frame = el.closest?.(".scroll-frame");
2035
+ return frame && frame !== el ? frame : void 0;
2036
+ };
2037
+ const setupScroll = (el) => {
2038
+ if (el.dataset?.gsapScroll) return;
2039
+ if (isTextElement(el)) return;
2040
+ if (isReduced(el)) return;
2041
+ el.dataset.gsapScroll = "1";
2042
+ const config = findSpawn(el);
2043
+ if (!config) return;
2044
+ const { from, typewriter: isTypewriter, typewriterSplit, play } = config;
2045
+ if (hasGClass(el, "scroll-progress")) {
2046
+ const ease = isTypewriter ? [...el.classList].find((c) => c.startsWith("ease-"))?.split("-")[1] ?? "none" : getEase(el);
2047
+ const to = {};
2048
+ for (const [key] of Object.entries(from || {})) if (key === "opacity") to[key] = 1;
2049
+ else if (key === "filter") to[key] = "blur(0px)";
2050
+ else if (key === "text") to[key] = stashText(el);
2051
+ else if (key === "clipPath") to[key] = "inset(0% 0% 0% 0%)";
2052
+ else if (key === "drawSVG") to[key] = "100%";
2053
+ else to[key] = key.startsWith("scale") ? 1 : 0;
2054
+ const startClass = readClassNumber(el, "progress-start-", null);
2055
+ const endClass = readClassNumber(el, "progress-end-", null);
2056
+ const clamp = (n) => Math.min(100, Math.max(0, n));
2057
+ const reverse = hasGClass(el, "progress-reverse");
2058
+ const rnd = !reverse && hasRandom(el) ? randomVars(el) : null;
2059
+ const rndEnds = rnd ? randomEnds(Object.keys(rnd)) : null;
2060
+ const tl = gsap.timeline({ scrollTrigger: {
2061
+ trigger: el,
2062
+ scroller: getScroller(el),
2063
+ start: startClass != null ? `top ${clamp(100 - startClass)}%` : defaults.progressStart,
2064
+ end: endClass != null ? `top ${clamp(100 - endClass)}%` : defaults.progressEnd,
2065
+ scrub: true
2066
+ } });
2067
+ if (config.count) {
2068
+ const { start, end, decimals } = countTargetVars(el);
2069
+ const obj = { n: reverse ? end : start };
2070
+ tl.fromTo(obj, { n: reverse ? end : start }, {
2071
+ n: reverse ? start : end,
2072
+ ease,
2073
+ onUpdate: () => {
2074
+ el.textContent = obj.n.toFixed(decimals);
2075
+ }
2076
+ }, 0);
2077
+ } else if (config.scramble) {
2078
+ const { segs, chars, speed, revealDelay, rtl } = scrambleVars(el);
2079
+ const all = el.classList.contains("scramble-all");
2080
+ segs.forEach(({ t, text }) => {
2081
+ if (all) tl.to(t, {
2082
+ scrambleText: {
2083
+ text,
2084
+ chars,
2085
+ speed,
2086
+ revealDelay,
2087
+ rightToLeft: rtl
2088
+ },
2089
+ ease
2090
+ }, 0);
2091
+ else tl.fromTo(t, { scrambleText: {
2092
+ text: reverse ? text : "",
2093
+ chars
2094
+ } }, {
2095
+ scrambleText: {
2096
+ text: reverse ? "" : text,
2097
+ chars,
2098
+ speed,
2099
+ revealDelay,
2100
+ rightToLeft: rtl
2101
+ },
2102
+ ease
2103
+ }, 0);
2104
+ });
2105
+ } else if (typewriterSplit) {
2106
+ const parts = getParts(el, getGranularity(el));
2107
+ if (parts.length) tl.fromTo(parts, { opacity: reverse ? 1 : 0 }, {
2108
+ opacity: reverse ? 0 : 1,
2109
+ ease
2110
+ });
2111
+ } else if (hasGClass(el, "fill-svg") && (hasGClass(el, "draw") || hasGClass(el, "draw-split"))) {
2112
+ const fillEaseCls = [...el.classList].find((c) => c.startsWith("fill-ease-"));
2113
+ const fillEase = fillEaseCls ? fillEaseCls.slice(10) : ease;
2114
+ const fillTimeCls = [...el.classList].find((c) => c.startsWith("fill-time-"));
2115
+ const fillDur = fillTimeCls ? Number(fillTimeCls.slice(10)) : .5;
2116
+ const drawDur = 1;
2117
+ gsap.set(el, { fillOpacity: reverse ? 1 : 0 });
2118
+ if (!reverse) {
2119
+ tl.fromTo(el, {
2120
+ drawSVG: "0%",
2121
+ ...rnd
2122
+ }, {
2123
+ drawSVG: "100%",
2124
+ ...rndEnds,
2125
+ ease,
2126
+ duration: drawDur
2127
+ });
2128
+ tl.fromTo(el, { fillOpacity: 0 }, {
2129
+ fillOpacity: 1,
2130
+ ease: fillEase,
2131
+ duration: fillDur
2132
+ });
2133
+ } else {
2134
+ tl.fromTo(el, { fillOpacity: 1 }, {
2135
+ fillOpacity: 0,
2136
+ ease: fillEase,
2137
+ duration: fillDur
2138
+ });
2139
+ tl.fromTo(el, {
2140
+ drawSVG: "100%",
2141
+ ...rndEnds
2142
+ }, {
2143
+ drawSVG: "0%",
2144
+ ...rnd,
2145
+ ease,
2146
+ duration: drawDur
2147
+ });
2148
+ }
2149
+ } else tl.fromTo(el, {
2150
+ ...reverse ? to : from,
2151
+ ...rnd
2152
+ }, {
2153
+ ...rndEnds,
2154
+ ...reverse ? from : to,
2155
+ ease
2156
+ });
2157
+ scrollTriggers.push(tl.scrollTrigger);
2158
+ return;
2159
+ }
2160
+ if (!hasGClass(el, "scroll")) return;
2161
+ const { delay, duration } = readTiming(el);
2162
+ const ease = isTypewriter ? [...el.classList].find((c) => c.startsWith("ease-"))?.split("-")[1] ?? "none" : getEase(el);
2163
+ const fullText = stashText(el);
2164
+ const enter = () => {
2165
+ if (el._scrollTween) el._scrollTween.kill();
2166
+ el._scrollTween = isTypewriter ? typewriterSplit ? playTypewriterSplit(el, delay, duration, ease) : typewriter(el, fullText, duration, delay, ease) : invokePlay(config, el, delay, duration, ease);
2167
+ el._scrollTween.eventCallback("onComplete", () => fireOnComplete(el, "spawn"));
2168
+ };
2169
+ const reverseToStart = () => {
2170
+ if (config.count) {
2171
+ const t = el._scrollTween;
2172
+ if (t && t.progress() > 0 && !t.reversed()) t.reverse();
2173
+ return;
2174
+ }
2175
+ el._scrollTween?.kill();
2176
+ if (isTypewriter && !typewriterSplit) {
2177
+ el.innerHTML = fullText;
2178
+ return;
2179
+ }
2180
+ if (typewriterSplit) {
2181
+ const parts = getParts(el, getGranularity(el));
2182
+ if (parts.length) gsap.to(parts, {
2183
+ opacity: 0,
2184
+ ease,
2185
+ duration: .3
2186
+ });
2187
+ return;
2188
+ }
2189
+ el._scrollTween = gsap.to(el, {
2190
+ ...from,
2191
+ ease,
2192
+ duration: .3
2193
+ });
2194
+ };
2195
+ const st = ScrollTrigger.create({
2196
+ trigger: el,
2197
+ scroller: getScroller(el),
2198
+ start: "top bottom",
2199
+ end: "bottom top",
2200
+ onEnter: enter,
2201
+ onEnterBack: enter,
2202
+ onLeave: reverseToStart,
2203
+ onLeaveBack: reverseToStart
2204
+ });
2205
+ scrollTriggers.push(st);
2206
+ };
2207
+ qAll("body *").filter((el) => hasGClass(el, "scroll") || hasGClass(el, "scroll-progress")).forEach((el) => runWithBreakpoint(el, () => setupScroll(el)));
2208
+ spawnConfigs.forEach(({ sel, from, typewriter: isTypewriter, text }) => {
2209
+ if (isTypewriter || text === false) return;
2210
+ const tSel = ".spawn-text-" + sel.slice(1);
2211
+ qAll("body *").filter((el) => elementMatchesSel(el, tSel) && hasGClass(el, "scroll") && !hasGClass(el, "scroll-progress")).forEach((el) => {
2212
+ const run = () => {
2213
+ if (isReduced(el)) return;
2214
+ const { delay, duration } = readTiming(el);
2215
+ const ease = getEase(el);
2216
+ const enter = () => {
2217
+ el._scrollTween?.kill();
2218
+ el._scrollTween = playText(el, from, delay, duration, ease);
2219
+ };
2220
+ const reverseToStart = () => {
2221
+ el._scrollTween?.kill();
2222
+ const parts = getParts(el, getGranularity(el));
2223
+ if (parts.length) gsap.to(parts, {
2224
+ ...from,
2225
+ ease,
2226
+ duration: .3
2227
+ });
2228
+ };
2229
+ scrollTriggers.push(ScrollTrigger.create({
2230
+ trigger: el,
2231
+ scroller: getScroller(el),
2232
+ start: "top bottom",
2233
+ end: "top top",
2234
+ onEnter: enter,
2235
+ onEnterBack: enter,
2236
+ onLeave: reverseToStart,
2237
+ onLeaveBack: reverseToStart
2238
+ }));
2239
+ };
2240
+ runWithBreakpoint(el, run);
2241
+ });
2242
+ qAll("body *").filter((el) => elementMatchesSel(el, tSel) && hasGClass(el, "scroll-progress")).forEach((el) => {
2243
+ const run = () => {
2244
+ if (isReduced(el)) return;
2245
+ const ease = getEase(el);
2246
+ const parts = getParts(el, getGranularity(el));
2247
+ if (!parts.length) return;
2248
+ const to = computeTo(from);
2249
+ const startClass = readClassNumber(el, "progress-start-", null);
2250
+ const endClass = readClassNumber(el, "progress-end-", null);
2251
+ const clamp = (n) => Math.min(100, Math.max(0, n));
2252
+ const tl = gsap.timeline({ scrollTrigger: {
2253
+ trigger: el,
2254
+ scroller: getScroller(el),
2255
+ start: startClass != null ? `top ${clamp(100 - startClass)}%` : defaults.progressStart,
2256
+ end: endClass != null ? `top ${clamp(100 - endClass)}%` : defaults.progressEnd,
2257
+ scrub: true
2258
+ } });
2259
+ const reverse = hasGClass(el, "progress-reverse");
2260
+ const rnd = !reverse && hasRandom(el) ? randomVars(el) : null;
2261
+ tl.fromTo(parts, {
2262
+ ...reverse ? to : from,
2263
+ ...rnd
2264
+ }, {
2265
+ ...rnd ? randomEnds(Object.keys(rnd)) : null,
2266
+ ...reverse ? from : to,
2267
+ ease
2268
+ });
2269
+ scrollTriggers.push(tl.scrollTrigger);
2270
+ };
2271
+ runWithBreakpoint(el, run);
2272
+ });
2273
+ });
2274
+ ScrollTrigger.refresh();
2275
+ window.addEventListener("load", ScrollTrigger.refresh);
2276
+ let refreshTimer = null;
2277
+ const scheduleRefresh = () => {
2278
+ clearTimeout(refreshTimer);
2279
+ refreshTimer = setTimeout(() => {
2280
+ refreshTimer = null;
2281
+ ScrollTrigger.refresh();
2282
+ }, 60);
2283
+ };
2284
+ setTimeout(scheduleRefresh, 400);
2285
+ setTimeout(scheduleRefresh, 1200);
2286
+ spawnConfigs.forEach((config) => {
2287
+ const { sel, typewriter: isTypewriter, typewriterSplit } = config;
2288
+ qAllAllVariants(sel).forEach((el) => {
2289
+ const run = () => {
2290
+ if (hasGClass(el, "scroll") || hasGClass(el, "scroll-progress")) return;
2291
+ if (isPreserved(el)) return;
2292
+ if (isReduced(el)) return;
2293
+ if (!elementMatchesSel(el, sel)) return;
2294
+ const { delay, duration } = readTiming(el);
2295
+ if (isTypewriter) {
2296
+ const easeClass = getActivePrefixedClass(el, "ease-") || [...el.classList].find((c) => c.startsWith("ease-"));
2297
+ const elEase = easeClass ? easeClass.slice(easeClass.indexOf("ease-") + 5) : "none";
2298
+ if (typewriterSplit) el._spawnTween = playTypewriterSplit(el, delay, duration, elEase);
2299
+ else {
2300
+ el.typewriter?.kill();
2301
+ el.typewriter = typewriter(el, stashText(el), duration, delay, elEase);
2302
+ }
2303
+ } else {
2304
+ el._spawnTween = invokePlay(config, el, delay, duration, getEase(el));
2305
+ el._spawnTween.eventCallback("onComplete", () => {
2306
+ if (hasGClass(el, "leave")) refreshLeaveRect(el);
2307
+ if (hasGClass(el, "flip")) captureFlip(el);
2308
+ if (isCompatibility(el)) resumeCompatLoops(el);
2309
+ scheduleRefresh();
2310
+ fireOnComplete(el, "spawn");
2311
+ });
2312
+ }
2313
+ markPreserved(el);
2314
+ el.dataset.gsapWired = "1";
2315
+ };
2316
+ runWithBreakpointForSel(el, sel, run);
2317
+ });
2318
+ });
2319
+ spawnConfigs.forEach(({ sel, from, typewriter: isTypewriter, text }) => {
2320
+ if (isTypewriter || text === false) return;
2321
+ const tSel = ".spawn-text-" + sel.slice(1);
2322
+ qAllAllVariants(tSel).forEach((el) => {
2323
+ const run = () => {
2324
+ if (hasGClass(el, "scroll") || hasGClass(el, "scroll-progress")) return;
2325
+ if (isPreserved(el)) return;
2326
+ if (isReduced(el)) return;
2327
+ if (!elementMatchesSel(el, tSel)) return;
2328
+ const { delay, duration } = readTiming(el);
2329
+ el._spawnTween = playText(el, from, delay, duration, getEase(el));
2330
+ markPreserved(el);
2331
+ el.dataset.gsapWired = "1";
2332
+ };
2333
+ runWithBreakpointForSel(el, tSel, run);
2334
+ });
2335
+ });
2336
+ const magnetQuery = typeof window !== "undefined" ? window.matchMedia("(hover: none)") : null;
2337
+ const magnetState = [];
2338
+ const magnetListeners = [];
2339
+ const magnetOnMove = (el, pull, grow, duration, elEase) => (ev) => {
2340
+ const r = el.getBoundingClientRect();
2341
+ const dx = ev.clientX - (r.left + r.width / 2);
2342
+ const dy = ev.clientY - (r.top + r.height / 2);
2343
+ magnet(el, dx * pull, dy * pull, grow, duration, elEase);
2344
+ };
2345
+ const magnetOnLeave = (el, duration, elEase) => () => magnet(el, 0, 0, 1, duration, elEase);
2346
+ const magnet3dOnMove = (el, pull, grow, tilt, duration, elEase) => (ev) => {
2347
+ const r = el.getBoundingClientRect();
2348
+ const dx = ev.clientX - (r.left + r.width / 2);
2349
+ const dy = ev.clientY - (r.top + r.height / 2);
2350
+ const relX = r.width ? (ev.clientX - r.left) / r.width - .5 : 0;
2351
+ const relY = r.height ? (ev.clientY - r.top) / r.height - .5 : 0;
2352
+ magnet3d(el, dx * pull, dy * pull, grow, -relY * tilt, relX * tilt, duration, elEase);
2353
+ };
2354
+ const magnet3dOnLeave = (el, duration, elEase) => () => magnet3d(el, 0, 0, 1, 0, 0, duration, elEase);
2355
+ const applyMagnet = () => {
2356
+ if (!magnetQuery) return;
2357
+ const touch = magnetQuery.matches;
2358
+ magnetListeners.forEach(({ el, type, fn }) => el.removeEventListener(type, fn));
2359
+ magnetListeners.length = 0;
2360
+ if (touch) return;
2361
+ magnetState.forEach(({ el, onMove, onLeave }) => {
2362
+ el.addEventListener("mousemove", onMove);
2363
+ el.addEventListener("mouseleave", onLeave);
2364
+ magnetListeners.push({
2365
+ el,
2366
+ type: "mousemove",
2367
+ fn: onMove
2368
+ }, {
2369
+ el,
2370
+ type: "mouseleave",
2371
+ fn: onLeave
2372
+ });
2373
+ });
2374
+ };
2375
+ const setupMagnet = (el) => {
2376
+ if (!hasGClass(el, "magnet") && !hasGClass(el, "magnet3d")) return;
2377
+ const threeD = hasGClass(el, "magnet3d");
2378
+ const duration = readClassNumber(el, "mtime-", .4);
2379
+ const pull = readClassNumber(el, "amount-", .3);
2380
+ const grow = readClassNumber(el, "mgrow-", 1.1);
2381
+ const tilt = readClassNumber(el, "mtilt-", 12);
2382
+ const elEase = getEase(el);
2383
+ const onMove = threeD ? magnet3dOnMove(el, pull, grow, tilt, duration, elEase) : magnetOnMove(el, pull, grow, duration, elEase);
2384
+ const onLeave = threeD ? magnet3dOnLeave(el, duration, elEase) : magnetOnLeave(el, duration, elEase);
2385
+ magnetState.push({
2386
+ el,
2387
+ onMove,
2388
+ onLeave
2389
+ });
2390
+ };
2391
+ if (magnetQuery) magnetQuery.addEventListener("change", applyMagnet);
2392
+ const isCompatibility = (el) => hasGClass(el, "compatibility");
2393
+ const compatLoopsOf = (el) => {
2394
+ if (!el._gsapCompatLoops) el._gsapCompatLoops = [];
2395
+ return el._gsapCompatLoops;
2396
+ };
2397
+ const trackCompatLoop = (el, tween) => {
2398
+ if (tween && isCompatibility(el)) compatLoopsOf(el).push(tween);
2399
+ return tween;
2400
+ };
2401
+ const pauseCompatLoops = (el) => compatLoopsOf(el).forEach((t) => t.pause());
2402
+ const resumeCompatLoops = (el) => compatLoopsOf(el).forEach((t) => t.resume());
2403
+ const setupClicks = (el) => {
2404
+ if (isReduced(el)) return;
2405
+ setupMagnet(el);
2406
+ if (hasGClass(el, "click-hover")) {
2407
+ const area = wrapTarget(el);
2408
+ let touch = false;
2409
+ const duration = readClassNumber(el, "ctime-", defaults.clickDuration);
2410
+ const lift = readClassNumber(el, "amount-", defaults.clickOffset);
2411
+ const elEase = getEase(el);
2412
+ addListener(area, "mousedown", () => {
2413
+ if (!touch) {
2414
+ pauseCompatLoops(el);
2415
+ verticalmove(el, -lift / 2, duration, elEase);
2416
+ }
2417
+ });
2418
+ addListener(area, "mouseover", () => {
2419
+ if (!touch) {
2420
+ pauseCompatLoops(el);
2421
+ verticalmove(el, -lift, duration, elEase);
2422
+ }
2423
+ });
2424
+ addListener(area, "mouseleave", () => {
2425
+ if (!touch) {
2426
+ verticalmove(el, 0, duration, elEase);
2427
+ resumeCompatLoops(el);
2428
+ }
2429
+ });
2430
+ addListener(area, "mouseup", () => {
2431
+ if (!touch) verticalmove(el, -lift, duration, elEase);
2432
+ });
2433
+ addListener(area, "touchstart", () => {
2434
+ touch = true, pauseCompatLoops(el), verticalmove(el, lift / 2, duration, elEase);
2435
+ });
2436
+ addListener(area, "touchend", () => {
2437
+ touch = true, verticalmove(el, 0, duration, elEase), setTimeout(() => {
2438
+ touch = false;
2439
+ }, 0);
2440
+ });
2441
+ }
2442
+ if (hasGClass(el, "click-expand")) {
2443
+ let touch = false;
2444
+ const duration = readClassNumber(el, "ctime-", defaults.clickDuration);
2445
+ const lift = readClassNumber(el, "amount-", defaults.clickExpandOffset);
2446
+ const elEase = getEase(el);
2447
+ addListener(el, "mousedown", () => {
2448
+ if (!touch) {
2449
+ pauseCompatLoops(el);
2450
+ expandmove(el, 10, duration, elEase).eventCallback("onComplete", () => fireOnComplete(el, "click"));
2451
+ }
2452
+ });
2453
+ addListener(el, "mouseover", () => {
2454
+ if (!touch) {
2455
+ pauseCompatLoops(el);
2456
+ expandmove(el, lift, duration, elEase);
2457
+ }
2458
+ });
2459
+ addListener(el, "mouseleave", () => {
2460
+ if (!touch) {
2461
+ expandmove(el, 10, duration, elEase);
2462
+ resumeCompatLoops(el);
2463
+ }
2464
+ });
2465
+ addListener(el, "mouseup", () => {
2466
+ if (!touch) expandmove(el, lift, duration, elEase);
2467
+ });
2468
+ addListener(el, "touchstart", () => {
2469
+ touch = true, pauseCompatLoops(el), expandmove(el, lift, duration, elEase);
2470
+ });
2471
+ addListener(el, "touchend", () => {
2472
+ touch = true, expandmove(el, 10, duration, elEase).eventCallback("onComplete", () => fireOnComplete(el, "click")), setTimeout(() => {
2473
+ touch = false;
2474
+ }, 0);
2475
+ });
2476
+ }
2477
+ };
2478
+ const readLoopCtx = (el) => ({
2479
+ edelay: readClassNumber(el, "edelay-", defaults.effectDelay),
2480
+ amount: readClassNumber(el, "amount-", defaults.effectOffset),
2481
+ etime: readClassNumber(el, "etime-", defaults.effectDuration),
2482
+ ease: getEase(el),
2483
+ time: readClassNumber(el, "time-", 20),
2484
+ mH: readClassNumber(el, "marquee-horizontal-offset-", 0),
2485
+ mV: readClassNumber(el, "marquee-vertical-offset-", 0),
2486
+ radiateZ: readClassNumber(el, "radiate-z-", null)
2487
+ });
2488
+ const loopEls = [];
2489
+ const buildLoops = (el) => {
2490
+ if (isReduced(el)) return;
2491
+ const ctx = readLoopCtx(el);
2492
+ loopConfigs.forEach(({ sel, build, key, loop }) => {
2493
+ if (elementMatchesSel(el, sel)) {
2494
+ el[key]?.kill();
2495
+ el[key] = trackCompatLoop(el, build(el, ctx));
2496
+ if (loop) el[key].repeat(-1);
2497
+ if (!loopEls.some((l) => l.el === el && l.key === key)) loopEls.push({
2498
+ el,
2499
+ key
2500
+ });
2501
+ el[key].eventCallback(el[key].repeat() === -1 ? "onRepeat" : "onComplete", () => fireOnComplete(el, "loop"));
2502
+ }
2503
+ });
2504
+ };
2505
+ const findSpawnTween = (el) => {
2506
+ for (let node = el; node && node.nodeType === 1; node = node.parentElement) {
2507
+ const t = node._spawnTween;
2508
+ if (t && t.progress() < 1) return t;
2509
+ }
2510
+ return null;
2511
+ };
2512
+ const deferLoopBuild = (el, tween) => {
2513
+ if (!tween.__gsapPendingLoops) tween.__gsapPendingLoops = /* @__PURE__ */ new Set();
2514
+ tween.__gsapPendingLoops.add(el);
2515
+ if (tween.__gsapPendingHooked) return;
2516
+ tween.__gsapPendingHooked = true;
2517
+ const existing = tween.eventCallback("onComplete");
2518
+ tween.eventCallback("onComplete", function() {
2519
+ existing && existing.call(this);
2520
+ const pending = tween.__gsapPendingLoops;
2521
+ tween.__gsapPendingLoops = /* @__PURE__ */ new Set();
2522
+ tween.__gsapPendingHooked = false;
2523
+ pending.forEach((e) => buildLoops(e));
2524
+ });
2525
+ };
2526
+ const setupLoops = (el) => {
2527
+ const spawnTween = isCompatibility(el) ? findSpawnTween(el) : null;
2528
+ if (spawnTween) {
2529
+ deferLoopBuild(el, spawnTween);
2530
+ return;
2531
+ }
2532
+ buildLoops(el);
2533
+ };
2534
+ const wrapTarget = (el) => {
2535
+ if (!hasGClass(el, "wrapdiv")) return el;
2536
+ if (el._gsapWrap) return el._gsapWrap;
2537
+ const area = document.createElement("div");
2538
+ el.before(area);
2539
+ area.appendChild(el);
2540
+ el._gsapWrap = area;
2541
+ return area;
2542
+ };
2543
+ const setupHoverClick = (el) => {
2544
+ if (isReduced(el)) return;
2545
+ const ctx = readLoopCtx(el);
2546
+ loopConfigs.forEach(({ sel, build, key }) => {
2547
+ if (sel.startsWith(".marquee")) return;
2548
+ const name = sel.slice(1);
2549
+ if (hasGClass(el, "hover-" + name)) {
2550
+ const area = wrapTarget(el);
2551
+ addListener(area, "mouseenter", () => {
2552
+ pauseCompatLoops(el);
2553
+ el[key]?.kill();
2554
+ el[key] = build(el, ctx).repeat(-1);
2555
+ el[key].eventCallback("onRepeat", () => fireOnComplete(el, "loop"));
2556
+ });
2557
+ addListener(area, "mouseleave", () => {
2558
+ el[key]?.kill();
2559
+ el[key] = reset(el, readClassNumber(el, "etime-", defaults.effectDuration), getEase(el));
2560
+ resumeCompatLoops(el);
2561
+ });
2562
+ } else if (hasGClass(el, "click-" + name)) {
2563
+ const area = wrapTarget(el);
2564
+ addListener(area, "mousedown", () => {
2565
+ pauseCompatLoops(el);
2566
+ el[key]?.kill();
2567
+ el[key] = build(el, ctx);
2568
+ el[key].eventCallback("onComplete", () => fireOnComplete(el, "click"));
2569
+ });
2570
+ addListener(area, "mouseleave", () => {
2571
+ resumeCompatLoops(el);
2572
+ });
2573
+ }
2574
+ });
2575
+ };
2576
+ const CSS_VAL = "(-?\\d+(?:\\.\\d+)?|#[0-9a-fA-F]{3,8})";
2577
+ const CSS_ANIM_RE = new RegExp(`^((spawn|hover|click)-)?css-([a-zA-Z]+)-${CSS_VAL}-${CSS_VAL}$`);
2578
+ const CSS_SINGLE_RE = new RegExp(`^((hover|click)-)css-([a-zA-Z]+)-${CSS_VAL}$`);
2579
+ const parseCssVal = (s) => /^#/.test(s) ? s : Number(s);
2580
+ const parseCssAnim = (el) => {
2581
+ for (const c of el.classList) {
2582
+ let m = c.match(CSS_ANIM_RE);
2583
+ if (m) return {
2584
+ mode: m[2] || "loop",
2585
+ prop: m[3],
2586
+ from: parseCssVal(m[4]),
2587
+ to: parseCssVal(m[5])
2588
+ };
2589
+ m = c.match(CSS_SINGLE_RE);
2590
+ if (m) return {
2591
+ mode: m[2],
2592
+ prop: m[3],
2593
+ to: parseCssVal(m[4]),
2594
+ single: true
2595
+ };
2596
+ }
2597
+ return null;
2598
+ };
2599
+ const cssTweens = [];
2600
+ const setupCssAnims = (el) => {
2601
+ if (isReduced(el)) return;
2602
+ const anim = parseCssAnim(el);
2603
+ if (!anim) return;
2604
+ const dur = readClassNumber(el, "time-", 1);
2605
+ const ease = getEase(el);
2606
+ const key = "_cssAnim";
2607
+ const loopVars = {
2608
+ [anim.prop]: anim.to,
2609
+ duration: dur,
2610
+ ease,
2611
+ yoyo: true,
2612
+ repeat: -1
2613
+ };
2614
+ if (anim.mode === "loop") {
2615
+ el[key]?.kill();
2616
+ el[key] = gsap.fromTo(el, { [anim.prop]: anim.from }, loopVars);
2617
+ cssTweens.push(el[key]);
2618
+ } else if (anim.mode === "spawn") {
2619
+ el[key]?.kill();
2620
+ el[key] = gsap.fromTo(el, { [anim.prop]: anim.from }, {
2621
+ [anim.prop]: anim.to,
2622
+ duration: dur,
2623
+ ease
2624
+ });
2625
+ cssTweens.push(el[key]);
2626
+ } else if (anim.mode === "hover") {
2627
+ const area = wrapTarget(el);
2628
+ if (anim.single) {
2629
+ const original = gsap.getProperty(el, anim.prop);
2630
+ addListener(area, "mouseenter", () => {
2631
+ el[key]?.kill();
2632
+ el[key] = gsap.to(el, {
2633
+ [anim.prop]: anim.to,
2634
+ duration: dur,
2635
+ ease
2636
+ });
2637
+ cssTweens.push(el[key]);
2638
+ });
2639
+ addListener(area, "mouseleave", () => {
2640
+ el[key]?.kill();
2641
+ el[key] = gsap.to(el, {
2642
+ [anim.prop]: original,
2643
+ duration: dur,
2644
+ ease
2645
+ });
2646
+ cssTweens.push(el[key]);
2647
+ });
2648
+ } else {
2649
+ addListener(area, "mouseenter", () => {
2650
+ el[key]?.kill();
2651
+ el[key] = gsap.fromTo(el, { [anim.prop]: anim.from }, { ...loopVars });
2652
+ cssTweens.push(el[key]);
2653
+ });
2654
+ addListener(area, "mouseleave", () => {
2655
+ el[key]?.kill();
2656
+ el[key] = gsap.to(el, {
2657
+ [anim.prop]: anim.from,
2658
+ duration: dur,
2659
+ ease
2660
+ });
2661
+ cssTweens.push(el[key]);
2662
+ });
2663
+ }
2664
+ } else if (anim.mode === "click") {
2665
+ const area = wrapTarget(el);
2666
+ if (anim.single) {
2667
+ const original = gsap.getProperty(el, anim.prop);
2668
+ addListener(area, "mousedown", () => {
2669
+ el[key]?.kill();
2670
+ el[key] = gsap.to(el, {
2671
+ [anim.prop]: anim.to,
2672
+ duration: dur,
2673
+ ease
2674
+ });
2675
+ el[key].eventCallback("onComplete", () => fireOnComplete(el, "click"));
2676
+ cssTweens.push(el[key]);
2677
+ });
2678
+ addListener(area, "mouseup", () => {
2679
+ el[key]?.kill();
2680
+ el[key] = gsap.to(el, {
2681
+ [anim.prop]: original,
2682
+ duration: dur,
2683
+ ease
2684
+ });
2685
+ cssTweens.push(el[key]);
2686
+ });
2687
+ } else addListener(area, "mousedown", () => {
2688
+ el[key]?.kill();
2689
+ el[key] = gsap.fromTo(el, { [anim.prop]: anim.from }, {
2690
+ [anim.prop]: anim.to,
2691
+ duration: dur,
2692
+ ease,
2693
+ yoyo: true,
2694
+ repeat: 1
2695
+ });
2696
+ el[key].eventCallback("onComplete", () => fireOnComplete(el, "click"));
2697
+ cssTweens.push(el[key]);
2698
+ });
2699
+ }
2700
+ };
2701
+ const setupTeardowns = [];
2702
+ const runSetup = (el) => {
2703
+ if (isReduced(el)) return;
2704
+ const ctx = readLoopCtx(el);
2705
+ animAll.forEach((a) => {
2706
+ if (a.setup && elementMatchesSel(el, a.sel)) {
2707
+ const teardown = a.setup(el, ctx);
2708
+ if (typeof teardown === "function") setupTeardowns.push(teardown);
2709
+ }
2710
+ });
2711
+ };
2712
+ qAll("body *").forEach((el) => {
2713
+ if (el.dataset?.gsapSetup) return;
2714
+ el.dataset.gsapSetup = "1";
2715
+ setupClicks(el);
2716
+ setupLoops(el);
2717
+ setupHoverClick(el);
2718
+ setupCssAnims(el);
2719
+ runSetup(el);
2720
+ });
2721
+ applyMagnet();
2722
+ let flipRoots = /* @__PURE__ */ new Set();
2723
+ let flipPendingRaf = null;
2724
+ const flushFlipRoots = () => {
2725
+ if (!flipRoots.size) return;
2726
+ const toFlip = /* @__PURE__ */ new Set();
2727
+ flipRoots.forEach((scope) => {
2728
+ if (!scope) return;
2729
+ gsap.utils.toArray(scope.querySelectorAll?.(".flip") || []).forEach((el) => {
2730
+ if (el.isConnected) toFlip.add(el);
2731
+ });
2732
+ });
2733
+ toFlip.forEach(playFlip);
2734
+ gsap.utils.toArray(document.body.querySelectorAll?.(".flip") || []).forEach(captureFlip);
2735
+ flipRoots = /* @__PURE__ */ new Set();
2736
+ };
2737
+ let flipObserver = null;
2738
+ const animateAppear = (el) => {
2739
+ if (!hasGClass(el, "appear") || el._appeared) return;
2740
+ if (!isTextElement(el) && (hasGClass(el, "scroll") || hasGClass(el, "scroll-progress"))) return;
2741
+ if (isReduced(el)) return;
2742
+ el._appeared = true;
2743
+ const { delay, duration, ease } = readTiming(el);
2744
+ const config = findSpawn(el);
2745
+ if (isTextElement(el)) {
2746
+ el._spawnTween = playText(el, config.from, delay, duration, ease);
2747
+ return;
2748
+ }
2749
+ if (!config) return el._spawnTween = SpawnV(el, delay, -defaults.spawnOffset, duration, ease);
2750
+ if (config.typewriter) {
2751
+ const easeClass = [...el.classList].find((c) => c.startsWith("ease-"));
2752
+ const elEase = easeClass ? easeClass.split("-")[1] : "none";
2753
+ el._spawnTween = config.typewriterSplit ? playTypewriterSplit(el, delay, duration, elEase) : invokePlay(config, el, delay, duration, elEase);
2754
+ } else {
2755
+ el._spawnTween = invokePlay(config, el, delay, duration, ease);
2756
+ el._spawnTween.eventCallback("onComplete", () => {
2757
+ if (hasGClass(el, "leave")) refreshLeaveRect(el);
2758
+ if (hasGClass(el, "flip")) captureFlip(el);
2759
+ fireOnComplete(el, "spawn");
2760
+ });
2761
+ }
2762
+ };
2763
+ let appearObserver = null;
2764
+ let leaveObserver = null;
2765
+ let hubObserver = null;
2766
+ let hubRaf = null;
2767
+ let hubQueue = [];
2768
+ let hubCurrentBatch = null;
2769
+ let hubCursor = 0;
2770
+ const handleFlipBatch = (mutations) => {
2771
+ for (const mutation of mutations) {
2772
+ if (mutation.type !== "childList") continue;
2773
+ const target = mutation.target;
2774
+ if (target.nodeType !== 1) continue;
2775
+ flipRoots.add(target);
2776
+ }
2777
+ };
2778
+ const handleAppearBatch = (mutations) => {
2779
+ mutations.forEach((mutation) => {
2780
+ mutation.addedNodes.forEach((node) => {
2781
+ if (node.nodeType !== 1) return;
2782
+ const els = node.querySelectorAll?.("*") ? [node, ...node.querySelectorAll("*")] : [node];
2783
+ let pinned = false;
2784
+ els.forEach((el) => {
2785
+ if (!hasGClass(el, "appear")) return;
2786
+ animateAppear(el);
2787
+ setupScroll(el);
2788
+ setupScrollDriven(el);
2789
+ if (el.dataset?.gsapSetup) return;
2790
+ el.dataset.gsapSetup = "1";
2791
+ setupClicks(el);
2792
+ setupLoops(el);
2793
+ setupHoverClick(el);
2794
+ setupCssAnims(el);
2795
+ runSetup(el);
2796
+ const wasPinned = el.dataset.gsapPinned;
2797
+ setupPin(el);
2798
+ if (!wasPinned && el.dataset.gsapPinned) pinned = true;
2799
+ });
2800
+ applyMagnet();
2801
+ if (pinned) ScrollTrigger.refresh();
2802
+ });
2803
+ });
2804
+ };
2805
+ const handleLeaveBatch = (mutations) => {
2806
+ mutations.forEach((mutation) => {
2807
+ if (mutation.type !== "childList") return;
2808
+ mutation.addedNodes.forEach((n) => collectLeave(n).forEach(captureLeave));
2809
+ mutation.removedNodes.forEach((n) => collectLeave(n).forEach(playLeave));
2810
+ });
2811
+ };
2812
+ const hubHandlers = [
2813
+ handleFlipBatch,
2814
+ handleAppearBatch,
2815
+ handleLeaveBatch
2816
+ ];
2817
+ const hubDrain = () => {
2818
+ hubRaf = null;
2819
+ if (!hubCurrentBatch) {
2820
+ if (!hubQueue.length) return;
2821
+ hubCurrentBatch = hubQueue.splice(0, hubQueue.length);
2822
+ hubCursor = 0;
2823
+ }
2824
+ const end = Math.min(hubCursor + throttlePerFrame, hubHandlers.length);
2825
+ for (let i = hubCursor; i < end; i++) {
2826
+ hubHandlers[i](hubCurrentBatch);
2827
+ if (hubHandlers[i] === handleFlipBatch) flushFlipRoots();
2828
+ }
2829
+ hubCursor = end;
2830
+ if (hubCursor < hubHandlers.length) hubRaf = requestAnimationFrame(hubDrain);
2831
+ else {
2832
+ hubCurrentBatch = null;
2833
+ hubCursor = 0;
2834
+ if (hubQueue.length) hubRaf = requestAnimationFrame(hubDrain);
2835
+ }
2836
+ };
2837
+ const scheduleHub = () => {
2838
+ if (hubRaf) return;
2839
+ hubRaf = requestAnimationFrame(hubDrain);
2840
+ };
2841
+ if (throttlePerFrame > 0) {
2842
+ hubObserver = new MutationObserver((mutations) => {
2843
+ hubQueue.push(...mutations);
2844
+ scheduleHub();
2845
+ });
2846
+ hubObserver.observe(document.body, {
2847
+ childList: true,
2848
+ subtree: true
2849
+ });
2850
+ } else {
2851
+ flipObserver = new MutationObserver((mutations) => {
2852
+ handleFlipBatch(mutations);
2853
+ if (!flipPendingRaf) flipPendingRaf = requestAnimationFrame(() => {
2854
+ flipPendingRaf = null;
2855
+ flushFlipRoots();
2856
+ });
2857
+ });
2858
+ flipObserver.observe(document.body, {
2859
+ childList: true,
2860
+ subtree: true
2861
+ });
2862
+ appearObserver = new MutationObserver((mutations) => {
2863
+ handleAppearBatch(mutations);
2864
+ });
2865
+ appearObserver.observe(document.body, {
2866
+ childList: true,
2867
+ subtree: true
2868
+ });
2869
+ qAll("body *").filter((el) => hasGClass(el, "leave")).forEach(captureLeave);
2870
+ leaveObserver = new MutationObserver((mutations) => {
2871
+ handleLeaveBatch(mutations);
2872
+ });
2873
+ leaveObserver.observe(document.body, {
2874
+ childList: true,
2875
+ subtree: true
2876
+ });
2877
+ }
2878
+ if (throttlePerFrame > 0) qAll("body *").filter((el) => hasGClass(el, "leave")).forEach(captureLeave);
2879
+ const qAllLeaves = () => qAll("body *").filter((el) => hasGClass(el, "leave"));
2880
+ let positionTick = false;
2881
+ const refreshLeavePositions = () => {
2882
+ if (positionTick) return;
2883
+ positionTick = true;
2884
+ requestAnimationFrame(() => {
2885
+ qAllLeaves().forEach((el) => {
2886
+ const s = leaveStates.get(el);
2887
+ if (s) s.rect = el.getBoundingClientRect();
2888
+ });
2889
+ positionTick = false;
2890
+ });
2891
+ };
2892
+ window.addEventListener("scroll", refreshLeavePositions, { passive: true });
2893
+ window.addEventListener("resize", refreshLeavePositions, { passive: true });
2894
+ const bpMqls = bpEntries.map(([bp, px]) => {
2895
+ const mql = typeof window !== "undefined" && window.matchMedia ? window.matchMedia(`(min-width: ${px}px)`) : null;
2896
+ if (!mql) return null;
2897
+ const fn = () => ScrollTrigger.refresh();
2898
+ mql.addEventListener?.("change", fn);
2899
+ return {
2900
+ mql,
2901
+ fn
2902
+ };
2903
+ }).filter(Boolean);
2904
+ return () => {
2905
+ appearObserver?.disconnect();
2906
+ leaveObserver?.disconnect();
2907
+ flipObserver?.disconnect();
2908
+ if (hubObserver) hubObserver.disconnect();
2909
+ if (hubRaf) cancelAnimationFrame(hubRaf);
2910
+ if (flipPendingRaf) cancelAnimationFrame(flipPendingRaf);
2911
+ window.removeEventListener("scroll", refreshLeavePositions);
2912
+ window.removeEventListener("resize", refreshLeavePositions);
2913
+ bpMqls.forEach(({ mql, fn }) => mql.removeEventListener?.("change", fn));
2914
+ mm.revert();
2915
+ window.removeEventListener("load", ScrollTrigger.refresh);
2916
+ clearTimeout(refreshTimer);
2917
+ scrollTriggers.forEach((t) => {
2918
+ const tw = t.trigger._scrollTween;
2919
+ const cls = t.trigger.classList;
2920
+ if (tw && !tw.reversed() && (cls?.contains("typewriter") || cls?.contains("scramble"))) tw.progress(1);
2921
+ t.kill(true);
2922
+ t.trigger._scrollTween?.kill();
2923
+ delete t.trigger._scrollTween;
2924
+ });
2925
+ ScrollTrigger.refresh();
2926
+ qAll("[data-gsap-scroll],[data-gsap-setup],[data-gsap-pinned],[data-gsap-scroll-driven]").forEach((el) => {
2927
+ delete el.dataset.gsapScroll;
2928
+ delete el.dataset.gsapSetup;
2929
+ delete el.dataset.gsapPinned;
2930
+ delete el.dataset.gsapScrollDriven;
2931
+ delete el._appeared;
2932
+ });
2933
+ registeredListeners.forEach(({ el, type, fn }) => el.removeEventListener(type, fn));
2934
+ magnetListeners.forEach(({ el, type, fn }) => el.removeEventListener(type, fn));
2935
+ magnetQuery?.removeEventListener("change", applyMagnet);
2936
+ loopEls.forEach(({ el, key }) => el[key]?.kill());
2937
+ document.querySelectorAll("[data-gsap-radiate]").forEach((n) => n.remove());
2938
+ cssTweens.forEach((t) => t?.kill());
2939
+ cssTweens.length = 0;
2940
+ qAll(".typewriter, .scramble").forEach((el) => {
2941
+ const keep = el.isConnected && underPreservedRoot(el);
2942
+ const tw = el.typewriter || el._spawnTween || el._scrollTween;
2943
+ if (!keep && tw && !tw.reversed()) tw.progress(1);
2944
+ tw?.kill();
2945
+ });
2946
+ textSplits.forEach((s) => {
2947
+ if (!(s.elements || []).some((e) => e.isConnected && underPreservedRoot(e))) {
2948
+ (s.elements || []).forEach((e) => splitCache.delete(e));
2949
+ revertSplitInstance(s);
2950
+ }
2951
+ });
2952
+ textSplits.length = 0;
2953
+ onCompleteTweens.forEach((t) => t?.kill());
2954
+ onCompleteTweens.length = 0;
2955
+ setupTeardowns.forEach((fn) => {
2956
+ try {
2957
+ fn();
2958
+ } catch {}
2959
+ });
2960
+ setupTeardowns.length = 0;
2961
+ };
2962
+ }
2963
+ //#endregion
2964
+ //#region AnimToggle.js
2965
+ var STORAGE_KEY = "gclass-animations-enabled";
2966
+ var REDUCED_KEY = "gclass-reduced-motion";
2967
+ var reducedMotionQuery = typeof window !== "undefined" ? window.matchMedia("(prefers-reduced-motion: reduce)") : null;
2968
+ var stored = readStored();
2969
+ var reduced = reducedMotionQuery?.matches ?? false;
2970
+ var forcedReduced = readReducedOverride();
2971
+ var subscribers = /* @__PURE__ */ new Set();
2972
+ function readStored() {
2973
+ if (typeof window === "undefined") return null;
2974
+ try {
2975
+ const raw = localStorage.getItem(STORAGE_KEY);
2976
+ return raw === null ? null : raw === "true";
2977
+ } catch {
2978
+ return null;
2979
+ }
2980
+ }
2981
+ function readReducedOverride() {
2982
+ if (typeof window === "undefined") return false;
2983
+ try {
2984
+ return localStorage.getItem(REDUCED_KEY) === "true";
2985
+ } catch {
2986
+ return false;
2987
+ }
2988
+ }
2989
+ function getEnabled() {
2990
+ if (forcedReduced) return false;
2991
+ return stored === null ? !reduced : stored;
2992
+ }
2993
+ function emit() {
2994
+ subscribers.forEach((fn) => fn(getEnabled()));
2995
+ }
2996
+ if (reducedMotionQuery) reducedMotionQuery.addEventListener("change", () => {
2997
+ reduced = reducedMotionQuery.matches;
2998
+ emit();
2999
+ });
3000
+ function toggleAnimations() {
3001
+ stored = !getEnabled();
3002
+ try {
3003
+ localStorage.setItem(STORAGE_KEY, String(stored));
3004
+ } catch {}
3005
+ emit();
3006
+ if (typeof window !== "undefined") window.location.reload();
3007
+ }
3008
+ function enableReducedMotion() {
3009
+ forcedReduced = true;
3010
+ try {
3011
+ localStorage.setItem(REDUCED_KEY, "true");
3012
+ } catch {}
3013
+ emit();
3014
+ if (typeof window !== "undefined") window.location.reload();
3015
+ }
3016
+ function disableReducedMotion() {
3017
+ forcedReduced = false;
3018
+ try {
3019
+ localStorage.removeItem(REDUCED_KEY);
3020
+ } catch {}
3021
+ emit();
3022
+ if (typeof window !== "undefined") window.location.reload();
3023
+ }
3024
+ var cleanup = null;
3025
+ var bootCleanup = null;
3026
+ var bootTimeout = null;
3027
+ var bootStyle = null;
3028
+ var hasBooted = false;
3029
+ var currentThrottle = 0;
3030
+ var currentFps = 0;
3031
+ var configSubscribers = /* @__PURE__ */ new Set();
3032
+ function getConfigSnapshot() {
3033
+ return {
3034
+ throttlePerFrame: currentThrottle,
3035
+ fps: currentFps
3036
+ };
3037
+ }
3038
+ function emitConfig() {
3039
+ configSubscribers.forEach((fn) => fn(getConfigSnapshot()));
3040
+ }
3041
+ function applyFps(fps) {
3042
+ const v = Number(fps) || 0;
3043
+ currentFps = v;
3044
+ if (v > 0) gsap.ticker.fps(v);
3045
+ else gsap.ticker.fps(0);
3046
+ emitConfig();
3047
+ }
3048
+ function normalizeGclassArgs(throttlePerFrame, fps) {
3049
+ if (typeof throttlePerFrame === "object" && throttlePerFrame !== null) {
3050
+ fps = throttlePerFrame.fps;
3051
+ throttlePerFrame = throttlePerFrame.throttlePerFrame;
3052
+ }
3053
+ return {
3054
+ nextThrottle: throttlePerFrame == null ? 0 : Number(throttlePerFrame) || 0,
3055
+ nextFps: fps == null ? 0 : Number(fps) || 0
3056
+ };
3057
+ }
3058
+ /**
3059
+ * Change GClass runtime options on the fly without reload.
3060
+ * gclassOpts(throttlePerFrame, fps) — both optional numbers.
3061
+ * gclassOpts() or gclassOpts(undefined, undefined) resets to defaults (no throttle, default ticker).
3062
+ * Also accepts gclassOpts({throttlePerFrame, fps}).
3063
+ * Example low-end button: onClick={() => gclassOpts(1, 30)}
3064
+ * Example reset: onClick={() => gclassOpts()} // 0, 60fps rAF
3065
+ */
3066
+ function gclassOpts(throttlePerFrame, fps) {
3067
+ const { nextThrottle, nextFps } = normalizeGclassArgs(throttlePerFrame, fps);
3068
+ currentThrottle = nextThrottle;
3069
+ applyFps(nextFps);
3070
+ if (typeof window !== "undefined" && cleanup && !bootTimeout) {
3071
+ try {
3072
+ cleanup();
3073
+ } catch {}
3074
+ cleanup = null;
3075
+ if (getEnabled()) cleanup = initListeners(document, currentThrottle);
3076
+ }
3077
+ return getConfigSnapshot();
3078
+ }
3079
+ function getGClassConfig() {
3080
+ return getConfigSnapshot();
3081
+ }
3082
+ function subscribeGClassConfig(cb) {
3083
+ configSubscribers.add(cb);
3084
+ return () => configSubscribers.delete(cb);
3085
+ }
3086
+ var readBootTime = (els, fallback) => {
3087
+ let max = null;
3088
+ for (const el of els) {
3089
+ const cls = [...el.classList].find((c) => c.startsWith("boot-time-"));
3090
+ if (cls) {
3091
+ const n = Number(cls.slice(10));
3092
+ if (!Number.isNaN(n)) max = max === null ? n : Math.max(max, n);
3093
+ }
3094
+ }
3095
+ return max ?? fallback;
3096
+ };
3097
+ function initAnimations(throttlePerFrame, fps) {
3098
+ let effThrottle = currentThrottle;
3099
+ let effFps = currentFps;
3100
+ if (throttlePerFrame !== void 0 || fps !== void 0) {
3101
+ const { nextThrottle, nextFps } = normalizeGclassArgs(throttlePerFrame, fps);
3102
+ effThrottle = nextThrottle;
3103
+ effFps = nextFps;
3104
+ currentThrottle = effThrottle;
3105
+ currentFps = effFps;
3106
+ if (effFps > 0) gsap.ticker.fps(effFps);
3107
+ else gsap.ticker.fps(0);
3108
+ emitConfig();
3109
+ } else if (effFps > 0) gsap.ticker.fps(effFps);
3110
+ else gsap.ticker.fps(0);
3111
+ if (typeof window === "undefined" || !getEnabled()) return;
3112
+ if (bootTimeout) {
3113
+ console.log(`[initAnimations] boot already in progress - ignoring duplicate call`);
3114
+ return;
3115
+ }
3116
+ if (cleanup) {
3117
+ cleanup();
3118
+ cleanup = null;
3119
+ }
3120
+ if (bootCleanup) {
3121
+ bootCleanup();
3122
+ bootCleanup = null;
3123
+ }
3124
+ if (bootStyle) {
3125
+ bootStyle.remove();
3126
+ bootStyle = null;
3127
+ document.documentElement.classList.remove("gclass-booting");
3128
+ }
3129
+ const hideBootEls = (els) => {
3130
+ els.forEach((el) => {
3131
+ el.style.display = "none";
3132
+ el.setAttribute("hidden", "");
3133
+ el.setAttribute("data-gclass-boot-hidden", "1");
3134
+ });
3135
+ };
3136
+ const bootEls = typeof document !== "undefined" ? [...document.querySelectorAll(".boot-up")].filter((el) => !el.hasAttribute("data-gclass-boot-hidden")) : [];
3137
+ if (!bootEls.length) {} else if (bootEls.length > 1) {
3138
+ console.error(`[initAnimations] Multiple .boot-up elements detected (${bootEls.length}) - skipping all boot animations`, bootEls);
3139
+ hideBootEls(bootEls);
3140
+ hasBooted = true;
3141
+ } else if (hasBooted && !bootTimeout) {
3142
+ console.log(`[initAnimations] skipping boot on path change (already booted)`, bootEls);
3143
+ hideBootEls(bootEls);
3144
+ hasBooted = true;
3145
+ } else {
3146
+ const bootEl = bootEls[0];
3147
+ if (![...bootEl.classList].some((c) => c.startsWith("boot-end-"))) {}
3148
+ const bootTime = readBootTime(bootEls, defaults.bootTime ?? 2);
3149
+ console.log(`[initAnimations] .boot-up found: ${bootEls.length} - pausing DOM for ${bootTime}s`, bootEls);
3150
+ hasBooted = true;
3151
+ bootStyle = document.createElement("style");
3152
+ bootStyle.id = "gclass-boot-style";
3153
+ bootStyle.textContent = `html.gclass-booting{visibility:hidden} html.gclass-booting .boot-up,html.gclass-booting .boot-up *{visibility:visible} html.gclass-booting .boot-up{position:fixed;inset:0;z-index:9999;display:grid;place-items:center}`;
3154
+ document.head.appendChild(bootStyle);
3155
+ document.documentElement.classList.add("gclass-booting");
3156
+ bootEls.forEach((el) => {
3157
+ el.style.visibility = "visible";
3158
+ });
3159
+ bootCleanup = initListeners(bootEl, effThrottle);
3160
+ bootTimeout = setTimeout(() => {
3161
+ const bootEndCls = [...bootEl.classList].find((c) => c.startsWith("boot-end-"));
3162
+ if (!bootEndCls) {
3163
+ bootCleanup?.();
3164
+ bootCleanup = null;
3165
+ document.documentElement.classList.remove("gclass-booting");
3166
+ bootStyle?.remove();
3167
+ bootStyle = null;
3168
+ hideBootEls(bootEls);
3169
+ bootTimeout = null;
3170
+ cleanup = initListeners(document, effThrottle);
3171
+ return;
3172
+ }
3173
+ const name = bootEndCls.slice(9);
3174
+ const cfg = animations.find((a) => a.sel === "." + name);
3175
+ const from = cfg?.from;
3176
+ const easeCl = [...bootEl.classList].find((c) => c.startsWith("ease-"));
3177
+ const ease = easeCl ? easeCl.split("-")[1] : defaults.ease;
3178
+ const dur = readBootTime([bootEl], defaults.effectDuration ?? 1);
3179
+ const endTimeCls = [...bootEl.classList].find((c) => c.startsWith("boot-end-time-"));
3180
+ const endDur = endTimeCls ? Number(endTimeCls.slice(14)) : dur;
3181
+ const finish = () => {
3182
+ bootCleanup?.();
3183
+ bootCleanup = null;
3184
+ document.documentElement.classList.remove("gclass-booting");
3185
+ bootStyle?.remove();
3186
+ bootStyle = null;
3187
+ hideBootEls(bootEls);
3188
+ bootTimeout = null;
3189
+ cleanup = initListeners(document, effThrottle);
3190
+ };
3191
+ if (!cfg || !from) {
3192
+ console.warn(`[initAnimations] boot-end-${name} has no from state - removing without animation`);
3193
+ finish();
3194
+ return;
3195
+ }
3196
+ gsap.to(bootEl, {
3197
+ ...from,
3198
+ duration: endDur,
3199
+ ease,
3200
+ onComplete: finish
3201
+ });
3202
+ }, bootTime * 1e3);
3203
+ return;
3204
+ }
3205
+ cleanup = initListeners(document, effThrottle);
3206
+ }
3207
+ //#endregion
3208
+ export { SpawnH, SpawnV, animatecss, animations, bell, bounce, countTargetVars, countUp, curtainHorizontal, curtainVertical, customAnims, defaults, disableReducedMotion, drawsvg, drawsvgSplit, enableReducedMotion, expandA, expandDown, expandH, expandLeft, expandRight, expandUp, expandV, expandmove, finalOpacity, flip, gclassOpts, getGClassConfig, hover, initAnimations, initListeners, magnet, magnet3d, marquee, normalize, pulse, radiate, registerComplete, reset, scramble, scrambleSegments, scrambleVars, shake, spawnBlur, spawnClipReveal, spawnFade, spawnSpinCCW, spawnSpinCW, spawnXDown, spawnXUp, spawnYLeft, spawnYRight, spinCCW, spinCW, splitPaths, stashText, subscribeGClassConfig, toggleAnimations, typewriter, verticalmove };