Crie uma animação “botão para modal” com GSAP

Neste novo tutorial, continuaremos trabalhando com GSAP e aprenderemos como criar uma animação de botão para modal fácil de seguir e atraente. Este tipo de animação é ideal para alternar formas modais.

Sem mais introdução, vamos explorar o resultado final!

1. Comece com a marcação da página

Dentro de um wrapper, colocaremos o gatilho modal e um elemento vazio. Também agruparemos o conteúdo do botão em um span elemento.

1
 class="wrapper">
2
   class="open-modal">
3
    Contact Us
4
  
5
   class="next">
6

Com relação à estrutura modal, vamos pegá-la emprestada junto com a maioria de seus estilos de um tutorial anterior:

1
 class="modal">
2
   class="modal-dialog">
3
     class="close-modal" aria-label="close modal" title="close modal">
4
5
    
6
     class="modal-content">...
7
  
8

2. Adicione o CSS

O botão e o elemento vazio terão dimensões fixas e a mesma cor de fundo.

O botão terá 190px x 50px, enquanto seu irmão terá 50px x 50px.

Além disso, o elemento vazio será posicionado de forma absoluta dentro de seu elemento pai e oculto por padrão, pois o botão terá um valor mais alto. z-index valor.

Aqui estão os estilos relacionados usando aninhamento CSS:

1
/*CUSTOM VARIABLES HERE*/
2

3
.wrapper {
4
  position: relative;
5

6
  > * {
7
    background: var(--black);
8
  }
9

10
  .open-modal {
11
    position: relative;
12
    display: block;
13
    width: 190px;
14
    height: var(--base-width);
15
    color: var(--white);
16
    border-radius: 30px;
17
    font-weight: bold;
18
    z-index: 1;
19
  }
20

21
  .next {
22
    position: absolute;
23
    top: 50%;
24
    left: 50%;
25
    transform: translate(-50%, -50%);
26
    width: var(--base-width);
27
    aspect-ratio: 1;
28
    border-radius: 50%;
29
  }
30
}

O modal será um elemento posicionado fixo e oculto por padrão.

Aqui estão todos os seus estilos:

1
/*CUSTOM VARIABLES HERE*/
2

3
.modal {
4
  position: fixed;
5
  left: 0;
6
  bottom: 0;
7
  right: 0;
8
  align-items: center;
9
  justify-content: center;
10
  background: var(--black);
11
  visibility: hidden;
12
  opacity: 0;
13
  z-index: 2;
14

15
  &,
16
  .close-modal {
17
    top: 0;
18
    color: var(--white);
19
  }
20

21
  .modal-dialog {
22
    display: flex;
23
    width: 100%;
24
    height: 100vh;
25
    overflow: auto;
26
  }
27

28
  .modal-content {
29
    max-width: 800px;
30
    padding: 1rem;
31
    margin: auto;
32

33
    p + p {
34
      margin-top: 1rem;
35
    }
36
  }
37

38
  .close-modal {
39
    position: absolute;
40
    right: 30px;
41
    font-size: 2rem;
42
  }
43
}

3. Adicione o JavaScript

Assim que o botão for clicado, iremos ocultá-lo e exibir o modal. Para facilitar esse processo, inicializaremos um cronograma GSAP que executará as seguintes ações:

  • Oculte o conteúdo do botão.
  • Defina a largura do botão igual à largura do irmão.
  • Dimensione o elemento vazio até um ponto em que ele cubra todo o tamanho da página. Para garantir isso, executaremos alguma lógica dentro do scaledValues() função.
  • Mostre o modal.
  • Assim que a linha do tempo terminar, adicionaremos o is-visible classe para o modal.

Aqui está o código JavaScript relacionado:

1
const openModal = document.querySelector(".open-modal");
2
const span = openModal.querySelector("span");
3
const next = openModal.nextElementSibling;
4
const modal = document.querySelector(".modal");
5
const closeModal = modal.querySelector(".close-modal");
6
const baseWidth = 50;
7
const IS_VISIBLE_CLASS = "is-visible";
8

9
function scaledValue() {
10
  let windowWidth = window.innerWidth;
11
  const windowHeight = window.innerHeight;
12

13
  if (windowHeight > windowWidth) {
14
    windowWidth = windowHeight;
15
  }
16
  const toScale = windowWidth / baseWidth + 10;
17
  return Math.ceil(toScale);
18
}
19

20
openModal.addEventListener("click", function () {
21
  const tl = gsap.timeline({
22
    onComplete: () => modal.classList.add(IS_VISIBLE_CLASS)
23
  });
24
  tl.to(span, { opacity: 0, duration: 0.25 })
25
    .to(this, { width: baseWidth })
26
    .to(next, { scale: scaledValue() })
27
    .to(modal, { autoAlpha: 1 });
28
});

Uma vez que .close-modal botão é clicado ou o ESC for pressionada, inverteremos a lógica. Neste caso, definiremos uma nova linha do tempo e reverteremos as animações anteriores.

Aqui está o código JavaScript responsável por fechar o modal:

1
...
2

3
closeModal.addEventListener("click", function () {
4
  const tl = gsap.timeline({
5
    onComplete: () => modal.classList.remove(IS_VISIBLE_CLASS)
6
  });
7
  tl.to(modal, { autoAlpha: 0 })
8
    .to(next, { scale: 1 })
9
    .to(openModal, { width: 190 })
10
    .to(span, { opacity: 1, duration: 0.25 });
11
});
12

13
document.addEventListener("keyup", (e) => {
14
  if (
15
    e.key == "Escape" &&
16
    document.querySelector(`.modal.${IS_VISIBLE_CLASS}`)
17
  ) {
18
    closeModal.click();
19
  }
20
});

Implementação Alternativa (método 2)

Uma forma alternativa e mais dinâmica é criar apenas um cronograma para ambas as ações e deixar o GSAP lidar com a lógica reversa através de seu reverse() método.

Aqui está a demonstração relacionada para isso:

Conclusão

Pronto, pessoal! Com essas etapas simples e a ajuda da poderosa biblioteca de animação JavaScript GSAP, desenvolvemos uma bela animação de botão para modal que chama a atenção dos visitantes e traz uma experiência UX única ao nosso site. Espero que você goste tanto quanto eu e o incorpore em um projeto da web.

Antes de encerrar, vamos relembrar nossa animação original:

Por último, não se esqueça de navegar na biblioteca Tuts+ para mais tutoriais de animação CSS e JavaScript.

Como sempre, muito obrigado pela leitura!

Deixe uma resposta