PageSourceSearch

https://marktuan.com/wp-content/plugins/pe-core/assets/js/widget-scripts.js?ver=7.1

js marktuan.com collected 2026-09-25 10:58:54 UTC 195,283 bytes, 5,074 lines download raw bytes

1(function ($) {
2    "use strict";
3
4    gsap.registerPlugin(Draggable, ScrollTrigger, ScrollToPlugin, InertiaPlugin, ScrollSmoother, Flip);
5
6    gsap.config({
7        nullTargetWarn: false
8    });
9
10    function parents(element, selector) {
11        const parentsArray = [];
12        let currentElement = element.parentElement;
13
14        while (currentElement !== null) {
15            if (currentElement.matches(selector)) {
16                parentsArray.push(currentElement);
17            }
18            currentElement = currentElement.parentElement;
19        }
20
21        return parentsArray;
22    }
23
24    var mobileQuery = window.matchMedia('(max-width: 450px)'),
25        siteHeader = $('.site-header'),
26        matchMedia = gsap.matchMedia(),
27        isPhone = '(max-width: 450px)',
28        isTablet = '(min-width: 450px) and (max-width: 900px)',
29        isDesktop = '(min-width: 900px)';
30
31
32
33    var cursor = document.getElementById('mouseCursor') ? document.getElementById('mouseCursor') : false,
34        cursorText = cursor ? cursor.querySelector('.cursor-text') : false,
35        cursorIcon = cursor ? cursor.querySelector('.cursor-icon') : false;
36
37
38    var keys = {
39        37: 1,
40        38: 1,
41        39: 1,
42        40: 1
43    };
44
45    function preventDefault(e) {
46        e.preventDefault();
47    }
48
49    function preventDefaultForScrollKeys(e) {
50        if (keys[e.keyCode]) {
51            preventDefault(e);
52            return false;
53        }
54    }
55
56
57    var supportsPassive = false;
58    try {
59        window.addEventListener("test", null, Object.defineProperty({}, 'passive', {
60            get: function () {
61                supportsPassive = true;
62            }
63        }));
64    } catch (e) { }
65
66    var wheelOpt = supportsPassive ? {
67        passive: false
68    } : false;
69    var wheelEvent = 'onwheel' in document.createElement('div') ? 'wheel' : 'mousewheel';
70
71    // call this to Disable
72    function disableScroll() {
73
74        if (ScrollSmoother.get()) {
75            let farahSmoother = ScrollSmoother.get();
76            farahSmoother.paused(true);
77        } else {
78
79            window.addEventListener('DOMMouseScroll', preventDefault, false); // older FF
80            window.addEventListener(wheelEvent, preventDefault, wheelOpt); // modern desktop
81            window.addEventListener('touchmove', preventDefault, wheelOpt); // mobile
82            window.addEventListener('keydown', preventDefaultForScrollKeys, false);
83        }
84
85    }
86
87    // call this to Enable
88    function enableScroll() {
89
90        if (ScrollSmoother.get()) {
91            let farahSmoother = ScrollSmoother.get();
92            farahSmoother.paused(false);
93        } else {
94            window.removeEventListener('DOMMouseScroll', preventDefault, false);
95            window.removeEventListener(wheelEvent, preventDefault, wheelOpt);
96            window.removeEventListener('touchmove', preventDefault, wheelOpt);
97            window.removeEventListener('keydown', preventDefaultForScrollKeys, false);
98        }
99
100    }
101
102
103    /////////////////////////
104    //   Global Scripts   //
105    /////////////////////////
106
107
108    function peScrollButton(button) {
109
110        var target = button.dataset.scrollTo,
111            duration = button.dataset.scrollDuration;
112
113        button.addEventListener('click', () => {
114
115            gsap.to(window, {
116                duration: duration,
117                scrollTo: isNaN(target) ? $(target).offset().top : target,
118                ease: 'expo.inOut',
119            });
120
121        })
122
123    }
124
125    function resetCursor() {
126
127        cursor.classList.remove('cursor--default')
128        cursor.classList.remove('cursor--text');
129        cursor.classList.remove('cursor--icon');
130        cursor.classList.remove('dragging--right');
131        cursor.classList.remove('dragging--left');
132        cursorText.innerHTML = '';
133        cursorIcon.innerHTML = '';
134
135    }
136
137    barba.hooks.before(() => {
138
139        resetCursor();
140    });
141
142    barba.hooks.afterEnter(() => {
143
144        resetCursor();
145    });
146
147
148    function peCursorInteraction(target) {
149
150        // Types: default/text/icon
151
152        var type = target.dataset.cursorType,
153            text = target.dataset.cursorText,
154            icon = target.dataset.cursorIcon;
155
156        target.addEventListener('mouseenter', () => {
157
158            if (!target.classList.contains('cursor--disabled')) {
159
160
161                if (type === 'default') {
162
163                    cursor.classList.add('cursor--default')
164                }
165
166                if (type === 'text') {
167
168                    cursor.classList.add('cursor--text');
169                    cursorText.innerHTML = text;
170
171                }
172
173                if (type === 'icon') {
174
175                    cursor.classList.add('cursor--icon');
176                    cursorIcon.innerHTML = icon;
177
178                }
179            }
180        });
181
182        target.addEventListener('mouseleave', () => resetCursor());
183
184    }
185
186
187    function peCursorDrag(target, init = true) {
188        resetCursor()
189
190        let width = target.clientWidth;
191
192        function init() {
193
194            cursor.classList.add('cursor--icon');
195            cursor.classList.add('cursor--drag');
196
197            cursorIcon.innerHTML = '<i aria-hidden="true" class="material-icons-sharp md-arrow_forward" data-md-icon="arrow_backward"></i>';
198
199        }
200
201
202        target.addEventListener('mousemove', e => {
203
204            if (e.clientX < width / 2) {
205
206                cursor.classList.remove('dragging--right');
207                cursor.classList.add('dragging--left');
208
209
210            } else if (e.clientX > e.clientX < width / 2) {
211
212                cursor.classList.remove('dragging--left');
213                cursor.classList.add('dragging--right');
214            }
215
216
217        })
218
219        target.addEventListener('mouseleave', () => resetCursor());
220        target.addEventListener('mouseenter', () => init());
221
222
223    }
224
225    function peCustomSelect(target) {
226
227        var x, i, j, l, ll, selElmnt, a, b, c;
228        /*look for any elements with the class "custom-select":*/
229        x = target;
230        l = x.length;
231        for (i = 0; i < l; i++) {
232            selElmnt = x[i].getElementsByTagName("select")[0];
233            ll = selElmnt.length;
234            /*for each element, create a new DIV that will act as the selected item:*/
235            a = document.createElement("DIV");
236            a.setAttribute("class", "select-selected");
237            a.innerHTML = selElmnt.options[selElmnt.selectedIndex].innerHTML;
238            a.setAttribute('data-select', selElmnt.options[selElmnt.selectedIndex].innerHTML);
239            x[i].appendChild(a);
240            /*for each element, create a new DIV that will contain the option list:*/
241            b = document.createElement("DIV");
242            b.setAttribute("class", "select-items select-hide");
243            for (j = 1; j < ll; j++) {
244                /*for each option in the original select element,
245                create a new DIV that will act as an option item:*/
246                c = document.createElement("DIV");
247                c.innerHTML = selElmnt.options[j].innerHTML;
248                c.addEventListener("click", function (e) {
249                    /*when an item is clicked, update the original select box,
250                    and the selected item:*/
251                    var y, i, k, s, h, sl, yl;
252                    s = this.parentNode.parentNode.getElementsByTagName("select")[0];
253                    sl = s.length;
254                    h = this.parentNode.previousSibling;
255                    for (i = 0; i < sl; i++) {
256                        if (s.options[i].innerHTML == this.innerHTML) {
257                            s.selectedIndex = i;
258                            h.setAttribute('data-select', this.innerHTML);
259                            y = this.parentNode.getElementsByClassName("same-as-selected");
260                            yl = y.length;
261                            for (k = 0; k < yl; k++) {
262                                y[k].removeAttribute("class");
263                            }
264                            this.setAttribute("class", "same-as-selected");
265                            break;
266                        }
267                    }
268                    h.click();
269                });
270                b.appendChild(c);
271            }
272            x[i].appendChild(b);
273            a.addEventListener("click", function (e) {
274                /*when the select box is clicked, close any other select boxes,
275                and open/close the current select box:*/
276                e.stopPropagation();
277                closeAllSelect(this);
278                this.nextSibling.classList.toggle("select-hide");
279                this.classList.toggle("select-arrow-active");
280            });
281        }
282
283        function closeAllSelect(elmnt) {
284            /*a function that will close all select boxes in the document,
285            except the current select box:*/
286            var x, y, i, xl, yl, arrNo = [];
287            x = document.getElementsByClassName("select-items");
288            y = document.getElementsByClassName("select-selected");
289            xl = x.length;
290            yl = y.length;
291            for (i = 0; i < yl; i++) {
292                if (elmnt == y[i]) {
293                    arrNo.push(i)
294                } else {
295                    y[i].classList.remove("select-arrow-active");
296                }
297            }
298            for (i = 0; i < xl; i++) {
299                if (arrNo.indexOf(i)) {
300                    x[i].classList.add("select-hide");
301                }
302            }
303        }
304        /*if the user clicks anywhere outside the select box,
305        then close all select boxes:*/
306        document.addEventListener("click", closeAllSelect);
307
308    }
309
310    function isPinnng(trigger, add) {
311
312        if (!mobileQuery.matches) {
313            if (add) {
314                if (document.querySelector(trigger)) {
315                    document.querySelector(trigger).classList.add('is-pinning')
316                }
317
318            } else {
319                if (document.querySelector(trigger)) {
320                    document.querySelector(trigger).classList.remove('is-pinning')
321                }
322            }
323
324        }
325
326    }
327
328    window.addEventListener('elementor/frontend/init', function () {
329
330        if (document.body.classList.contains('e-preview--show-hidden-elements')) {
331
332            document.body.setAttribute('data-barba-prevent', 'all');
333
334        }
335
336        elementorFrontend.hooks.addAction('frontend/element_ready/global', function ($scope, $) {
337
338            var jsScopeArray = $scope.toArray();
339            for (var i = 0; i < jsScopeArray.length; i++) {
340                var scope = jsScopeArray[i],
341                    id = scope.dataset.id;
342
343                // Reset on Editor 
344                if (document.body.classList.contains('e-preview--show-hidden-elements')) {
345                    if (ScrollTrigger.getById(id)) {
346                        ScrollTrigger.getById(id).kill();
347                    }
348
349                }
350                // Reset on Editor 
351
352                var containerBg = document.querySelector('.bg--for--' + id);
353                containerBg ? scope.prepend(containerBg) : '';
354
355                if (scope.querySelector('.container--bg')) {
356
357                    //                    let video = scope.querySelector('.container--bg').querySelector('.pe-video');
358                    //                    video ? pe_coreVideo(video) : '';
359                }
360
361                if (scope.classList.contains('animate--radius')) {
362
363                    setTimeout(() => {
364
365                        let radius = window.getComputedStyle(scope).borderRadius.split(' '),
366                            width = scope.getBoundingClientRect().width,
367                            padding = getComputedStyle(scope).getPropertyValue('--container-default-padding-left');
368
369                        gsap.to(scope, {
370                            borderRadius: '0px',
371                            width: scope.classList.contains('integared--width') ? '100%' : '--width',
372                            padding: padding,
373                            ease: 'none',
374                            scrollTrigger: {
375                                trigger: scope,
376                                start: 'top bottom',
377                                end: 'top top',
378                                scrub: true
379                            }
380                        })
381
382                        gsap.fromTo(scope, {
383                            borderRadius: '0px 0px 0px 0px',
384                            padding: padding,
385                        }, {
386                            borderRadius: radius,
387                            width: width,
388                            padding: 0,
389                            ease: 'none',
390                            immediateRender: false,
391                            scrollTrigger: {
392                                trigger: scope,
393                                start: 'bottom  bottom',
394                                end: 'bottom center',
395                                scrub: true
396                            }
397                        })
398
399                    }, 1);
400
401                }
402
403                if (scope.classList.contains('backward__container')) {
404                    setTimeout(function(){
405                        ScrollTrigger.create({
406                            trigger: scope,
407                            start: 'bottom bottom',
408                            end: 'bottom top',
409                            scrub: 2,
410                            pin: true,
411                            pinSpacing: false,
412                            id: id
413                        })
414                    }, 1000)
415                    
416
417                }
418
419                if (scope.classList.contains('parallax__active')) {
420
421                    gsap.fromTo(scope.querySelector('.parallax--wrap'), {
422                        yPercent: -20
423                    }, {
424                        yPercent: 0,
425                        scrollTrigger: {
426                            trigger: scope,
427                            start: 'top bottom',
428                            end: 'bottom top',
429                            scrub: true
430                        }
431                    })
432                }
433
434
435                //Animations
436                setTimeout(() => {
437
438                    if (scope.hasAttribute('data-anim-general')) {
439
440                        new peGeneralAnimation(scope, id);
441
442                    }
443
444                    if (scope.classList.contains('will__animated') && scope.querySelector('.container--anim--hold')) {
445
446                        let hold = scope.querySelector('.container--anim--hold'),
447                            anim = hold.dataset.animation,
448                            sett = hold.dataset.settings;
449
450                        scope.setAttribute('data-animation', anim);
451                        scope.setAttribute('data-settings', sett);
452
453                        new peGeneralAnimation(scope, id);
454
455
456                    }
457
458                }, 10);
459
460                if (scope.classList.contains('convert--carousel')) {
461
462                    let width = scope.offsetWidth,
463                        classList = scope.className,
464                        classes = classList.split(' '),
465                        carouselIdClass = classes.find(cls => cls.startsWith('carousel_id')),
466                        carouselTriggerClass = classes.find(cls => cls.startsWith('carousel_trigger')),
467                        trigger = carouselTriggerClass ? carouselTriggerClass.substring("carousel_trigger_".length) : '.' + scope.classList[0],
468                        id = carouselIdClass ? carouselIdClass.substring("carousel_id_".length) : scope.dataset.id,
469                        items = scope.children;
470
471                    for (var i = 0; i < items.length; i++) {
472
473                        items[i].classList.contains('e-con') ? items[i].classList.add('cr--item') : '';
474                        items[i].setAttribute('data-cr', i + 1);
475
476                    }
477
478                    scope.setAttribute('data-total', scope.querySelectorAll('.cr--item').length);
479
480                    if (scope.classList.contains('cr--drag')) {
481
482                        Draggable.create(scope, {
483                            id: id,
484                            type: 'x',
485                            bounds: {
486                                minX: 0,
487                                maxX: -width + document.body.clientWidth
488                            },
489                            lockAxis: true,
490                            dragResistance: 0.5,
491                            inertia: true,
492                        });
493
494                        scope.classList.contains('cursor_drag') ? peCursorDrag(scope) : '';
495
496
497                    } else if (scope.classList.contains('cr--scroll')) {
498
499                        gsap.to(scope, {
500                            x: (-1 * width) + document.body.clientWidth,
501                            scrollTrigger: {
502                                id: id,
503                                trigger: trigger,
504                                scrub: true,
505                                pin: trigger,
506                                ease: "elastic.out(1, 0.3)",
507                                start: 'center center',
508                                end: 'bottom+=6000 bottom'
509                            }
510                        })
511
512                    }
513
514                }
515
516                if (scope.classList.contains('convert--layered')) {
517                    setTimeout(function(){
518
519                    let items = scope.children,
520                        classList = scope.className,
521                        classes = classList.split(' '),
522                        speedClass = classes.find(cls => cls.startsWith('layered_speed')),
523                        speed = speedClass ? speedClass.substring("layered_speed_".length) : '.' + scope.classList[0],
524                        triggerClass = classes.find(cls => cls.startsWith('layered_target')),
525                        trigger = triggerClass ? triggerClass.substring("layered_target_".length) : scope;
526
527                    let tl = gsap.timeline({
528                        scrollTrigger: {
529                            trigger: trigger,
530                            start: 'top top',
531                            end: 'bottom+=' + speed + ' top',
532                            pin: trigger,
533                            scrub: true,
534                            markers: false
535                        }
536                    });
537
538                    
539
540                    for (var i = 0; i < items.length; i++) {
541
542                        if (items[i].classList.contains('e-con')) {
543
544                            if (i != 0) {
545                                tl.to(items[i], {
546                                    yPercent: 0,
547                                    y: 0,
548                                    ease: 'none'
549                                }, 'label_' + i)
550
551                                if (window.screen.height < items[i].getBoundingClientRect().height) {
552
553                                    tl.to(items[i], {
554                                        y: window.screen.height - items[i].getBoundingClientRect().height,
555                                        ease: 'none'
556                                    }, 'label_' + i)
557
558                                }
559
560                                tl.to(items[i - 1], {
561                                    // opacity: 0,
562                                    // scale: 0.9,
563                                    // '--op': 1,
564                                    ease: 'none'
565                                }, 'label_' + i)
566
567                            }
568                        }
569
570
571
572                    }
573                }, 500)
574                }
575
576                if (scope.classList.contains('convert--tabs')) {
577                    let id = scope.dataset.id,
578                        innerContent = scope.innerHTML,
579                        titles,
580                        wrap = document.createElement("div");
581
582                    wrap.classList.add('tabs--wrapper');
583                    scope.insertBefore(wrap, scope.childNodes[0])
584
585                    let wrapper = scope.querySelector('.tabs--wrapper'),
586                        econs = Array.from(scope.children).filter(child => child.classList.contains('e-con'));
587
588                    if (scope.querySelector('.container--tab--titles--wrap')) {
589                        titles = scope.querySelector('.container--tab--titles--wrap');
590                        scope.insertBefore(titles, scope.firstChild);
591
592                    } else {
593                        titles = document.querySelector('.container--tab--titles__' + id);
594                        scope.insertBefore(titles, scope.firstChild);
595                    }
596
597                    let titlesWrap = scope.querySelector('.container--tab--titles--wrap');
598
599
600
601
602                    for (let i = 0; i <= econs.length; i++) {
603                        let tab = econs[i];
604
605                        if (tab && tab.nodeName === 'DIV' && tab.classList.contains('e-con')) {
606                            tab.classList.add('container--tab--item');
607                        }
608                    }
609
610                    let tabItems = scope.querySelectorAll('.container--tab--item');
611
612                    tabItems.forEach((tabItem, i) => {
613                        i++
614                        tabItem.classList.add('tab--item__' + i);
615                        if (i == 1) {
616                            tabItem.classList.add('active');
617                        }
618                    });
619
620                    gsap.set(wrapper, {
621                        height: scope.querySelector('.container--tab--item.active').offsetHeight
622                    })
623
624                    let arr = [];
625
626                    titles.querySelectorAll('.container--tab--title').forEach(title => {
627
628
629                        arr.push(title.getBoundingClientRect().left);
630
631                        title.addEventListener('click', (self) => {
632
633                            if (titlesWrap.getBoundingClientRect().width > document.body.clientWidth) {
634
635                                gsap.to(titlesWrap, {
636                                    x: arr[title.dataset.index - 1] * -1
637                                })
638                            }
639
640                            scope.querySelector('.container--tab--title.active').classList.remove('active');
641                            title.classList.add('active');
642
643                            let findCont = scope.querySelector('.tab--item__' + title.dataset.index),
644                                state = Flip.getState(tabItems);
645
646                            gsap.set(tabItems, {
647                                display: 'none',
648                            })
649
650                            gsap.set(findCont, {
651                                display: 'flex',
652                            });
653
654                            Flip.from(state, {
655                                duration: .75,
656                                ease: "power3.inOut",
657                                absolute: true,
658                                fade: true,
659                                onStart: () => {
660
661                                    gsap.to(wrapper, {
662                                        height: findCont.offsetHeight,
663                                        duration: .75,
664                                        ease: "power3.inOut",
665                                    })
666
667                                },
668                                onComplete: () => {
669                                    ScrollTrigger.refresh();
670                                },
671                                onEnter: (elements) =>
672                                    gsap.fromTo(
673                                        elements,
674                                        {
675                                            opacity: 0,
676                                            // y: 300,
677                                            scale: 0.9
678                                        },
679                                        {
680                                            opacity: 1,
681                                            scale: 1,
682                                            duration: .75,
683                                            // y: 0,
684                                            delay: 0,
685                                            ease: "power3.inOut",
686                                        }
687                                    ),
688                                onLeave: (elements) =>
689                                    gsap.to(elements, {
690                                        opacity: 0,
691                                        scale: .9,
692                                        duration: .75,
693                                        ease: "power3.inOut",
694                                    })
695                            });
696
697                        })
698
699                    })
700
701
702
703                }
704                if (scope.dataset.title && parents(scope, '.convert--accordion').length) {
705
706                    scope.classList.add('container--accordion--item');
707                    scope.classList.add('acc--item__' + scope.dataset.id);
708                }
709
710                if (scope.querySelector('.container--accordion--title') && (!scope.classList.contains('convert--accordion')) && (!scope.classList.contains('convert--tabs'))) {
711
712                    let title = scope.querySelector('.container--accordion--title');
713
714                    title.setAttribute('data-id', scope.dataset.id)
715
716                    scope.classList.add('container--accordion--item');
717                    scope.classList.add('acc--item__' + scope.dataset.id);
718
719                    scope.parentNode.insertBefore(title, scope);
720
721
722                }
723
724
725                setTimeout(() => {
726                    if (scope.classList.contains('convert--accordion')) {
727
728                        let titles = scope.querySelectorAll('.container--accordion--title'),
729                            contents = scope.querySelectorAll('.container--accordion--item');
730
731
732                        if (scope.classList.contains('active--first')) {
733                            contents[0].classList.add('cont--acc--active')
734                        }
735
736                        titles.forEach((title, i) => {
737                            i++
738                            title.querySelector('.ac-order').innerHTML = '(0' + i + ')';
739
740                            title.addEventListener('click', () => {
741
742                                let id = title.dataset.id,
743                                    content = scope.querySelector('.acc--item__' + id);
744
745                                if (content.classList.contains('cont--acc--active')) {
746
747                                    title.classList.remove('active')
748
749                                    var contentState = Flip.getState(content);
750                                    content.classList.remove('cont--acc--active');
751
752                                    Flip.from(contentState, {
753                                        duration: .75,
754                                        ease: 'expo.inOut',
755                                        absolute: false,
756                                        absoluteOnLeave: false,
757                                        onComplete: () => {
758                                            ScrollTrigger.refresh();
759                                        },
760                                    })
761
762                                } else {
763
764                                    var currentActive = scope.querySelector('.cont--acc--active');
765
766                                    if (currentActive) {
767                                        let currentTitle = scope.querySelector('.container--accordion--title.active');
768
769                                        currentTitle.classList.remove('active');
770
771                                        let currentContentState = Flip.getState(currentActive);
772
773                                        currentActive.classList.remove('cont--acc--active');
774
775                                        Flip.from(currentContentState, {
776                                            duration: .75,
777                                            ease: 'expo.inOut',
778                                            absolute: false,
779                                            absoluteOnLeave: false,
780                                            onComplete: () => {
781                                                ScrollTrigger.refresh();
782                                            },
783                                        })
784
785                                    }
786
787                                    //Open
788                                    var contentState = Flip.getState(content);
789                                    content.classList.add('cont--acc--active');
790                                    title.classList.add('active')
791                                    Flip.from(contentState, {
792                                        duration: .75,
793                                        ease: 'expo.inOut',
794                                        absolute: false,
795                                        absoluteOnLeave: false,
796                                        onComplete: () => {
797                                            ScrollTrigger.refresh();
798                                        },
799                                    })
800                                }
801                            })
802                        })
803                    }
804                }, 10);
805
806                if (scope.classList.contains('switch_on_enter')) {
807
808                    function switcherClick() {
809
810                        if (!document.documentElement.classList.contains('barba--running')) {
811
812                            let switcher = document.querySelector('.pe-layout-switcher');
813
814                            if (switcher) {
815                                switcher.click();
816                            } 1
817                        }
818
819
820                    }
821                    ScrollTrigger.create({
822                        trigger: scope,
823                        start: 'top center',
824                        end: 'bottom center',
825                        onEnter: () => switcherClick(),
826                        onLeave: () => switcherClick(),
827                        onEnterBack: () => switcherClick(),
828                        onLeaveBack: () => switcherClick(),
829                    })
830
831                }
832
833
834                if (scope.classList.contains('pinned_true')) {
835
836                    let items = scope.children,
837                        classList = scope.className,
838                        classes = classList.split(' '),
839                        targetClass = classes.find(cls => cls.startsWith('pin_container')),
840                        target = targetClass ? targetClass.substring("pin_container_".length) : '.' + scope.classList[0];
841
842                    let pinnedScroll = ScrollTrigger.create({
843                        trigger: document.querySelector(target),
844                        pin: scope,
845                        pinSpacing: true,
846                        start: 'top top',
847                        end: 'bottom bottom',
848                    })
849
850                    matchMedia.add({
851                        isMobile: "(max-width: 550px)"
852
853                    }, (context) => {
854
855                        let {
856                            isMobile
857                        } = context.conditions;
858
859                        pinnedScroll.kill();
860
861                    });
862
863                }
864
865
866
867                setTimeout(() => {
868                    if (scope.classList.contains('curved_true')) {
869
870                        let rhTop = document.querySelector('.rh--top.reverse__' + scope.dataset.id);
871                        let rhBottom = document.querySelector('.rh--bottom.reverse__' + scope.dataset.id);
872
873                        if (rhTop) {
874                            gsap.set(rhTop, {
875                                '--mainBackground': window.getComputedStyle(scope).backgroundColor
876                            })
877                        }
878                        if (rhBottom) {
879                            gsap.set(rhBottom, {
880                                '--mainBackground': window.getComputedStyle(scope).backgroundColor
881                            })
882
883                        }
884                    }
885
886                }, 50);
887
888
889
890                if (scope.classList.contains('e-parent')) {
891
892                    var scopeBg = getComputedStyle(scope).getPropertyValue('background-color');
893
894                    if (scopeBg !== 'rgba(0, 0, 0, 0)') {
895
896                        function integrateColors() {
897
898                            if (!parents(scope, '.site-header').length) {
899
900
901                                let headerColor = getComputedStyle(document.querySelector('.site-header')).getPropertyValue('--intColor'),
902                                    headerBrightness = gsap.utils.splitColor(headerColor, true)[2],
903                                    scopeBg = getComputedStyle(scope).getPropertyValue('background-color'),
904                                    scopeBrightness = gsap.utils.splitColor(scopeBg, true)[2];
905
906                                if (headerBrightness > scopeBrightness) {
907                                    document.querySelector('.site-header').classList.add('header--switched')
908
909                                }
910                            }
911
912                        }
913
914                        setTimeout(() => {
915
916                            ScrollTrigger.create({
917                                trigger: scope,
918                                start: 'top top+=50',
919                                end: 'bottom top+=50',
920                                onEnter: () => {
921                                    integrateColors()
922                                },
923                                onEnterBack: () => {
924                                    integrateColors()
925                                },
926                                onLeave: () => {
927                                    document.querySelector('.site-header').classList.remove('header--switched')
928                                },
929                                onLeaveBack: () => {
930                                    document.querySelector('.site-header').classList.remove('header--switched')
931                                },
932                            })
933
934
935                        }, 50);
936
937                    }
938
939                }
940                if (scope.dataset.cursor) {
941
942                    peCursorInteraction(scope);
943
944
945
946                }
947
948            }
949
950
951
952        })
953
954        elementorFrontend.hooks.addAction('frontend/element_ready/widget', function ($scope, $) {
955
956            var jsScopeArray = $scope.toArray();
957            for (var i = 0; i < jsScopeArray.length; i++) {
958                var scope = jsScopeArray[i],
959                    id = scope.dataset.id;
960
961                // Scroll Buttons
962                scope.querySelector('.pe--scroll--button') ? peScrollButton(scope.querySelector('.pe--scroll--button')) : '';
963                // Scroll Buttons
964
965                if (scope.querySelector('.pe--browser--back')) {
966
967                    scope.querySelector('.pe--browser--back').addEventListener('click', () => {
968
969                        window.history.back();
970                    })
971                }
972
973                //Animations
974                setTimeout(() => {
975
976                    if (scope.querySelector('[data-anim-general="true"]')) {
977
978                        var hasAnim = scope.querySelectorAll('[data-anim-general="true"]');
979
980                        hasAnim.forEach(element => {
981
982                            if (!scope.querySelector('div[data-elementor-type="pe-menu"]')) {
983
984                                new peGeneralAnimation(element)
985
986                            }
987                        })
988
989                    }
990
991                }, 10);
992
993
994                if (scope.querySelector('[data-anim-image="true"]')) {
995
996                    var hasAnim = scope.querySelectorAll('[data-anim-image="true"]');
997
998                    hasAnim.forEach(element => {
999
1000                        if (!scope.querySelector('div[data-elementor-type="pe-menu"]')) {
1001
1002                            new peImageAnimation(element)
1003                        }
1004
1005                    })
1006
1007                }
1008
1009                setTimeout(() => {
1010
1011                    if (scope.querySelector('[data-cursor="true"]')) {
1012
1013                        var targets = scope.querySelectorAll('[data-cursor="true"]');
1014
1015                        targets.forEach(target => {
1016
1017                            peCursorInteraction(target);
1018
1019                        })
1020
1021                    }
1022
1023                }, 10);
1024
1025
1026
1027                if (scope.querySelector('[data-animate="true"]')) {
1028
1029                    scope.querySelectorAll('[data-animate="true"]').forEach(text => {
1030                        if (!scope.querySelector('div[data-elementor-type="pe-menu"]')) {
1031
1032                            document.fonts.ready.then((fontFaceSet) => {
1033
1034                                if (!text.classList.contains('anim--hold')) {
1035                                    new peTextAnimation(text, false, false, id);
1036
1037                                } else {
1038
1039                                    let mainNav = scope.querySelector('.main-navigation > .menu'),
1040                                        items = mainNav.childNodes;
1041
1042                                    for (let i = 0; i < items.length; i++) {
1043
1044                                        if (items[i].tagName && items[i].tagName === 'LI') {
1045                                            items[i].querySelector('a').classList.add('menu--item--anim')
1046                                        }
1047
1048                                    }
1049
1050                                    mainNav.querySelectorAll('.menu--item--anim').forEach(link => {
1051                                        if (!link.classList.contains('anim--once')) {
1052                                            new peTextAnimation(link, text.dataset.settings, text.dataset.animation);
1053                                        }
1054
1055                                    })
1056
1057
1058                                }
1059
1060
1061
1062                            });
1063
1064                        }
1065                    });
1066
1067                }
1068
1069                setTimeout(() => {
1070
1071                    if (scope.querySelector('.pe-video')) {
1072
1073                        let videos = scope.querySelectorAll('.pe-video')
1074
1075                        for (var i = 0; i < videos.length; i++) {
1076                            new peVideoPlayer(videos[i]);
1077                        }
1078
1079                    }
1080
1081                }, 10);
1082
1083
1084
1085
1086
1087            }
1088
1089        })
1090
1091        elementorFrontend.hooks.addAction('frontend/element_ready/pe-slider.default', function ($scope, $) {
1092
1093            peSlider();
1094
1095            function peSlider() {
1096
1097                var main = $scope.find('.pe-slider');
1098
1099                main.each(function () {
1100                    let $this = $(this),
1101                        wrapper = $this.find('.slider-wrapper'),
1102                        slide = $this.find('.pe-slide'),
1103                        itemWidth = slide.outerWidth(true),
1104                        itemHeight = slide.outerHeight(true),
1105                        navButton = $this.find('.navigate-button'),
1106                        pinTarget = $this.data('pin-target'),
1107                        speed = $this.data('speed'),
1108                        next = $this.find('.next'),
1109                        prev = $this.find('.prev'),
1110                        fraction = $this.find('.pe-fraction'),
1111                        activeEl = fraction.find('.active'),
1112                        total = fraction.find('.total'),
1113                        trigger = pinTarget ? pinTarget : $this;
1114
1115                    total.html(slide.length)
1116
1117                    if (!pinTarget) {
1118                        pinTarget = true
1119                    }
1120
1121                    slide.each(function (i) {
1122                        i++;
1123
1124                        let item = $(this)
1125
1126                        item.attr('data-index', i);
1127                        item.addClass('data-index_' + i)
1128
1129                        item.find('.item-wrap').css('width', parseInt(itemWidth))
1130                        item.find('.item-wrap').css('height', parseInt(itemHeight))
1131
1132                        item.find('.slide-image').css('width', parseInt(itemWidth))
1133                        item.find('.slide-image').css('height', parseInt(itemHeight))
1134
1135                    })
1136
1137
1138                    if ($this.hasClass('nav_scroll')) {
1139
1140
1141                        let tl = gsap.timeline({
1142                            scrollTrigger: {
1143                                trigger: trigger,
1144                                start: 'top top',
1145                                end: 'bottom bottom',
1146                                pin: $this,
1147                                scrub: true,
1148                                onUpdate: (self) => {
1149                                    let prog = self.progress * slide.length;
1150
1151                                    if (prog > 1) {
1152                                        activeEl.html(Math.floor(prog))
1153                                    }
1154                                }
1155                            }
1156                        })
1157
1158                        slide.each(function (i) {
1159                            let item = $(this);
1160
1161                            if ($this.hasClass('vertical')) {
1162
1163                                tl.to($(this), {
1164                                    ease: 'none',
1165                                    height: '100%'
1166                                })
1167
1168                                slide.first().nextAll().css('height', 0)
1169
1170                            } else {
1171
1172                                tl.to($(this), {
1173                                    ease: 'none',
1174                                    width: '100%'
1175                                })
1176
1177                                slide.first().nextAll().css('width', 0)
1178
1179                            }
1180
1181                        })
1182
1183                    } else if ($this.hasClass('nav_button')) {
1184
1185                        var x;
1186                        x = 1
1187
1188                        navButton.on('click', function (e) {
1189
1190                            if ($(this).hasClass('prev')) {
1191                                x--;
1192
1193                            } else if ($(this).hasClass('next')) {
1194                                x++;
1195                            }
1196
1197                            if (x <= 1) {
1198                                x = 1
1199
1200                                gsap.to(prev, {
1201                                    opacity: 0.2
1202                                })
1203
1204                                gsap.to(next, {
1205                                    opacity: 1
1206                                })
1207
1208                            } else if (x >= slide.length) {
1209                                x = slide.length
1210
1211                                gsap.to(next, {
1212                                    opacity: 0.2
1213                                })
1214
1215                                gsap.to(prev, {
1216                                    opacity: 1
1217                                })
1218
1219
1220                            } else if (1 < x < slide.length) {
1221
1222                                gsap.to(next, {
1223                                    opacity: 1
1224                                })
1225
1226                                gsap.to(prev, {
1227                                    opacity: 1
1228                                })
1229
1230                            }
1231
1232                            if ($(this).hasClass('prev')) {
1233
1234                                if ($this.hasClass('vertical')) {
1235
1236                                    gsap.to($this.find('.data-index_' + (x + 1)), {
1237                                        height: '0%',
1238                                        duration: 0.1
1239                                    })
1240
1241                                } else {
1242
1243                                    gsap.to($this.find('.data-index_' + (x + 1)), {
1244                                        width: '0%',
1245                                        duration: 0.1
1246                                    })
1247
1248                                }
1249
1250                                activeEl.html(x)
1251
1252                            } else if ($(this).hasClass('next')) {
1253
1254                                gsap.to($this.find('.data-index_' + x), {
1255                                    width: '100%',
1256                                    height: '100%',
1257                                    duration: 0.1
1258                                })
1259
1260                                activeEl.html(x)
1261
1262                            }
1263
1264
1265
1266                        })
1267
1268                    }
1269
1270
1271
1272                })
1273
1274            }
1275
1276
1277
1278        });
1279
1280        elementorFrontend.hooks.addAction('frontend/element_ready/petable.default', function ($scope, $) {
1281
1282            var jsScopeArray = $scope.toArray();
1283
1284            for (var i = 0; i < jsScopeArray.length; i++) {
1285                var scope = jsScopeArray[i],
1286                    rows = scope.querySelectorAll('.pe--table--row');
1287
1288                rows.forEach(row => {
1289
1290                    let image = row.querySelector('.pe--table--row--image');
1291
1292                    row.addEventListener("mouseenter", (e) => {
1293                        if (image) {
1294                            gsap.set(image, {
1295                                x: e.layerX,
1296                                y: e.layerY
1297                            })
1298                        }
1299
1300
1301                    });
1302                    row.addEventListener("mousemove", (e) => {
1303                        if (image) {
1304                            gsap.to(image, {
1305                                x: e.layerX + 10,
1306                                y: e.layerY + 10,
1307                                rotate: e.movementX / 2
1308                            })
1309                        }
1310
1311                    });
1312
1313                })
1314
1315
1316            }
1317
1318        });
1319
1320        elementorFrontend.hooks.addAction('frontend/element_ready/pegooglemaps.default', function ($scope, $) {
1321
1322            var jsScopeArray = $scope.toArray();
1323
1324            for (var i = 0; i < jsScopeArray.length; i++) {
1325                var scope = jsScopeArray[i];
1326
1327                function initMap(latitude, longitude, zoomLevel, mapStyles, markerIcon) {
1328
1329                    var mapOptions = {
1330                        zoom: zoomLevel,
1331                        center: { lat: parseFloat(latitude), lng: parseFloat(longitude) },
1332                        styles: mapStyles,
1333                        disableDefaultUI: true,
1334                        mapTypeControl: false,
1335                        fullscreenControl: false,
1336                        zoomControl: false,
1337                        streetViewControl: false,
1338                        rotateControl: false,
1339                        scaleControl: false
1340                    };
1341
1342                    var map = new google.maps.Map(document.getElementById('pe--google--map'), mapOptions);
1343
1344                    var markerOptions = {
1345                        position: mapOptions.center,
1346                        map: map,
1347                        icon: {
1348                            url: markerIcon,
1349                            scaledSize: new google.maps.Size(60, 60)
1350                        }
1351                    };
1352
1353                    var marker = new google.maps.Marker(markerOptions);
1354                }
1355
1356                var mapElement = document.getElementById('pe--google--map');
1357
1358                if (mapElement) {
1359
1360                    var latitude = mapElement.getAttribute('data-latitude');
1361                    var longitude = mapElement.getAttribute('data-longitude');
1362                    var zoomLevel = parseInt(mapElement.getAttribute('data-zoom-level'));
1363                    var mapStyles = JSON.parse(mapElement.getAttribute('data-map-styles'));
1364                    var markerIcon = mapElement.getAttribute('data-marker-icon');
1365
1366                    initMap(latitude, longitude, zoomLevel, mapStyles, markerIcon);
1367
1368                }
1369
1370            }
1371
1372        });
1373
1374        elementorFrontend.hooks.addAction('frontend/element_ready/petestimonials.default', function ($scope, $) {
1375
1376            var jsScopeArray = $scope.toArray();
1377
1378            for (var i = 0; i < jsScopeArray.length; i++) {
1379                var scope = jsScopeArray[i],
1380                    testimonials = scope.querySelector('.pe--testimonials'),
1381                    wrapper = testimonials.querySelector('.pe--testimonials--wrapper'),
1382                    gap = window.getComputedStyle(wrapper).getPropertyValue('gap'),
1383                    wrapperHeight = wrapper.clientHeight,
1384                    wrapperWidth = wrapper.clientWidth,
1385                    items = wrapper.querySelectorAll('.pe-testimonial');
1386
1387                let maxX = document.body.clientWidth * 0.75,
1388                    yVals = [];
1389
1390                items.forEach((item, i) => {
1391
1392                    if (testimonials.classList.contains('test--dynamic')) {
1393                        let itemX = item.getBoundingClientRect().x - testimonials.getBoundingClientRect().x,
1394                            itemWidth = item.getBoundingClientRect().width,
1395                            randX = gsap.utils.random((-maxX / 2), (maxX / 2)),
1396                            randY = gsap.utils.random(0, 400),
1397                            randR = gsap.utils.random(-15, 15);
1398
1399
1400                        if (itemX > maxX) {
1401
1402                            gsap.set(item, {
1403                                x: (-itemX + (maxX / 2) - (itemWidth / 2) + (parseFloat(gap) * 3)) + randX,
1404                                y: randY,
1405                                rotate: randR
1406                            })
1407
1408                        } else if (itemX < (maxX / 2)) {
1409
1410                            gsap.set(item, {
1411                                x: gsap.utils.random(-250, -100),
1412                                y: gsap.utils.random(100, 300),
1413                                rotate: randR
1414                            })
1415
1416                        } else if (itemX > (maxX / 2)) {
1417
1418                            gsap.set(item, {
1419                                x: gsap.utils.random(100, (maxX / 3)),
1420                                y: gsap.utils.random(100, 300),
1421                                rotate: randR
1422                            })
1423
1424                        }
1425
1426                        yVals.push(randY)
1427
1428                    }
1429
1430
1431                })
1432
1433                wrapper.style.height = (100 + wrapperHeight + Math.max(...yVals)) + 'px';
1434
1435                if (testimonials.classList.contains('carousel--centered')) {
1436
1437                    gsap.set(wrapper, {
1438                        x: wrapperWidth / -6
1439                    })
1440
1441                }
1442
1443                Draggable.create(wrapper, {
1444                    type: 'x',
1445                    bounds: {
1446                        minX: 0,
1447                        maxX: -wrapperWidth + document.body.clientWidth - 50
1448                    },
1449                    lockAxis: true,
1450                    dragResistance: 0.5,
1451                    inertia: true,
1452                });
1453
1454                var drag = Draggable.get(wrapper);
1455
1456                if (testimonials.classList.contains('test--dynamic')) {
1457
1458                    drag.disable();
1459
1460                    wrapper.addEventListener('click', () => {
1461
1462                        var state = Flip.getState(items);
1463
1464                        testimonials.classList.add('pt--carousel')
1465
1466                        gsap.set(items, {
1467                            clearProps: 'all'
1468                        })
1469
1470                        Flip.from(state, {
1471                            duration: 1,
1472                            ease: "power3.inOut",
1473                            absolute: true,
1474                            absoluteOnLeave: true,
1475                            stagger: -0.05
1476                        });
1477
1478                        drag.enable();
1479                        peCursorDrag(scope);
1480                        wrapper.classList.add('cursor--disabled');
1481
1482                    })
1483
1484                }
1485
1486
1487
1488                matchMedia.add({
1489                    isMobile: "(max-width: 570px)"
1490                }, (context) => {
1491
1492                    let {
1493                        isMobile
1494                    } = context.conditions;
1495
1496                    wrapper.click();
1497                    gsap.set(wrapper, {
1498                        height: 'auto'
1499                    })
1500
1501                });
1502
1503            }
1504        });
1505
1506        elementorFrontend.hooks.addAction('frontend/element_ready/pesitenavigation.default', function ($scope, $) {
1507
1508            var jsScopeArray = $scope.toArray();
1509
1510            for (var i = 0; i < jsScopeArray.length; i++) {
1511                var scope = jsScopeArray[i],
1512                    nav = scope.querySelector('.site--nav'),
1513                    toggle = scope.querySelector('.menu--toggle'),
1514                    menu = scope.querySelector('.site--menu'),
1515                    hideElements = nav.dataset.hideElements,
1516                    clicks = 0;
1517
1518                function hideOnMenu(hide) {
1519
1520                    if (hideElements) {
1521
1522                        if (hide) {
1523
1524                            gsap.to(hideElements, {
1525                                opacity: 0
1526                            })
1527
1528                        } else {
1529                            gsap.to(hideElements, {
1530                                opacity: 1
1531                            })
1532                        }
1533
1534                    }
1535
1536                }
1537
1538
1539                toggle.addEventListener('click', () => {
1540                    clicks++
1541
1542                    if (clicks % 2 == 0) {
1543
1544                        if (nav.querySelectorAll('.st--active').length) {
1545
1546                            nav.querySelectorAll('.st--active').forEach(st => {
1547                                st.click();
1548                            })
1549                        }
1550
1551                        // Close
1552                        toggle.classList.remove('active');
1553                        enableScroll();
1554
1555                        if (nav.classList.contains('nav--popup')) {
1556                            popUpNav(false);
1557
1558                        } else if (nav.classList.contains('nav--fullscreen')) {
1559                            fullscreenNav(false);
1560                        }
1561                        hideOnMenu(false)
1562
1563                    } else {
1564                        // Open
1565                        toggle.classList.add('active');
1566                        // disableScroll();
1567
1568                        hideOnMenu(true)
1569
1570                        if (nav.classList.contains('nav--popup')) {
1571
1572                            popUpNav(true)
1573
1574                        } else if (nav.classList.contains('nav--fullscreen')) {
1575
1576                            fullscreenNav(true);
1577
1578                        }
1579
1580                    }
1581
1582                })
1583
1584                // Popup Navigation 
1585
1586                function popUpNav(open) {
1587
1588                    if (open) {
1589
1590                        gsap.to(menu, {
1591                            xPercent: 0,
1592                            x: 0,
1593                            duration: 1.4,
1594                            ease: 'expo.inOut',
1595                            onStart: () => {
1596                                menu.classList.add('active')
1597                            }
1598                        })
1599
1600
1601                    } else {
1602
1603                        gsap.to(menu, {
1604                            xPercent: 100,
1605                            duration: 1.4,
1606                            ease: 'expo.inOut',
1607                            onComplete: () => {
1608                                menu.classList.remove('active')
1609                            }
1610                        })
1611                    }
1612
1613                }
1614
1615                // Popup Navigation 
1616
1617                // Fullscreen Navigation 
1618                function fullscreenNav(open) {
1619
1620                    if (nav.classList.contains('overlay--slide')) {
1621
1622                        if (open) {
1623
1624                            gsap.to(menu, {
1625                                height: '100vh',
1626                                duration: .8,
1627                                ease: 'power4.out'
1628                            })
1629
1630                            gsap.to('#primary', {
1631                                y: '50vh',
1632                                duration: .8,
1633                                ease: 'power4.out'
1634                            })
1635
1636
1637                        } else {
1638
1639                            gsap.to(menu, {
1640                                height: '0vh',
1641                                duration: .8,
1642                                ease: 'power4.out'
1643                            })
1644                            gsap.to('#primary', {
1645                                y: '0vh',
1646                                duration: .8,
1647                                ease: 'power4.out'
1648                            })
1649
1650                        }
1651
1652                    } else if (nav.classList.contains('overlay--blocks')) {
1653
1654                        let blocksWrapper = scope.querySelector('.nav--blocks');
1655
1656                        if (open) {
1657
1658                            gsap.to(scope.querySelectorAll('.fullscreen--menu--block'), {
1659                                height: '100vh',
1660                                duration: 1,
1661                                ease: 'power4.out',
1662                                overwrite: true,
1663                                stagger: {
1664                                    grid: [1, 20],
1665                                    from: "random",
1666                                    amount: .3,
1667                                },
1668                                onStart: () => {
1669                                    gsap.set([blocksWrapper, menu], {
1670                                        visibility: 'visible'
1671                                    })
1672
1673                                }
1674                            })
1675
1676
1677                        } else {
1678
1679                            gsap.to(scope.querySelectorAll('.fullscreen--menu--block'), {
1680                                height: '0vh',
1681                                duration: 1,
1682                                ease: 'power4.inOut',
1683                                overwrite: true,
1684                                id: 'fs--menu--blocks',
1685                                stagger: {
1686                                    grid: [1, 20],
1687                                    from: "random",
1688                                    amount: .3,
1689                                },
1690                                onComplete: () => {
1691                                    gsap.set([blocksWrapper, menu], {
1692                                        visibility: 'hidden'
1693                                    })
1694
1695                                }
1696                            })
1697
1698
1699                        }
1700
1701
1702                    }
1703
1704                }
1705
1706
1707                // Fullscreen Navigation 
1708
1709
1710
1711
1712            }
1713        });
1714
1715        elementorFrontend.hooks.addAction('frontend/element_ready/penavmenu.default', function ($scope, $) {
1716            var jsScopeArray = $scope.toArray();
1717
1718            for (var i = 0; i < jsScopeArray.length; i++) {
1719                var scope = jsScopeArray[i];
1720
1721                var nav = scope.querySelector('#site-navigation'),
1722                    menus = scope.querySelectorAll('ul'),
1723                    parentMenu = scope.querySelector('ul.main-menu'),
1724                    items = nav.querySelectorAll('.menu-item'),
1725                    toggleHTML = nav.dataset.subToggle,
1726                    toggle = document.createElement('div');
1727
1728
1729                items.forEach(item => {
1730                    item.querySelector('a').classList.add('menu--link')
1731                })
1732
1733                if (!scope.classList.contains('nav--init')) {
1734
1735                    scope.classList.add('nav--init');
1736
1737                    toggle.classList.add('st--wrap');
1738                    toggle.innerHTML = toggleHTML;
1739
1740                    var childrens = [];
1741                    var childNodes = parentMenu.childNodes;
1742
1743                    for (var i = 0; i < childNodes.length; i++) {
1744
1745                        if (childNodes[i].nodeType === 1 && childNodes[i].tagName.toLowerCase() === "li") {
1746
1747                            childrens.push(childNodes[i]);
1748                        }
1749                    }
1750
1751                    if (!parentMenu.classList.contains('menu--horizontal')) {
1752
1753                        parentMenu.querySelectorAll('.farah-sub-menu-wrap').forEach((sub) => {
1754                            sub.remove();
1755                        });
1756
1757                    }
1758
1759                    childrens.forEach((item, i) => {
1760
1761                        i++
1762                        item.setAttribute('data-index', i);
1763
1764                        if (item.classList.contains('menu-item-has-children') || item.classList.contains('farah-has-children')) {
1765
1766                            let sub = item.querySelector('.sub-menu'),
1767                                a = item.childNodes[0];
1768
1769                            item.insertBefore(toggle.cloneNode(true), sub);
1770
1771                            item.querySelector('.st--wrap').addEventListener('click', (self) => {
1772
1773                                self.target.classList.toggle('st--active');
1774
1775                                if (item.classList.contains('sub--active')) {
1776
1777                                    let subState = Flip.getState(sub, {
1778                                        props: ['padding']
1779                                    });
1780                                    item.classList.remove('sub--active');
1781
1782                                    Flip.from(subState, {
1783                                        duration: .75,
1784                                        ease: 'expo.inOut',
1785                                        absolute: false,
1786                                        absoluteOnLeave: false,
1787                                    })
1788
1789                                } else {
1790
1791                                    nav.querySelector('.sub--active') ? nav.querySelector('.sub--active > .st--wrap').click() : '';
1792
1793                                    let subState = Flip.getState(sub, {
1794                                        props: ['padding']
1795                                    });
1796
1797                                    item.classList.add('sub--active');
1798
1799                                    Flip.from(subState, {
1800                                        duration: .75,
1801                                        ease: 'expo.inOut',
1802                                        absolute: false,
1803                                        absoluteOnLeave: false,
1804                                    })
1805                                }
1806
1807                            });
1808
1809                            if (!nav.classList.contains('st--only')) {
1810
1811                                a.addEventListener('click', (e) => {
1812
1813                                    e.preventDefault();
1814                                    item.querySelector('.st--wrap').click();
1815
1816                                })
1817
1818                            }
1819
1820                        }
1821                        // Has Children
1822
1823                    })
1824
1825                }
1826
1827            }
1828        });
1829
1830
1831
1832        elementorFrontend.hooks.addAction('frontend/element_ready/petextwrapper.default', function ($scope, $) {
1833
1834            var jsScopeArray = $scope.toArray();
1835
1836            for (var i = 0; i < jsScopeArray.length; i++) {
1837                var scope = jsScopeArray[i],
1838                    wrapper = scope.querySelector('.text-wrapper');
1839
1840                document.fonts.ready.then((fontFaceSet) => {
1841                    //Inner Elements
1842                    var innerElements = wrapper.querySelectorAll('[class^="inner--"]');
1843
1844                    innerElements.forEach((element) => {
1845
1846                        let classes = element.classList,
1847                            hasMotion = Array.from(classes).some(className => className.startsWith('me--'));
1848
1849
1850                        // Motion Effects
1851                        if (hasMotion) {
1852
1853                            let motion = hasMotion ? Array.from(classes).find(className => className.startsWith('me--')) : null,
1854                                duration = element.dataset.duration,
1855                                delay = element.dataset.delay,
1856                                ease = motion === 'me--flip-x' ? 'none' : motion === 'me--flip-y' ? 'none' : motion === 'me--hearthbeat-x' ? 'power4.inOut' : motion === 'me--slide-left' ? 'power3.in' : motion === 'me--slide-right' ? 'power3.in' : 'expo.out',
1857                                tl = gsap.timeline({
1858                                    repeat: -1,
1859                                    repeatDelay: parseInt(delay, 10)
1860                                }),
1861                                target = element;
1862
1863
1864                            if (motion === 'me--slide-left' || motion === 'me--slide-right') {
1865
1866                                target = element.firstElementChild;
1867                            }
1868
1869                            tl.fromTo(target, {
1870                                xPercent: 0,
1871                                scale: motion === 'me--hearth-beat' ? 0.6 : 1
1872                            }, {
1873
1874                                scale: 1,
1875                                rotate: motion === 'me--rotate' ? -360 : 0,
1876                                rotateX: motion === 'me--flip-x' ? -360 : 0,
1877                                rotateY: motion === 'me--flip-y' ? -360 : 0,
1878                                xPercent: motion === 'me--slide-left' ? -100 : motion === 'me--slide-right' ? 100 : 0,
1879                                duration: duration,
1880                                ease: ease,
1881
1882                            })
1883
1884                            if (motion === 'me--slide-left' || motion === 'me--slide-right') {
1885
1886                                tl.fromTo(target, {
1887                                    xPercent: motion === 'me--slide-left' ? 100 : motion === 'me--slide-right' ? -100 : 0
1888                                }, {
1889                                    xPercent: 0,
1890                                    duration: duration,
1891                                    ease: 'power3.out',
1892                                })
1893                            }
1894
1895                            if (motion === 'me--hearth-beat') {
1896
1897                                tl.to(target, {
1898                                    scale: 0.6,
1899                                    duration: duration
1900                                })
1901                            }
1902
1903                        }
1904
1905                        if (element.classList.contains('inserted--pin')) {
1906
1907                            let state = Flip.getState(element),
1908                                target = element.dataset.zoomPin ? element.dataset.zoomPin : scope,
1909                                tl = gsap.timeline({
1910                                    scrollTrigger: {
1911                                        trigger: target,
1912                                        scrub: true,
1913                                        pin: true,
1914                                        start: 'center center',
1915                                        end: 'bottom+=500 top',
1916                                    }
1917                                });
1918
1919                            gsap.set(element, {
1920                                position: 'fixed',
1921                                width: '100vw',
1922                                height: '100vh',
1923                                top: 0,
1924                                left: 0,
1925
1926                            })
1927
1928                            let fl = Flip.from(state, {
1929                                absolute: false,
1930                                absoluteOnLeave: false,
1931                            })
1932
1933                            tl.add(fl, 0)
1934
1935                        }
1936
1937                    })
1938                    //Inner Elements
1939
1940                    //Dyanmic words
1941                    function dynamicWordAnimation() {
1942
1943                        let dynamicWords = wrapper.querySelectorAll('.pe-dynamic-words');
1944
1945                        dynamicWords.forEach((dynamic) => {
1946
1947                            if (!dynamic.classList.contains('dyno--init')) {
1948                                dynamic.classList.add('dyno--init');
1949
1950                                let innerWrap = dynamic.firstElementChild,
1951                                    words = innerWrap.querySelectorAll('span'),
1952                                    duration = parseFloat(dynamic.dataset.duration),
1953                                    delay = parseFloat(dynamic.dataset.delay),
1954                                    pin = dynamic.dataset.pin,
1955                                    scrub = dynamic.dataset.scrub,
1956                                    scroll = false;
1957
1958                                if (pin === 'true' || scrub === 'true') {
1959
1960                                    scroll = {
1961                                        trigger: scope,
1962                                        pin: pin === 'true' ? scope : false,
1963                                        scrub: 1,
1964                                        start: pin === 'true' ? 'center center' : 'top bottom',
1965                                        end: pin === 'true' ? 'bottom+=500 top' : 'bottom top',
1966                                    };
1967
1968                                }
1969
1970                                let tl = gsap.timeline({
1971                                    repeat: pin === 'true' ? 0 : scrub === 'true' ? 0 : -1,
1972                                    scrollTrigger: scroll
1973                                });
1974
1975                                dynamic.style.width = Math.ceil(words[0].getBoundingClientRect().width) + 'px';
1976
1977                                words.forEach((word, i) => {
1978
1979                                    tl.to(innerWrap, {
1980                                        yPercent: -100 / words.length * i,
1981                                        duration: duration,
1982                                        delay: i == 0 ? 0 : delay,
1983                                        ease: scroll ? 'none' : 'expo.inOut'
1984                                    }, 'label_' + i)
1985
1986                                    tl.to(dynamic, {
1987                                        width: Math.ceil(word.getBoundingClientRect().width),
1988                                        duration: duration,
1989                                        delay: delay,
1990                                        ease: scroll ? 'none' : 'expo.inOut'
1991                                    }, 'label_' + i)
1992
1993
1994                                })
1995
1996                            }
1997
1998
1999
2000                        })
2001
2002                    }
2003
2004                    dynamicWordAnimation();
2005                    //Dyanmic words
2006
2007                    setTimeout(() => {
2008
2009                        if (scope.querySelector('.custom-lines-hold')) {
2010
2011                            for (let i = 0; i < wrapper.childNodes.length; i++) {
2012
2013                                if (wrapper.childNodes[i].tagName) {
2014                                    new SplitText(wrapper.childNodes[i], {
2015                                        type: "lines",
2016                                        linesClass: "customized--line",
2017                                    });
2018                                }
2019
2020                            }
2021
2022                            wrapper.querySelectorAll('.customized--line').forEach((line, i) => {
2023                                i++
2024                                line.classList.add('cs--line--' + i)
2025                            })
2026
2027                            let holds = scope.querySelectorAll('.csl--hold');
2028
2029                            if (holds) {
2030
2031                                holds.forEach(hold => {
2032
2033                                    let line = hold.dataset.line,
2034                                        id = hold.dataset.id,
2035                                        findLine = '.cs--line--' + line;
2036
2037                                    if (scope.querySelector(findLine)) {
2038
2039                                        scope.querySelector(findLine).classList.add('elementor-repeater-item-' + id);
2040
2041                                    }
2042
2043
2044
2045
2046
2047                                })
2048                            }
2049
2050                        }
2051
2052                    }, 50);
2053
2054
2055
2056                });
2057
2058            }
2059
2060        });
2061
2062        elementorFrontend.hooks.addAction('frontend/element_ready/pevideo.default', function ($scope, $) {
2063
2064            var jsScopeArray = $scope.toArray();
2065            for (var i = 0; i < jsScopeArray.length; i++) {
2066                var scope = jsScopeArray[i];
2067
2068                // new peVideoPlayer(scope.querySelector('.pe-video'));
2069
2070
2071            }
2072
2073        });
2074
2075        elementorFrontend.hooks.addAction('frontend/element_ready/pecircletext.default', function ($scope, $) {
2076
2077            var jsScopeArray = $scope.toArray();
2078
2079            for (var i = 0; i < jsScopeArray.length; i++) {
2080                var scope = jsScopeArray[i];
2081
2082                if (scope) {
2083                    var circularText = scope.querySelectorAll('.pe-circular-text');
2084
2085
2086                    circularText.forEach(function ($this) {
2087                        var textWrap = $this.querySelector('.circular-text-wrap'),
2088                            circularContent = $this.querySelector(".circular-text-content"),
2089                            dataHeight = $this.dataset.height,
2090                            dataDuration = $this.dataset.duration,
2091                            dataTarget = $this.dataset.target,
2092                            circleSplit = new SplitText($this.querySelector('.circle-text'), {
2093                                type: "words, chars",
2094                                charsClass: "circle-char",
2095                                wordsClass: "circle-word",
2096                                position: "absolute"
2097                            }),
2098                            fontSize = parseInt(window.getComputedStyle($this.querySelector('.circle-char')).fontSize),
2099                            charLength = $this.querySelectorAll('.circle-char').length,
2100                            textLength = (dataHeight / charLength) / (fontSize / 1.75),
2101                            circleChar = $this.querySelectorAll('.circle-char'),
2102                            circleWord = $this.querySelectorAll('.circle-word'),
2103                            snap = gsap.utils.snap(1),
2104                            dataIcon = $this.dataset.icon;
2105
2106                        for (var i = 2; i <= snap(textLength); i++) {
2107                            var clonedContent = circularContent.cloneNode(true);
2108                            textWrap.appendChild(clonedContent);
2109                        }
2110                        circularContent = $this.querySelectorAll(".circular-text-content");
2111
2112                        gsap.set(circularContent, {
2113                            width: dataHeight,
2114                            height: dataHeight
2115                        })
2116
2117                        var circleWordElements = $this.querySelectorAll('.circle-word');
2118
2119                        circleWordElements.forEach(function (circleWordElement) {
2120                            var circleCharElement = document.createElement('span');
2121                            circleCharElement.className = 'circle-char';
2122                            circleWordElement.appendChild(circleCharElement);
2123                        });
2124
2125                        $this.querySelectorAll('.circle-word').forEach(function (circleWordElement) {
2126                            gsap.set(circleWordElement, {
2127                                left: '50%',
2128                                top: 0,
2129                                height: "100%",
2130                                xPercent: -50
2131                            })
2132                        });
2133
2134                        var charElements = $this.querySelectorAll('.circle-char'),
2135                            rotateMultiplier = 360 / charElements.length;
2136
2137                        charElements.forEach(function (charElement, index) {
2138
2139                            gsap.set(charElement, {
2140                                rotate: rotateMultiplier * index,
2141                                left: '50%',
2142                                xPercent: -50,
2143                                top: 0,
2144                                height: "50%"
2145                            });
2146
2147                        });
2148
2149                        var tl = gsap.timeline();
2150
2151                        gsap.set(textWrap, {
2152                            width: dataHeight,
2153                            height: dataHeight
2154                        });
2155
2156                        if ($this.classList.contains('counter-clockwise')) {
2157                            tl.to(textWrap, {
2158                                rotation: -360,
2159                                duration: dataDuration,
2160                                ease: "none",
2161                                repeat: -1
2162                            });
2163                        } else {
2164                            tl.to(textWrap, {
2165                                rotation: 360,
2166                                duration: dataDuration,
2167                                ease: "none",
2168                                repeat: -1
2169                            });
2170                        }
2171
2172                        let whaler = Hamster(document.querySelector('body')),
2173                            wheelDeltaY, currentDeltaY;
2174
2175                        function createWheelStopListener(element, callback, timeout) {
2176                            var handle = null;
2177                            var onScroll = function () {
2178                                if (handle) {
2179                                    clearTimeout(handle);
2180                                }
2181                                handle = setTimeout(callback, timeout || 200); // 
2182                            };
2183                            element.addEventListener('wheel', onScroll);
2184                            return function () {
2185                                element.removeEventListener('wheel', onScroll);
2186                            };
2187                        }
2188
2189                        whaler.wheel(function (event, delta, deltaX, deltaY) {
2190
2191                            wheelDeltaY = event.deltaY;
2192                            event.deltaY < 0 ? wheelDeltaY = -1 * event.deltaY : '';
2193                            tl.timeScale(1 + (wheelDeltaY * 2))
2194
2195                        });
2196
2197                        createWheelStopListener(window, function () {
2198                            tl.timeScale(1)
2199                        });
2200
2201                        $this.addEventListener('click', function () {
2202                            window.scrollTo({
2203                                top: document.querySelector(dataTarget).offsetTop,
2204                                behavior: "smooth"
2205                            });
2206                        });
2207
2208
2209                    })
2210
2211                }
2212
2213
2214
2215
2216
2217            }
2218        });
2219
2220        elementorFrontend.hooks.addAction('frontend/element_ready/pesccontrols.default', function ($scope, $) {
2221
2222            setTimeout(function () {
2223
2224                var jsScopeArray = $scope.toArray();
2225
2226                for (var i = 0; i < jsScopeArray.length; i++) {
2227
2228                    var scope = jsScopeArray[i],
2229                        control = scope.querySelector('.pe--sc--controls'),
2230                        id = control.dataset.id,
2231                        target = document.querySelector('.' + id),
2232                        items = target.querySelectorAll('.cr--item'),
2233                        vars = {
2234                            progress: '',
2235                            current: '',
2236                            total: target.dataset.total,
2237                            width: items[0].offsetWidth
2238                        };
2239
2240                    control.classList.add('sc--id__' + id)
2241
2242                    if (scope.querySelector('.sc--fraction')) {
2243
2244                        const totalElement = scope.querySelector('.sc--total');
2245                        if (totalElement) {
2246                            if (control.classList.contains('unitaze--numbers')) {
2247                                totalElement.innerHTML = vars.total < 10 ? '0' + vars.total : vars.total;
2248                            } else {
2249                                totalElement.innerHTML = vars.total;
2250                            }
2251                        }
2252
2253                    }
2254
2255                    function getCurrentItem() {
2256
2257                        let crValues = [];
2258
2259                        items.forEach(item => {
2260
2261                            if (item.getBoundingClientRect().x < (document.body.clientWidth * 0.75)) {
2262                                crValues.push(parseInt(item.dataset.cr, 10));
2263                            }
2264
2265                        });
2266
2267                        if (crValues.length > 0) {
2268                            let maxCrValue = Math.max(...crValues);
2269                            if (control.classList.contains('unitaze--numbers')) {
2270
2271                                vars.current = maxCrValue < 10 ? '0' + maxCrValue : maxCrValue;
2272
2273                            } else {
2274                                vars.current = maxCrValue;
2275                            }
2276
2277                        }
2278
2279                        scope.querySelector('.sc--current') ? scope.querySelector('.sc--current').innerHTML = vars.current : '';
2280
2281                    }
2282
2283                    getCurrentItem()
2284
2285                    function updateOthers() {
2286
2287                        let allControls = document.querySelectorAll('.sc--id__' + id);
2288
2289                        if (allControls.length > 1) {
2290
2291                            allControls.forEach(control => {
2292
2293                                let fraction = control.querySelector('.sc--fraction');
2294
2295                                if (fraction) {
2296
2297                                    let current = fraction.querySelector('.sc--current'),
2298                                        total = fraction.querySelector('.sc--total');
2299
2300                                    getCurrentItem()
2301
2302                                    if (control.classList.contains('unitaze--numbers')) {
2303
2304                                        current.innerHTML = vars.current < 10 ? '0' + vars.current : vars.current;
2305                                        total.innerHTML = vars.total < 10 ? '0' + vars.total : vars.total;
2306
2307                                    } else {
2308                                        current.innerHTML = vars.current;
2309                                        total.innerHTML = vars.total;
2310
2311                                    }
2312
2313                                }
2314
2315                            })
2316
2317                        }
2318
2319                    }
2320
2321                    if (target.classList.contains('cr--scroll')) {
2322
2323                        let tween = gsap.getById(id);
2324
2325                        tween.eventCallback('onUpdate', self => {
2326
2327                            vars.progress = tween.progress() * 100;
2328
2329
2330                            let crValues = [];
2331
2332                            items.forEach(item => {
2333
2334                                if (item.getBoundingClientRect().x < (document.body.clientWidth * 0.75)) {
2335
2336                                    crValues.push(parseInt(item.dataset.cr, 10));
2337                                }
2338
2339                            });
2340
2341                            if (crValues.length > 0) {
2342                                let maxCrValue = Math.max(...crValues);
2343                                vars.current = maxCrValue;
2344
2345                            }
2346
2347
2348                            if (scope.querySelector('.sc--fraction')) {
2349
2350                                let current = scope.querySelector('.sc--current'),
2351                                    total = scope.querySelector('.sc--total');
2352
2353                                current.innerHTML = vars.current;
2354                                total.innerHTML = vars.total;
2355
2356
2357                            }
2358
2359                            if (scope.querySelector('.sc--progressbar')) {
2360
2361                                let prog = scope.querySelector('.sc--prog');
2362
2363                                gsap.to(prog, {
2364                                    width: vars.progress + '%'
2365                                })
2366
2367                            }
2368
2369                        })
2370
2371
2372                    }
2373
2374                    if (target.classList.contains('cr--drag') || target.classList.contains('cr__drag')) {
2375
2376                        let draggable = Draggable.get(target);
2377
2378                        if (draggable) {
2379
2380                            draggable.addEventListener('throwupdate', () => {
2381
2382                                vars.progress = draggable.x / draggable.minX * 100;
2383
2384                                if (scope.querySelector('.sc--fraction')) {
2385
2386                                    let current = scope.querySelector('.sc--current'),
2387                                        total = scope.querySelector('.sc--total');
2388
2389                                    getCurrentItem()
2390
2391                                    current.innerHTML = vars.current;
2392                                    total.innerHTML = vars.total;
2393
2394                                }
2395
2396                                if (scope.querySelector('.sc--progressbar')) {
2397
2398                                    let prog = scope.querySelector('.sc--prog');
2399
2400                                    gsap.to(prog, {
2401                                        width: vars.progress + '%'
2402                                    })
2403                                }
2404
2405                            });
2406
2407
2408                            if (scope.querySelector('.sc--navigation')) {
2409
2410                                let next = scope.querySelector('.sc--next'),
2411                                    prev = scope.querySelector('.sc--prev'),
2412                                    xVal = 0;
2413
2414                                next.addEventListener('click', () => {
2415
2416                                    xVal = draggable.x;
2417                                    xVal -= vars.width;
2418
2419                                    gsap.to(target, {
2420                                        x: xVal,
2421                                        onUpdate: () => {
2422                                            draggable.update(true);
2423                                            updateOthers();
2424                                        }
2425                                    })
2426
2427                                })
2428
2429                                prev.addEventListener('click', () => {
2430
2431                                    xVal = draggable.x;
2432                                    xVal += vars.width;
2433
2434                                    gsap.to(target, {
2435                                        x: xVal,
2436                                        onUpdate: () => {
2437                                            draggable.update(true);
2438                                            updateOthers();
2439                                        }
2440                                    })
2441
2442
2443                                })
2444
2445                            }
2446
2447                        }
2448
2449                    }
2450
2451
2452                    if (target.classList.contains('cr--slideshow')) {
2453
2454
2455
2456
2457                    }
2458
2459                }
2460
2461            }, 10)
2462        })
2463
2464        elementorFrontend.hooks.addAction('frontend/element_ready/pecarousel.default', function ($scope, $) {
2465
2466            var jsScopeArray = $scope.toArray();
2467            for (var i = 0; i < jsScopeArray.length; i++) {
2468
2469                var scope = jsScopeArray[i],
2470                    carousel = scope.querySelector('.pe--carousel'),
2471                    wrapper = carousel.querySelector('.carousel--wrapper'),
2472                    id = carousel.dataset.id ? carousel.dataset.id : scope.dataset.id,
2473                    items = carousel.querySelectorAll('.carousel--item'),
2474                    length = items.length,
2475                    wrapperWidth = wrapper.offsetWidth,
2476                    carouselWidth = carousel.offsetWidth,
2477                    trigger = carousel.dataset.trigger ? carousel.dataset.trigger : '.' + carousel.classList[0];
2478
2479                // document.querySelector(trigger) ? document.querySelector(trigger).classList.add('pin--trigger') : '';
2480
2481                items.forEach(item => {
2482                    var index = parseInt(item.dataset.index);
2483                });
2484
2485                function carouselScroll() {
2486
2487                    gsap.to(wrapper, {
2488                        x: (-1 * wrapperWidth) + carouselWidth,
2489                        scrollTrigger: {
2490                            trigger: trigger,
2491                            scrub: true,
2492                            pin: trigger,
2493                            ease: "elastic.out(1, 0.3)",
2494                            start: 'center center',
2495                            end: 'bottom+=6000 bottom',
2496                            pinSpacing: 'padding',
2497                            onEnter: () => isPinnng(trigger, true),
2498                            onEnterBack: () => isPinnng(trigger, true),
2499                            onLeave: () => isPinnng(trigger, false),
2500                            onLeaveBack: () => isPinnng(trigger, false),
2501                        }
2502                    })
2503
2504                }
2505
2506                function carouselDrag() {
2507
2508                    Draggable.create(wrapper, {
2509                        type: 'x',
2510                        bounds: {
2511                            minX: 0,
2512                            maxX: -wrapperWidth + document.body.clientWidth - 50
2513                        },
2514                        lockAxis: true,
2515                        dragResistance: 0.5,
2516                        inertia: true,
2517                    });
2518
2519
2520                }
2521
2522                function carouselLoop() {
2523
2524                    var tl = gsap.timeline({
2525                        repeat: -1,
2526                    }),
2527                        direction = wrapper.dataset.direction,
2528                        speed = parseInt(wrapper.dataset.speed),
2529                        speedUp = wrapper.dataset.speedUp;
2530
2531                    items.forEach(item => {
2532                        let clone = item.cloneNode(true);
2533                        wrapper.appendChild(clone);
2534                    });
2535
2536                    if (direction !== 'right-to-left') {
2537                        // Reverse the order of items and prepend
2538                        Array.from(items).reverse().forEach(item => {
2539                            let clone = item.cloneNode(true);
2540                            wrapper.prepend(clone);
2541                        });
2542                    }
2543
2544                    wrapper.style.width = wrapperWidth * 2
2545
2546                    let gap = window.getComputedStyle(wrapper).getPropertyValue('gap');
2547
2548                    if (direction === 'right-to-left') {
2549
2550                        tl.to(wrapper, {
2551                            x: -wrapperWidth - parseFloat(gap),
2552                            duration: speed,
2553                            ease: 'none',
2554                        });
2555
2556                    } else {
2557
2558                        gsap.set(wrapper, {
2559                            x: -wrapperWidth - parseFloat(gap)
2560                        })
2561
2562                        tl.fromTo(wrapper, {
2563                            x: -wrapperWidth - parseFloat(gap)
2564                        }, {
2565                            x: 0,
2566                            duration: speed,
2567                            ease: 'none',
2568                        })
2569                    }
2570
2571                    if (speedUp) {
2572
2573                        let whaler = Hamster(document.querySelector('body')),
2574                            wheelDeltaY, currentDeltaY;
2575
2576                        function createWheelStopListener(element, callback, timeout) {
2577                            var handle = null;
2578                            var onScroll = function () {
2579                                if (handle) {
2580                                    clearTimeout(handle);
2581                                }
2582                                handle = setTimeout(callback, timeout || 200); // 
2583                            };
2584                            element.addEventListener('wheel', onScroll);
2585                            return function () {
2586                                element.removeEventListener('wheel', onScroll);
2587                            };
2588                        }
2589
2590                        whaler.wheel(function (event, delta, deltaX, deltaY) {
2591
2592                            wheelDeltaY = event.deltaY;
2593                            event.deltaY < 0 ? wheelDeltaY = -1 * event.deltaY : '';
2594                            tl.timeScale(1 + (wheelDeltaY * 3))
2595
2596                        });
2597
2598                        createWheelStopListener(window, function () {
2599                            tl.timeScale(1)
2600                        });
2601
2602                    }
2603
2604                }
2605
2606                carousel.classList.contains('cr--scroll') ? carouselScroll() : carousel.classList.contains('cr--drag') ? carouselDrag() : carouselLoop();
2607
2608            }
2609
2610        });
2611
2612        elementorFrontend.hooks.addAction('frontend/element_ready/peicon.default', function ($scope, $) {
2613
2614            var jsScopeArray = $scope.toArray();
2615            for (var i = 0; i < jsScopeArray.length; i++) {
2616                var scope = jsScopeArray[i],
2617                    animated = scope.querySelectorAll('.icon--motion');
2618
2619                animated.forEach((element) => {
2620
2621                    let classes = element.classList,
2622                        hasMotion = Array.from(classes).some(className => className.startsWith('me--'));
2623
2624                    // Motion Effects
2625                    if (hasMotion) {
2626
2627                        let motion = hasMotion ? Array.from(classes).find(className => className.startsWith('me--')) : null,
2628                            duration = element.dataset.duration,
2629                            delay = element.dataset.delay,
2630                            ease = motion === 'me--flip-x' ? 'none' : motion === 'me--flip-y' ? 'none' : motion === 'me--hearthbeat-x' ? 'power4.inOut' : motion === 'me--slide-left' ? 'power3.in' : motion === 'me--slide-right' ? 'power3.in' : motion === 'me--slide-down' ? 'expo.in' : motion === 'me--slide-up' ? 'expo.in' : 'expo.out',
2631                            tl = gsap.timeline({
2632                                repeat: -1,
2633                                repeatDelay: parseInt(delay, 10)
2634                            }),
2635                            target = element.querySelector('i, svg');
2636
2637
2638
2639                        if (motion === 'me--slide-left' || motion === 'me--slide-right') {
2640
2641                            target = element.firstElementChild;
2642                        }
2643
2644                        tl.fromTo(target, {
2645                            xPercent: 0,
2646                            yPercent: 0,
2647                            scale: motion === 'me--hearth-beat' ? 0.6 : 1
2648                        }, {
2649
2650                            scale: 1,
2651                            rotate: motion === 'me--rotate' ? -360 : 0,
2652                            rotateX: motion === 'me--flip-x' ? -360 : 0,
2653                            rotateY: motion === 'me--flip-y' ? -360 : 0,
2654                            xPercent: motion === 'me--slide-left' ? -300 : motion === 'me--slide-right' ? 300 : 0,
2655                            yPercent: motion === 'me--slide-down' ? 200 : motion === 'me--slide-up' ? -200 : 0,
2656                            duration: duration,
2657                            ease: ease,
2658
2659                        })
2660
2661                        if (motion === 'me--slide-left' || motion === 'me--slide-right') {
2662
2663                            tl.fromTo(target, {
2664                                xPercent: motion === 'me--slide-left' ? 300 : motion === 'me--slide-right' ? -300 : 0
2665                            }, {
2666                                xPercent: 0,
2667                                duration: duration,
2668                                ease: 'power3.out',
2669                            })
2670                        }
2671
2672                        if (motion === 'me--slide-down' || motion === 'me--slide-up') {
2673
2674                            tl.fromTo(target, {
2675                                yPercent: motion === 'me--slide-down' ? -200 : motion === 'me--slide-up' ? 200 : 0
2676                            }, {
2677                                yPercent: 0,
2678                                duration: duration,
2679                                ease: 'power3.out',
2680                            })
2681                        }
2682
2683                        if (motion === 'me--hearth-beat') {
2684
2685                            tl.to(target, {
2686                                scale: 0.6,
2687                                duration: duration
2688                            })
2689                        }
2690
2691                    }
2692
2693                })
2694
2695
2696            }
2697
2698        });
2699
2700        elementorFrontend.hooks.addAction('frontend/element_ready/pelayoutswitcher.default', function ($scope, $) {
2701
2702            var jsScopeArray = $scope.toArray();
2703            for (var i = 0; i < jsScopeArray.length; i++) {
2704                var scope = jsScopeArray[i],
2705                    switcher = scope.querySelector('.pe-layout-switcher');
2706
2707                let mainColors = [
2708                    getComputedStyle(document.documentElement).getPropertyValue('--mainColor'),
2709                    getComputedStyle(document.documentElement).getPropertyValue('--mainBackground'),
2710                    getComputedStyle(document.documentElement).getPropertyValue('--secondaryColor'),
2711                    getComputedStyle(document.documentElement).getPropertyValue('--secondaryBackground'),
2712                ]
2713
2714                let switchedColors = [
2715                    getComputedStyle(document.querySelector('.layout--colors')).getPropertyValue('--mainColor'),
2716                    getComputedStyle(document.querySelector('.layout--colors')).getPropertyValue('--mainBackgroun
2716d'),
2717                    getComputedStyle(document.querySelector('.layout--colors')).getPropertyValue('--secondaryColor'),
2718                    getComputedStyle(document.querySelector('.layout--colors')).getPropertyValue('--secondaryBackground'),
2719                ]
2720
2721
2722                switcher.addEventListener('click', () => {
2723
2724                    if (document.body.classList.contains('layout--switched')) {
2725
2726                        gsap.fromTo(document.body, {
2727                            '--mainColor': switchedColors[0],
2728                            '--mainBackground': switchedColors[1],
2729                            '--secondaryColor': switchedColors[2],
2730                            '--secondaryBackground': switchedColors[3],
2731                        }, {
2732                            '--mainColor': mainColors[0],
2733                            '--mainBackground': mainColors[1],
2734                            '--secondaryColor': mainColors[2],
2735                            '--secondaryBackground': mainColors[3],
2736                            duration: 1,
2737                            ease: 'power3.out',
2738                            onStart: () => {
2739                                document.body.classList.remove('layout--switched')
2740                            }
2741                        })
2742
2743                    } else {
2744
2745
2746                        gsap.fromTo(document.body, {
2747                            '--mainColor': mainColors[0],
2748                            '--mainBackground': mainColors[1],
2749                            '--secondaryColor': mainColors[2],
2750                            '--secondaryBackground': mainColors[3],
2751                        }, {
2752                            '--mainColor': switchedColors[0],
2753                            '--mainBackground': switchedColors[1],
2754                            '--secondaryColor': switchedColors[2],
2755                            '--secondaryBackground': switchedColors[3],
2756                            duration: 1,
2757                            ease: 'power3.out',
2758                            onStart: () => {
2759                                document.body.classList.add('layout--switched')
2760                            }
2761                        })
2762
2763                    }
2764
2765                })
2766
2767
2768
2769            }
2770
2771        });
2772
2773        elementorFrontend.hooks.addAction('frontend/element_ready/peteammember.default', function ($scope, $) {
2774
2775            var jsScopeArray = $scope.toArray();
2776            for (var i = 0; i < jsScopeArray.length; i++) {
2777                var scope = jsScopeArray[i],
2778                    member = scope.querySelector('.pe--team--member'),
2779                    toggle = scope.querySelector('.team--member--toggle');
2780
2781                toggle.addEventListener('click', () => {
2782
2783                    member.classList.toggle('active');
2784
2785                })
2786
2787
2788            }
2789
2790        })
2791
2792        elementorFrontend.hooks.addAction('frontend/element_ready/peclients.default', function ($scope, $) {
2793
2794            var jsScopeArray = $scope.toArray();
2795            for (var i = 0; i < jsScopeArray.length; i++) {
2796                var scope = jsScopeArray[i],
2797                    clients = scope.querySelector('.pe--clients');
2798
2799                if (clients.classList.contains('pe--clients--carousel')) {
2800
2801                    let wrapper = clients.querySelector('.pe--clients--wrapper'),
2802                        wrapperWidth = wrapper.offsetWidth,
2803                        items = wrapper.querySelectorAll('.pe-client'),
2804                        speed = clients.dataset.speed,
2805                        direction = clients.dataset.direction,
2806                        stopHover = clients.dataset.hover;
2807
2808                    if (items.length > 0) {
2809
2810                        var tl = gsap.timeline({
2811                            repeat: -1,
2812                        });
2813
2814                        items.forEach(item => {
2815                            let clone = item.cloneNode(true);
2816                            wrapper.appendChild(clone);
2817                        });
2818
2819                        if (direction !== 'right-to-left') {
2820                            // Reverse the order of items and prepend
2821                            Array.from(items).reverse().forEach(item => {
2822                                let clone = item.cloneNode(true);
2823                                wrapper.prepend(clone);
2824                            });
2825                        }
2826
2827
2828                        wrapper.style.width = wrapperWidth * 2
2829
2830
2831                        let gap = window.getComputedStyle(wrapper).getPropertyValue('gap');
2832
2833                        if (direction === 'right-to-left') {
2834
2835                            tl.to(wrapper, {
2836                                x: -wrapperWidth - parseFloat(gap),
2837                                duration: speed,
2838                                ease: 'none',
2839
2840                            });
2841
2842
2843                        } else {
2844
2845                            gsap.set(wrapper, {
2846                                x: -wrapperWidth - parseFloat(gap)
2847                            })
2848
2849                            tl.fromTo(wrapper, {
2850                                x: -wrapperWidth - parseFloat(gap)
2851                            }, {
2852                                x: 0,
2853                                duration: speed,
2854                                ease: 'none',
2855                            })
2856                        }
2857
2858                    }
2859
2860                    if (stopHover) {
2861                        wrapper.addEventListener('mouseenter', () => {
2862                            tl.pause();
2863                        })
2864
2865                        wrapper.addEventListener('mouseleave', () => {
2866                            tl.play();
2867                        })
2868                    }
2869
2870
2871                }
2872
2873            }
2874
2875
2876        });
2877
2878        elementorFrontend.hooks.addAction('frontend/element_ready/peaccordion.default', function ($scope, $) {
2879
2880            var jsScopeArray = $scope.toArray();
2881            for (var i = 0; i < jsScopeArray.length; i++) {
2882                var scope = jsScopeArray[i],
2883                    accordion = scope.querySelector('.pe--accordion'),
2884                    wrapper = accordion.querySelector('.pe--accordion--wrapper'),
2885                    items = wrapper.querySelectorAll('.pe-accordion-item');
2886
2887                items.forEach(item => {
2888
2889                    let title = item.querySelector('.pe-accordion-item-title'),
2890                        content = item.querySelector('.pe-accordion-item-content');
2891
2892                    title.addEventListener('click', () => {
2893
2894                        if (item.classList.contains('accordion--active')) {
2895
2896                            var contentState = Flip.getState(content);
2897                            item.classList.remove('accordion--active');
2898
2899                            Flip.from(contentState, {
2900                                duration: .75,
2901                                ease: 'expo.inOut',
2902                                absolute: false,
2903                                absoluteOnLeave: false,
2904                            })
2905
2906
2907                        } else {
2908
2909
2910                            if (!accordion.classList.contains('open--multiple')) {
2911
2912                                var currentActive = accordion.querySelector('.accordion--active');
2913
2914                                if (currentActive) {
2915
2916                                    let currentContentState = Flip.getState(currentActive.querySelector('.pe-accordion-item-content'));
2917
2918                                    currentActive.classList.remove('accordion--active');
2919
2920                                    Flip.from(currentContentState, {
2921                                        duration: .75,
2922                                        ease: 'expo.inOut',
2923                                        absolute: false,
2924                                        absoluteOnLeave: false,
2925                                    })
2926
2927                                }
2928                            }
2929                            //Open
2930
2931                            var contentState = Flip.getState(content);
2932                            item.classList.add('accordion--active');
2933
2934                            Flip.from(contentState, {
2935                                duration: .75,
2936                                ease: 'expo.inOut',
2937                                absolute: false,
2938                                absoluteOnLeave: false,
2939                            })
2940
2941                        }
2942
2943
2944                    })
2945
2946                })
2947
2948            }
2949
2950        });
2951
2952        elementorFrontend.hooks.addAction('frontend/element_ready/pesingleimage.default', function ($scope, $) {
2953            var jsScopeArray = $scope.toArray();
2954            for (var i = 0; i < jsScopeArray.length; i++) {
2955                var scope = jsScopeArray[i],
2956                    image = scope.querySelector('.single-image');
2957
2958
2959                imagesLoaded(image, function (instance) {
2960
2961                    if (image.classList.contains('zoomed--image')) {
2962
2963                        var before = image.querySelector('.zoomed--before'),
2964                            center = image.querySelector('.zoomed--center'),
2965                            after = image.querySelector('.zoomed--after'),
2966                            centerWidth = center.getBoundingClientRect().width,
2967                            centerHeight = center.getBoundingClientRect().height;
2968
2969
2970                        let hold = document.createElement('div');
2971
2972                        image.insertBefore(hold, after);
2973
2974                        center.classList.add('zoomed');
2975
2976                        let tl = gsap.timeline({
2977                            scrollTrigger: {
2978                                trigger: scope,
2979                                start: 'top bottom',
2980                                end: 'center center',
2981                                scrub: true
2982                            }
2983                        });
2984
2985                        tl.fromTo(image, {
2986                            xPercent: -100,
2987
2988                        }, {
2989                            xPercent: 0,
2990                            duration: 20,
2991                            ease: 'none'
2992                        }, 0)
2993
2994                        gsap.to(center, {
2995                            width: '100%',
2996                            height: '100%',
2997                            scrollTrigger: {
2998                                trigger: scope,
2999                                scrub: true,
3000                                pin: scope,
3001                                start: 'center center',
3002                                pinSpacing: 'margin'
3003
3004                            }
3005                        })
3006
3007                    }
3008
3009                    if (image.classList.contains('parallax--image')) {
3010
3011                        let img = image.querySelectorAll('img');
3012
3013                        for (var i = 0; i < img.length; i++) {
3014
3015                            gsap.set(img[i], {
3016                                scale: 1.2
3017                            })
3018
3019                            gsap.fromTo(img[i], {
3020                                yPercent: -10
3021                            }, {
3022                                yPercent: 10,
3023                                ease: 'none',
3024                                scrollTrigger: {
3025                                    trigger: image,
3026                                    scrub: true,
3027                                    start: 'top bottom',
3028                                    end: 'bottom top'
3029                                }
3030                            })
3031
3032
3033                        }
3034
3035                    }
3036
3037                });
3038
3039            }
3040
3041
3042        });
3043
3044        elementorFrontend.hooks.addAction('frontend/element_ready/pemarquee.default', function ($scope, $) {
3045
3046            var jsScopeArray = $scope.toArray();
3047            for (var i = 0; i < jsScopeArray.length; i++) {
3048                var scope = jsScopeArray[i],
3049                    marquee = document.querySelectorAll('.pe-marquee');
3050
3051                marquee.forEach(function (marqueeElement) {
3052
3053                    var text = marqueeElement.children,
3054                        dataDuration = marqueeElement.getAttribute('data-duration'),
3055                        separator = marqueeElement.getAttribute('data-seperator');
3056                    var wrapperElement = document.createElement("div");
3057                    wrapperElement.className = "marquee-wrap";
3058
3059                    while (marqueeElement.firstChild) {
3060                        wrapperElement.appendChild(marqueeElement.firstChild);
3061                    }
3062                    marqueeElement.appendChild(wrapperElement);
3063
3064                    var infItem = marqueeElement.querySelector('.marquee-wrap'),
3065                        infWidth = infItem.offsetWidth;
3066
3067                    if (infWidth > 0) {
3068
3069                        var infLength = window.innerWidth / infWidth,
3070                            gap = infItem.getBoundingClientRect().left;
3071                        if (marqueeElement.classList.contains('icon_font')) {
3072                            var separators = infItem.querySelectorAll('.seperator');
3073                            separators.forEach(function (separator) {
3074                                separator.style.fontSize = window.getComputedStyle(separator.parentNode).getPropertyValue('font-size');
3075                            });
3076                        }
3077
3078                        function infinityOnResize() {
3079                            for (var i = 2; i < infLength + 2; i++) {
3080                                var clonedItem = infItem.cloneNode(true);
3081                                marqueeElement.appendChild(clonedItem);
3082                            }
3083                            var infItemLength = marqueeElement.querySelectorAll('.marquee-wrap').length;
3084                            infWidth = parseInt(infWidth);
3085                            infItem.style.width = infWidth + 'px';
3086                            marqueeElement.style.width = (infItemLength * infItem.offsetWidth) + 'px';
3087                            marqueeElement.style.display = 'flex';
3088
3089                            var tl = gsap.timeline({
3090                                repeat: -1
3091                            });
3092                            var tl2 = gsap.timeline({
3093                                repeat: -1
3094                            });
3095
3096                            if (marqueeElement.classList.contains('left-to-right')) {
3097                                tl.fromTo(marqueeElement, {
3098                                    x: -1 * (infWidth + gap)
3099                                }, {
3100                                    x: -1 * gap,
3101                                    ease: 'none',
3102                                    duration: infWidth / 1000 * dataDuration
3103                                });
3104                            } else {
3105                                tl.fromTo(marqueeElement, {
3106                                    x: -1 * gap
3107                                }, {
3108                                    x: -1 * (infWidth + gap),
3109                                    ease: 'none',
3110                                    duration: infWidth / 1000 * dataDuration
3111                                });
3112                            }
3113
3114                            if (marqueeElement.classList.contains('rotating_seperator')) {
3115                                var sepDuration = marqueeElement.getAttribute('data-sepduration');
3116                                var rotateValue = marqueeElement.classList.contains('counter-clockwise') ? -360 : 360;
3117                                tl2.fromTo(marqueeElement.querySelectorAll('.seperator'), {
3118                                    rotate: 0
3119                                }, {
3120                                    rotate: rotateValue,
3121                                    duration: sepDuration,
3122                                    ease: 'none'
3123                                });
3124                            }
3125                        }
3126
3127                        infinityOnResize();
3128                    }
3129                });
3130            }
3131
3132        });
3133        elementorFrontend.hooks.addAction('frontend/element_ready/peblogposts.default', function ($scope, $) {
3134
3135            var jsScopeArray = $scope.toArray();
3136            for (var i = 0; i < jsScopeArray.length; i++) {
3137                var scope = jsScopeArray[i],
3138                    grid = scope.querySelector('.pe--posts--grid'),
3139                    wrapper = scope.querySelector('.grid--posts--wrapper'),
3140                    posts = wrapper.querySelectorAll('.grid--post--item'),
3141                    filters = grid.querySelector('.grid--filters');
3142
3143                if (filters) {
3144
3145                    let filter = filters.querySelectorAll('.post-filter'),
3146                        ul = filters.querySelector('.filters-list');
3147
3148                    let filterAll = ul.querySelector('.filter--all');
3149
3150                    gsap.set(ul, {
3151                        '--activeLeft': filterAll.offsetLeft - 10 + 'px',
3152                        '--activeWidth': filterAll.offsetWidth + filterAll.offsetLeft - 35 + 'px',
3153                    })
3154
3155                    filter.forEach(filter => {
3156
3157
3158
3159                        filter.addEventListener('click', () => {
3160
3161                            filters.querySelector('.active').classList.remove('active');
3162                            filter.classList.add('active');
3163
3164                            gsap.to(ul, {
3165                                '--activeLeft': filter.offsetLeft - 10 + 'px',
3166                                '--activeWidth': filter.offsetWidth + filter.offsetLeft - 35 + 'px',
3167                                duration: .5,
3168                                ease: 'expo.out'
3169                            })
3170
3171                            let cat = filter.dataset.category,
3172                                findPosts = 'cat_' + cat;
3173
3174                            let state = Flip.getState(posts);
3175
3176                            posts.forEach(post => {
3177
3178                                if (cat !== 'all') {
3179
3180                                    post.classList.contains(findPosts) ? post.style.display = 'block' : post.style.display = 'none';
3181
3182                                } else {
3183
3184                                    post.style.display = 'block'
3185                                }
3186
3187                            })
3188
3189                            Flip.from(state, {
3190                                duration: 1,
3191                                absolute: false,
3192                                absoluteOnLeave: false,
3193                                ease: "expo.inOut",
3194                                onEnter: elements => gsap.fromTo(elements, {
3195                                    opacity: 0,
3196                                    xPercent: 100
3197                                }, {
3198                                    opacity: 1,
3199                                    xPercent: 0
3200                                }),
3201                                onLeave: elements => gsap.fromTo(elements, {
3202                                    opacity: 1,
3203                                    xPercent: 0
3204                                }, {
3205                                    opacity: 0,
3206                                    xPercent: -100,
3207                                    stagger: 0.1
3208                                }),
3209                            })
3210
3211                        })
3212
3213                    })
3214
3215                }
3216
3217                if (grid.querySelector('.pe-load-more')) {
3218
3219                    let button = grid.querySelector('.pe-load-more'),
3220                        currentWrapper = wrapper,
3221                        count = grid.dataset.total,
3222                        link = button.querySelector('a');
3223
3224                    link.addEventListener('click', (e) => {
3225
3226                        let apiUrl = link.getAttribute("href");
3227                        e.preventDefault();
3228
3229                        button.classList.add('plm--loading');
3230                        document.documentElement.classList.add('loading');
3231
3232                        var xhr = new XMLHttpRequest();
3233                        xhr.open('GET', apiUrl);
3234                        xhr.onreadystatechange = function () {
3235
3236                            if (xhr.readyState === XMLHttpRequest.DONE) {
3237
3238                                if (xhr.status === 200) {
3239
3240                                    var response = xhr.responseText;
3241
3242                                    setTimeout(function () {
3243                                        var parser = new DOMParser(),
3244                                            htmlDoc = parser.parseFromString(response, 'text/html'),
3245                                            newPosts = htmlDoc.querySelectorAll('.pe--posts--grid .grid--post--item'),
3246                                            newUrl = htmlDoc.querySelector('.pe-load-more a').getAttribute('href');
3247
3248                                        link.setAttribute("href", newUrl);
3249
3250                                        if (newPosts.length > 0) {
3251
3252                                            let tl = gsap.timeline({
3253                                                onComplete: () => {
3254                                                    ScrollTrigger.refresh()
3255
3256                                                }
3257                                            });
3258
3259                                            newPosts.forEach(function (post, i) {
3260
3261                                                let clone = post.cloneNode(true)
3262                                                currentWrapper.appendChild(clone);
3263
3264                                                tl.fromTo(clone, {
3265                                                    opacity: 0,
3266                                                    yPercent: 100
3267                                                }, {
3268                                                    opacity: 1,
3269                                                    yPercent: 0,
3270                                                    duration: .75,
3271                                                    ease: 'expo.out'
3272                                                }, i * 0.15)
3273
3274                                            });
3275
3276
3277
3278
3279                                            if (grid.querySelectorAll('.grid--post--item').length >= count) {
3280                                                button.classList.add('plm--disabled');
3281                                            }
3282
3283                                            button.classList.remove('plm--loading');
3284                                            document.documentElement.classList.remove('loading');
3285                                        }
3286
3287                                    }, 200);
3288                                } else {
3289                                    console.error('Request failed. Status: ' + xhr.status);
3290                                }
3291                            }
3292                        };
3293                        xhr.send();
3294
3295                    })
3296
3297                }
3298
3299            }
3300
3301        });
3302
3303        elementorFrontend.hooks.addAction('frontend/element_ready/pepostmedia.default', function ($scope, $) {
3304            var jsScopeArray = $scope.toArray();
3305            for (var i = 0; i < jsScopeArray.length; i++) {
3306                var scope = jsScopeArray[i],
3307                    image = scope.querySelector('.single-image');
3308
3309                if (image.classList.contains('parallax--image')) {
3310
3311                    let img = image.querySelectorAll('img');
3312
3313                    for (var i = 0; i < img.length; i++) {
3314
3315                        gsap.fromTo(img[i], {
3316                            yPercent: 0
3317                        }, {
3318                            yPercent: -10,
3319                            ease: 'none',
3320                            scrollTrigger: {
3321                                trigger: image,
3322                                scrub: true,
3323                                start: 0,
3324                                end: 'bottom top'
3325                            }
3326                        })
3327
3328
3329                    }
3330
3331                }
3332            }
3333
3334        });
3335
3336        elementorFrontend.hooks.addAction('frontend/element_ready/projectmedia.default', function ($scope, $) {
3337            var jsScopeArray = $scope.toArray();
3338            for (var i = 0; i < jsScopeArray.length; i++) {
3339                var scope = jsScopeArray[i],
3340                    gallery = scope.querySelector('.project--image--gallery');
3341
3342                if (gallery) {
3343
3344                    let wrapper = gallery.querySelector('.project--image--gallery--wrapper'),
3345                        images = wrapper.querySelectorAll('.project--gallery--image'),
3346                        gap = parseInt(window.getComputedStyle(wrapper).getPropertyValue('gap')),
3347                        val = wrapper.getBoundingClientRect().left + (wrapper.offsetWidth - document.body.clientWidth) + gap,
3348                        id = wrapper.dataset.id ? wrapper.dataset.id : scope.dataset.id,
3349                        trigger = gallery.dataset.trigger ? gallery.dataset.trigger : scope,
3350                        speed = wrapper.dataset.speed,
3351                        integrated = gallery.dataset.integrated;
3352
3353                    wrapper.classList.add(id);
3354                    wrapper.setAttribute('data-total', images.length);
3355                    images.forEach((image, i) => {
3356
3357                        image.setAttribute('data-cr', i + 1);
3358                    })
3359
3360                    if (scope.classList.contains('cr--scroll')) {
3361
3362                        wrapper.classList.add('cr--scroll');
3363
3364                        let crScroll = gsap.to(wrapper, {
3365                            id: id,
3366                            x: -val,
3367                            ease: "sine.inOut",
3368                            scrollTrigger: {
3369                                trigger: trigger,
3370                                pin: trigger,
3371                                pinSpacing: 'margin',
3372                                scrub: true,
3373                                start: 'top top',
3374                                end: 'bottom+=3000 top',
3375                                onEnter: () => isPinnng(trigger, true),
3376                                onEnterBack: () => isPinnng(trigger, true),
3377                                onLeave: () => isPinnng(trigger, false),
3378                                onLeaveBack: () => isPinnng(trigger, false),
3379                                onUpdate: self => {
3380
3381                                    if (integrated && !mobileQuery.matches) {
3382
3383                                        gsap.to(integrated, {
3384                                            opacity: 1 - (self.progress * 5)
3385                                        })
3386                                    }
3387                                }
3388                            }
3389                        })
3390
3391                        matchMedia.add({
3392                            isPhone: "(max-width: 550px)"
3393                        }, (context) => {
3394
3395                            crScroll.scrollTrigger.kill(true);
3396
3397                            Draggable.create(wrapper, {
3398                                type: 'x',
3399                                dragResistance: 0.35,
3400                                inertia: true,
3401                                bounds: {
3402                                    minX: 0,
3403                                    maxX: -val
3404                                },
3405                            })
3406
3407                        });
3408
3409                    }
3410
3411                    if (scope.classList.contains('cr--drag')) {
3412
3413                        wrapper.classList.add('cr--drag');
3414
3415                        let drag = Draggable.create(wrapper, {
3416                            id: id,
3417                            type: 'x',
3418                            dragResistance: 0.35,
3419                            inertia: true,
3420                            bounds: {
3421                                minX: 0,
3422                                maxX: -val
3423                            },
3424                            onThrowUpdate: () => {
3425                                let prog = drag[0].x / drag[0].minX;
3426
3427                                if (integrated) {
3428
3429                                    gsap.to(integrated, {
3430                                        opacity: 1 - (prog * 5)
3431                                    })
3432                                }
3433
3434                            },
3435                            onMove: () => {
3436
3437                                let prog = drag[0].x / drag[0].minX;
3438
3439                                if (integrated) {
3440
3441                                    gsap.to(integrated, {
3442                                        opacity: 1 - (prog * 5)
3443                                    })
3444                                }
3445
3446                            },
3447                            lockAxis: true,
3448                            dragResistance: 0.5,
3449                            inertia: true,
3450                        });
3451
3452                    }
3453
3454
3455                } else {
3456
3457                    let image = scope.querySelector('.project-featured-image');
3458
3459                    if (image && image.classList.contains('parallax--image')) {
3460
3461                        let img = image.querySelectorAll('img');
3462
3463
3464                        for (var i = 0; i < img.length; i++) {
3465
3466                            gsap.fromTo(img[i], {
3467                                yPercent: 0
3468                            }, {
3469                                yPercent: 20,
3470                                ease: 'none',
3471                                scrollTrigger: {
3472                                    trigger: image,
3473                                    scrub: 1.2,
3474                                    start: 'top top',
3475                                    end: 'bottom top'
3476                                }
3477                            })
3478
3479
3480                        }
3481
3482                    }
3483                }
3484
3485            }
3486
3487        });
3488
3489        elementorFrontend.hooks.addAction('frontend/element_ready/peportfolio.default', function ($scope, $) {
3490
3491            var jsScopeArray = $scope.toArray();
3492            for (var i = 0; i < jsScopeArray.length; i++) {
3493                var scope = jsScopeArray[i],
3494                    filters = scope.querySelector('.portfolio--filters'),
3495                    id = scope.dataset.id,
3496                    wrapper = scope.querySelector('.portfolio--projects--wrapper'),
3497                    url = scope.querySelector('input[name="url"]').value,
3498                    catdata = scope.querySelector('input[name="cat"]'),
3499                    portfolio = scope.querySelector('.pe--portfolio'),
3500                    pagination = scope.querySelector('.portfolio--pagination'),
3501                    switcher = scope.querySelector('.ps--switch'),
3502                    projects = scope.querySelectorAll('.portfolio--project');
3503
3504                if (switcher) {
3505
3506                    let switchGrid = switcher.querySelector('.ps--grid'),
3507                        switchList = switcher.querySelector('.ps--list'),
3508                        follower = switcher.querySelector('.ps--follower'),
3509                        sgWidth = switchGrid.offsetWidth,
3510                        slWidth = switchList.offsetWidth;
3511
3512                    if (portfolio.classList.contains('portfolio--list')) {
3513
3514                        switchGrid.classList.remove('active')
3515                        switchList.classList.add('active')
3516
3517                        switcher.classList.contains('switcher--switcher') ? follower.style.width = slWidth + 'px' : '';
3518
3519                    } else {
3520
3521                        switchGrid.classList.add('active')
3522                        switchList.classList.remove('active')
3523
3524                        switcher.classList.contains('switcher--switcher') ? follower.style.width = sgWidth + 'px' : '';
3525
3526                    }
3527
3528                    switcher.addEventListener('click', () => {
3529
3530                        let tl = gsap.timeline();
3531
3532                        tl.to(wrapper, {
3533                            opacity: 0,
3534                            duration: .5,
3535                            onComplete: () => {
3536
3537                                if (portfolio.classList.contains('portfolio--list')) {
3538
3539                                    portfolio.classList.remove('portfolio--list')
3540                                    portfolio.classList.add('portfolio--grid');
3541
3542                                    switchGrid.classList.add('active')
3543                                    switchList.classList.remove('active')
3544
3545
3546                                } else {
3547                                    portfolio.classList.remove('portfolio--grid')
3548                                    portfolio.classList.add('portfolio--list')
3549
3550                                    farahPortfolioList();
3551
3552                                    switchGrid.classList.remove('active')
3553                                    switchList.classList.add('active')
3554                                }
3555                            }
3556                        })
3557
3558                        tl.to(wrapper, {
3559                            opacity: 1,
3560                            duration: .5
3561                        })
3562
3563
3564
3565
3566                    })
3567
3568                }
3569
3570                if (filters) {
3571
3572                    let trigger = filters.querySelector('.filter--active'),
3573                        cats = filters.querySelectorAll('.filter--cat');
3574
3575                    trigger.addEventListener('click', () => {
3576
3577                        filters.classList.toggle('filt--active');
3578
3579
3580                    })
3581
3582                    cats.forEach(cat => {
3583
3584                        cat.addEventListener('click', (e) => {
3585
3586                            scope.querySelector('.filter--cat.active').classList.remove('active');
3587                            cat.classList.add('active');
3588
3589                            var apiUrl = cat.dataset.id ? url + '?cat=' + cat.dataset.id : url;
3590
3591                            e.preventDefault();
3592
3593                            document.documentElement.classList.add('loading');
3594
3595                            var xhr = new XMLHttpRequest();
3596                            xhr.open('GET', apiUrl);
3597                            xhr.onreadystatechange = function () {
3598
3599                                if (xhr.readyState === XMLHttpRequest.DONE) {
3600
3601                                    if (xhr.status === 200) {
3602
3603                                        var response = xhr.responseText;
3604
3605                                        setTimeout(function () {
3606
3607                                            let items = wrapper.querySelectorAll('.portfolio--project'),
3608                                                state = Flip.getState(items);
3609
3610                                            items.forEach(item => item.classList.add('hidden'))
3611
3612                                            Flip.from(state, {
3613                                                duration: 1,
3614                                                ease: "power3.inOut",
3615                                                fade: true,
3616                                                absolute: false,
3617                                                absoluteOnLeave: false,
3618                                                onComplete: () => {
3619                                                    items.forEach(item => item.remove())
3620
3621                                                },
3622                                                onLeave: elements => gsap.fromTo(elements, {
3623                                                    opacity: 1,
3624                                                    y: 0
3625                                                }, {
3626                                                    opacity: 0,
3627                                                    y: -50,
3628                                                }),
3629                                            });
3630
3631                                            var parser = new DOMParser(),
3632                                                htmlDoc = parser.parseFromString(response, 'text/html'),
3633                                                newElement = htmlDoc.querySelector('.elementor-element-' + id),
3634                                                newPosts = newElement.querySelectorAll('.portfolio--project');
3635
3636
3637                                            if (newPosts.length > 0) {
3638                                                portfolio.setAttribute('data-max-pages', newElement.querySelector('.pe--portfolio').dataset.maxPages)
3639
3640
3641                                                let tl = gsap.timeline({
3642                                                    onComplete: () => {
3643                                                        ScrollTrigger.refresh()
3644
3645                                                    }
3646                                                });
3647
3648                                                newPosts.forEach(function (post, i) {
3649
3650                                                    let clone = post.cloneNode(true)
3651                                                    wrapper.appendChild(clone);
3652
3653                                                    tl.fromTo(clone, {
3654                                                        opacity: 0,
3655                                                        yPercent: 100
3656                                                    }, {
3657                                                        opacity: 1,
3658                                                        yPercent: 0,
3659                                                        duration: .75,
3660                                                        ease: 'expo.out'
3661                                                    }, i * 0.15)
3662
3663                                                });
3664
3665
3666                                                cat.dataset.id ? trigger.classList.add('filtered') : trigger.classList.remove('filtered');
3667                                                cat.dataset.id ? portfolio.classList.add('filtered') : portfolio.classList.remove('filtered');
3668                                                filters.classList.remove('filt--active');
3669                                                trigger.innerHTML = cat.innerHTML;
3670                                                trigger.setAttribute('data-length', cat.dataset.length)
3671                                                document.documentElement.classList.remove('loading');
3672                                                catdata.value = cat.dataset.id;
3673                                            }
3674
3675                                        }, 200);
3676                                    } else {
3677                                        console.error('Request failed. Status: ' + xhr.status);
3678                                    }
3679                                }
3680                            };
3681                            xhr.send();
3682
3683                        })
3684
3685
3686                    })
3687
3688                }
3689
3690                if (pagination) {
3691
3692                    let loadMore = pagination.querySelector('a'),
3693                        clicks = 0;
3694
3695                    if (loadMore) {
3696
3697                        loadMore.addEventListener('click', (e) => {
3698
3699                            pagination.classList.add('loading');
3700
3701                            clicks++
3702                            var apiUrl = catdata.value ? url + '?offset=' + clicks + '&cat=' + catdata.value : url + '?offset=' + clicks;
3703
3704                            e.preventDefault();
3705
3706
3707                            document.documentElement.classList.add('loading');
3708                            pagination.classList.add('loading');
3709
3710                            var xhr = new XMLHttpRequest();
3711                            xhr.open('GET', apiUrl);
3712                            xhr.onreadystatechange = function () {
3713
3714                                if (xhr.readyState === XMLHttpRequest.DONE) {
3715
3716                                    if (xhr.status === 200) {
3717
3718                                        var response = xhr.responseText;
3719
3720                                        setTimeout(function () {
3721
3722                                            var parser = new DOMParser(),
3723                                                htmlDoc = parser.parseFromString(response, 'text/html'),
3724                                                newElement = htmlDoc.querySelector('.elementor-element-' + id),
3725                                                newPosts = newElement.querySelectorAll('.portfolio--project');
3726
3727                                            if (newPosts.length > 0) {
3728
3729                                                let tl = gsap.timeline({
3730                                                    onComplete: () => {
3731                                                        ScrollTrigger.refresh()
3732
3733                                                    }
3734                                                });
3735
3736                                                newPosts.forEach(function (post, i) {
3737
3738                                                    let clone = post.cloneNode(true)
3739                                                    wrapper.appendChild(clone);
3740
3741                                                    tl.fromTo(clone, {
3742                                                        opacity: 0,
3743                                                        yPercent: 100
3744                                                    }, {
3745                                                        opacity: 1,
3746                                                        yPercent: 0,
3747                                                        duration: .75,
3748                                                        ease: 'expo.out',
3749                                                        onComplete: () => {
3750                                                            pagination.classList.remove('loading');
3751
3752                                                            if (clone.querySelector('.pe-video')) {
3753
3754                                                                let videos = clone.querySelectorAll('.pe-video')
3755
3756                                                                for (var i = 0; i < videos.length; i++) {
3757                                                                    new peVideoPlayer(videos[i]);
3758                                                                }
3759
3760                                                            }
3761
3762                                                        }
3763                                                    }, i * 0.15)
3764
3765                                                });
3766
3767                                                if (portfolio.dataset.maxPages == clicks + 1) {
3768
3769                                                    pagination.classList.add('hidden');
3770                                                }
3771
3772                                                document.documentElement.classList.remove('loading');
3773
3774                                            }
3775
3776                                        }, 200);
3777                                    } else {
3778                                        console.error('Request failed. Status: ' + xhr.status);
3779                                    }
3780                                }
3781                            };
3782                            xhr.send();
3783
3784                        })
3785
3786                    }
3787
3788                }
3789
3790                function farahPortfolioList() {
3791
3792                    let portfolio = $scope.find('.pe--portfolio'),
3793                        titlesWrap = $scope.find('.portfolio--projects--wrapper'),
3794                        imagesWrap = $scope.find('.portfolio--list--images--wrapper');
3795
3796
3797                    titlesWrap.hover(
3798                        () => {
3799                            imagesWrap.addClass('active');
3800                            titlesWrap.addClass('active');
3801
3802                        },
3803                        () => {
3804                            imagesWrap.removeClass('active')
3805                            titlesWrap.removeClass('active')
3806                        }
3807                    );
3808
3809                    gsap.set(imagesWrap, {
3810                        xPercent: -75,
3811                        yPercent: -50
3812                    });
3813
3814                    titlesWrap.on('mousemove', function (e) {
3815
3816                        let xTo = gsap.quickTo(imagesWrap, "left", {
3817                            duration: 0.6,
3818                            ease: "power3"
3819                        }),
3820                            yTo = gsap.quickTo(imagesWrap, "top", {
3821                                duration: 0.6,
3822                                ease: "power3"
3823                            });
3824
3825
3826                        function icko(e) {
3827                            xTo(e.pageX);
3828                            yTo(e.pageY - portfolio.offset().top);
3829                        }
3830
3831                        icko(e)
3832
3833                    });
3834
3835                    matchMedia.add({
3836                        isMobile: "(max-width: 550px)"
3837
3838                    }, (context) => {
3839                        let {
3840                            isMobile
3841                        } = context.conditions;
3842
3843                        titlesWrap.off('mousemove')
3844
3845                        return () => {
3846
3847                            titlesWrap.on('mousemove')
3848
3849                        }
3850                    });
3851
3852
3853
3854                    let projects = titlesWrap.find('.portfolio--project'),
3855                        count = 0;
3856
3857
3858                    projects.each(function () {
3859
3860                        let $this = $(this);
3861
3862                        $this.on('mouseenter', function () {
3863
3864                            let image = $('.image_' + $this.data('id'));
3865                            $this.addClass('active')
3866
3867                            gsap.set(image, {
3868                                zIndex: 1
3869                            })
3870
3871                            image.addClass('active')
3872                            image.addClass('trans-media')
3873
3874                            let tl = gsap.timeline();
3875
3876                            tl.fromTo(image, {
3877
3878                                y: '100%'
3879                            }, {
3880
3881                                y: '0%',
3882                                duration: 1.5,
3883                                ease: 'power3.inOut'
3884                            }, 0)
3885
3886                            tl.fromTo(image.children('div'), {
3887
3888                                scale: 1.3,
3889                                y: '-100%'
3890                            }, {
3891
3892                                y: '0%',
3893                                scale: 1,
3894                                duration: 1.5,
3895                                ease: 'power3.inOut'
3896                            }, 0)
3897
3898                        })
3899
3900                        $this.on('mouseleave', function () {
3901
3902                            count++
3903
3904                            $this.removeClass('active')
3905
3906                            let image = $('.image_' + $this.data('id'));
3907
3908                            image.removeClass('active')
3909                            image.removeClass('trans-media')
3910
3911                            gsap.set(image, {
3912                                zIndex: 0 - count
3913                            })
3914
3915                            let tl = gsap.timeline();
3916
3917                            tl.fromTo(image, {
3918
3919                                y: '0%'
3920                            }, {
3921
3922                                y: '-100%',
3923                                duration: 1.5,
3924                                ease: 'power3.inOut'
3925                            }, 0)
3926
3927                            tl.fromTo(image.children('div'), {
3928
3929                                y: '0%',
3930                                scale: 1
3931                            }, {
3932
3933                                y: '100%',
3934                                scale: 1.3,
3935                                duration: 1.5,
3936                                ease: 'power3.inOut'
3937                            }, 0)
3938
3939                        })
3940
3941                        $this.find('a').on('click', function () {
3942
3943                            $this.off('mouseleave')
3944
3945
3946                        })
3947
3948
3949                    })
3950
3951
3952                }
3953
3954                if (portfolio.classList.contains('portfolio--list')) {
3955
3956                    farahPortfolioList();
3957
3958                }
3959
3960
3961
3962
3963            }
3964
3965        });
3966
3967        // Showcases 
3968        elementorFrontend.hooks.addAction('frontend/element_ready/pefullscreenslideshow.default', function ($scope, $) {
3969            var jsScopeArray = $scope.toArray();
3970
3971            for (var i = 0; i < jsScopeArray.length; i++) {
3972                var scope = jsScopeArray[i],
3973                    fullscreenSlideshow = document.querySelectorAll('.fullscreen--slideshow');
3974
3975                fullscreenSlideshow.forEach(function ($this) {
3976                    let interleaveOffset = 0.5,
3977                        swiper = new Swiper('.fullscreen--slideshow', {
3978                            slidesPerView: 1,
3979                            speed: 1500,
3980                            autoplay: ($this.classList.contains('autoplay__active')) ? true : false,
3981                            delay: parseInt($this.getAttribute('data-delay')),
3982                            loop: ($this.classList.contains('loop__active')) ? true : false,
3983                            direction: 'horizontal',
3984                            pagination: {
3985                                el: ".sc--fraction",
3986                                type: "fraction",
3987                            },
3988                            parallax: true,
3989                            navigation: {
3990                                nextEl: '.sc--next',
3991                                prevEl: '.sc--prev',
3992                            },
3993                            mousewheel: {
3994                                invert: false
3995                            },
3996                            watchSlideProgress: true,
3997                            on: {
3998                                progress: function () {
3999                                    let swiper = this;
4000                                    for (let i = 0; i < swiper.slides.length; i++) {
4001                                        let slideProgress = swiper.slides[i].progress,
4002                                            innerOffset = swiper.width * interleaveOffset,
4003                                            innerTranslate = slideProgress * innerOffset;
4004
4005                                        swiper.slides[i].querySelector(".slide-bgimg").style.transform =
4006                                            "translateX(" + innerTranslate + "px)";
4007                                        if (!mobileQuery.matches) {
4008                                            swiper.slides[i].querySelector(".project--top").style.transform =
4009                                                "translateX(" + innerTranslate / 2 + "px)";
4010                                            swiper.slides[i].querySelector(".project--excerpt").style.transform =
4011                                                "translateX(" + innerTranslate / 2 + "px)";
4012                                        }
4013
4014
4015                                    }
4016                                },
4017                                setTransition: function (speed) {
4018                                    let swiper = this;
4019                                    for (let i = 0; i < swiper.slides.length; i++) {
4020                                        swiper.slides[i].style.transition = speed + "ms";
4021                                        swiper.slides[i].querySelector(".slide-bgimg").style.transition = 1500 + "ms";
4022                                        swiper.slides[i].querySelector(".project--top").style.transition = 1500 + "ms";
4023                                        swiper.slides[i].querySelector(".project--excerpt").style.transition = 1500 + "ms";
4024                                    }
4025                                },
4026                                slideChangeTransitionEnd: () => {
4027
4028                                    for (let i = 0; i < swiper.slides.length; i++) {
4029
4030                                        let bgs = swiper.slides[i].querySelector('.slide-bgimg');
4031
4032                                        swiper.slides[i].querySelector(".slide-bgimg").style.transform =
4033                                            "translateX(0px)";
4034
4035                                        if (!mobileQuery.matches) {
4036                                            swiper.slides[i].querySelector(".project--top").style.transform =
4037                                                "translateX(0px)";
4038                                            swiper.slides[i].querySelector(".project--excerpt").style.transform =
4039                                                "translateX(0px)";
4040                                        }
4041                                    }
4042                                }
4043                            }
4044                        });
4045
4046                    if ($this.classList.contains('autoplay__active')) {
4047                        $this.querySelectorAll('.project--button').forEach(function (button) {
4048                            button.addEventListener('mouseenter', function () {
4049                                swiper.autoplay.stop()
4050                            })
4051                            button.addEventListener('mouseleave', function () {
4052                                swiper.autoplay.start()
4053                            })
4054                        })
4055                    }
4056                })
4057
4058            }
4059        });
4060
4061
4062        elementorFrontend.hooks.addAction('frontend/element_ready/peinfinitecarousel.default', function ($scope, $) {
4063            var jsScopeArray = $scope.toArray();
4064            for (var i = 0; i < jsScopeArray.length; i++) {
4065                var scope = jsScopeArray[i];
4066
4067                let infiniteCarousel = document.querySelectorAll('.infinite--carousel');
4068                infiniteCarousel.forEach(function ($this) {
4069                    let wrap = $this.querySelector('.infinite--carousel--wrapper'),
4070                        inner = $this.querySelector('.infinite--carousel--inner'),
4071                        project = $this.querySelectorAll('.showcase--project'),
4072                        width = project[1].offsetWidth,
4073                        activeWidth = project[0].offsetWidth,
4074                        plength = project.length,
4075                        totalWidth = inner.offsetWidth,
4076                        totalHeight = inner.offsetHeight,
4077                        length = project.length;
4078
4079                    for (let i = 0; i <= 1; i++) {
4080                        project.forEach(function (item, i) {
4081                            let clone = item.cloneNode(true)
4082                            inner.appendChild(clone)
4083                        })
4084                    }
4085                    project = $this.querySelectorAll('.showcase--project');
4086
4087
4088                    matchMedia.add({
4089                        isDesktop: "(min-width: 571px)"
4090
4091                    }, (context) => {
4092
4093                        let {
4094                            isDesktop
4095                        } = context.conditions;
4096                        let wheeler = Hamster($this),
4097                            prog1 = activeWidth / 2;
4098
4099                        gsap.set(wrap, {
4100                            x: (-1 * totalWidth) + (document.body.offsetWidth / 2)
4101                        })
4102                        gsap.set(inner, {
4103                            x: -1 * prog1
4104                        })
4105
4106                        wheeler.wheel(function (event, delta, deltaX, deltaY) {
4107                            
4108
4109
4110                            matchMedia.add({
4111                                isDesktop: "(min-width: 551px)"
4112
4113                            }, (context) => {
4114
4115                                if (window.navigator.platform === 'MacIntel') {
4116                                    prog1 += event.deltaY * 2;
4117                                } else {
4118                                    prog1 += event.deltaY * 10;
4119                                }
4120
4121
4122
4123                            });
4124
4125
4126                            matchMedia.add({
4127                                isPhone: "(max-width: 550px)"
4128                            }, (context) => {
4129                                prog1 += event.deltaY * 2;
4130                            });
4131
4132
4133
4134                            if (prog1 > totalWidth) {
4135                                prog1 = prog1 - totalWidth
4136                            } else if (prog1 < 0) {
4137                                prog1 = prog1 + totalWidth
4138                            }
4139
4140                            gsap.set(inner, {
4141                                x: (-1 * prog1)
4142                            })
4143
4144                            let centerIndex = Math.floor(prog1 / (totalWidth / plength));
4145
4146                            if (centerIndex >= length) {
4147                                centerIndex = centerIndex - length
4148                            } else if (centerIndex < 0) {
4149                                centerIndex = centerIndex + length
4150                            }
4151
4152                            project.forEach((item, index) => {
4153
4154                                index = index % length
4155
4156                                // if (index === centerIndex) {
4157                                //     item.classList.add('showcase--project--active')
4158                                //     gsap.to(item, {
4159                                //         minWidth: activeWidth,
4160                                //     })
4161                                // } else {
4162                                //     item.classList.remove('showcase--project--active')
4163                                //     gsap.to(item, {
4164                                //         minWidth: width,
4165                                //     })
4166                                // }
4167                            });
4168                        });
4169                    });
4170
4171                    matchMedia.add({
4172                        isMobile: "(max-width: 570px)"
4173                    }, (context) => {
4174                        let activeHeight = project[0].offsetHeight,
4175                            normalHeight = project[1].offsetHeight
4176                        gsap.set(wrap, {
4177                            x: (-1 * totalWidth) + (document.body.offsetHeight / 2)
4178                        })
4179                        let drag = Draggable.create(inner, {
4180                            type: 'x',
4181                            inertia: true,
4182                            onThrowUpdate: function () {
4183                                if (this.x < -1 * totalWidth) {
4184                                    gsap.set(inner, {
4185                                        x: this.x + totalWidth
4186                                    })
4187                                } else if (this.y > 0) {
4188                                    gsap.set(inner, {
4189                                        x: this.x - totalWidth
4190                                    })
4191                                }
4192                                let activeIndex = parseInt(this.y / (totalWidth / plength))
4193
4194                                if (activeIndex < 0) {
4195                                    activeIndex = activeIndex * -1
4196                                }
4197
4198                                activeIndex = activeIndex % plength;
4199
4200
4201
4202                            }
4203                        })
4204                    })
4205                })
4206            }
4207        });
4208
4209        elementorFrontend.hooks.addAction('frontend/element_ready/peshowcaselist.default', function ($scope, $) {
4210            var jsScopeArray = $scope.toArray();
4211
4212            for (var i = 0; i < jsScopeArray.length; i++) {
4213                var scope = jsScopeArray[i],
4214                    fsList = document.querySelectorAll('.showcase--list');
4215                fsList.forEach(function ($this) {
4216                    let project = $this.querySelectorAll('.showcase--project');
4217                    project.forEach(function (item) {
4218                        let content = item.querySelector('.project--content');
4219                        item.querySelector('.project--head').addEventListener('click', function (click) {
4220                            if (!item.classList.contains('showcase--project--active')) {
4221
4222                                project.forEach(function (close) {
4223                                    content = close.querySelectorAll('.project--content')
4224                                    var contentState = Flip.getState(content, {
4225                                        props: ['padding']
4226                                    });
4227                                    close.classList.remove('showcase--project--active')
4228
4229                                    Flip.from(contentState, {
4230                                        duration: .75,
4231                                        ease: 'expo.inOut',
4232                                        absolute: false,
4233                                        absoluteOnLeave: false,
4234                                    })
4235                                })
4236
4237                                content = item.querySelectorAll('.project--content')
4238                                var contentState = Flip.getState(content, {
4239                                    props: ['padding']
4240                                });
4241                                item.classList.add('showcase--project--active')
4242                                Flip.from(contentState, {
4243                                    duration: .75,
4244                                    ease: 'expo.inOut',
4245                                    absolute: false,
4246                                    absoluteOnLeave: false,
4247                                    onStart: () => {
4248                                        if (!$this.classList.contains('project__active')) {
4249                                            $this.classList.add('project__active')
4250                                        }
4251
4252                                    }
4253                                })
4254                            } else {
4255                                content = item.querySelectorAll('.project--content')
4256                                var contentState = Flip.getState('.project--content', {
4257                                    props: ['padding']
4258                                })
4259                                item.classList.remove('showcase--project--active')
4260                                Flip.from(contentState, {
4261                                    duration: .75,
4262                                    ease: 'expo.inOut',
4263                                    absolute: false,
4264                                    absoluteOnLeave: false,
4265                                    onComplete: () => {
4266                                        $this.classList.remove('project__active')
4267                                    }
4268                                })
4269                            }
4270                        })
4271                    })
4272                })
4273            }
4274        }); 1
4275
4276        elementorFrontend.hooks.addAction('frontend/element_ready/peshowcasevoid.default', function ($scope, $) {
4277            var jsScopeArray = $scope.toArray();
4278
4279            for (var i = 0; i < jsScopeArray.length; i++) {
4280                var scope = jsScopeArray[i],
4281                    fsList = document.querySelectorAll('.showcase--void');
4282                fsList.forEach(function ($this) {
4283                    let wrapper = $this.querySelector('.showcase--void--wrapper'),
4284                        metaWrapper = $this.querySelector('.showcase--void--meta--wrapper'),
4285                        project = $this.querySelectorAll('.showcase--project'),
4286                        meta = $this.querySelectorAll('.project--meta'),
4287                        length = project.length;
4288
4289                    if (length % 2 !== 0) {
4290                        var middleIndex = Math.floor(length / 2),
4291                            middleElement = project[middleIndex],
4292                            clone = middleElement.cloneNode(true);
4293                        clone.classList.add('clone')
4294                        wrapper.appendChild(clone);
4295
4296                    }
4297
4298                    
4299
4300                    project = $this.querySelectorAll('.showcase--project')
4301
4302                    project.forEach(function (item, i) {
4303                        gsap.set(item, {
4304                            top: gsap.utils.random(0, 100) + '%',
4305                        })
4306                        if (i % 2 === 0) {
4307                            gsap.set(item, {
4308                                left: gsap.utils.random(-5, -25) + '%'
4309                            })
4310                        } else {
4311                            gsap.set(item, {
4312                                left: gsap.utils.random(50, 90) + '%'
4313                            })
4314                        }
4315                        let clone = item.cloneNode(true)
4316                        clone.classList.add('clone')
4317                        wrapper.appendChild(clone)
4318                    })
4319
4320
4321                    project = $this.querySelectorAll('.showcase--project')
4322                    project.forEach(function (item, i) {
4323                        item.setAttribute('data-z', -3000 * i)
4324                        item.setAttribute('data-opacity', 1 - (i * 0.2))
4325                        gsap.set(item, {
4326                            z: -3000 * i,
4327                        })
4328                        item.style.opacity = 1 - (i * 0.25)
4329                        item.style.zIndex = 100 - i
4330                    })
4331
4332                    let wheeler = Hamster(document.querySelector('body')),
4333                        z = 0;
4334                    project = $this.querySelectorAll('.showcase--project'),
4335                        meta = $this.querySelectorAll('.project--meta');
4336                    let smoothZ = 0;
4337
4338                    wheeler.wheel(function (event, delta, deltaX, deltaY) {
4339                        updateProjects(deltaY);
4340                    });
4341
4342                    matchMedia.add({
4343                        isMobile: "(max-width: 570px)"
4344
4345                    }, (context) => {
4346
4347                        let {
4348                            isMobile
4349                        } = context.conditions;
4350
4351                        let touchStartY = 0;
4352
4353                        document.addEventListener('touchstart', function (event) {
4354                            touchStartY = event.touches[0].clientY;
4355                        });
4356
4357                        document.addEventListener('touchmove', function (event) {
4358                            let touchEndY = event.touches[0].clientY;
4359                            let deltaY = touchStartY - touchEndY;
4360                            touchStartY = touchEndY;
4361                            updateProjects(deltaY * -10);
4362                        });
4363
4364
4365                    });
4366
4367                    function updateProjects(deltaY) {
4368                        z += deltaY * -1;
4369                    }
4370
4371                    function smoothAnimation() {
4372                        if (window.navigator.platform === 'MacIntel') {
4373                            smoothZ += (z - smoothZ) * 0.1;
4374                        } else {
4375                            smoothZ += (z * 50 - smoothZ) 
4376                        }
4377                        
4378                        project.forEach(function (item, i) {
4379                            gsap.set(item, {
4380                                z: parseInt(item.getAttribute('data-z')) + smoothZ
4381                            });
4382                            item.style.opacity = (1 - (i * 0.25)) + (smoothZ / 12000);
4383
4384                            if (smoothZ > $this.querySelectorAll('.clone').length * 3000) {
4385                                smoothZ = 0;
4386                                z = 0;
4387                            } else if (smoothZ < 0) {
4388                                smoothZ = $this.querySelectorAll('.clone').length * 3000 + smoothZ;
4389                                z = smoothZ;
4390                            }
4391                        });
4392
4393                        meta.forEach(function ($meta, i) {
4394                            if ((1 - (i * 0.25)) + (smoothZ / 12000) > 0.85) {
4395                                $meta.classList.add('project--meta--active');
4396                                //    scope.querySelector('.project_' + $meta.dataset.id).classList.add('showcase--project--active')
4397
4398                            } else {
4399                                $meta.classList.remove('project--meta--active');
4400                                // scope.querySelector('.project_' + $meta.dataset.id).classList.remove('showcase--project--active')
4401                            }
4402                            if ((1 - (i * 0.25)) + (smoothZ / 12000) > 1.1) {
4403                                $meta.classList.remove('project--meta--active');
4404                                // scope.querySelector('.project_' + $meta.dataset.id).classList.remove('showcase--project--active')
4405                            }
4406                        });
4407
4408                        requestAnimationFrame(smoothAnimation);
4409                    }
4410                    smoothAnimation();
4411                })
4412            }
4413        });
4414
4415        elementorFrontend.hooks.addAction('frontend/element_ready/peshowcaseslider.default', function ($scope, $) {
4416            var jsScopeArray = $scope.toArray();
4417
4418            for (var i = 0; i < jsScopeArray.length; i++) {
4419                var scope = jsScopeArray[i],
4420                    fsList = document.querySelectorAll('.showcase--slider');
4421                fsList.forEach(function ($this) {
4422                    let project = $this.querySelectorAll('.showcase--project'),
4423                        total = $this.querySelector('.fraction--item.item--total');
4424                    total.innerText = project.length;
4425
4426                    function linesAnimate(image) {
4427
4428                        let grid = scope.querySelector('.showcase--slider--gri
4428d'),
4429                            lines = grid.querySelectorAll('span');
4430
4431                        lines.forEach((line, i) => {
4432
4433                            gsap.to(line, {
4434                                x: i = 0 ? image.getBoundingClientRect().left : ''
4435                            })
4436
4437                        })
4438
4439                    }
4440
4441                    project.forEach(function (item, i) {
4442                        let headerHeight = document.querySelector('.site-header').offsetHeight,
4443                            image = item.querySelector('.project--image');
4444
4445                        linesAnimate
4446
4447                        gsap.set(item, {
4448                            top: gsap.utils.random(headerHeight, $this.offsetHeight - item.offsetHeight - $this.querySelector('.showcase--slider--footer').offsetHeight),
4449                            left: gsap.utils.random(0, $this.offsetWidth - item.offsetWidth)
4450                        })
4451
4452                        gsap.set(item.querySelector('.project--image'), {
4453                            height: item.querySelector('.project--meta--bottom').offsetHeight
4454                        })
4455
4456                    })
4457
4458
4459                    let navItem = $this.querySelectorAll('.nav--item');
4460                    navItem.forEach(function (navClick) {
4461                        let activeIndex = 0;
4462                        navClick.addEventListener('click', function () {
4463                            if (!$this.classList.contains('is_animating')) {
4464                                gsap.to($this.querySelectorAll('.project--image'), {
4465                                    clipPath: 'inset(0% 100% 0% 0%)',
4466                                    ease: 'expo.in',
4467                                    duration: .75,
4468                                    onStart: () => {
4469                                        $this.classList.add('is_animating')
4470                                    }
4471                                })
4472                                if (navClick.classList.contains('nav--prev')) {
4473                                    if (activeIndex === 0) {
4474                                        activeIndex = project.length - 1
4475                                    } else {
4476                                        activeIndex = activeIndex - 1
4477                                    }
4478                                } else if (navClick.classList.contains('nav--next')) {
4479                                    if (activeIndex === project.length - 1) {
4480                                        activeIndex = 0
4481                                    } else {
4482                                        activeIndex = activeIndex + 1
4483                                    }
4484                                }
4485
4486                                gsap.fromTo(project[activeIndex].querySelectorAll('.project--image'), {
4487                                    clipPath: 'inset(0% 0% 0% 100%)'
4488                                }, {
4489                                    clipPath: 'inset(0% 0% 0% 0%)',
4490                                    duration: .75,
4491                                    ease: 'expo.out',
4492                                    delay: .75,
4493                                    onComplete: () => {
4494                                        $this.classList.remove('is_animating')
4495                                    }
4496                                })
4497
4498                                project.forEach(function (item) {
4499                                    item.classList.remove('showcase--project--active')
4500                                })
4501                                $this.querySelector('.showcase--project__' + activeIndex).classList.add('showcase--project--active')
4502                                $this.querySelector('.fraction--item.item--active').innerText = activeIndex + 1
4503                            }
4504                        })
4505
4506                        if ($this.classList.contains('wheel--navigate')) {
4507                            let wheler = Hamster($this);
4508                            wheler.wheel(function (deltaY) {
4509                                let delta = event.deltaY
4510                                if (delta > 0) {
4511                                    navItem[1].click();
4512                                } else if (delta < 0) {
4513                                    navItem[0].click();
4514                                }
4515                                $this.classList.add('is_animating')
4516                            });
4517
4518                            let touchStartY = 0;
4519
4520                            $this.addEventListener('touchstart', function (event) {
4521                                touchStartY = event.touches[0].clientY;
4522                            });
4523
4524                            $this.addEventListener('touchmove', function (event) {
4525                                let touchEndY = event.touches[0].clientY;
4526                                let deltaY = touchStartY - touchEndY;
4527
4528                                if (deltaY > 0) {
4529                                    navItem[1].click();
4530                                } else if (deltaY < 0) {
4531                                    navItem[0].click();
4532                                }
4533                                $this.classList.add('is_animating');
4534                                touchStartY = touchEndY;
4535                            });
4536                        }
4537
4538                    })
4539
4540                    if ($this.classList.contains('autoplay')) {
4541                        let delay,
4542                            autoplay;
4543                        if ($this.dataset.delay) {
4544                            delay = parseInt($this.dataset.delay)
4545                        } else {
4546                            delay = 5000
4547                        }
4548
4549                        function startAutoplay() {
4550                            autoplay = setInterval(function () {
4551                                navItem[1].click();
4552                            }, delay)
4553                        }
4554
4555                        function stopAutoplay() {
4556                            clearInterval(autoplay);
4557                        }
4558
4559                        startAutoplay();
4560
4561                        project.forEach(function (item) {
4562                            item.querySelector('.project-button').addEventListener('mouseenter', function () {
4563                                stopAutoplay();
4564                            })
4565                            item.querySelector('.project-button').addEventListener('mouseleave', function () {
4566                                startAutoplay();
4567                            })
4568                        })
4569
4570
4571
4572
4573                    }
4574
4575
4576                })
4577            }
4578        });
4579
4580        elementorFrontend.hooks.addAction('frontend/element_ready/peinfinitegrid.default', function ($scope, $) {
4581            var jsScopeArray = $scope.toArray();
4582
4583            for (var i = 0; i < jsScopeArray.length; i++) {
4584                var scope = jsScopeArray[i],
4585                    infiniteGrid = document.querySelectorAll('.infinite--grid');
4586                infiniteGrid.forEach(function ($this) {
4587                    let column = parseInt($this.getAttribute('data-column')),
4588                        wrapper = $this.querySelector('.infinite--grid--wrapper'),
4589                        gridColumn = $this.querySelectorAll('.grid--column'),
4590                        project = $this.querySelectorAll('.showcase--project'),
4591                        residual = column - (project.length % column),
4592                        tl = gsap.timeline({
4593                            repeat: -1
4594                        }),
4595                        wheeler = Hamster(document.querySelector('body')),
4596                        autoplay = $this.dataset.autoplay,
4597                        duration = $this.dataset.autoplayDuration,
4598                        prog = 0,
4599                        wheelDeltaY;
4600
4601                    matchMedia.add({
4602                        isDesktop: "(min-width: 571px)"
4603
4604                    }, (context) => {
4605
4606                        let {
4607                            isDesktop
4608                        } = context.conditions;
4609
4610                        let e = 0
4611                        if (residual !== column) {
4612                            for (e = 0; e < residual; e++) {
4613                                let clone = $this.querySelector('.project__' + e).cloneNode(true);
4614                                gridColumn[e + (column - residual)].appendChild(clone)
4615                            }
4616                        }
4617                        gridColumn.forEach(function (grid, i) {
4618                            if (i % 2 === 0) {
4619                                grid.classList.add('grid__up')
4620                            } else {
4621                                grid.classList.add('grid__down')
4622                            }
4623                            let item = grid.querySelectorAll('.showcase--project');
4624                            for (let clone = 0; clone < 2; clone++) {
4625                                item.forEach(function (item) {
4626                                    let itemClone = item.cloneNode(true);
4627                                    grid.appendChild(itemClone);
4628                                });
4629                            }
4630                        })
4631
4632
4633
4634                        if (autoplay == 'true') {
4635
4636                            gridColumn.forEach(function (grid) {
4637                                if (grid.classList.contains('grid__up')) {
4638                                    tl.to(grid, {
4639                                        y: -33.3333333 + '%',
4640                                        duration: duration,
4641                                        ease: 'none'
4642                                    }, 0)
4643                                } else {
4644                                    tl.fromTo(grid, {
4645                                        y: -33.333333 + '%'
4646                                    }, {
4647                                        y: -0 + '%',
4648                                        duration: duration,
4649                                        ease: 'none'
4650                                    }, 0)
4651                                }
4652                            })
4653                        }
4654
4655                        wheeler.wheel(function (event, deltaY) {
4656                            prog = prog + (deltaY / 100)
4657
4658                            if (autoplay == 'true') {
4659
4660                                wheeler.wheel(function (event, delta, deltaX, deltaY) {
4661
4662                                    wheelDeltaY = event.deltaY;
4663                                    event.deltaY < 0 ? wheelDeltaY = -1 * event.deltaY : '';
4664                                    tl.timeScale(1 + (wheelDeltaY * 5))
4665
4666                                });
4667
4668                            } else {
4669
4670                                if (prog < -33.333333) {
4671                                    prog = 0
4672                                } else if (prog > 0) {
4673                                    prog = -33.333333
4674                                }
4675
4676
4677                                gridColumn.forEach(function (grid) {
4678                                    if (grid.classList.contains('grid__up')) {
4679                                        gsap.set(grid, {
4680                                            y: prog + '%'
4681                                        })
4682                                    } else {
4683                                        gsap.set(grid, {
4684                                            y: (-33.333333 - prog) + '%'
4685                                        })
4686                                    }
4687                                })
4688                            }
4689                        })
4690
4691                        project = $this.querySelectorAll('.showcase--project')
4692                        project.forEach(function (item) {
4693                            const mouseEnterHandler = function () {
4694                                $this.classList.add('hovered');
4695                                prog = 0
4696                                this.classList.add('showcase--project--active');
4697                                tl.pause();
4698                            };
4699
4700                            const mouseLeaveHandler = function () {
4701                                $this.classList.remove('hovered');
4702                                prog = 0
4703                                this.classList.remove('showcase--project--active');
4704                                tl.play();
4705                            };
4706
4707                            const clickHandler = function () {
4708                                tl.pause();
4709                                prog = 0
4710                                item.removeEventListener('mouseleave', mouseLeaveHandler);
4711                            };
4712
4713                            item.addEventListener('mouseenter', mouseEnterHandler);
4714                            item.addEventListener('mouseleave', mouseLeaveHandler);
4715                            item.addEventListener('click', clickHandler);
4716                        });
4717
4718
4719
4720                    });
4721
4722                    matchMedia.add({
4723                        isMobile: "(max-width: 570px)"
4724
4725                    }, (context) => {
4726
4727                        let {
4728                            isMobile
4729                        } = context.conditions;
4730
4731                        gridColumn.forEach(function (column) {
4732                            let clone = column.cloneNode(true);
4733                            wrapper.appendChild(clone)
4734                        })
4735                        let drag = Draggable.create(wrapper, {
4736                            type: 'y',
4737                            inertia: true,
4738                            onThrowUpdate: function () {
4739                                var yPosition = this.y;
4740                                if (yPosition > 0) {
4741                                    gsap.set(wrapper, {
4742                                        y: -1 * (wrapper.offsetHeight / 2) + yPosition
4743                                    })
4744                                } else if (yPosition < -1 * (wrapper.offsetHeight / 2)) {
4745                                    gsap.set(wrapper, {
4746                                        y: yPosition + (wrapper.offsetHeight / 2)
4747                                    })
4748                                }
4749                            },
4750                        })
4751
4752
4753                    });
4754
4755                })
4756
4757
4758
4759
4760            }
4761        });
4762
4763        elementorFrontend.hooks.addAction('frontend/element_ready/peshowcasewall.default', function ($scope, $) {
4764            var jsScopeArray = $scope.toArray();
4765
4766            for (var i = 0; i < jsScopeArray.length; i++) {
4767                var scope = jsScopeArray[i],
4768                    showcaseWall = scope.querySelector('.showcase--wall'),
4769                    wrapper = showcaseWall.querySelector('.showcase--wall--wrapper'),
4770                    pinnedElements = wrapper.dataset.pinnedElements,
4771                    project = scope.querySelectorAll('.showcase--project');
4772                let speed;
4773                if (showcaseWall.dataset.speed) {
4774                    speed = 'bottom+=' + showcaseWall.dataset.speed + ' top'
4775                } else {
4776                    speed = 'bottom+=5000 top'
4777                }
4778
4779                let tl = gsap.timeline({
4780                    scrollTrigger: {
4781                        trigger: showcaseWall,
4782                        start: 'top top',
4783                        end: speed,
4784                        pin: true,
4785                        scrub: 1.5
4786                    }
4787                });
4788
4789
4790                setTimeout(() => {
4791                    if (pinnedElements) {
4792
4793                        document.querySelectorAll(pinnedElements).forEac
4793h(element => {
4794
4795                            ScrollTrigger.create({
4796                                trigger: element,
4797                                start: 0,
4798                                end: tl.scrollTrigger.end - tl.scrollTrigger.start,
4799                                pin: true,
4800                                pinSpacing: false,
4801                            })
4802                        })
4803                    }
4804                }, 50);
4805
4806                matchMedia.add({
4807                    isMobile: "(max-width: 570px)"
4808                }, (context) => {
4809
4810                    let {
4811                        isMobile
4812                    } = context.conditions;
4813
4814                    tl.to(document.querySelectorAll('.left__to__right'), {
4815                        x: '100%',
4816                    }, 0)
4817
4818                    tl.to(document.querySelectorAll('.right__to__left'), {
4819                        x: '-100%'
4820                    }, 0)
4821
4822
4823                });
4824
4825                matchMedia.add({
4826                    isDesktop: "(min-width: 571px)"
4827                }, (context) => {
4828                    let {
4829                        isDesktop
4830                    } = context.conditions;
4831
4832                    tl.to(document.querySelectorAll('.left__to__right'), {
4833                        x: '50%'
4834                    }, 0)
4835
4836                    tl.to(document.querySelectorAll('.right__to__left'), {
4837                        x: '-50%'
4838                    }, 0)
4839
4840
4841                });
4842
4843
4844
4845                project.forEach(function (item) {
4846                    item.addEventListener('mouseenter', function () {
4847                        showcaseWall.classList.add('showcase--hovered')
4848                        let activeIndex = parseInt(item.getAttribute('data-index'))
4849                        document.querySelector('.image__' + activeIndex).classList.add('showcase--image--active')
4850                    })
4851                    item.addEventListener('mouseleave', function () {
4852                        showcaseWall.classList.remove('showcase--hovered')
4853                        let activeIndex = parseInt(item.getAttribute('data-index'))
4854                        document.querySelector('.image__' + activeIndex).classList.remove('showcase--image--active')
4855                    })
4856
4857                    item.addEventListener('mousemove', function (e) {
4858
4859                        let mouseLeft = e.clientX,
4860                            mouseTop = e.clientY,
4861                            movX = event.movementX < 0 ? event.movementX * -1 : event.movementX;
4862
4863                        gsap.to(document.querySelector('.showcase--wall--image--overlay'), {
4864                            left: mouseLeft,
4865                            top: mouseTop,
4866                            rotate: gsap.utils.clamp(-10, 10, (event.movementX / 5)),
4867                            duration: 1,
4868                            ease: 'power3.out',
4869                        })
4870                    })
4871                })
4872
4873            }
4874        });
4875
4876        elementorFrontend.hooks.addAction('frontend/element_ready/peshowcasecarousel.default', function ($scope, $) {
4877            var jsScopeArray = $scope.toArray();
4878
4879            for (var i = 0; i < jsScopeArray.length; i++) {
4880
4881                var scope = jsScopeArray[i],
4882                    showcaseCarousel = document.querySelectorAll('.showcase--carousel');
4883
4884                showcaseCarousel.forEach(function ($this) {
4885                    let wrap = $this.querySelector('.showcase--carousel--wrapper'),
4886                        project = $this.querySelectorAll('.showcase--project'),
4887                        centersArray = [],
4888                        pinnedElements = $this.dataset.pinnedElements,
4889                        sizes = getComputedStyle($this),
4890                        activeWidth = sizes.getPropertyValue('--activeWidth'),
4891                        act = document.body.clientWidth / (100 / parseInt(activeWidth)),
4892                        finish;
4893                    if ($this.dataset.speed) {
4894                        finish = 'bottom+=' + $this.dataset.speed + ' center';
4895                    } else {
4896                        finish = 'bottom+=3000 center';
4897                    }
4898                    // matchMedia.add({
4899                    //     isMobile: "(max-width: 570px)"
4900                    // }, (context) => {
4901                    //     let {
4902                    //         isMobile
4903                    //     } = context.conditions;
4904                    //     project[0].classList.add('showcase--project--active')
4905                    // });
4906
4907                    var tl = gsap.timeline(),
4908                        scrollera = ScrollTrigger.create({
4909                            trigger: $this,
4910                            start: 'center center',
4911                            end: finish,
4912                            pin: true,
4913                            scrub: 1.5,
4914                            id: 'showcase--scroll',
4915                            animation: tl,
4916                            onUpdate: function (self) {
4917                                matchMedia.add({
4918                                    isMobile: "(max-width: 570px)"
4919                                }, (context) => {
4920                                    let {
4921                                        isMobile
4922                                    } = context.conditions;
4923                                    let activeIndex = Math.round(self.progress * project.length)
4924                                    project.forEach(function ($item, index) {
4925                                        if (index === activeIndex) {
4926                                            $item.classList.add('showcase--project--active')
4927                                        } else {
4928                                            $item.classList.remove('showcase--project--active')
4929                                        }
4930                                    })
4931
4932
4933                                });
4934                            }
4935                        });
4936
4937                    setTimeout(() => {
4938                        if (pinnedElements) {
4939
4940                            document.querySelectorAll(pinnedElements).forEac
4940h(element => {
4941
4942                                ScrollTrigger.create({
4943                                    trigger: element,
4944                                    start: 0,
4945                                    end: tl.scrollTrigger.end - tl.scrollTrigger.start,
4946                                    pin: true,
4947                                    pinSpacing: false,
4948                                })
4949                            })
4950                        }
4951                    }, 50);
4952
4953                    matchMedia.add({
4954                        isMobile: "(max-width: 550px)"
4955
4956                    }, (context) => {
4957
4958                        let {
4959                            isMobile
4960                        } = context.conditions;
4961
4962                        tl.kill();
4963                        scrollera.kill(true)
4964
4965                        let wrapper = scope.querySelector('.showcase--carousel--wrapper');
4966
4967
4968                        Draggable.create(wrapper, {
4969                            type: 'x',
4970                            bounds: {
4971                                // minX: 0,
4972                                // maxX: -wrap.getBoundingClientRect().width + document.body.clientWidth
4973                            },
4974                            lockAxis: true,
4975                            dragResistance: 0.5,
4976                            inertia: true,
4977                        });
4978
4979
4980                    });
4981
4982                    var end = wrap.getBoundingClientRect().width - (document.body.clientWidth / 2);
4983
4984                    if (!mobileQuery.matches) {
4985
4986                        project.forEach(function (item, i) {
4987
4988                            let sc = item.getBoundingClientRect().left + item.getBoundingClientRect().width - (item.getBoundingClientRect().width / 2) - (document.body.clientWidth / 2),
4989                                bc = item.getBoundingClientRect().left + act - (act / 2) - (document.body.clientWidth / 2);
4990
4991                            centersArray.push({
4992                                smallCenter: sc,
4993                                bigCenter: bc
4994                            })
4995                            if (bc > 0) {
4996
4997                                tl.to(wrap, {
4998                                    x: -1 * (bc + (item.getBoundingClientRect().width)),
4999                                    ease: 'none'
5000                                }, 'label_' + (item.dataset.index))
5001                            }
5002
5003                            item.addEventListener('click', function (i) {
5004
5005                                reset();
5006                                gsap.to(item, {
5007                                    width: activeWidth,
5008                                    height: sizes.getPropertyValue('--activeHeight'),
5009                                    duration: .75,
5010                                    ease: 'expo.inOut',
5011                                    onStart: () => {
5012                                        item.classList.add('showcase--project--active')
5013                                    },
5014                                })
5015
5016                                gsap.to(window, {
5017                                    scrollTo: scrollera.labelToScroll('label_' + (parseInt(item.dataset.index))),
5018                                    duration: .75,
5019                                    ease: 'expo.inOut',
5020                                });
5021
5022                            })
5023                        })
5024
5025                    }
5026
5027                    let animating = false;
5028
5029                    function reset() {
5030                        if (scope.querySelector('.showcase--project--active')) {
5031
5032                            gsap.to(scope.querySelector('.showcase--project--active'), {
5033                                width: sizes.getPropertyValue('--inactiveWidth'),
5034                                height: sizes.getPropertyValue('--inactiveHeight'),
5035                                duration: .75,
5036                                ease: 'expo.inOut',
5037                                onComplete: () => {
5038                                    animating = false
5039                                },
5040                                onStart: () => {
5041                                    animating = true;
5042                                    if (scope.querySelector('.showcase--project--active')) {
5043                                        scope.querySelector('.showcase--project--active').classList.remove('showcase--project--active')
5044                                    }
5045
5046                                }
5047                            })
5048                        }
5049
5050                    }
5051
5052                    $this.addEventListener('wheel', () => {
5053                        if (!animating) {
5054                            reset();
5055                        }
5056                    })
5057
5058                    document.addEventListener('keydown', function (event) {
5059                        if (event.key === 'Escape' || event.keyCode === 27) {
5060                            reset();
5061                        }
5062                    });
5063
5064
5065                })
5066
5067            }
5068        });
5069
5070
5071    })
5072
5073
5074}
5074)(jQuery)

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.