fancoolo-fx 1.0.2 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fancoolo-fx",
3
- "version": "1.0.2",
3
+ "version": "1.1.0",
4
4
  "description": "A class-driven GSAP animation wrapper for WordPress and static sites.",
5
5
  "main": "src/fx.js",
6
6
  "keywords": ["gsap", "animation", "scrolltrigger", "splittext", "wordpress", "gutenberg"],
package/src/fx.js CHANGED
@@ -84,6 +84,10 @@
84
84
  spinReveal: { duration: 1.4, ease: 'power3.out' },
85
85
  bgReveal: { duration: 1, ease: 'power3.out' },
86
86
  scaleIn: { duration: 1, ease: 'power3.out' },
87
+ fadeIn: { duration: 0.8, ease: 'power2.out' },
88
+ blurIn: { duration: 1.2, ease: 'power2.out' },
89
+ clipUp: { duration: 1, ease: 'power3.inOut' },
90
+ clipDown: { duration: 1, ease: 'power3.inOut' },
87
91
  };
88
92
 
89
93
  // ── Helpers ──────────────────────────────────
@@ -241,6 +245,79 @@
241
245
  gsap.from(el, tweenVars);
242
246
  }
243
247
 
248
+ function fadeIn(el, opts) {
249
+ opts = opts || {};
250
+ var o = resolveOptions(el, 'fadeIn', opts);
251
+
252
+ var tweenVars = {
253
+ opacity: 0,
254
+ duration: o.duration,
255
+ ease: o.ease,
256
+ delay: o.delay,
257
+ };
258
+
259
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
260
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
261
+ }
262
+
263
+ gsap.from(el, tweenVars);
264
+ }
265
+
266
+ function blurIn(el, opts) {
267
+ opts = opts || {};
268
+ var o = resolveOptions(el, 'blurIn', opts);
269
+
270
+ var tweenVars = {
271
+ filter: 'blur(' + (opts.blur != null ? opts.blur : 12) + 'px)',
272
+ opacity: 0,
273
+ duration: o.duration,
274
+ ease: o.ease,
275
+ delay: o.delay,
276
+ };
277
+
278
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
279
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
280
+ }
281
+
282
+ gsap.from(el, tweenVars);
283
+ }
284
+
285
+ function clipUp(el, opts) {
286
+ opts = opts || {};
287
+ var o = resolveOptions(el, 'clipUp', opts);
288
+
289
+ var tweenVars = {
290
+ clipPath: 'inset(100% 0 0 0)',
291
+ duration: o.duration,
292
+ ease: o.ease,
293
+ delay: o.delay,
294
+ };
295
+
296
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
297
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
298
+ }
299
+
300
+ gsap.from(el, tweenVars);
301
+ }
302
+
303
+ function clipDown(el, opts) {
304
+ opts = opts || {};
305
+ var o = resolveOptions(el, 'clipDown', opts);
306
+
307
+ var tweenVars = {
308
+ clipPath: 'inset(0 0 100% 0)',
309
+ duration: o.duration,
310
+ ease: o.ease,
311
+ delay: o.delay,
312
+ };
313
+
314
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
315
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
316
+ }
317
+
318
+ gsap.from(el, tweenVars);
319
+ }
320
+
244
321
  // ── Class-to-effect mapping ─────────────────
245
322
 
246
323
  var effects = {
@@ -249,6 +326,10 @@
249
326
  'fx-spin-reveal': spinReveal,
250
327
  'fx-bg-reveal': bgReveal,
251
328
  'fx-scale-in': scaleIn,
329
+ 'fx-fade-in': fadeIn,
330
+ 'fx-blur-in': blurIn,
331
+ 'fx-clip-up': clipUp,
332
+ 'fx-clip-down': clipDown,
252
333
  };
253
334
 
254
335
  var effectsByName = {
@@ -257,6 +338,10 @@
257
338
  spinReveal: spinReveal,
258
339
  bgReveal: bgReveal,
259
340
  scaleIn: scaleIn,
341
+ fadeIn: fadeIn,
342
+ blurIn: blurIn,
343
+ clipUp: clipUp,
344
+ clipDown: clipDown,
260
345
  };
261
346
 
262
347
  // ── Helpers ──────────────────────────────────
@@ -321,6 +406,8 @@
321
406
  });
322
407
 
323
408
  // 3. Bare class inside a section: .fx-<name> (no suffix)
409
+ // Only elements inside a matching section are picked up,
410
+ // but each element triggers itself (same as -st).
324
411
  if (config.sectionSelector) {
325
412
  document.querySelectorAll(config.sectionSelector).forEach(function (section) {
326
413
  var bareEls = Array.from(section.querySelectorAll('.' + name))
@@ -329,8 +416,14 @@
329
416
 
330
417
  var groups = groupByParent(bareEls);
331
418
  groups.forEach(function (group) {
332
- applyScrollGroup(fn, group, section);
333
- group.forEach(function (el) { processed.add(el); });
419
+ group.forEach(function (el, i) {
420
+ fn(el, {
421
+ trigger: 'scroll',
422
+ delay: i * 0.15,
423
+ scrollTrigger: { trigger: el },
424
+ });
425
+ processed.add(el);
426
+ });
334
427
  });
335
428
  });
336
429
  }
@@ -356,6 +449,49 @@
356
449
  });
357
450
  });
358
451
  }
452
+ // 5. fx-stagger-all-[selector] — target children, effect from sibling class
453
+ // Requires an effect class on the same element (e.g. fx-reveal-st).
454
+ document.querySelectorAll('[class*="fx-stagger-all-"]').forEach(function (container) {
455
+ // Parse selector from fx-stagger-all-[img,p]
456
+ var childSelector = null;
457
+ for (var ci = 0; ci < container.classList.length; ci++) {
458
+ var cls = container.classList[ci];
459
+ if (cls.indexOf('fx-stagger-all-[') === 0 && cls.charAt(cls.length - 1) === ']') {
460
+ childSelector = cls.slice('fx-stagger-all-['.length, -1);
461
+ break;
462
+ }
463
+ }
464
+ if (!childSelector) return;
465
+
466
+ // Find which effect class is on this container
467
+ var effectFn = null;
468
+ var effectName = null;
469
+ Object.keys(effects).forEach(function (name) {
470
+ if (container.classList.contains(name + '-st') ||
471
+ container.classList.contains(name + '-pl') ||
472
+ container.classList.contains(name)) {
473
+ effectFn = effects[name];
474
+ effectName = name;
475
+ }
476
+ });
477
+ if (!effectFn) return; // No effect class paired — do nothing
478
+
479
+ var isScroll = container.classList.contains(effectName + '-st') ||
480
+ container.classList.contains(effectName);
481
+ var children = Array.from(container.querySelectorAll(childSelector))
482
+ .filter(function (el) { return !processed.has(el); });
483
+ if (children.length === 0) return;
484
+
485
+ children.forEach(function (child, i) {
486
+ var opts = { delay: i * 0.15 };
487
+ if (isScroll) {
488
+ opts.trigger = 'scroll';
489
+ opts.scrollTrigger = { trigger: child };
490
+ }
491
+ effectFn(child, opts);
492
+ processed.add(child);
493
+ });
494
+ });
359
495
  }
360
496
 
361
497
  // ── Boot ────────────────────────────────────
@@ -389,6 +525,10 @@
389
525
  spinReveal: spinReveal,
390
526
  bgReveal: bgReveal,
391
527
  scaleIn: scaleIn,
528
+ fadeIn: fadeIn,
529
+ blurIn: blurIn,
530
+ clipUp: clipUp,
531
+ clipDown: clipDown,
392
532
  init: init,
393
533
  };
394
534
  })();
@@ -84,6 +84,10 @@
84
84
  spinReveal: { duration: 1.4, ease: 'power3.out' },
85
85
  bgReveal: { duration: 1, ease: 'power3.out' },
86
86
  scaleIn: { duration: 1, ease: 'power3.out' },
87
+ fadeIn: { duration: 0.8, ease: 'power2.out' },
88
+ blurIn: { duration: 1.2, ease: 'power2.out' },
89
+ clipUp: { duration: 1, ease: 'power3.inOut' },
90
+ clipDown: { duration: 1, ease: 'power3.inOut' },
87
91
  };
88
92
 
89
93
  // ── Helpers ──────────────────────────────────
@@ -241,6 +245,79 @@
241
245
  gsap.from(el, tweenVars);
242
246
  }
243
247
 
248
+ function fadeIn(el, opts) {
249
+ opts = opts || {};
250
+ var o = resolveOptions(el, 'fadeIn', opts);
251
+
252
+ var tweenVars = {
253
+ opacity: 0,
254
+ duration: o.duration,
255
+ ease: o.ease,
256
+ delay: o.delay,
257
+ };
258
+
259
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
260
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
261
+ }
262
+
263
+ gsap.from(el, tweenVars);
264
+ }
265
+
266
+ function blurIn(el, opts) {
267
+ opts = opts || {};
268
+ var o = resolveOptions(el, 'blurIn', opts);
269
+
270
+ var tweenVars = {
271
+ filter: 'blur(' + (opts.blur != null ? opts.blur : 12) + 'px)',
272
+ opacity: 0,
273
+ duration: o.duration,
274
+ ease: o.ease,
275
+ delay: o.delay,
276
+ };
277
+
278
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
279
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
280
+ }
281
+
282
+ gsap.from(el, tweenVars);
283
+ }
284
+
285
+ function clipUp(el, opts) {
286
+ opts = opts || {};
287
+ var o = resolveOptions(el, 'clipUp', opts);
288
+
289
+ var tweenVars = {
290
+ clipPath: 'inset(100% 0 0 0)',
291
+ duration: o.duration,
292
+ ease: o.ease,
293
+ delay: o.delay,
294
+ };
295
+
296
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
297
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
298
+ }
299
+
300
+ gsap.from(el, tweenVars);
301
+ }
302
+
303
+ function clipDown(el, opts) {
304
+ opts = opts || {};
305
+ var o = resolveOptions(el, 'clipDown', opts);
306
+
307
+ var tweenVars = {
308
+ clipPath: 'inset(0 0 100% 0)',
309
+ duration: o.duration,
310
+ ease: o.ease,
311
+ delay: o.delay,
312
+ };
313
+
314
+ if (opts.trigger === 'scroll' || opts.scrollTrigger) {
315
+ tweenVars.scrollTrigger = buildScrollTrigger(el, opts.scrollTrigger || {});
316
+ }
317
+
318
+ gsap.from(el, tweenVars);
319
+ }
320
+
244
321
  // ── Class-to-effect mapping ─────────────────
245
322
 
246
323
  var effects = {
@@ -249,6 +326,10 @@
249
326
  'fx-spin-reveal': spinReveal,
250
327
  'fx-bg-reveal': bgReveal,
251
328
  'fx-scale-in': scaleIn,
329
+ 'fx-fade-in': fadeIn,
330
+ 'fx-blur-in': blurIn,
331
+ 'fx-clip-up': clipUp,
332
+ 'fx-clip-down': clipDown,
252
333
  };
253
334
 
254
335
  var effectsByName = {
@@ -257,6 +338,10 @@
257
338
  spinReveal: spinReveal,
258
339
  bgReveal: bgReveal,
259
340
  scaleIn: scaleIn,
341
+ fadeIn: fadeIn,
342
+ blurIn: blurIn,
343
+ clipUp: clipUp,
344
+ clipDown: clipDown,
260
345
  };
261
346
 
262
347
  // ── Helpers ──────────────────────────────────
@@ -321,6 +406,8 @@
321
406
  });
322
407
 
323
408
  // 3. Bare class inside a section: .fx-<name> (no suffix)
409
+ // Only elements inside a matching section are picked up,
410
+ // but each element triggers itself (same as -st).
324
411
  if (config.sectionSelector) {
325
412
  document.querySelectorAll(config.sectionSelector).forEach(function (section) {
326
413
  var bareEls = Array.from(section.querySelectorAll('.' + name))
@@ -329,8 +416,14 @@
329
416
 
330
417
  var groups = groupByParent(bareEls);
331
418
  groups.forEach(function (group) {
332
- applyScrollGroup(fn, group, section);
333
- group.forEach(function (el) { processed.add(el); });
419
+ group.forEach(function (el, i) {
420
+ fn(el, {
421
+ trigger: 'scroll',
422
+ delay: i * 0.15,
423
+ scrollTrigger: { trigger: el },
424
+ });
425
+ processed.add(el);
426
+ });
334
427
  });
335
428
  });
336
429
  }
@@ -356,6 +449,49 @@
356
449
  });
357
450
  });
358
451
  }
452
+ // 5. fx-stagger-all-[selector] — target children, effect from sibling class
453
+ // Requires an effect class on the same element (e.g. fx-reveal-st).
454
+ document.querySelectorAll('[class*="fx-stagger-all-"]').forEach(function (container) {
455
+ // Parse selector from fx-stagger-all-[img,p]
456
+ var childSelector = null;
457
+ for (var ci = 0; ci < container.classList.length; ci++) {
458
+ var cls = container.classList[ci];
459
+ if (cls.indexOf('fx-stagger-all-[') === 0 && cls.charAt(cls.length - 1) === ']') {
460
+ childSelector = cls.slice('fx-stagger-all-['.length, -1);
461
+ break;
462
+ }
463
+ }
464
+ if (!childSelector) return;
465
+
466
+ // Find which effect class is on this container
467
+ var effectFn = null;
468
+ var effectName = null;
469
+ Object.keys(effects).forEach(function (name) {
470
+ if (container.classList.contains(name + '-st') ||
471
+ container.classList.contains(name + '-pl') ||
472
+ container.classList.contains(name)) {
473
+ effectFn = effects[name];
474
+ effectName = name;
475
+ }
476
+ });
477
+ if (!effectFn) return; // No effect class paired — do nothing
478
+
479
+ var isScroll = container.classList.contains(effectName + '-st') ||
480
+ container.classList.contains(effectName);
481
+ var children = Array.from(container.querySelectorAll(childSelector))
482
+ .filter(function (el) { return !processed.has(el); });
483
+ if (children.length === 0) return;
484
+
485
+ children.forEach(function (child, i) {
486
+ var opts = { delay: i * 0.15 };
487
+ if (isScroll) {
488
+ opts.trigger = 'scroll';
489
+ opts.scrollTrigger = { trigger: child };
490
+ }
491
+ effectFn(child, opts);
492
+ processed.add(child);
493
+ });
494
+ });
359
495
  }
360
496
 
361
497
  // ── Boot ────────────────────────────────────
@@ -389,6 +525,10 @@
389
525
  spinReveal: spinReveal,
390
526
  bgReveal: bgReveal,
391
527
  scaleIn: scaleIn,
528
+ fadeIn: fadeIn,
529
+ blurIn: blurIn,
530
+ clipUp: clipUp,
531
+ clipDown: clipDown,
392
532
  init: init,
393
533
  };
394
534
  })();
@@ -1,9 +1,9 @@
1
1
  <?php
2
2
  /**
3
3
  * Plugin Name: Fancoolo FX
4
- * Plugin URI: https://github.com/krstivoja/gsap-animations-template
4
+ * Plugin URI: https://github.com/krstivoja/fancoolo-fx
5
5
  * Description: A class-driven GSAP animation wrapper. Add CSS classes in Gutenberg and get animations — no JavaScript needed.
6
- * Version: 1.0.2
6
+ * Version: 1.1.0
7
7
  * Author: Fancoolo
8
8
  * Author URI: https://github.com/krstivoja
9
9
  * License: ISC
@@ -14,7 +14,7 @@ if ( ! defined( 'ABSPATH' ) ) {
14
14
  exit;
15
15
  }
16
16
 
17
- define( 'FANCOOLO_FX_VERSION', '1.0.2' );
17
+ define( 'FANCOOLO_FX_VERSION', '1.1.0' );
18
18
  define( 'FANCOOLO_FX_PATH', plugin_dir_path( __FILE__ ) );
19
19
  define( 'FANCOOLO_FX_URL', plugin_dir_url( __FILE__ ) );
20
20
 
@@ -346,6 +346,33 @@ FX.init();</pre>
346
346
  <div class="ffx-class-row"><code data-copy>fx-scale-in-st</code><span class="ffx-desc">Scroll triggered</span></div>
347
347
  <div class="ffx-class-row"><code data-copy>fx-scale-in</code><span class="ffx-desc">Auto triggered inside a section</span></div>
348
348
 
349
+ <!-- Fade In -->
350
+ <div class="ffx-group-title">Fade In</div>
351
+ <div class="ffx-class-row"><code data-copy>fx-fade-in-pl</code><span class="ffx-desc">Page load — opacity only, no movement</span></div>
352
+ <div class="ffx-class-row"><code data-copy>fx-fade-in-st</code><span class="ffx-desc">Scroll triggered</span></div>
353
+ <div class="ffx-class-row"><code data-copy>fx-fade-in</code><span class="ffx-desc">Auto triggered inside a section</span></div>
354
+
355
+ <!-- Blur In -->
356
+ <div class="ffx-group-title">Blur In</div>
357
+ <div class="ffx-class-row"><code data-copy>fx-blur-in-pl</code><span class="ffx-desc">Page load — fade in while deblurring</span></div>
358
+ <div class="ffx-class-row"><code data-copy>fx-blur-in-st</code><span class="ffx-desc">Scroll triggered</span></div>
359
+ <div class="ffx-class-row"><code data-copy>fx-blur-in</code><span class="ffx-desc">Auto triggered inside a section</span></div>
360
+
361
+ <!-- Clip Up -->
362
+ <div class="ffx-group-title">Clip Reveal</div>
363
+ <div class="ffx-class-row"><code data-copy>fx-clip-up-pl</code><span class="ffx-desc">Page load — clip-path wipe from bottom</span></div>
364
+ <div class="ffx-class-row"><code data-copy>fx-clip-up-st</code><span class="ffx-desc">Scroll triggered</span></div>
365
+ <div class="ffx-class-row"><code data-copy>fx-clip-up</code><span class="ffx-desc">Auto triggered inside a section</span></div>
366
+ <div class="ffx-class-row"><code data-copy>fx-clip-down-pl</code><span class="ffx-desc">Page load — clip-path wipe from top</span></div>
367
+ <div class="ffx-class-row"><code data-copy>fx-clip-down-st</code><span class="ffx-desc">Scroll triggered</span></div>
368
+ <div class="ffx-class-row"><code data-copy>fx-clip-down</code><span class="ffx-desc">Auto triggered inside a section</span></div>
369
+
370
+ <!-- Stagger All -->
371
+ <div class="ffx-group-title" style="margin-top: 20px;">Stagger Children <span style="font-weight:normal;color:#646970;font-size:12px;">(pair with an effect class)</span></div>
372
+ <div class="ffx-class-row"><code data-copy>fx-stagger-all-[img]</code><span class="ffx-desc">Target all img children — requires effect class</span></div>
373
+ <div class="ffx-class-row"><code data-copy>fx-stagger-all-[img,p]</code><span class="ffx-desc">Target img and p children</span></div>
374
+ <div class="ffx-class-row"><code data-copy>fx-stagger-all-[.card]</code><span class="ffx-desc">Target children by CSS class</span></div>
375
+
349
376
  <!-- Modifiers -->
350
377
  <div class="ffx-group-title" style="margin-top: 20px;">Modifiers <span style="font-weight:normal;color:#646970;font-size:12px;">(combine with any effect class)</span></div>
351
378
  <div class="ffx-class-row"><code data-copy>fx-duration-[1.5]</code><span class="ffx-desc">Custom duration (seconds)</span></div>
@@ -360,7 +387,7 @@ FX.init();</pre>
360
387
  <strong style="color:#1d2327;">Important:</strong> Always add <code>FX.init();</code> at the end when changing config — it re-scans the page with your new settings.
361
388
  </p>
362
389
  <p style="margin-top: 12px;">
363
- <a href="https://krstivoja.github.io/gsap-animations-template/documentation/" target="_blank">
390
+ <a href="https://krstivoja.github.io/fancoolo-fx/documentation/" target="_blank">
364
391
  Full Documentation &rarr;
365
392
  </a>
366
393
  </p>