PageSourceSearch

https://stsl.ru/bitrix/templates/stsl_new/js/modules/modules.js

js stsl.ru collected 2026-10-01 11:59:45 UTC 11,791 bytes, 319 lines download raw bytes

1const $body = document.querySelector('body');
2let scrollPosition = 0;
3
4var utility = {
5    setVH: function() {
6        let vh = window.innerHeight * 0.01;
7        document.documentElement.style.setProperty('--vh', `${vh}px`);
8    },
9    debounce: function(callback, wait, immediate) {
10        let timeout;
11        return function() {
12            let context = this;
13            let args = arguments;
14            let later = function() {
15                timeout = null;
16                if (!immediate) {
17                    callback.apply(context, args);
18                }
19            };
20            let callNow = immediate && !timeout;
21            clearTimeout(timeout);
22            timeout = setTimeout(later, wait);
23            if (callNow) {
24                callback.apply(context, args);
25            }
26        }
27    },
28    throttle: function(callback, limit) {
29        let wait = false;
30        return function() {
31            if (!wait) {
32                callback.apply(null, arguments);
33                wait = true;
34                setTimeout(function(){
35                    wait = false;
36                }, limit);
37            }
38        }
39    },
40    enableScroll: function() {
41        $body.style.removeProperty('overflow');
42        $body.style.removeProperty('position');
43        $body.style.removeProperty('top');
44        $body.style.removeProperty('width');
45        $body.classList.remove('page--fixed');
46        window.scrollTo(0, scrollPosition);
47    },
48    disableScroll: function() {
49        scrollPosition = window.pageYOffset;
50        $body.style.overflow = 'hidden';
51        $body.style.position = 'fixed';
52        $body.style.top = `-${scrollPosition}px`;
53        $body.style.width = '100%';
54        $body.classList.add('page--fixed');
55    },
56    lerp: function(a, b, n) {
57        return (1 - n) * a + n * b;
58    },
59    isTouchDevice: function() {
60        try {
61            document.createEvent("TouchEvent");
62            return true;
63        } catch (e) {
64            return false;
65        }
66    },
67    lineEq: function(y2, y1, x2, x1, currentVal) {
68        var m = (y2 - y1) / (x2 - x1), b = y1 - m * x1;
69        return m * currentVal + b;
70    },
71    getRandomNumber: function(min, max) {
72        return Math.round(Math.random() * (max - min) + min);
73    }
74}
75
76if (!disableAnimations) {
77    window.pageScroll = new LocomotiveScroll({
78        el: document.querySelector('.scroll-container'),
79        getDirection: true,
80        scrollFromAnywhere: true,
81        smoothMobile: false,
82        smooth: true,
83        lerp: 0.075
84    });
85}
86
87var ScrollAnimations = {
88    initScroll: function() {
89        gsap.registerPlugin(ScrollTrigger);
90
91        /* setup SmoothScroll */
92        const smoothScroll = window.pageScroll;
93        smoothScroll.on("scroll", ScrollTrigger.update);
94
95        /* setup ScrollTrigger */
96        ScrollTrigger.scrollerProxy(".scroll-container", {
97            scrollTop(value) {
98            return arguments.length ? smoothScroll.scrollTo(value, 0, 0) : smoothScroll.scroll.instance.scroll.y;
99            },
100            getBoundingClientRect() {
101            return {top: 0, left: 0, width: window.innerWidth, height: window.innerHeight};
102            },
103            pinType: document.querySelector(".scroll-container").style.transform ? "transform" : "fixed"
104        });
105
106        ScrollAnimations.floatHeader(smoothScroll);
107
108        /* update and refresh ScrollTrigger */
109        window.addEventListener('resize', function(){
110            ScrollTrigger.refresh();
111            ScrollTrigger.update()
112        });
113        ScrollTrigger.addEventListener("refresh", () => smoothScroll.update());
114        ScrollTrigger.refresh();
115    },
116    floatHeader: function(smoothScroll) {
117        var self = ScrollAnimations;
118        gsap.set('.section--header-float', { yPercent: -100 });
119        this.tl = gsap.timeline();
120        var currentScrollTop;
121        smoothScroll.on('scroll', function(data){
122            currentScrollTop = data.scroll.y;
123            if (data.direction == "down"){
124                self.hideFloatingHeader();
125            } else {
126                self.showFloatingHeader(currentScrollTop);
127            }
128        });
129    },
130    hideFloatingHeader: function() {
131        if (ScrollAnimations.tl) {
132            ScrollAnimations.tl.kill();
133            ScrollAnimations.tl = gsap.timeline();
134        }
135        ScrollAnimations.tl.to('.section--header-float', { duration: 0.25, ease: Power2.easeOut, yPercent: -100 });
136    },
137    showFloatingHeader: function(currentScrollTop) {
138        var self = ScrollAnimations;
139        if (currentScrollTop > 0.5 * window.innerHeight) {
140            if (ScrollAnimations.tl) {
141                ScrollAnimations.tl.kill();
142                ScrollAnimations.tl = gsap.timeline();
143            }
144            ScrollAnimations.tl.to('.section--header-float', { duration: 0.5, ease: Power2.easeOut, yPercent: 0 });
145        } else {
146            self.hideFloatingHeader();
147        }
148    }
149}
150
151var HeroAnimations = {
152    initHero: function() {
153        HeroAnimations.tl = gsap.timeline();
154        HeroAnimations.animate();
155    },
156    animate: function() {
157        let self = HeroAnimations;
158        let state = HeroAnimations.captureState(".logo, .header__logo, .slogan__progress, .hero__back-bg, .header__menu, .hero__video, .hero__main, .header__lang, .blog__rest--left, .blog__rest--right, .menu__item, .section--header .header");
159
160        if (HeroAnimations.tl) {
161            HeroAnimations.tl.kill();
162            HeroAnimations.tl = gsap.timeline({
163                onComplete: () => self.animateComplete(state)
164            });
165        }
166
167        let logoOffset = document.querySelector('.logo').getBoundingClientRect();
168        let mainDelay = 0.5;
169        let logoDuration = 1;
170        let slideDuration = 1;
171        let logoTargerOffset = 12 - logoOffset.top - 49;
172
173        let header = document.querySelector('.page--initial .section--header .header');
174        let headerSection = document.querySelector('.page--initial .section--header');
175        let headerMenu = document.querySelector('.header__menu');
176        let headerMenuBg = headerMenu.querySelector('.header__menu-bg');
177        let headerMenuItems = headerMenu.querySelectorAll('.menu__item');
178        let headerLang = document.querySelector('.header__lang');
179        let heroMain = document.querySelector('.hero__main');
180        let heroVideo = document.querySelector('.hero__video');
181        let newsCards = document.querySelectorAll('.blog__news .card');
182        let mainCards = document.querySelectorAll('.blog__main .card');
183        let shortCards = document.querySelectorAll('.blog__short .card');
184        let restLeft = document.querySelectorAll('.blog__rest--left');
185        let restRight = document.querySelectorAll('.blog__rest--right');
186
187        HeroAnimations.tl.set(header, {
188            height: "auto",
189            display: "block"
190        }).set(headerSection, {
191            overflow: "visible"
192        }).set(headerMenu, {
193            display: "block",
194            margin: 0,
195            y: 88 + 16
196        }).set(headerMenuBg, {
197            opacity: 0
198        }).set(headerMenuItems, {
199            yPercent: -100,
200            opacity: 0
201        }).set(headerLang, {
202            display: "flex",
203            opacity: 0
204        }).set(heroMain, {
205            y: 50
206        }).set(heroVideo, {
207            y: 50
208        }).set(newsCards, {
209            y: 24
210        }).set(mainCards, {
211            y: 24
212        }).set(shortCards, {
213            y: 24
214        });
215
216        if (document.documentElement.clientWidth >= 1640) {
217            HeroAnimations.tl.set(restLeft, {
218                y: 36
219            }).set(restRight, {
220                y: 48
221            });
222        }
223
224        HeroAnimations.tl.to(document.querySelector('.logo'), {
225            duration: logoDuration,
226            width: 34,
227            ease: Power2.easeOut
228        }, mainDelay).to(document.querySelector('.header__logo'), {
229            duration: logoDuration,
230            y: logoTargerOffset,
231            ease: Power2.easeOut
232        }, mainDelay).to(document.querySelector('.slogan__progress'), {
233            duration: logoDuration,
234            opacity: 0,
235            ease: Power2.easeOut
236        }, mainDelay).to(headerMenuBg, {
237            duration: 0.5 * slideDuration,
238            opacity: 1,
239            ease: Power2.easeOut
240        }, mainDelay + 1.25 * logoDuration).to(headerMenuItems, {
241            duration: 0.75 * slideDuration,
242            stagger: 0.05 * slideDuration,
243            yPercent: 0,
244            opacity: 1,
245            ease: Power3.easeOut
246        }, mainDelay + 1.25 * logoDuration).to(document.querySelector('.hero__back-bg'), {
247            duration: slideDuration,
248            opacity: 1,
249            scaleY: 1,
250            ease: Power2.easeOut
251        }, mainDelay + 0.25 * logoDuration).to(document.querySelector('.hero__back'), {
252            duration: slideDuration,
253            opacity: 1,
254            ease: Power2.easeOut
255        }, mainDelay + 0.25 * logoDuration + 0.5 * slideDuration).to(heroMain, {
256            duration: slideDuration,
257            opacity: 1,
258            y: 0,
259            ease: Power2.easeOut
260        }, mainDelay + 0.25 * logoDuration + 0.4 * slideDuration).to(heroVideo, {
261            duration: slideDuration,
262            opacity: 1,
263            y: 0,
264            ease: Power2.easeOut
265        }, mainDelay + 0.25 * logoDuration + 0.5 * slideDuration).to(headerLang, {
266            duration: 0.5 * slideDuration,
267            opacity: 1,
268            ease: Power2.easeOut
269        }, mainDelay + 0.25 * logoDuration + 0.75 * slideDuration).to(newsCards, {
270            duration: 0.5 * slideDuration,
271            stagger: 0.05 * slideDuration,
272            opacity: 1,
273            y: 0,
274            ease: Power2.easeOut
275        }, mainDelay + 0.25 * logoDuration + 1.25 * slideDuration).to(mainCards, {
276            duration: 0.5 * slideDuration,
277            stagger: 0.05 * slideDuration,
278            opacity: 1,
279            y: 0,
280            ease: Power2.easeOut
281        }, mainDelay + 0.25 * logoDuration + 1.35 * slideDuration).to(shortCards, {
282            duration: 0.5 * slideDuration,
283            stagger: 0.05 * slideDuration,
284            opacity: 1,
285            y: 0,
286            ease: Power2.easeOut
287        }, mainDelay + 0.25 * logoDuration + 1.45 * slideDuration);
288
289        if (document.documentElement.clientWidth >= 1640) {
290            HeroAnimations.tl.to(restLeft, {
291                duration: 0.5 * slideDuration,
292                opacity: 1,
293                y: 0,
294                ease: Power2.easeOut
295            }, mainDelay + 0.25 * logoDuration + 1.5 * slideDuration).to(restRight, {
296                duration: 0.5 * slideDuration,
297                opacity: 1,
298                y: 0,
299                ease: Power2.easeOut
300            }, mainDelay + 0.25 * logoDuration + 1.55 * slideDuration)
301        }
302    },
303    animateComplete: function(state) {
304        HeroAnimations.revertState(state);
305        document.body.classList.remove('page--initial');
306        let scrollAnimations = ScrollAnimations;
307        scrollAnimations.initScroll();
308    },
309    captureState: function(elements) {
310        let state = [];
311        gsap.utils.toArray(elements).forEach(element => state.push(element, element.style.cssText));
312        return state;
313    },
314    revertState: function(state) {
315        for (let i = 0; i < state.length; i+=2) {
316            state[i].style.cssText = state[i+1];
317        }
318    }
319}

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.