PageSourceSearch

https://superhumano.ai/assets/js/text-animation.js?v=2

js superhumano.ai collected 2026-10-05 12:42:15 UTC 3,107 bytes, 90 lines download raw bytes

1gsap.registerPlugin(ScrollTrigger, SplitText);
2gsap.config({
3    nullTargetWarn: false,
4    trialWarn: false
5});
6
7// Um titulo que ja esta dentro do viewport quando esta funcao corre ja foi
8// pintado pelo browser: o visitante esta a le-lo. Aplicar-lhe opacity 0 para
9// depois o revelar faz com que desapareca e volte. Como isto so corre no
10// refresh do ScrollTrigger, ou seja depois de o GSAP ter carregado, em rede
11// lenta a homepage mostrava o h1 aos 0,3s, apagava-o aos 5,4s e so o repunha
12// aos 7,6s - 2,2 segundos sem titulo.
13//
14// A animacao continua a aplicar-se a tudo o que esta abaixo da dobra, que e
15// onde ela existe para servir: um reveal a medida que se faz scroll.
16function tg_is_in_viewport(el) {
17    var rect = el.getBoundingClientRect();
18    var vh = window.innerHeight || document.documentElement.clientHeight;
19    return rect.top < vh && rect.bottom > 0;
20}
21
22function tg_title_animation() {
23
24    var tg_var = jQuery('.tg-heading-subheading');
25    if (!tg_var.length) {
26        return;
27    }
28    const quotes = document.querySelectorAll(".tg-heading-subheading .tg-element-title");
29
30    quotes.forEach(quote => {
31
32        // Decidido uma unica vez, na primeira passagem: um titulo visivel a
33        // entrada fica como esta. Guardado no elemento para que os refresh
34        // seguintes (resize, por exemplo) nao voltem a apanha-lo ja com a
35        // pagina noutra posicao de scroll.
36        if (!quote.dataset.tgSkipAnim && !quote.animation && tg_is_in_viewport(quote)) {
37            quote.dataset.tgSkipAnim = "1";
38        }
39        if (quote.dataset.tgSkipAnim) return;
40
41        //Reset if needed
42        if (quote.animation) {
43            quote.animation.progress(1).kill();
44            quote.split.revert();
45        }
46
47        var getclass = quote.closest('.tg-heading-subheading').className;
48        var animation = getclass.split('animation-');
49        if (animation[1] == "style4") return
50
51        quote.split = new SplitText(quote, {
52            type: "lines,words,chars",
53            linesClass: "split-line"
54        });
55        gsap.set(quote, { perspective: 400 });
56
57        if (animation[1] == "style1") {
58            gsap.set(quote.split.chars, {
59                opacity: 0,
60                y: "90%",
61                rotateX: "-40deg"
62            });
63        }
64        if (animation[1] == "style2") {
65            gsap.set(quote.split.chars, {
66                opacity: 0,
67                x: "50"
68            });
69        }
70        if (animation[1] == "style3") {
71            gsap.set(quote.split.chars, {
72                opacity: 0,
73            });
74        }
75        quote.animation = gsap.to(quote.split.chars, {
76            scrollTrigger: {
77                trigger: quote,
78                start: "top 90%",
79            },
80            x: "0",
81            y: "0",
82            rotateX: "0",
83            opacity: 1,
84            duration: 2,
85            ease: Back.easeOut,
86            stagger: .02
87        });
88    });
89}
90ScrollTrigger.addEventListener("refresh", tg_title_animation);

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.