DEV Community

Cover image for Teleport do Vue.js 3 vs Portals do ReactJS: uma análise comparativa para lidar com elementos fora do contexto do componente pai.
Jonathan Santos da Silva
Jonathan Santos da Silva

Posted on

Teleport do Vue.js 3 vs Portals do ReactJS: uma análise comparativa para lidar com elementos fora do contexto do componente pai.

O Vue.js 3 é uma das mais populares bibliotecas de JavaScript para construção de interfaces de usuário, e sua recente atualização trouxe consigo um novo componente interessante, o Teleport. Neste post, vamos fazer uma introdução ao Teleport e também uma comparação com os Portals do ReactJS.

Antes de começarmos, é importante entendermos que ambos os recursos foram criados para resolver um problema comum em aplicações web: como lidar com elementos que precisam ser exibidos fora do contexto do seu componente pai.

Em Vue, um componente é renderizado dentro de sua própria estrutura de componentes, o que significa que todas as suas propriedades e métodos são restritos a essa estrutura. No entanto, às vezes é necessário exibir um elemento em outro local da página, fora do contexto de seu componente pai. É nesse momento que podemos utilizar o Teleport.

O Teleport permite que nosso componente seja "teletransportado" como filho de outro elemento e em qualquer outro lugar da página, sem termos que nos preocupar com renderização e interação, mantendo os dados e informações do componente mesmo após ser mudado de lugar.

Para podermos utilizar do componente Teleport, só precisamos envolver o elemento a ser teleportado em uma tag <teleport> </teleport> e especificarmos o local que o elemento deve ser renderizado, como no exemplo a baixo:


Modal.vue

<template> <teleport to="#modal-target"> <div v-if="show" class="modal__body"> <h1>Modal Title</h1> <p>Modal Content</p> </div> </teleport> </template> <script lang="ts"> export default { props: { show: { type: Boolean, required: true, }, }, }; </script> 
Enter fullscreen mode Exit fullscreen mode

App.vue

<template> <div id="modal-target" class="modal__target"></div> <button @click="show = !show">Toggle Modal</button> <Modal :show="show" /> </template> <script lang="ts"> import Modal from './components/Modal.vue'; export default { data() { return { show: false, }; }, components: { Modal, }, }; </script> 
Enter fullscreen mode Exit fullscreen mode

Com o código acima, você pode ver que o elemento modal é renderizado como filho, no local especificado pela propriedade "to" que funciona da mesma forma que um seletor CSS. Com isso podemos alterar o local de renderização do nosso componente de modal, independente da sua posição na estrutura de elementos. Obtendo o seguinte resultado:


Resultado da abordagem utilizando componente raw `Teleport` endraw do vue3

O Teleport também possui uma propriedade para desabilita-lo em algum caso, podemos passar, por exemplo, para que ele seja desabilitado caso estejamos utilizando um dispositivo mobile apenas criando uma validação de tamanho de tela:


computed: { isMobile() { return screen.width <= 760; }, }, 
Enter fullscreen mode Exit fullscreen mode

E adicionando isso na propriedade "disabled" do nosso componente Teleport:

 <teleport :disabled="isMobile" to="#modal-target"> <div v-if="show" class="modal__body" style=""> <h1>Modal Title</h1> <p>Modal Content</p> </div> </teleport> 
Enter fullscreen mode Exit fullscreen mode

Resultado da abordagem utilizando componente raw `Teleport` endraw do vue3 porém com propriedade disbled


Um comparativo com portals do ReactJS

Agora vamos comparar o Teleport com os Portals do ReactJS. Em React, os Portais são usados para exibir elementos fora do contexto de seu componente pai. A ideia é semelhante ao Teleport, mas a implementação é um pouco diferente.

Em React, você precisa criar um componente Portal e usá-lo como um componente comum em sua aplicação. Aqui está um exemplo de código:

App.jsx

import React, { useState } from 'react'; import { createPortal } from 'react-dom'; import './App.css'; function Modal() { return createPortal( <div> <h1>Modal Title</h1> <p>Modal Content</p> </div>, document.getElementById('modal-root') ); } function App() { const [show, setShow] = useState(false); return ( <div> <button onClick={() => setShow(!show)}>Toggle Modal</button> {show && <Modal />} <div id="modal-root" class="modal__root"></div> </div> ); } export default App; 
Enter fullscreen mode Exit fullscreen mode

Assim como o Teleport, podemos obter um resultado parecido, nos permitindo renderizar o componente em qualquer local da página.

Resultado da abordagem utilizando componente raw `Portals` endraw do react

No entanto, a implementação é um pouco diferente, pois você precisa criar um componente específico e usá-lo como um componente comum.

Em resumo, o Teleport e os Portais são recursos semelhantes, criados para resolver o mesmo problema de exibir elementos fora do contexto de seu componente pai. O Teleport é uma adição interessante ao Vue.js 3 e é fácil de usar, enquanto os Portais são uma abordagem mais flexível, porém requerem uma implementação um pouco mais complexa.

A escolha entre o Teleport e os Portals depende da sua familiaridade com as ferramentas e do que você acha mais fácil de aprender. Se você já trabalha com Vue.js 3, o Teleport é uma opção fácil de implementar e pode ser mais adequado. Se você já está mais familiarizado com os Portals do ReactJS, pode ser mais fácil continuar usando essa abordagem. O importante é escolher a opção que você se sinta mais confortável em trabalhar e que seja mais fácil para você aprender.

Obrigado pela leitura!! Críticas construtivas e comentários são muito bem vindos 💚💙

Top comments (0)