Guia Completo de Frontend para Iniciantes
Guia Completo de Frontend para Iniciantes
244-31 - HP0355234876
Versão 5.0
Sinopse
mundo JavaScript. Mas a base de tudo ainda gira em torno das três
tecnologias principais.
Isso quer dizer que não importa a época ou a tecnologia, a base sempre
vai ser a mesma. Então antes de pular para o tão famoso framework,
temos que aprender a base dele para realmente entender o que está por
trás dos panos. Sei que encontrar material de qualidade e com uma
linguagem simples para quem está começando não é uma tarefa muito
fácil. Com essa premissa em mente, criei esse ebook onde irei ensinar
desenvolvimento frontend.
@iuricode 1
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sumário
HTML 15 tópicos neste módulo
O que é .................................................................................................................... 13
Iniciando ................................................................................................................. 13
Sintaxe .................................................................................................................... 15
Títulos ...................................................................................................................... 17
Textos ....................................................................................................................... 17
Imagem ................................................................................................................... 18
Div ............................................................................................................................ 24
Link .......................................................................................................................... 25
Comentários ......................................................................................................... 25
Tabela ..................................................................................................................... 26
Listas ....................................................................................................................... 29
Formulário ............................................................................................................. 30
2
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é ................................................................................................................... 42
Iniciando ................................................................................................................... 42
Sintaxe .................................................................................................................... 44
Comentários ......................................................................................................... 44
Variáveis ................................................................................................................. 45
Reset ....................................................................................................................... 47
Cores ....................................................................................................................... 51
Seletores ................................................................................................................ 53
Preenchimentos .................................................................................................. 55
Display .................................................................................................................... 58
3
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Position ................................................................................................................... 59
Flexbox ................................................................................................................... 64
Responsividade ................................................................................................... 72
Grid .......................................................................................................................... 76
O que é ................................................................................................................... 87
Iniciando ................................................................................................................. 87
Variáveis ................................................................................................................. 88
Operadores ........................................................................................................... 94
4
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
5
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
6
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
7
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
8
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
9
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
10
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
11
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
12
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 1
HTML
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é
Iniciando
HTML é escrito em arquivos com o formato .html. Para criar uma página
em HTML é fácil, entre em seu editor de código (se não tiver uma
instalado eu recomendo o Visual Studio Code) e salve o arquivo em
branco como [Link] (você pode nomeá-lo como quiser, mas não
esqueça do .html).
13
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<!DOCTYPE html>
2
<html>
3
<head></head>
4
<body></body>
5 </html>
14
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sintaxe
Os elementos HTML são escritos usando tags. Todas as tags tem uma
chave de abertura e fechamento. A tag de fechamento tem uma barra
após o primeiro colchete.
1 <tag>iuricode</tag>
1
<pai>
2
<filho>Esta tag está dentro de outra tag</filho>
3 </pai>
15
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Indentação adequada
As quebras de linha entre suas tags são super importantes para escrever
um bom código HTML. Abaixo temos um bom exemplo disso.
1
...
2
<body>
3
<h1>Aqui temos um título</h1>
4
<p>E aqui um parágrafo</p>
5
</body>
6 ...
1
<!DOCTYPE html> <html> <head> </head> <body> <h1>
16
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Títulos
As tags de títulos são representadas em até seis níveis. <h1> é o nível
mais alto e <h6> é o mais baixo. Quanto maior for o nível da tag, maior vai
ser o tamanho da fonte apresentada na tela e sua importância no SEO.
1
<h1>Título do h1</h1>
2
<h2>Título do h2</h2>
3
<h3>Título do h3</h3>
4
<h4>Título do h4</h4>
5
<h5>Título do h5</h5>
6 <h6>Título do h6</h6>
Textos
As tags de texto, definem diferentes formatações para diversos tipos de
texto. Desde estilos de fonte, parágrafos, quebra de linha ou até mesmo
spans. Iremos conhecê-las:
17
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Tags de medias
As tags de medias ajuda na criação de experiências multimídia em uma
página da web. Isso é, adicionar em nossas páginas imagens, vídeos,
áudios e entre outros conteúdos de medias.
Imagem
18
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<img src="nomeDaPasta/[Link]"
2
alt="descrição sobre a imagem"
3 />
O src vem de source, ele é atributo da tag <img>, nele vai conter o
caminho da imagem que será inserida por você.
Além dele, temos o atributo alt. Recomendo que você sempre coloque o
atributo alt para que pessoas com deficiências saibam (através de um
leitor) do que se trata a imagem na página.
Pontos importantes
Audio
19
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<audio controls>
2
<source src="arquivo.mp3" type="audio/mpeg" />
3 </audio>
A tag <source> define uma fonte de arquivo de áudio, e junto a ela temos
dois atributos
20
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Video
1
<video width="320" controls>
2
<source src="video.mp4" type="video/mp4" />
3 </video>
21
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iframe
1
<iframe src="[Link]
2
style="width: 100%; height: 350px;">
3 </iframe>
22
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Canvas
1
<canvas id="jogo" width="400" height="250">
2
Opa, ocorreu um erro!
3 </canvas>
23
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Div
A tag <div> é utilizada para dividir elementos para fins de estilos (usando
class ou id). Ele deve ser utilizado somente quando não tiver outro
elemento de semântica.
1
<div>
2
<p>Entrou dentro de uma div</p>
3 </div>
24
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Link
A tag <a> (ou elemento âncora) é um hiperlink, que é usado para vincular
uma página a outra. O conteúdo dentro de cada <a> precisará indicar o
destino do link utilizando o atributo href. Se a tag <a> não tiver o atributo
href, ela será apenas um espaço reservado para um hiperlink.
1 <a href="[Link]/efront">eFront</a>
Comentários
Para adicionar um comentário em um código HTML, é preciso utilizar as
tags próprias para esse propósito, nosso é <!-- -->.
Portanto, todo o código que estiver dentro dessa tag não será executado.
25
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Tabela
A criação de uma tabela em uma página HTML é feita com a tag <table>.
1 <table></table>
TR
Em todas as tabelas existem linhas. Para isso, utilizamos a tag <tr>, ela
pode ser inserida em diferentes áreas da tabela, como no cabeçalho, no
corpo e no rodapé.
1 <tr></tr>
26
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
TH
A tag <th> é utilizada para inserir o cabeçalho na tabela, ela pode ser
inserida em diferentes áreas. Na região do corpo da tabela, ela serve para
dar destaque e identificar cada coluna específica.
1 <th></th>
TD
Além das linhas, toda tabela precisa de uma coluna. Isso significa que é
preciso adicionar a tag <td> em todas as linhas para criar as colunas
desejadas e inserir o conteúdo a ser exibido.
1 <td></td>
27
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<table>
2
<tr>
3
<th>Nome</th>
4
</tr>
5
<tr>
6
<td>Iuri</td>
7
</tr>
8 </table>
28
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Listas
Vamos agora falar um pouco sobre as listas (ordenadas e desordenadas)
e como elas funcionam. As listas são muito importantes quando
queremos listar itens na página.
O elemento <li> é usado para representar um item que faz parte de uma
lista. Este item deve estar contido em um elemento pai: uma lista
ordenada (<ol>) ou uma lista desordenada (<ul>).
Lista ordenada
1
<ol>
2
<li>HTML</li>
3
<li>CSS</li>
4
<li>JavaScript</li>
5
<li>React</li>
6 </ol>
29
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Listas desordenadas
1
<ul>
2
<li>HTML</li>
3
<li>CSS</li>
4
<li>JavaScript</li>
5
<li>React</li>
6 </ul>
Formulário
Formulários são um dos principais pontos de interação entre o usuário e
sua página. Um formulário HTML é feito de um ou mais widgets. Esses
widgets podem ser campos de texto, caixas de seleção, botões,
checkboxes, radio buttons e entre outros elementos HTML.
30
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Form
Label
1 <label>Nome:</label>
Input
31
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 <input type="email"></input>
No input temos o atributo type. Esse atributo define o tipo do nosso input.
32
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Fieldset
1 <fieldset></fieldset>
Legend
1 <legend>Contato</legend>
1
<form action="/" method="post">
2
<label>Nome:</label>
3
<input type="text"/>
4 ...
33
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
<label>Email:</label>
3
<input type="email">
5
<input type="submit" value="Enviar"/>
6 </form>
Tags semânticas
Na vida sempre temos uma forma correta de fazer as coisas, no HTML
não é diferente. As tags semânticas além de deixar o código melhor para
o SEO, ele ajuda outros desenvolvedores a entender seu código.
Informações importante
As tags semânticas não têm nenhum efeito na apresentação na
página
As tags semânticas tem significado e deixam seu conteúdo claro.
34
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 <div>Sou o rodapé</div>
Seria melhor:
1 <footer>Sou o rodapé</footer>
Section
1 <section></section>
35
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Article
1 <article></article>
Aside
36
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 <aside></aside>
Header
1 <header></header>
Footer
1 <footer></footer>
37
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Nav
1 <nav></nav>
Main
1 <main></main>
38
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Meta tags
SEO (Search Engine Optimization) é o conjunto de técnicas responsáveis
por fazer com que determinada página de um site apareça nas primeiras
páginas do Google. Quanto melhor for o SEO de um site, maiores as
chances de que a página apareça logo de cara para quem pesquisa por
determinado assunto.
Informações importantes
39
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Title
1 <title>Nome da página</title>
Description
1
<meta name="description"
2
content="Descrição sobre a página"
3 />
Charset
40
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 <meta charset="UTF-8">
Keywords
Author
41
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 2
CSS
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é
Iniciando
42
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Certifique-se de que sua página HTML e sua folha de estilo CSS estão
no mesmo nível de pasta, caso ele esteja dentro de uma pasta diferente
do arquivo HTML basta colocar o nome da pasta antes do nome do
arquivo separado com uma barra (/).
1
h1 {
2
color: #00f;
3
font-size: 26px;
4 }
43
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sintaxe
1
seletor {
2
propriedade: valor;
3 }
Comentários
1
div {
2
/* color: blue; */
3 }
44
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Variáveis
frequente. Por exemplo, a mesma cor pode ser usada em vários lugares
na cor, teríamos que procurar todos os lugares que essa cor foi
outros lugares. Isso é ótimo para nós desenvolvedores pois, caso seja
1
:root {
2
--cor: black;
3 }
45
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
h1 {
2
var(--cor);
3 }
Aplicando fontes
Para colocar uma fonte em sua página primeiro é preciso chamar ele no
seu HTML, para isso vamos entrar no site do Google Fonts. Logo em
seguida, procure a fonte que você deseja e clique no botão "Select this
style" para assim adicionar os estilos de fontes que você deseja.
Perceba que quando você selecionou abriu uma aba na lateral na direita.
Nessa aba vai ter duas opções para aplicar a fonte em sua página, uma é
o <link> e o outro @import. O <link> é para importar pelo seu documento
HTML e o @import é para o seu documento CSS. Você pode escolher
qualquer um, isso vai com seu gosto, mas importar pelo HTML nos trás
uma melhor performance.
46
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
* {
2
font-family: 'Nome da fonte aqui';
3 }
Reset
Quando criamos uma página HTML, por padrão, nosso site tem um
espaçamento em volta da página. Para tirar esse padrão usamos duas
coisas: o padding (espaçamento dentro do conteúdo) e o margin
(espaçamento fora do conteúdo). Iremos zerar eles.
47
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
body {
2
padding: 0;
3
margin: 0;
4 }
Mas a gente não quer isso, não é? Queremos que o elemento continue
300px e com um espaçamento interno. É aí que entra o nosso querido
box-sizing: border-box. Ele irá manter o tamanho do container e com o
valor do espaçamento aplicado nele.
1
* {
2
padding: 0;
3
margin: 0;
4
box-sizing: border-box;
5 }
48
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Unidades de medidas
Medidas absolutas: Essas são as mais comuns que vemos no dia a dia.
São medidas que não estão referenciadas a qualquer outra unidade, ou
seja, não dependem de um valor de referência. São unidades de medidas
definidas pela física, como o pixel, centímetro, metro, etc...
PX
49
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
h1 {
2
font-size: 18px;
3 }
REM
1
h1 {
2
font-size: 1rem; // Igual a 16px
3 }
Como disse acima, o valor base é 16px, e isso pode acabar gerando
dificuldades para que encontremos alguns tamanhos padrões que
costumam ser utilizados. Por exemplo, como faríamos para atingir um
tamanho de 10px utilizando rem? Para isso precisamos calcular. Mas ficar
calculando esses números não é algo muito "amigável", porém, podemos
adicionar um pequeno truque para nos ajudar.
50
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
html {
2
font-size: 62,5%;
3
}
5
h1 {
6
font-size: 1.2rem; /*equivalente a 12px*/
7 }
Cores
RGB
O processo é simples: como na vida real onde você mistura cores para
obter uma outra cor como resultado, você faz a mesma coisa como o RGB.
51
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sua sintaxe utiliza a soma de 3 valores: Red, Green e Blue. Onde o valor
máximo de todas as cores é 255 e o mínimo é 0.
1
h1 {
2
color: rgb(255, 200, 10);
3 }
1
h1 {
2
color: rgba(255, 200, 10, 0.4);
3 }
HEX
Hex, ou Hexadecimal, tem sintaxe muito mais curta que o RGB. O código
Hexadecimal consiste em seis letras ou números precedidos por um “#”.
52
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
h1 {
2
color: #00ff00;
3 }
Seletores
“Okay, mas se eu tiver mais de um elemento <p> e quiser mudar a cor do
texto só de um?”.
53
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.souClass {
2
color: #f00;
3 }
1
<p class="souClass">Sou um elemento com Class</p>
Outros seletores
54
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
div + p {
2
color: #f00;
3 }
1
[Link] {
2
color: #f00;
3 }
1
div > p {
2
color: #f00;
3 }
Preenchimentos
As propriedades de preenchimento CSS são usadas para gerar espaço
em torno ou dentro do conteúdo.
55
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Padding
Margin
margin border
padding
Conteúdo
56
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.class {
2
margin: 20px;
3 }
1
.class {
2
margin: 5px 10px;
3 }
1
.class {
2
margin: 0px 5px 10px 15px;
3 }
57
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Display
Block
O elemento block, não aceita elementos na mesma linha que ele, ou seja,
quebra a linha após o elemento, e sua área ocupa toda a linha onde ele é
inserido.
Alguns elementos que têm como padrão block: <div>, <h1> até <h6>,
Inline
O elemento inline não inicia em uma nova linha nem quebra de linha após
Alguns elementos que têm como padrão inline: <span>, <a>, <img>.
58
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Position
A propriedade position específica como um elemento será posicionado
na tela, podemos até posicionar em um ponto específico controlando
com os parâmetros top, right, bottom e left.
59
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Static
Relative
Absolute
Fixed
60
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Exemplo ilustrativo:
body
elementoFilho
1
.elementoFilho {
2
position: absolute;
3
bottom: 0;
4
right: 0;
5 }
61
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
elementoPai
body
elementoFilho
1
.elementoPai {
2
position: relative;
3
}
5
.elementoFilho {
6
position: absolute;
7
bottom: 0;
8
right: 0;
9 }
62
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<body>
2
<div class="elementoPai">
3
<div class="elementoFilho"></div>
4
</div>
5 </body>
“Okay Iuri, quer dizer que se o elementoFilho ficar fora do elementoPai ele
irá se referenciar ao body?”
63
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Flexbox
64
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
justify-content
1
.elementoPai {
2
display: flex;
3
justify-content: flex-start;
4 }
display flex e
justify-content
flex-start (padrão)
65
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
flex-end
flex-center
66
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
space-between
space-around
space-evenly
67
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
align-items
1
.elementoPai {
2
display: flex;
3
align-items: flex-start;
4 }
display flex e
align-items
68
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
flex-start
flex-end
stretch
69
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
center
baseline
1 4
3
70
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Outras propriedades
71
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Pesquisar
1
nav {
2
display: flex;
3
align-items: center;
4
justify-content: space-between;
5 }
Responsividade
Sites responsivos são aqueles que adaptam o tamanho das suas páginas
ao tamanho das telas que estão sendo exibidos, como as telas de
celulares, tablets e televisões (como a Netflix e o YouTube).
72
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Os types definem para que tipo de media um certo código CSS será
aplicado.
Media type
73
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
@media screen and (max-width: 480px) {
2
body {
3
background-color: #00ff00;
4
}
5 }
Sempre que vamos fazer algo no media queries, temos antes que dizer
que é para um media que estamos desenvolvendo para isso colocamos
@media. Logo em seguida o tipo dessa media (no nosso caso foi o
screen) e um operador lógico (no nosso caso foi o and).
Perceba que usamos o max, nesse caso estamos dizendo que será
aplicado quando tiver 480 pixels de largura ou menos.
74
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
@media screen and (max-width: 480px) {
2
.card {
3
width: 100%;
4
}
5 }
Uma coisa super importante é que você não precisa escrever todas as
propriedades de uma class ou id dentro do seu @media, somente o que
você quer que mude. Que no caso o tamanho de cada card terá o
tamanho da resolução do dispositivo.
75
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Padrões de resoluções
Fonte: [Link]
CSS Grid
O CSS Grid é um sistema de estruturação de layout. A diferença dele pro
Flexbox é que ele nos permite configurar layouts em duas dimensões
(linhas e colunas) sendo que no Flexbox é apenas um dimensão.
76
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Grid Container
1
.container {
2
display: grid;
3 }
1
<div class="container">
2
<div class="item">1</div>
3
<div class="item">2</div>
4
<div class="item">3</div>
5
<div class="item">4</div>
6 </div>
Isso irá criar uma grid do tipo block, significando que o .container irá
ocupar a linha inteira.
77
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
2
3
4
5
6
grid-template-columns
1
.container {
2
display: grid;
3
grid-template-columns: 200px 200px;
4 }
78
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 2
3 4
5 6
1
.container {
2
display: grid;
3
grid-template-columns: 200px 1fr;
4 }
1 2
3 4
5 6
79
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
grid-template-rows
1
.container {
2
display: grid;
3
grid-template-columns: 200px 1fr;
4
grid-template-rows: 200px 100px;
5 }
1 2
3 4
5 6
80
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
grid-template-areas
Você deve ter notado que nossos itens vão se organizando na grid de
acordo com a ordem em que estão no HTML.
Porém, podemos dar nomes para cada área da nossa grade e depois
indicar onde cada elemento deve ir.
1
<div class="container">
2
<div class="item header">Header</div>
3
<div class="item sidenav">Sidenav</div>
4
<div class="item main">Main</div>
5
<div class="item footer">Footer</div>
6 </div>
81
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para cada item, vamos declarar a propriedade grid-area, que serve para
indicar o nome da área em que cada elemento deverá ocupar na grid.
1
.header {
2
grid-area: header;
3
}
4
.sidenav {
5
grid-area: sidenav;
6
}
7
.content {
8
grid-area: main;
9
}
10
.footer {
11
grid-area: footer;
12 }
Para dar nomes às áreas de uma mesma linha, escrevemos dentro de ""
(aspas). Ao abrir novas aspas estaremos indicando que estamos indo
para a linha seguinte.
82
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.container {
2
grid-template-areas: "header header"
3
"sidenav main"
4
"footer footer";
5 }
1
.container {
2
display: grid;
3
grid-template-columns: 30% 60%;
4
grid-template-rows: 30px 80px 20px;
5
grid-template-areas: "header header"
6
"sidenav main"
7
"footer footer";
8 }
83
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Header
Aside Main
Footer
grid-auto-rows
Um Dois
Três Quatro
Cinco Seis
Sete
84
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.container {
2
display: grid;
3
gap: 10px;
5
/* grid explícito */
6
grid-template-columns: 2fr 1fr;
7
grid-template-rows: 100px 100px 100px;
9
/* grid implícito */
10
grid-auto-rows: 100px;
11 }
85
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Um Dois
Três Quatro
Cinco Seis
Sete
86
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 3
JavaScript
Pegue o café e prepare-se para mais um módulo. Lembre-se
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é
Iniciando
é fácil, basta salvar o arquivo como [Link] (lembro que você pode
nomeá-lo como quiser, mas não esqueça do .js) dessa forma teremos
87
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Variáveis
isso não significa que ela não tem tipo. Isso torna o JavaScript uma
Então se você tiver uma variável chamado “nome” com o valor de “iuri” e
ao longo do nosso código mudar seu valor para 10, para o JavaScript isso
1
let nome = "Iuri"; // Está correto
2
nome = 10; // Está correto também
88
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Bem, para declarar uma variável temos três opções: var, let e const
Uso do var: Uma variável declarada com var possui o que chamamos
de escopo de função. Isso significa que se criarmos uma variável
deste tipo dentro de uma função, você pode modificar em qualquer
parte desta função, mesmo se criar outra função dentro dela
Uso do let: Diferente de var, declarar como let leva em conta o bloco
de código onde foi declarada. Isso significa que se a declararmos
dentro de um uma função, ela será “enxergada” apenas dentro deste
escopo
Uso do const: Uma variável const é usada para definir uma constante.
Diferente de var e let, as variáveis de const não podem ser
atualizadas nem declaradas novamente.
89
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Var
1
function exibirNome() {
2
var nome = "Iuri";
3
}
Let
1
let nome = "Iuri";
3
if (true) {
4
let nome = "Kenay";
5
[Link](nome); // Retornará "Kenay"
6
}
Por que isso não retorna um erro? Porque as duas instâncias são tratadas
como variáveis diferentes, já que são de escopos diferentes.
90
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Const
1
const nome = "Iuri";
2
nome = "Kenay";
Tipos de variáveis
String
1
var nome = "Iuri";
2
// Ou
91
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Number
1
var numero = 10;
2 var pi = 3.14;
Boolean
1
var javascript = true;
Object
92
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var pessoa = {
2
nome: "Iuri",
3
idade: 22,
4
frontend: true,
5 };
Function
1
function nome() {
2
[Link]("Iuri");
3 }
Undefined
Uma variável que não foi atribuída a um valor específico, assume o valor
undefined (indefinido).
93
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 var texto
Null
Operadores
Operadores em JavaScript são símbolos especiais que envolvem um ou
mais operandos com a finalidade de produzir um determinado resultado.
Não irei citar todos os operadores, somente os mais utilizados. Caso
queria ver todos os operadores clique aqui e leia mais.
94
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Operadores de atribuição
Atribuição
x = y
Atribuição de adição
x += y
Atribuição de subtração
x -= y
Atribuição de multiplicação
x *= y
Atribuição de divisão
x /= y
Atribuição de resto x %= y
95
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Operadores aritméticos
Operador Descrição
Módulo (%)
Retorna o inteiro restante da divisão dos dois operadores.
Incremento (++)
Adiciona um ao seu operando.
Decremento (--)
Subtrai um de seu operando.
Negação (-)
Retorna a negação de seu operando.
96
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Operadores de comparação
Operador Descrição
Igual (==)
Retorna true caso os operandos sejam iguais.
Menor que ou igual (<=) Retorna true caso o operando da esquerda seja menor ou igual que o da direita.
97
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Declarações condicionais
1
if (condicao) {
2
// O código será executado caso a condição
3
// seja verdadeira
4 }
Agora você deve estar se perguntando “Mas Iuri, e se essa condição for
falsa?”. Nesse nosso exemplo, se a condição for falsa o fluxo irá continuar
Declarações condicionais
Agora, caso você queira executar algo quando a condição for falsa,
utilizamos o else (se não). O else sempre será executado caso o if seja
falso.
98
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
if (condicao) {
2
// Será executado caso a condição seja verdadeiro
3
} else {
4
// Será executado caso a condição seja falso
5 }
O else if (se não se) nos ajuda a fazer mais do que uma condição, ou seja
se a condição anterior não for verdadeira verifique uma nova condição.
1
if (condicao) {
2
// Será executado caso a condição seja verdadeiro
3
} else if (condicaoDois) {
4
// Será executado caso a primeira condição seja falsa
5
} else {
6
// Será executado caso todas as condições sejam falsas
7 }
99
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Function
tarefa.
Imagine que você tenha duas tarefas, uma é executar a soma de dois
que essas tarefas são duas funções diferentes? Imagine essas duas
tarefas espalhadas em nosso código, iria atrapalhar muito, mas com uma
Nome da função
vírgulas
somar:
100
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function somar(numero) {
2
return numero * numero;
3
}
5 [Link](somar(10));
Object
Imagine que você tenha uma variável chamada pessoa e queira ter uma
coleção de propriedades, como nome, idade, cidade... Isso é possível?
Claro que é, isso é chamado de objeto. Objeto é uma coleção de
propriedades, sendo cada propriedade definida como uma sintaxe de
chave: valor. A chave pode ser uma string e o valor pode ser qualquer
informação.
101
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
const pessoa = {
2
nome: "Iuri",
3
idade: 22,
4 };
Para acessar uma propriedade de um objeto, use uma das duas notações
(sintaxes)
1
[Link]; // Resultado: Iuri
Array
Arrays, ou matrizes são lista de objetos. Elas são objetos que contêm
múltiplos valores armazenados em uma lista.
102
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Vamos supor que queremos armazenar a nossa lista de frutas, nós temos
o seguinte código.
1 frutas[2];
103
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Métodos de array
concat(
join(
push(
pop(
shift(
slice(
splice(
reverse()
Concat
104
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var front = ["html", "css", "javascript"];
2
var back = ["java", "php", "node"];
4
front = [Link](back);
5
[Link](front);
Join
1
var front = ["html", "css", "javascript"];
2
front = [Link]("-");
4
[Link](front);
5
// Resultado será as propriedades do array
Push
105
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var front = ["html", "css", "javascript"];
2
[Link]("react");
4
[Link](front);
Pop
1
var front = ["html", "css", "javascript"];
2
[Link]();
4
[Link](front);
Shift
106
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var front = ["html", "css", "javascript"];
2
[Link]();
4
[Link](front);
Reverse
1
var front = ["html", "css", "javascript"];
2
[Link]();
4
[Link](front);
Loops
Laços de repetição, ou loops como o próprio nome já diz, ele faz com que
blocos de códigos sejam repetidos diversas vezes até que certa
condição seja cumprida.
107
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
For
O primeiro que você usará na maior parte do tempo, é o loop for, ele tem a
seguinte sintaxe:
1
for (inicializador; condição; expressão) {
2
// Código que será executado
3 }
108
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
For na prática
1
for (let i = 1; i <= 5; i++) {
2
[Link](i); // Saída: 1, 2, 3, 4, 5
3 }
109
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Explicando: dentro do nosso laço for temos o “let i=1;” ele é o nosso
inicializador, ele basicamente está falando que nossa variável de
inicialização é o “i” que tem o valor de 1.
While
110
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
inicializador;
2
while (condição) {
3
// Código
4
expressão;
5 }
Do while
1
inicializador;
2
do {
3
// Código
4
expressão;
5 } while (condição);
111
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
DOM
112
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Principais eventos
113
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Inline
Em um arquivo externo, usando um manipulador de eventos.
1
<button onclick="alert('Oi')">
2
Sou um evento inline
3 </button>
114
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
[Link]("button").addEventListener(
2
"click", () => {
3
alert("oi");
4 });
Sei que olhando esse código parece que utilizar eventos inline é mais
fácil e rápido, mas estamos utilizando só um exemplo, imagina uma
aplicação cheia de animações e interações do usuário, você mesmo
ficaria perdido e terá um código JavaScript maior.
Tenha calma que irei explicar cada parte desse código futuramente.
getElementById(
getElementsByClassName(
querySelector(
querySelectorAll()
115
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
getElementById
getElementsByClassName
Como o próprio nome já diz, essa função vai retornar os elementos que
possuem uma mesma classe passada.
116
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
querySelector
Diferente dos outros métodos, este método utiliza “.” para indicar a
seleção de uma classes, “#” para indicar seleção de ids ou a própria tag.
1
let teste1 = [Link]("#souId");
2
let teste2 = [Link](".souClass");
querySelectorAll
117
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
let teste = [Link]("div");
Interações do usuário
Estilos Inline
Classes CSS a elementos.
1
var button = [Link]("button");
3
[Link]("click", () => {
4
[Link] = "red";
5 });
118
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var elementoDiv = [Link]("iuricode");
3
[Link]("click", () => {
4
[Link]("outraCor");
5 });
119
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
id=”iuricode”).
addEventListener
Sintaxe do addEventListener:
1 [Link](evento, função);
120
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
var nomeElemento = [Link]("div");
3
[Link]("click", () => {
4
...
5 });
O arrow function não terá uma explicação mais afundo pois ele é um
recursos introduzido no ES6 e estamos apenas abordando os
fundamentos. Mas caso queria saber sobre ele clique aqui.
121
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é Axios?
1
<script
2
src="[Link]
3
</script>
4 <script src="[Link]"></script>
122
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Adicionando a API
1 [Link]("[Link]
Primeiro, você importa o Axios para que possa ser usado na aplicação.
Em seguida, executa uma requisição utilizando o GET através do método
get() para obter uma promessa que retorna um objeto de resposta que
pode dar sucesso ou erro, dependendo da resposta da API.
1
axios
2
.get("[Link]
3
.then(function (response) {
4
[Link]([Link]);
5
[Link]([Link]);
6
})
7
.catch(function (error) {
8
[Link](error);
9 });
123
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
124
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Por outro lado, uma conversa online via a mensagem, como o WhatsApp,
é um exemplo de comunicação assíncrona: quando enviamos uma
mensagem e as informações não chegam logo em sequência, a gente
espera até a outra pessoa responder.
125
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sintaxe
Utilizamos o prefixo async antes de definir uma função para indicar que
estamos tratando de um código assíncrono, e com o prefixo adicionado,
podemos utilizar o await antes das Promises indicando um ponto a ser
aguardado pelo código. Já irei explicar melhor sobre Async e Await.
1
// Sem o Async/Await
2
function fetchUser(user) {
3
[Link]().then(response => {
4
[Link](response); });
5
}
7
// Com o Async/Await
8
async function fetchUser(user) {
9
const response = await [Link]();
10
[Link](response);
11 }
Veja como o código ficou mais limpo, não precisamos mais declarar os
.then ou .catch e ter medo de alguma Promise não executar antes de
utilizarmos seu resultado pois o await faz todo papel de aguardar com
que a requisição retorne seu resultado.
126
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Async. Essa palavra pode ser usada ao criar uma função. Quando
adicionamos esse identificador na criação da função, nós definimos
que ela será uma função assíncrona, e o melhor, retornará uma
promessa. Quando usarmos a expressão return estaremos, na
realidade, resolvendo uma promessa
127
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function primeiraFuncao() {
2
[Link]("Segundo");
3
}
5
async function segundaFuncao() {
6
await primeiraFuncao()
8
[Link]("Primeiro");
9
}
10
11 segundaFuncao()
128
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
129
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 4
Sass
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
Assim como qualquer linguagem, sempre temos que evoluir e com CSS
não é diferente. Neste pequeno módulo iremos abordar o famoso Sass.
Com ele, podemos separar o nosso CSS em módulos, criar funções,
implementar lógica de programação, e muito mais. Mas fique tranquilo,
Sass e CSS são muito semelhantes, então se você tem a base de CSS a
curva de aprendizado com Sass será curta. Além disso, depois que você
aprender a utilizar Sass em suas aplicações nunca mais vai voltar pro
CSS puro.
O que é
130
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iniciando
É bem simples iniciar com Sass, basta entrar em seu editor de código e
criar um arquivo com o formato .scss.
Dessa forma estamos criando um documento Sass que irá criar estilos
para o nosso documento HTML. Mas tenha calma, talvez você tenha
tentando chamar o documento Sass no HTML, mas não deu certo.
Isso aconteceu porque estamos estilizando com Sass, mas não quer
dizer que o nosso documento Sass irá ser referenciado no HTML, mas
sim o arquivo CSS.
Confuso né?
“Espera Iuri, quer dizer que todo nosso estilo com Sass vai virar um CSS
no final?”
Exato! Mas calma, isso vai trazer muitas vantagens que iremos descobrir
ao decorrer do módulo.
131
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
“Ok Iuri, mas como tenho acesso a esse CSS que foi feito pelo Sass?”.
Primeiro vamos criar o diretório onde será “cuspido” o nosso CSS e assim
referenciar ele no nosso HTML.
132
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
iremos colocar o caminho onde será transpilado o arquivo CSS. Veja que
falaram qual será o formato que será transpilado, que em nosso caso é o
.css e temos também a opção “format” que diz que se o CSS “cuspido”
133
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Vamos fazer um teste para ver se nosso CSS está sendo transpilado
corretamente. Para isso, crie um estilo qualquer e clique em “Watch Sass”
localizado no barra inferior do editor de código (lembrando que essa
opção só irá parecer se tiver utilizando a extensão “Live Sass Compiler”).
134
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sintaxe
.scss .sass
1
button {
1
button
2
padding: 10px 20px;
2
padding: 10px 20px
3
border-radius: 5px;
3
border-radius: 5px
4 } 4
SCSS: É bastante semelhante ao CSS. Você pode até dizer que SCSS é
SCSS válido. Devido à sua semelhança com CSS, é a sintaxe SASS mais
vírgulas do SCSS.
135
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Comentários
Os comentários no Sass funcionam de maneira semelhante aos
comentários em outras linguagens, como JavaScript. Comentários de
linha única começam com // e vão até o final da linha. Esses comentários
não são mostrados no CSS compilado, somente comentários com /**/
1
// Este comentário não irá aparecer no CSS.
Variáveis
Podemos declarar uma variável utilizando o operador $, então passamos
a propriedade. No Sass geralmente utilizamos variáveis para guardar o
valor de uma cor, fonte, tamanho da fonte, largura ou altura, etc.
1
$cor: #0f0;
3
h1 {
4
color: $cor;
5 }
136
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Import/Use
137
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
@import "[Link]";
Extend
O @extend permite compartilhar um conjunto de propriedades de um
seletor para outro. Isso é muito útil se você tiver elementos de estilo
quase idênticos que diferem apenas em alguns pequenos detalhes.
1
.button-simples {
2
font-size: 16px;
3
color: #0f0;
4
}
6
.button-vermelho {
7
@extend .button-simples;
8
background-color: red;
9 }
138
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.button-simples, .button-vermelho {
2
font-size: 16px;
3
color: #0f0;
4
}
6
.button-vermelho {
7
background-color: red;
8 }
Mixin
Algumas coisas em CSS são um pouco trabalhosa de escrever. Um Mixin
permite criar grupos de declarações CSS que você deseja reutilizar em
todo o site. Você pode até passar valores para tornar seu Mixin mais
flexível.
1
@mixin theme {
2
font-size: 14px;
3
color: #fff;
4 }
139
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.erro {
2
@include theme;
3
background-color: red;
4 }
1
@mixin theme {
2
background-color: $cor;
3
}
5
.erro {
6
@include theme($cor: red);
7 }
140
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
@mixin theme($cor: green) {
2
background-color: $cor;
3
}
5
h1 {
6
@include theme();
7
}
9
.erro {
10
@include theme($cor: red);
11 }
141
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Nested
O Sass permitirá que você aninhe seus seletores CSS de uma maneira
que siga a mesma hierarquia visual do seu HTML. Enquanto em CSS, as
regras são definidas uma a uma (não aninhadas):
.scss .css
1
section {
1
section {
2
padding: 80px;
2
padding: 80px;
3
h2 {
3
}
4
font-size: 32px;
4
section h2 {
5
}
5
font-size: 32px;
6 } 6 }
142
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 5
Bootstrap
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
À medida que você evolui como desenvolvedor frontend, é mais provável
que você use tecnologias que o ajudem a fazer mais escrevendo menos
código. O framework Bootstrap é uma maneira de se conseguir isso.
O que é
Bootstrap é um framework frontend que fornece estruturas de CSS para
a criação de sites e aplicações responsivas de forma rápida e simples.
Ele foi desenvolvido para o Twitter por um grupo de desenvolvedores e
se tornou uma das estruturas de frontend e projetos de código aberto
mais populares do mundo.
143
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
144
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iniciando
Para isso basta colocar a tag <link> dentro da tag <head> e a tag
<script> antes do fechamento </body>.
1
<!DOCTYPE html>
2
<html lang="pt-br">
3
<head>
4
<meta charset="UTF-8" />
5
<meta name="viewport"
6
content="width=device-width, initial-scale=1.0" />
7 ...
145
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
8
...
9
<title>Bootstrap</title>
10
<link
11
href="[Link]
12
5.3.0-alpha1/dist/css/[Link]"
13
rel="stylesheet"
14
crossorigin="anonymous"
15
/>
16
</head>
17
<body>
18
19
<script
20
src="[Link]
21
-alpha1/dist/js/[Link]"
22
crossorigin="anonymous"
23
></script>
24
25
</body>
26 </html>
Pronto! Somente com esses dois CDNs já está tudo pronto para utilizar
os componentes do Bootstrap.
146
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Componentes
Alerts
1
<div class="alert alert-danger" role="alert">
2
Olá, sou um alert do Bootstrap!
3 </div>
147
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Carousel
Navbar
Outra ferramenta que não podemos deixar de citar é o navbar. Com ele, é
possível criar menus de navegação responsivos e com um layout
agradável ao usuário. Também é útil em formulários, além de permitir a
inserção de pedaços de texto.
Card
148
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Pagination
Buttons
1
<button type="button" class="btn btn-danger">
2
Eu sou um botão
3 </button>
Eu sou um botão
149
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Cores
As cores estão disponíveis por meio de variáveis Sass e CSS com o
objetivo de facilitar a personalização dos componentes. As cores no
Bootstrap são definidas dessa forma:
1
<div class="p-3 rounded-3 bg-info">
2
Sou um fundo azul
3 </div>
Para cor de texto aplicamos da mesma forma, só mudar o “bg” para “text”.
Spacing
O Bootstrap contém um sistema de espaçamento que ajuda a manter
uma escala consistente em todo design no site. Tudo que você tem que
saber é a sintaxe para aplicar cada utilidade.
150
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para aplicá-los aos seus elementos, você teria que usar os números
apropriados fornecidos pelo Bootstrap:
1
<div class="p-3 mt-5 rounded-3 bg-info">
2
Sou um fundo azul com margin-top e padding
3 </div>
151
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sizing
O Bootstrap também tem um sistema que define a largura e altura de um
elemento. As utilidades pré-definidas para padding e margin são muito
similares. Você só tem que substituir o “w” por um “h”.
1
<div class="p-3 mt-5 w-25 rounded-3 bg-info">
2
Sou um fundo azul com largura de 25%
3 </div>
Width 25%
Width 50%
Width 75%
Width 100%
Width auto
152
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Responsividade
O container garante que o seu layout vai ficar alinhado corretamente na
página. Ele pode definir as margens laterais da página, ou deixar sem
margens e, também, posiciona o conteúdo no centro da página.
1
<div class="container">
2
...
3 </div>
153
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<div class="container">
2
<div class="row">
3
...
4
</div>
5 </div>
Seu layout pode ter quantas rows forem necessárias. E você pode
colocar rows dentro de rows, também. As rows sempre irão ficar uma
abaixo da outra.
Para criar uma column, você pode criar uma div com os prefixos pré-
definidos pelo Bootstrap, como no exemplo:
154
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<div class="container">
2
<div class="row">
3
<div class="col-md-6"></div>
4
<div class="col-md-6"></div>
5
</div>
6 </div>
Neste exemplo, temos uma linha (.row) com duas colunas (.col-md-6).
155
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Bootstrap Icons é uma biblioteca com mais de 1.800 ícones, nele temos
ícones line e preenchidos para usar em seus projetos. Para a sua
utilização basta adicionar o CND e adicionar a tag “i” com o nome do
ícones que deseja. Você pode ver a lista completa de ícones aqui.
1
<link rel="stylesheet"
2
href="[Link]
3
@1.10.3/font/[Link]"
4 />
1 <i class="bi-alarm"></i>
156
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 6
React
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
tem nas criações de sites. Você está pronto para entrar para o mundo do
O que é
primeira vez em que o usuário acessa a aplicação. Isso faz com que o
157
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
funcionalidades.
React.
158
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
para produção. Será necessário ter o Node na sua máquina para criar um
projeto em React.
159
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Explicando o comando
cd iuricode
code .
160
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Code.
nossa aplicação:
161
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
npm start
[Link]
162
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Estrutura da pasta
Está bem, mas o que exatamente o CRA criou para nós, Iuri? Como dito
anteriormente, o CRA criou um conjunto de ferramentas e
funcionalidades pré-configuradas para a gente iniciar nossa aplicação
React. Na imagem a seguir iremos ver quais foram os conjuntos criados:
163
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Dentro da pasta src temos alguns arquivos que não iremos utilizar na
aplicação, mas antes deletá-los irei explicar sobre os mesmos pois é
sempre bom saber para que servem.
164
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
165
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
[Link]
[Link]
reportWebVitals.j
setupTests.j
[Link]
Além desses arquivos que não serão utilizado por nós, iremos limpar
também os arquivos dentro da pasta public e as importações das
imagens no [Link]
[Link]
[Link]
[Link]
[Link]
[Link]
166
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
JSX
167
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Essa é uma extensão de sintaxe especial e válida para o React, seu nome
vem do JavaScript XML. Normalmente, mantemos o código em HTML,
CSS e JavaScript em arquivos separados. Porém no React, isso funciona
de um modo um pouco diferente.
168
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function App() {
2
return <h1>Sou um título</h1>;
3
}
169
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Alguns editores de código, como Visual Studio Code, podem vir mais
preparados.
Por exemplo: se você utilizar .jsx, pode ser que tenha vantagens no
autocomplete das tags e também no highlight do código.
170
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Após mudar o formato dos arquivos de .js para .jsx teremos o seguinte erro:
Uma coisa muito importante sobre o JSX é que sempre que utilizamos
mais de uma tag HTML no retorno da função, precisamos englobadas em
uma tag pai. No exemplo abaixo é uma demonstração incorreta.
1
function App() {
2
return (
3
<h1>Sou um título</h1>
4
<p>Sou uma descrição</p>
5
);
6
}
171
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function App() {
2
return (
3
<div>
4
<h1>Sou um título</h1>
5
<p>Sou uma descrição</p>
6
</div>
7
);
8
}
Porém nem sempre queremos que o retorno tenha uma tag pai
englobando tudo. Para isso temos o Fragment do React, que nada menos
é uma tag vazia/sem significado.
1
...
2
<>
3
<h1>Sou um título</h1>
4
<p>Sou uma descrição</p>
5
</>
6 ...
172
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Você pode fazer dessa forma também (observe que importamos o React):
1
import React from "react";
3
function App() {
4
return (
5
<[Link]>
6
<h1>Sou um título</h1>
7
<p>Sou uma descrição</p>
8
</[Link]>
9
);
10
}
11
Componentes
173
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<article>
2
<img src="[Link]" alt="Imagem do card" />
3
<div>
4
<h2>Título de um post</h2>
5
<p>Sou apenas uma pequena descrição</p>
6
</div>
7
<a href="[Link]/efront">Acessar post</a>
8 </article>
174
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Até aqui está tudo bem. Mas imagine que queremos 6 (seis) cards iguais
a esse. Normalmente com HTML iremos duplicar esse código em 6 (seis)
vezes, correto?
Agora imagine que por algum motivo seja preciso adicionar uma tag span
para sinalizar a data da postagem. Teríamos que mudar em todos! Pior
ainda, imagine que existe este card em várias páginas em nossa
aplicação. Concordo que iria demorar muito para dar manutenção neste
código, por causa de uma simples alteração?
1
function Card() {
2
return (
3
Aqui vai o código do exemplo anterior
4
);
5
}
175
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import Card from './Card';
3
function App() {
4
return (
5
<div>
6
<Card />
7
<Card />
8
<Card />
9
</div>
10
);
11
}
176
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Bem, tudo que tiver dentro da pasta public pode ser acessado apenas
com o nome e formato do arquivo, diferente do HTML tradicional que
teria que escrever o caminho das pasta até acessar o arquivo desejado.
Mas você deve estar se perguntando “Ok Iuri, mas se caso eu queira que
cada componente do arquivo Card tenha um título, descrição e/ou
imagem diferente das outras?”
Props
177
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import Card from "./Card";
3
function App() {
4
return (
5
<div>
6
<Card title="React" />
7
<Card title="Front-end" />
8
<Card title="iuricode" />
9
</div>
10
);
11
}
178
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function Card(props) {
2
return (
3
<article>
4
<img src="[Link]" alt="Imagem do card" />
5
<div>
6
<h2>{[Link]}</h2>
7
<p>Sou apenas uma pequena descrição</p>
8
</div>
9
<a href="[Link]">Acessar post</a>
10
</article>
11
);
12
}
CSS Modules
Quando criamos nossa aplicação com CRA, foram criados dois arquivos
CSS ([Link] e [Link]) que são responsáveis por adicionar estilos na
aplicação toda. Porém existe um problema com os classNames ao
adicionar estilos dessa forma que foi feito pelo CRA.
179
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Antes:
180
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Depois:
Depois de fazer isso, deverá alterar seu import dos estilos e a utilização
dos classNames para a seguinte forma:
1
import styles from "./[Link]";
3
function App() {
4
return <h1 className={[Link]}>Hello</h1>;
5
}
181
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Você deve estar se perguntando “como que isso funciona por baixo dos
panos?”. O css-modules cria um className único para cada local em
que é utilizado.
Eventos
Manipular eventos com elementos React é muito semelhante ao
tratamento de eventos em elementos DOM. Existem algumas diferenças
sintáticas para as quais devemos atentar:
182
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<button onclick="ativarDesconto()">
2
Ativar Desconto
3 </button>
1
<button onclick={ativarDesconto}>
2
Ativar Desconto
3 </button>
183
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function App() {
2
const exibirAviso = () => {
3
alert("Cuidado!");
5
};
7
return (
8
<button onClick={exibirAviso}>Exibir aviso</button>
9
);
10
}
184
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Hooks
Hooks foram adicionados ao React na versão 16.8.
185
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
usaState
1
import React, { useState } from "react";
3
function App() {
5
// Declaramos a nova variável de estado,
6
// que chamaremos de "count"
7
const [count, setCount] = useState(0);
9
return (
10
<div>
11
<p>Você clicou {count} vezes</p>
12
<button onClick={() => setCount(count + 1)}>
14
Click
15
</button>
16
</div>
17
);
18
}
186
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O estado atual
Uma função que atualiza o estado.
187
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState } from "react";
3
function App() {
4
const [color, setColor] = useState("vermelho");
5
}
188
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Correto:
1
import React, { useState } from "react";
3
function App() {
4
const [color, setColor] = useState("vermelho");
6
return (
7
<div>
8
<h1>Minha cor favorita é {color}!</h1>
9
<button type="button"
10
onClick={() => setColor("azul")}> Mudar para azul
11
</button>
12
</div>
13
);
14
}
189
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState } from "react";
3
function App() {
4
const [color, setColor] = useState("vermelho");
6
return (
7
<div>
8
<h1>Minha cor favorita é {color}!</h1>
9
<button type="button"
10
onClick={() => color("azul")}> Mudar para azul
11
</button>
12
</div>
13
);
14
}
190
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState } from "react";
3
function App() {
4
const [brand, setBrand] = useState("Ford");
5
const [model, setModel] = useState("Mustang");
6
const [year, setYear] = useState("1964");
7
const [color, setColor] = useState("red");
8
}
1
const [car, setCar] = useState({
2
brand: "Ford",
3
model: "Mustang",
4
year: "1964",
5
color: "red",
6 });
191
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
useEffect
1 useEffect(<Função>, <Dependência>)
Por fim, no trecho de código abaixo você vai ver o useEffect usado para
mudar o título de uma página usando como base o estado da variável
‘count’. Note que, como dependência, o useEffect vai utilizar o ‘count’
justamente porque o ‘[Link]’ precisa ser executado novamente
toda vez que o ‘count’ mudar de estado. Portanto, se não houvesse
dependência, a função seria executada somente uma vez ao renderizar o
componente.
192
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState, useEffect } from "react";
3
function App() {
4
const [count, setCount] = useState(0);
6
useEffect(() => {
7
[Link] = `Você clicou ${count} vezes`;
8
});
10
return (
11
<div>
12
<p>Você clicou {count} vezes</p>
13
<button
14
onClick={() => setCount(count + 1)}> Clique aqui
15
</button>
16
</div>
17
);
18
}
Claro que esses não são os únicos Hooks disponíveis no React. Abaixo
deixa a lista dos principais Hook: useState, useEffect, useContext, useRef,
useReducer, useCallbak e useMemo.
193
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
API
Agora que entendemos como funciona os Hooks useState e useEffect já
podemos trazer um exemplo prático da sua utilização. Em nosso exemplo
com os Hooks, teremos um componente que será responsável por listar
os nossos repositórios do GitHub.
1
import React, { useEffect } from "react";
3
function App() {
4
useEffect(() => {
5
async function carregaRepositorios() {
6
const resposta = await fetch(
7
"[Link]
8
);
9 ...
194
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
10
...
11
const repositorios = await [Link]();
12
return repositorios;
13
}
14
15
carregaRepositorios();
16
}, []);
17
return <h1>Retorno da função</h1>;
18
}
195
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState, useEffect } from "react";
3
function App() {
4
const [repositorio, setRepositorio] = useState([]);
6
useEffect(() => {
7
async function carregaRepositorios() {
8
const resposta = await fetch(
9
"[Link]
10
);
11
12
const repositorios = await [Link]();
13
return repositorios;
14
}
15
carregaRepositorios();
16
}, []);
17
18
return <h1>Retorno da função</h1>;
19
}
196
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState, useEffect } from "react";
3
function App() {
4
const [repositorio, setRepositorio] = useState([]);
6
useEffect(() => {
7
async function carregaRepositorios() {
8
const resposta = await fetch(
9
"[Link]
10
);
11
12
const repositorios = await [Link]();
13
setRepositorio(repositorios);
14
}
15
carregaRepositorios();
16
}, []);
17
18
return <h1>Retorno da função</h1>;
19
}
197
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React, { useState, useEffect } from "react";
3
function App() {
4
const [repositorio, setRepositorio] = useState([]);
6
useEffect(() => {
7
async function carregaRepositorios() {
8
const resposta = await fetch(
9
"[Link]
10
);
11
12
const repositorios = await [Link]();
13
setRepositorio(repositorios);
14
}
15 ...
198
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
carregaRepositorios();
3
}, []);
5
return (
6
<ul>
7
{[Link]((repositorio) => (
8
<li key={[Link]}>{[Link]}</li>
9
))}
10
</ul>
11
);
12
}
199
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 7
React Router
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
Iniciando
200
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
npm i react-router-dom
1
import React from "react";
2
import ReactDOM from "react-dom/client";
3
import "./[Link]";
4
import App from "./App";
5
import { BrowserRouter } from "react-router-dom";
7
const root = [Link](
8
[Link]("root")
9
);
10 ...
201
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
7
[Link](
8
<[Link]>
9
<BrowserRouter>
10
<App />
11
</BrowserRouter>
12
</[Link]>
13 );
Criando as rotas
202
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iremos criar um arquivo novo como [Link]. Nele iremos colocar todas
as nossas rotas que queremos. Este arquivo deverá se importado no
[Link] assim como o [Link]. Lembrando que os dois devem estar
dentro do BrowserRouter:
1
...
2
import { BrowserRouter } from "react-router-dom";
3
import AppRoutes from "./routes";
4
import App from "./App";
6
...
7
<BrowserRouter>
8
<AppRoutes />
9
<App />
10
</BrowserRouter>
11 ...
203
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
3
const Home = () => {
4
return <h1>Home</h1>;
5
};
204
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
path: este é o URL para o qual o link nos levará. Este suporte é
semelhante ao suporte to do componente Link que iremos falar no
próximo tópico.
element: contém o elemento que será renderizado quando a página
navegar para essa rota.
1
import { Routes, Route } from "react-router-dom";
3
import Home from "./pages/Home";
4
import Login from "./pages/Login";
5
import Profile from "./pages/Profile";
6 ...
205
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
7
...
8
const AppRoutes = () => {
9
return (
10
<Routes>
11
<Route path="/" element={<Home />} />
12
<Route path="login" element={<Login />} />
13
<Route path="profile" element={<Profile />} />
14
</Routes>
15
);
16
};
17
Como dito, perceba que dentro o “path” passamos o valor que irá
valor pela URL, para a experiência do usuário isso não é legal. Iremos
206
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Navegação de links
Vamos criar alguns links de navegação que vão apontar para algumas
rotas dentro do nosso [Link]. Essas rotas foram passadas para o
[Link] porque queremos que fiquem visíveis em todas as páginas. Para
fazer isso, devemos importar o componente Link. Este é um componente
de link (semelhante à tag <a>) que nos ajuda a navegar entre as rotas
sem passar o valor direto na URL.
1
import React from "react";
2
import { Link } from "react-router-dom";
4
const App = () => {
5
return (
6
<nav>
7
<ul>
8
<li>
9
<Link to="/">Home</Link>
10
</li>
11 ...
207
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
12
...
13
<li>
14
<Link to="/login/efront">Login</Link>
15
</li>
16
<li>
17
<Link to="/profile">Profile</Link>
18
</li>
19
</ul>
20
</nav>
21
);
22
};
23
Rota 404
A página de erro foi criada para que as rotas que não correspondam a
nenhuma das rotas definidas acima sejam atribuídas à página de erro
(essencialmente, esta será nossa página de erro 404 personalizada).
Primeira coisa que iremos fazer é criar uma rota dentro a pasta “pages”,
irei chamar ele de ”[Link]”.
208
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
3
const Error = () => {
4
return <h1>Ops, página não encontrada!</h1>;
5
};
1
...
2
<Route path="*" element={<Error />} />
3 ...
Agora qualquer valor que for acessado na URL que não estiver
configurado dentro do nosso arquivo [Link] será encaminhado para a
página de erro 404 personalizada por nós.
209
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Rotas dinâmicas
Importaremos o useParams para a página Login para que possamos usá-
lo para obter o parâmetro de URL e, em seguida, usar esse parâmetro
para exibir ele na tela. Além disso iremos desestruturar para que
possamos acessar diretamente o parâmetro slug e utilizá-lo dentro do
nosso Login. Dessa forma:
1
import React from "react";
2
import { useParams } from "react-router-dom";
4
const Login = () => {
5
const { slug } = useParams();
7
return <h1>Login {slug}</h1>;
8
};
210
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
211
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
212
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 8
TypeScript
Pegue o café e prepare-se para mais um módulo. Lembre-se
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
valores para uma variável, hora pode receber uma string, hora um number
e isso pode prejudicar a nossa aplicação a medida que ela vai crescendo.
Exemplo: imagina que você tem uma variável chamada “nome” que no
1
let nome = “Iuri”;
2 nome = 12;
1
let nome:string = “Iuri”;
213
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é
Iniciando
214
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
tsc [Link]
Perceba que agora um arquivo [Link] foi criado na pasta raiz do nosso
projeto.
215
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Tipos
String
1
let nome:string = “Iuri”;
2
// Ou
Template string
216
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
let nome:string = “Iuri”;
Boolean
Number
217
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Array
1
let nomes: Array<string> = [
2
‘Iuri’, ‘Eiji’
3 ]
218
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
let nomes: (string | number)[] = [
2
‘Iuri’, 22, ‘Eiji’, 21
3
]
5
// Ou
7
let nomes: Array<string | number> = [
8
‘Iuri’, 22, ‘Eiji’, 21
9 ]
Tuple
1
let pessoa: [number, string] = [
2
2000, ‘Iuri’
3 ]
219
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Enum
Enum numéric
Enum strin
Enum heterogêneo
Enum numérico
220
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
enum Direcao {
2
Norte,
3
Leste,
4
Sul,
5
Oeste,
6 }
1
enum Direcao {
2
Norte, // 0
3
Leste, // 1
4
Sul, // 2
5
Oeste, // 3
6 }
Enum string
221
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
enum Direcao {
2
Norte = “Norte”,
3
Leste = “Leste”,
4
Sul = “Sul”,
5
Oeste = “Oeste”,
6 }
Enum heterogêneo
222
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
enum Direcao {
2
Norte = “OK”,
3
Leste = 1,
4
Sul,
5
Oeste,
6 }
Any
1
let nome:any = “Iuri”;
Da mesma forma, você pode criar um array do tipo any [] se não tiver
certeza sobre os tipos de valores que podem conter essa array.
223
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Void
O void é usado onde não há dados. Por exemplo, se uma função não
retornar nenhum valor, você pode especificar void como tipo de retorno.
1
function mensagem():void {
2
[Link](“iuricode”);
3 }
Never
O tipo never é usado quando você tem certeza de que algo nunca
acontecerá. Por exemplo, você escreve uma função que não retorna ao
seu ponto final.
1
function mensagem():void {
2
while(true) {
3
[Link](“iuricode”);
4
}
5 }
224
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Union
1
let dev: (string | number);
3
dev = 123;
4
dev = ‘iuri’;
Interface
No TypeScript, temos as interfaces que são um conjunto de métodos e
propriedades que descrevem um objeto. As interfaces desempenham a
função de nomear esses tipos e são uma maneira poderosa de definir
“contrato”.
225
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function somar(x, y) {
2
return x + y;
3 }
226
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
interface Pessoa {
2
nome: string;
3
idade: number;
4 }
1
interface Pessoa {
2
nome: string;
3
idade: number;
4
}
6
let dev: Pessoa = {
7
nome: “Iuri”,
8
idade: 22,
9 }
227
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Propriedades opcionais
Nem sempre temos certeza que um dado será exibido ou lido em nossa
aplicação, para isso temos a propriedade opcional do TypeScript, que são
marcadas com um "?". Nesses casos, os objetos da interface podem ou
não definir essas propriedades.
1
interface Pessoa {
2
nome: string;
3
sobrenome?: string;
4
}
6
let dev1: Pessoa = {
7
nome: “Iuri”,
8
sobrenome: “Silva”,
9
} // OK
10
11
let dev2: Pessoa = {
12
nome: “Eiji”,
13 } // OK
228
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Estendendo Interfaces
As interfaces podem estender uma ou mais interfaces, isso é, uma
interface pode ter as propriedades declaradas em uma outra interface.
Isso torna as interfaces e suas propriedades mais flexíveis e reutilizáveis.
1
interface Pessoa {
2
nome: string;
3
idade: number;
4
}
6
interface Pessoa2 extends Pessoa {
7
front: boolean;
8
}
10
let dev2: Pessoa2 = {
11
nome: “Eiji”,
12
idade: 21,
13
front: true
14 }
229
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
TypeScript no React
Agora que aprendemos o tipos que temos no TypeScript e como utilizar
ele no JavaScript nativo, iremos aplicar esses conhecimentos em uma
aplicação feita com React.
1
import React, { useState, useEffect } from "react";
3
function App() {
4
const [repositorio, setRepositorio] = useState([]);
6
useEffect(() => {
7
async function carregaRepositorios() {
8
const resposta = await fetch(
9
"[Link]
10
);
11
12
const repositorios = await [Link]();
13
setRepositorio(repositorios);
14
}
15 ...
230
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
16
17
carregaRepositorios();
18
}, []);
19
20
return (
21
<ul>
22
{[Link]((repositorio) => (
23
<li key={[Link]}>{[Link]}</li>
24
))}
25
</ul>
26
);
27
}
Instalando
@types/react-dom @types/jest
231
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
{
2
"compilerOptions": {
3
"target": "es5",
4
"lib": [
5
"dom",
6
"[Link]",
7
"esnext"
8
],
9 ...
232
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
10
"allowJs": true,
11
"skipLibCheck": true,
12
"esModuleInterop": true,
13
"allowSyntheticDefaultImports": true,
14
"strict": true,
15
"forceConsistentCasingInFileNames": true,
16
"noFallthroughCasesInSwitch": true,
17
"module": "esnext",
18
"moduleResolution": "node",
19
"resolveJsonModule": true,
20
"isolatedModules": true,
22
"noEmit": true,
23
"jsx": "react-jsx"
24
},
25
"include": [
26
"src"
27
]
28 }
233
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
TSX
Agora para que o TypeScript entenda que nossos arquivo contém código
em TypeScript, precisamos mudar o formato deles de .jsx para .tsx
234
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
235
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para resolver isso iremos criar uma Interface e tipar o “id” e “name”:
1
interface IRepositorios {
2
id: number;
3
name: string;
4 }
236
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Sei que essa foi uma forma básica de como tipar dados em aplicações
React, mas com esse exemplo conseguimos ter uma noção melhor de
como funciona o TypeScript.
237
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 9
styled-components
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
238
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Vantagens
239
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iniciando
240
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
[Link]
"resolutions": {
"styled-components": "^5"
Aplicando estilos
1
import styled from "styled-components";
3
const Title = styled.h1`
4
font-size: 1.5em;
5
text-align: center;
6
color: palevioletred;
7
`;
9
function App() {
10
return <Title>Hello World!</Title>;
11
}
241
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Hello World!
1
const Title = styled.h1`
2
font-size: 1.5em;
3
text-align: center;
4
color: palevioletred;
5 `;
242
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Hello World!
[Link]
Estilos dinâmicos
1
const Title = styled.h1`
2
font-size: 1.5em;
3
text-align: center;
4
color: ${(props) => (
5
[Link] ? "green" : "palevioletred"
6
)};
7 `;
243
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
function App() {
2
return (
3
<div>
4
<Title iuricode>Hello World!</Title>
5
<Title>Hello World!</Title>
6
</div>
7
);
8 }
Hello World!
Hello World!
244
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Estendendo estilos
O styled-components também permite estender estilos entre os
componentes de forma bem simples.
1
const Title = styled.h1`
2
font-size: 1.5em;
3
text-align: center;
4
color: palevioletred;
5
`;
7
const Title2 = styled(Title)`
8
font-size: 4.5em;
9 `;
Hello World!
Hello World!
245
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Arquivos separados
“Okay Iuri, mas é estranho colocar os estilos no mesmo arquivo da lógica
da aplicação!” É, de fato é mesmo! Para resolver isso, o styled-
components nos dá a possibilidade de separar a lógica do estilo, isso é,
criando arquivos separados.
1
import styled from "styled-components";
3
export const Title = styled.h1`
4
font-size: 1.5em;
5
text-align: center;
6
color: palevioletred;
7 `;
Feito isso basta agora importar dessa forma no nosso arquivo [Link]
246
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Okay Iuri, mas toda vez que eu tiver um componente/elemento vou ter
que importar ele assim? Se todos os elementos tiver dentro de um
elemento pai não será preciso criar componente por componente no
styled-components, pois ele funciona da mesma forma do Sass, basta
chamar o elemento pai.
1
<Title>
2
Hello World! <span>texto maior</span>
3 </Title>
Para estilizar a tag span bata chamar ele dentro do componente Tiltle,
dessa forma:
247
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import styled from "styled-components";
3
export const Title = styled.h1`
4
font-size: 1.5em;
5
text-align: center;
6
color: palevioletred;
8
span {
9
font-size: 4.5em;
10
}
11 `;
248
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { createGlobalStyle } from "styled-components";
3
export const GlobalStyle = createGlobalStyle`
4
body {
5
margin: 0;
6
padding: 0;
7
font-family: Open-Sans, Helvetica, Sans-Serif;
8
background-color: #121212;
9
}
10 `;
1
import React from "react";
2
import ReactDOM from "react-dom/client";
3
import App from "./App";
4
import { GlobalStyle } from "./[Link]";
6 ...
249
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
7
const root = [Link](
8
[Link]("root")
9
);
10
[Link](
11
<[Link]>
12
<GlobalStyle />
13
<App />
14
</[Link]>
15 );
250
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 10
Tailwind CSS
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
Neste módulo, vamos aprender sobre um dos frameworks CSS que mais
estão em alta no mercado, que tem como objetivo auxiliar na construção
e design de páginas feita com HTML, React e outras bibliotecas JS.
O que é
251
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<p className="text-lg font-medium">
2
Sou um texto estilizado pelo Tailwind
3 </p>
Iniciando
O Tailwind normalmente recomenda que você instale por meio de um
gerenciador de pacotes para obter a funcionalidade completa.
252
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
/** @type {import('tailwindcss').Config} */
3
[Link] = {
4
content: ["./src/**/*.{js,jsx,ts,tsx}"],
5
theme: {
6
extend: {},
7
},
8
plugins: [],
9 };
1
@tailwind base;
2
@tailwind components;
3 @tailwind utilities;
253
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
const App = () => {
2
return <p className="text-3xl text-red-500">Oi</p>
3
}
npm start
254
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Responsividade
No Tailwind é utilizado a abordagem de mobile-first, similar ao que temos
no Bootstrap, e isto quer dizer que quando um estilo é adicionado ao
código, ele é aplicado da menor para a maior resolução.
255
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
const App = () => {
2
return (
3
<p className="text-red-500 md:text-indigo-900">
4
Oi
5
</p>
6
);
7
};
256
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
const App = () => {
2
return (
3
<p className="text-red-500 hover:text-indigo-900">
4
Oi
5
</p>
6
);
7
};
Dark mode
O Dark Mode é uma opção que está se tornando cada vez mais comum
criar uma versão escura do seu site para acompanhar o design padrão.
257
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O Tailwind inclui uma variante “dark” que permite estilizar seu site de
maneira diferente quando o modo escuro está ativado:
1
const App = () => {
2
return (
3
<button className="bg-white dark:bg-gray-900">
4
Sou um botão
5
</button>
6
);
7
};
Diretivas
As diretivas são regras CSS (at-rules) personalizadas do framework para
usar no CSS e ter acesso a funcionalidades especiais do Tailwind. As
diretivas são três:
258
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
@tailwind
1
@tailwind base;
2
@tailwind components;
3
@tailwind utilities;
4 @tailwind variants;
@layer
259
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
@layer base {
2
h1 {
3
@apply text-2xl;
4
}
6
h2 {
7
@apply text-xl;
8
}
9 }
@apply
1
.botao-iuricode {
2
@apply text-base font-medium p-3;
3 }
260
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<button className="botao-iuricode">
2
Sou um botão
3 </button>
Extra
Cores
261
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Padding e Margin
Para aplicá-los aos seus elementos, você teria que usar os números
apropriados fornecidos pelo Tailwind:
262
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<button className="p-4 bg-slate-400">
2
Sou um botão
3 </button>
Sizing
263
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
264
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 11
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
265
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iniciando
Para iniciar com React Hook Form não tem segredo. A instalação requer
apenas um único comando e você está pronto para começar.
1
import { useForm } from "react-hook-form";
3
export default function App() {
4
const {
5
register,
6
handleSubmit,
7
watch,
8
formState: { errors },
9
} = useForm();
10
11
const onSubmit = (data) => [Link](data);
12 ...
266
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
13
...
14
[Link](watch("example"));
15
16
return (
17
<form onSubmit={handleSubmit(onSubmit)}>
18
<input defaultValue="test"
19
{...register("example")} />
20
21
<input {...register("exampleRequired",
22
{ required: true })} />
23
24
{[Link] &&
25
<span>This field is required</span>}
26
27
<input type="submit" />
28
</form>
29
);
30 }
267
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Esse é um formulário simples sem utilizar React Hook Form. Agora iremos
aplicar os recursos da biblioteca para criar as validações. Mas perceba
que a forma que está não sabemos o que o usuário irá colocar em nosso
input, ou se até mesmo ele irá colocar algo.
1
export default function App() {
2
return (
3
<form>
4
<input />
5
<input type="submit" />
6
</form>
7
);
8 }
Registrando campo
268
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Registro
seguinte forma:
269
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { useForm } from "react-hook-form";
3
export default function App() {
4
const { register } = useForm();
6
return (
7
<form>
8
<input {...register("nome")} />
9
<input type="submit" />
10
</form>
11
);
12 }
Está tudo ok, mas ainda não falamos/chamamos a função que receberá
os dados do formulário se a validação do formulário for bem-sucedida.
1
...
2
<form onSubmit={handleSubmit()}>
3 ...
270
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Agora vamos criar a função que irá mostrar o que foi digitado no input
1
...
2
<form onSubmit={handleSubmit(submitConsole)}>
3 ...
Dessa forma já está tudo pronto para ver o que foi digitado no campo e
271
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { useForm } from "react-hook-form";
3
export default function App() {
4
const { register, handleSubmit } = useForm();
6
const submitConsole = (data) => [Link](data);
8
return (
9
<form onSubmit={handleSubmit(submitConsole)}>
10
<input {...register("nome")} />
11
<input type="submit" />
12
</form>
13
);
14 }
Uma coisa bem simples que podemos fazer é adicionar um valor padrão
para nosso input. Dependendo do formulário essa função pode ser muito
útil e de grande ajuda na experiência do usuário. A função defaultValue
que iremos usar não é importado do hook useForm, basta apenas chamar.
272
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Aplicando validação
1
<input {...register("nome", { required: true })} />
2
<input {...register("senha",
3
{ required: true, minLength: 6})}
4 />
Agora você deve estar se perguntando: “Ok Iuri, mas tudo isso da para
fazer só com HTML sem precisar de uma biblioteca”.
De fato! Mas tenha calma que ainda estamos no meio do caminho sobre
validações em formulários.
273
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Agora para adicionar a validação temos que chamar nosso objeto “erros”
e passar o nome do nosso campo que adicionamos na função register e
logo em seguida a mensagem que queremos mostrar na tela.
1
<input {...register("nome", { required: true })} />
274
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<input {...register("senha",
2
{ required: true, minLength: 6})}
3
/>
4
{[Link] && <p>Coloque sua senha!</p>}
5
{[Link]?.type === "minLength" &&
Por fim, a validação de padrão pode ser usada para definir o padrão regex
para um campo de formulário.
1
<input {...register("senha",
2
{required: true, minLength: 6, pattern: /[a-z]/,})}
3 />
275
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
{[Link]?.type === "pattern" && (
2
<p>Escreva em letras minúsculas!</p>
3 )}
Criando componentes
Criar um componente de input é bem simples, única coisa que precisamos
e passar o register e o nome que irei dar a ele pelo parâmetros.
1
import React from "react";
2
import { useForm } from "react-hook-form";
4
const Input = ({ label, register, required }) => {
5
return <input {...register(label, { required })} />
6
};
7 ...
276
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
const App = () => {
3
const { register, handleSubmit } = useForm();
4
const onSubmit = (data) => [Link](data);
6
return (
7
<form onSubmit={handleSubmit(onSubmit)}>
8
<Input label="Nome" register={register} required />
9
<input type="submit" />
10
</form>
11
);
12
};
13
Watch
Este método observará o input e retornará seu valor. Isso é útil para
renderizar o valor de entrada e para determinar o que renderizar por
condição.
277
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1 [Link](watch("nome"));
Agora tudo que for digitado no campo nome irá aparecer no console.
Focus
278
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
useEffect(() => {
2
setFocus("nome");
3 }, [setFocus]);
Pronto!
Form Provider
Até agora aprendemos a como criar os campos e validar eles com o
React Hook Form, mas temos um problema. Caso um dos nossos inputs
seja um componente, isso é, esteja em um arquivo separado, não iremos
conseguir aplicar a validação., pois o React Hook Form entende que o
componente input não faz parte do formulário, e sim algo independente.
279
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { useForm } from "react-hook-form";
3
function Senha() {
4
const { register } = useForm();
5
return <input {...register("senha")} />;
6
}
8
const onSubmit = (data) => [Link](data);
10
function App() {
11
const { register, handleSubmit } = useForm();
12
13
return (
14
<form onSubmit={handleSubmit(onSubmit)}>
15
<input {...register("nome")} />
16
<Senha />
17
<input type="submit" />
18
</form>
19
);
20
}
21
280
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para resolver isso utilizamos o Form Provider, que basicamente vai fazer
que o formulário interprete que o componente Input faz parte do mesmo
contento do formulário.
1
import {
2
useForm, FormProvider, useFormContext
3 } from "react-hook-form";
1
function Senha() {
2
const { register } = useFormContext();
3
return <input {...register("senha")} />;
4 }
281
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<FormProvider {...methods}>
2
...
3 </FormProvider>
282
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
<form onSubmit={[Link](onSubmit)}>
3
<input {...[Link]("nome")} />
4 ...
283
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 12
Radix UI
Pegue o café e prepare-se para mais um módulo. Lembre-se
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
Iniciando
284
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
2
import * as Popover from “@radix-ui/react-popover”;
4
const App = () => (
5
<h2>Radix</h2>
6
);
285
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
2
import * as Popover from “@radix-ui/react-popover”;
4
const App = () => (
5
<[Link]>
6
<[Link]>More info</[Link]>
7
<[Link]>
8
<[Link]>
9
Some more info…
10
<[Link] />
11
</[Link]>
12
</[Link]>
13
</[Link]>
14
);
15
286
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Aplicando estilos
1
import React from "react";
2
import * as Popover from “@radix-ui/react-popover”;
4
const App = () => (
5
<[Link]>
6
<[Link] className="PopoverTrigger">
7
More info
8
</[Link]>
9
<[Link]>
10
<[Link] className="PopoverContent">
11
Some more info…
12
<[Link] className="PopoverArrow" />
13
</[Link]>
14
</[Link]>
15
</[Link]>
16
);
17
287
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.PopoverTrigger {
2
display: inline-flex;
3
align-items: center;
4
justify-content: center;
5
border-radius: 4px;
6
padding: 0 15px;
7
font-size: 15px;
8
line-height: 1;
9
font-weight: 500;
10
height: 35px;
11
background-color: white;
12
color: var(--violet11);
13
box-shadow: 0 2px 10px var(--blackA7);
14
margin-top: 150px;
15
}
16
17
.PopoverTrigger:hover {
18
background-color: var(--mauve3);
19
}
20
21
.PopoverTrigger:focus {
22
box-shadow: 0 0 0 2px black;
23 }
288
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
24
.PopoverContent {
25
border-radius: 4px;
26
padding: 20px;
27
width: 260px;
28
font-size: 15px;
29
line-height: 1;
30
color: var(--violet11);
31
background-color: white;
32
}
33
34
.PopoverContent:focus {
35
outline: none;
36
}
37
38
.PopoverArrow {
39
fill: white;
40 }
1
@import "@radix-ui/colors/[Link]";
2
@import "@radix-ui/colors/[Link]";
3 @import "@radix-ui/colors/[Link]";
289
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Cores
Okay, já entendemos como utilizar as cores da paleta de cores do Radix,
basta importar e chamar elas em nosso código. Porém vale a pena
abordar um pouco mais sobre elas, ainda mais se você estiver iniciando.
290
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Ícones
291
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
import { RocketIcon } from "@radix-ui/react-icons";
4
const App = () => (
5
...
6
<[Link] className="PopoverTrigger">
7
<RocketIcon /> More info
8
</[Link]>
9
...
10
);
11
292
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Componentes
Já entendemos como utilizar o componente do Radix, mas para fixar o
aprendizado iremos ver a utilização de mais um componente dessa
biblioteca maravilhosa. Caso você queira ver a lista completa dos
componentes disponíveis basta clicar aqui.
Slider
293
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
import * as Slider from "@radix-ui/react-slider";
3 ...
componente Slider:
1
...
2
<form>
3
<[Link]
4
className="SliderRoot"
5
defaultValue={[50]}
6
max={100}
7
step={1}
8
aria-label="Volume"
9
>
10
<[Link] className="SliderTrack">
11
<[Link] className="SliderRange" />
12
</[Link]>
13
<[Link] className="SliderThumb" />
14
</[Link]>
15
</form>
16 ...
294
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Aplicando CSS
295
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
.SliderRoot {
2
position: relative;
3
display: flex;
4
align-items: center;
5
user-select: none;
6
touch-action: none;
7
width: 200px;
8
height: 20px;
9 }
10
.SliderTrack {
11
background-color: var(--blackA10);
12
position: relative;
13
flex-grow: 1;
14
border-radius: 100px;
15
height: 3px;
16 }
296
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
17
.SliderRange {
18
position: absolute;
19
background-color: white;
20
border-radius: 100px;
21
height: 100%;
22 }
23
.SliderThumb {
24
display: block;
25
width: 20px;
26
height: 20px;
27
background-color: white;
28
box-shadow: 0 2px 10px var(--blackA7);
29
border-radius: 10px;
30 }
297
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
31
.SliderThumb:hover {
32
background-color: var(--violet3);
33
}
34
35
.SliderThumb:focus {
36
outline: none;
37
box-shadow: 0 0 0 5px var(--blackA8);
38 }
1
@import “@radix-ui/colors/[Link]”;
2 @import “@radix-ui/colors/[Link]”;
298
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
299
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 13
Storybook
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
Iniciando
300
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
301
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
uma nova guia do navegador e você será saudado por uma tela de boas-
vindas.
casso é o [Link]
302
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
303
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Estrutura do Storybook
Agora vamos entender melhor o que foi gerado pelo Storybook em nossa
aplicação antes de documentar algo.
1
import { Meta } from "@storybook/addon-docs";
3
<Meta title="Example/Introduction" />
5 # eFront
304
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Storybook do zero.
305
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Criando componente
Diferente do padrão do Storybook que adicionar os componentes na
pasta stories, iremos adicionar nosso componente em uma pasta criada
por nós. Dentro da pasta src irei criar uma pasta chamada “components”,
e dentro de components teremos dois arquivos: [Link] e
[Link]
1
import { Meta } from "@storybook/addon-docs";
3
<Meta title="Components/Button" components={Button}/>
5 # Button
306
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Mas tenha calma, ele ainda não irá aparecer em nossa documentação.
Lembra que mudamos nosso componente da pasta stories para
components? Então, agora precisamos avisar aos Storybook onde ele irá
encontrar os componente que serão documentados por ele.
307
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
308
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
3
const Button = () => {
4
return <button>Sou um botão</button>;
5
};
Documentando o componente
Agora iremos documentar o nosso componente. Primeira coisa que
iremos fazer e importar e chamar o componente em nosso arquivo
[Link].
1
import { Meta } from "@storybook/addon-docs";
2
import Button from "./Button";
4
<Meta title="Components/Button" components={Button}/>
5
# Button
6 <Button />
309
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import {
2
Meta, Story, Canvas, ArgsTable
3 } from "@storybook/addon-docs";
310
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import {
2
Meta, Story, Canvas, ArgsTable
3
} from "@storybook/addon-docs";
4
import Button from "./Button";
6
<Meta
7
title="Components/Button" components={Button}
8
/>
10
# Button
11
12
<ArgsTable of={Button} />
13
14 <Button />
311
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from "react";
3
const Button = ({ label }) => {
4
return <button>{label}</button>;
5
};
7
export default Button;
9
[Link] = {
10
label: "Sou um texto padrão",
11 };
312
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para isso iremos utilizar o PropTypes para a chegagem do tipo e dizer que
nosso label é do tipo string. Para a sua utilização precisamos instalar o
pacote via comando.
1
import React from "react";
2
import PropTypes from "prop-types";
4
const Button = ({ label }) => {
5
return <button>{label}</button>;
6
};
8
export default Button;
10 ...
313
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
11
...
12
13
[Link] = {
14
label: [Link],
15
};
16
17
[Link] = {
18
label: "Sou um texto padrão",
19 };
314
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
315
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
<Canvas>
2
<Story
3
name="Story Button"
4
args={{
5
...[Link]
6
}}
7
>
8
{(args) => <Button {...args} />}
9
</Story>
10 </Canvas>
316
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
317
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Veremos aqui o código gerado pelo Storybook (menos o CSS), veja que
agora que aprendemos não é muito difícil de saber o que cada coisa faz.
Arquivo [Link]:
1
import React from "react";
2
import { Button } from "./Button";
4
export default {
5
title: "Components/Button",
6
component: Button,
8
argTypes: {
9
backgroundColor: { control: "color" },
10
},
11
};
12
13
const Template = (args) => <Button {...args} />;
14
15
export const Primary = [Link]({});
16
17
[Link] = {
18
primary: true,
19
label: "Button",
20 };
318
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Arquivo [Link]:
1
import React from "react";
2
import PropTypes from "prop-types";
3
import "./[Link]";
5
export const Button = ({
6
primary, backgroundColor, size, label, ...props
7
}) => {
8
const mode = primary ? "storybook-button--primary"
9
: "storybook-button--secondary";
10
11
return (
12
<button
13
className={["storybook-button",
14
`storybook-button--${size}`, mode].join(" ")}
15
style={backgroundColor && { backgroundColor }}
16
{...props}
17
>
18
{label}
19
</button>
20
);
21
};
22 ...
319
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
25
...
26
[Link] = {
27
primary: [Link],
28
backgroundColor: [Link],
29
size: [Link](["small", "medium", "large"]),
30
label: [Link],
31
onClick: [Link],
32
};
33
34
[Link] = {
35
backgroundColor: null,
36
primary: false,
37
size: "medium",
38
onClick: undefined,
39 };
320
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
321
módulo 14
Cypress
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
322
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Iniciando
Após o comando cypress open irá abrir a seguinte tela falando sobre os
novos recursos do Cypress e pedindo para você clicar em “Continue”.
323
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
selecionar qual será o nosso tipo de teste. Iremos utilizar “E2E Testing”.
324
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Na nova tela será solicitado para escolher qual navegador você quer
325
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
326
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Por último ele irá falar se você quer rodar um teste de exemplo.
Basicamente este exemplo irá visitar uma URL do site de exemplo do
Cypress, porém o mais legal de tudo é quando executamos o teste.
Conseguimos um ter uma ideia de como funciona os testes no Cypress.
327
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Você terá acesso ao código do teste na pasta cypress criado pelo próprio
Cypress durante a configuração. Além desta pasta, o Cypress criou o
arquivo [Link] na raiz do nosso projeto.
Já que citei nosso projeto, vamos ver de fato o que é ele antes de testar.
328
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
describe("Cadastrando conta", () => {
2
beforeEach(() => {
3
[Link]("[Link]
4
});
5 });
329
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
várias describe() no mesmo arquivo. Além disso, uma describe() pode ser
Em nosso próximo teste não iremos utilizar o describe() mas sim o it().
330
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
describe("Cadastrando conta", () => {
2
beforeEach(() => {
3
[Link]("[Link]
4
});
6
it("Formulário renderizado com sucesso", () => {
7
[Link]("form");
8
});
9 });
331
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Vamos fazer isso por etapa, primeiro irei criar o teste utilizando os
recursos já utilizado até aqui: describe, it e get.
1
...
2
describe("Se o formulário estiver completo", () => {
3
it("Deve cadastrar com sucesso", () => {
4
[Link]("input[placeholder="Nome"]");
5
[Link]("input[placeholder="Sobrenome"]");
6
[Link]("input[placeholder="Email"]");
7
[Link]("select");
8
[Link]("button");
9
});
10
});
11 ...
Se a gente rodar este teste não teremos nenhum erro, porém a única
coisa que estamos fazendo é verificar se o elemento estão na tela.
332
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
[Link]("input[placeholder="Nome"]")
3
.type("Iuri");
4
[Link]("input[placeholder="Sobrenome"]")
5
.type("Silva");
6
[Link]("input[placeholder="Email"]")
7
.type("iuricode@[Link]");
8 ...
333
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
[Link]("select").select("Básico");
3 ...
Agora iremos fazer com que nosso teste clique no botão “Confirmar”.
1
...
2
[Link]("button").contains("Confirmar").click();
3 ...
334
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
...
2
[Link]("#add-profile-btn").click();
3
[Link]("input[placeholder="Nome do perfil"]")
4
.type("iuricode");
5 ...
de um ID no CSS.
1
...
2
[Link]("window:alert", (str) => {
3
expect(str).[Link]("Registrado com sucesso!");
4
});
5 ...
335
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O [Link] é responsável por capturar eventos, seja uma alerta, seja uma
336
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
describe("Cadastrando conta", () => {
2
beforeEach(() => {
3
[Link]("[Link]
4
});
6
it("Formulário renderizado com sucesso", () => {
7
[Link]("form");
8
});
10
describe("Se o formulário estiver completo", () => {
11
it("Deve cadastrar com sucesso", () => {
12
[Link]("input[placeholder="Nome"]").type("Iuri");
13
[Link]("input[placeholder="Sobrenome"]")
14
.type("Silva");
15
[Link]("input[placeholder="Email"]")
16
.type("iuricode@[Link]");
17
[Link]("select").select("Básico");
18
[Link]("#add-profile-btn").click();
19
[Link]("input[placeholder="Nome do perfil"]")
20
.type("iuricode");
21
[Link]("button").contains("Confirmar").click();
22 ...
337
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
23
...
24
[Link]("window:alert", (str) => {
25
expect(str).[Link]("Registrado com sucesso!");
26
});
27
});
28
});
29 });
testes do front-end, mas sem dúvida após executar este passo a passo,
você terá uma boa base de como utilizar Cypress em grandes projetos.
338
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 15
[Link]
Pegue o café e prepare-se para mais um módulo. Lembre-se
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
O que é
Iniciando
339
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Veja que a única diferença está no “next” que no caso dos projetos feitos
em React é escrito “react” no lugar.
Estrutura
Após rodar nosso comando e o Node criar nossa aplicação, teremos a
seguinte estrutura de pastas e arquivos:
340
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
341
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
“Okay Iuri, mas para que queremos que a nossa aplicação seja
renderizada do lado do servidor?”
342
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Como toda renderização é feita pelo lado do cliente, para que o conteúdo
da página seja “mostrado” precisamos acessar e esperar a renderização.
Isso acaba dificultando a indexação dos navegadores, pois não é
possível recomendar o conteúdo se ele não “existe” naquele momento.
Isso é diferente com o Next, pois todo o conteúdo (HTML) já está sendo
apresentado no código-fonte da nossa página. Não é preciso esperar o
JavaScript mostrar o conteúdo na página.
343
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
344
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Na pasta pages temos o arquivo _app.js. O [Link] usa este arquivo para
inicializar as páginas.
345
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Dentro da pasta pages temos a pasta api que contém o arquivo [Link]
Está rota fornece uma solução para criar sua API com [Link], mas fique
tranquilo que teremos um tópico para abordar este tema.
Por últimos vamos falar sobre o arquivo _document.js. Este arquivo não
existe em nossa aplicação mas ela pode ser criada no mesmo diretório
do arquivo _app.js.
346
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Rotas
347
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Dessa forma tudo que for componente, estilos CSS e entre outros, devem
estar fora da pasta pages. Para não ficar criando várias pastas na raiz do
projeto, podemos criar a pasta “src” e adicionar as rotas, styles e
componentes dentro dele, pois o Next suporta/entende esta pasta.
Mas fique tranquilo que o Next criou uma solução para personalizar as
rotas de erros de uma forma bem simples e fácil.
348
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para criar uma página 404 personalizada, você pode criar um arquivo
[Link]. Este arquivo é gerado estaticamente no momento da compilação.
1
export default function Custom404() {
2
return <h1>Página não encontrada</h1>;
3 }
Para finalizar este tópico vamos falar sobre rotas dinâmicas no Next.
349
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para definir rotas dinâmicas usamos colchetes nos nomes dos arquivos
que queremos como rotas. Exemplo: [id].js. Esse id é o id do parâmetro
que você irá receber na rota.
Como podemos ver logo acima, temos um arquivo que contém o nome
[id] na qual id será o parâmetro que vamos receber dessa rota.
350
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para capturar o valor dessa rota acessada pelo usuário, podemos usar o
hook useParams, que nos fornece uma propriedade chamada query que
é onde ficará armazenada uma propriedade com o nome que
escolhemos para o arquivo (que nesse caso foi id), e é nessa propriedade
que podemos ter acesso a rota que o usuário acessou.
1
import { useRouter } from "next/router";
3
export default function Posts() {
4
const router = useRouter();
5
const parametro = [Link];
7
return <h1>{parametro}</h1>;
8 }
351
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
API Reference
Como você viu no tópico anterior usamos um recurso do Next, o
useRouter. Agora neste tópico iremos abordar os recursos mais utilizados
pela comunidade.
1
import { useRouter } from "next/router";
3
export default function Posts() {
4
const router = useRouter();
5
const parametro = [Link];
7
return <h1>{parametro}</h1>;
8 }
352
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import Link from "next/link";
2
3
function Home() {
4
return (
5
<ul>
6
<li>
7
<Link href="/">Home</Link>
8
</li>
9
<li>
10
<Link href="/blog">Blog</Link>
11
</li>
12
</ul>
13
)
14
}
15
353
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import Head from "next/head";
2
3
function IndexPage() {
4
return (
5
<div>
6
<Head>
7
<title>Título da página</title>
8
</Head>
9
<p>eFront</p>
10
</div>
11
)
12
}
13
354
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import Image from "next/image";
2
import profile from "../public/[Link]";
4
function Profile() {
5
return (
6
<Image
7
src={profile} alt="Foto usuário"
8
width={300}
9
height={300}
10
/>
11
)
12
}
355
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Rotas API
Agora vamos entender melhor o que são Rotas API no [Link].
Se você abrir a pasta pages no diretório raiz do projeto, deverá ver uma
pasta api nela. A pasta api contém um exemplo de rota API nomeada
[Link] com o seguinte conteúdo:
1
export default function handler(req, res) {
2
[Link](200).json({ name: 'John Doe' })
3 }
356
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Para que uma rota de API funcione, você precisa exportar uma função
como padrão (request handler ) que então recebe os seguintes
parâmetros
Obs: da mesma forma que é criado uma rota dinâmica na pasta pages, é
a forma para criar uma rota API dinâmica.
Data Fetching
357
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
export async function getStaticProps(context) {
2
const res = await fetch(`[Link]
3
const data = await [Link]()
4
5
if (!data) {
6
return {
7
notFound: true,
8
}
9
}
10
11
return {
12
props: {},
13
}
14 }
358
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
export async function getServerSideProps(context) {
2
const res = await fetch(`[Link]
3
const data = await [Link]()
4
5
if (!data) {
6
return {
7
notFound: true,
8
}
9
}
10
11
return {
12
props: {},
13
}
14 }
359
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
360
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
módulo 16
Bônus
Pegue o café e prepare-se para mais um módulo. Lembre-se
de que, ao final de cada módulo, você pode avaliar seus
conhecimentos por meio de um questionário no Notion.
@iuricode
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Introdução
Vite
361
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Diferenças
Vamos dar uma olhada em algumas das principais diferenças entre essas
duas ferramentas.
362
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
webpack.
mais rapidamente.
atualizado.
Permite que você escolha como deseja configurar seu projeto, dando
mais rápido, mais leve e mais flexível para trabalhar com outras
tecnologias modernas.
363
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
React Query
No módulo de JavaScript abordamos o Axios, que é uma forma de
consumir dados da API, assim como o fetch que já é algo nativo da
linguagem JavaScript para consumo de dados. Porém a melhor forma de
consumir APIs em aplicações React é o React Query.
Instalação de Config
364
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import React from 'react';
2
import ReactDOM from 'react-dom';
3
import {
4
QueryClient, QueryClientProvider
5
} from 'react-query';
6
import App from './App';
8
const queryClient = new QueryClient();
10
[Link](
11
<[Link]>
12
<QueryClientProvider client={queryClient}>
13
<App />
14
</QueryClientProvider>
15
</[Link]>,
16
[Link]('root')
17 );
365
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Buscando dados
1
import { useQuery } from 'react-query';
2
import axios from 'axios';
4
const fetchAllPokemon = async () => {
5
const response = await [Link](
6
'[Link]
7
);
8
return [Link];
9
};
10
11
function PokemonList() {
12
const {
13
data, isLoading, error
14
} = useQuery('pokemonList', fetchAllPokemon);
15 ...
366
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Carregamento e error
1
if (isLoading) return <p>Carregando...</p>
367
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
return (
2
<ul>
3
{[Link]((pokemon) => (
4
<li key={[Link]}>{[Link]}</li>
5
))}
6
</ul>
7 );
“Okay Iuri, mas o exemplo você está utilizando o Axios para consumir a
nossa API”.
368
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Conclusão
Ele também fornece alguns hooks e eventos para mutação e query para
lidar com erros e outros estados dos efeitos colaterais, o que remove a
necessidade de usar hooks como useState e useEffect e os substitui por
algumas linhas com React Query.
369
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Node
No módulo de React, utilizamos o Node como base para a construção da
aplicação, mas muitas vezes não exploramos detalhadamente o papel do
Node neste contexto, e é exatamente que isso que faremos neste tópico.
Abordaremos sobre o gerenciamento de pacotes.
370
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
NPM
npm install
371
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
372
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
npm update
Executando tarefas
373
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Por exemplo:
{
"scripts": {
"start-dev": "node lib/server-development",
"start": "node lib/server-production"
}
}
374
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
375
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
[Link]
376
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
377
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
"name": "naped",
"version": "0.1.0",
"lockfileVersion": 2,
"requires": true,
"packages": {
...
378
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
"node_modules/@ampproject/remapping": {
"version": "2.2.0",
"resolved": "https:/...",
"integrity": "sha512-RMP1eZuhxH5Jc26w==",
"peer": true,
"dependencies": {
...
},
"engines": {
"node": ">=6.0.0"
},
...
[Link]
379
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
{}
Está vazio! Não existem campos fixos obrigatórios que devem ser
incluídos no arquivo [Link] para uma aplicação. A única exigência
é que ele siga o formato JSON. Caso contrário, programas que tentem
acessar as propriedades de forma programática não terão sucesso.
{
"name": "test-project"
}
380
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
"name": "test-project",
"version": "1.0.0",
"main": "src/[Link]",
"private": true,
"scripts": {
...
},
"dependencies": {
...
},
"devDependencies": {
...
},
"engines": {
...
},
"browserslist": [...]
381
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Todas essas propriedades são usadas tanto pelo NPM quanto por outras
ferramentas para a gestão e execução da aplicação.
382
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
383
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
i18n
"i18n" é uma abreviação para "internacionalização". É um processo
usado para tornar um software fácil de ser adaptado para diferentes
idiomas e regiões do mundo. Isso significa projetar o software de forma
que ele possa exibir texto, datas, números e outros elementos de acordo
com as preferências culturais de cada região. Dessa forma, mais pessoas
ao redor do mundo podem usar o software em seu próprio idioma.
1
import i18n from 'i18next';
384
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
3
import translationEN from './locales/en/[Link]';
4
import translationPT from './locales/pt/[Link]';
6
const resources = {
7
en: { translation: translationEN },
8
pt: { translation: translationPT }
9
};
10
11
[Link](initReactI18next).init({
12
resources,
13
lng: 'en', // Idioma padrão
14
fallbackLng: 'en', // Idioma de fallback
15
interpolation: {
16
escapeValue: false,
17
},
18
});
19
385
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
// src/locales/en/[Link]
3
{
4
"welcome": "Welcome to my app!",
5
"button": "Click me"
6 }
1
// src/locales/pt/[Link]
3
{
4
"welcome": "Bem-vindo ao meu app!",
5
"button": "Clique aqui"
6 }
386
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { useTranslation } from 'react-i18next';
3
const MyComponent = () => {
4
const { t } = useTranslation();
6
return (
7
<div>
8
<h1>{t('welcome')}</h1>
9
<button>{t('button')}</button>
10
</div>
11
);
12
};
13
387
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
1
import { useTranslation } from 'react-i18next';
3
const LanguageSelector = () => {
4
const { i18n } = useTranslation();
6
const changeLanguage = (event) => {
7
const selectedLanguage = [Link];
8
[Link](selectedLanguage);
9
};
10
11
return (
12
<select onChange={changeLanguage}>
13
<option value="en">English</option>
14
<option value="pt">Português</option>
15
</select>
16
);
17
};
18
388
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Dica extra
1
import { useTranslation } from 'react-i18next';
3
const DynamicComponent = [Link](
4
() => import('./DynamicComponent')
5
);
7
function App() {
8
const { t } = useTranslation();
10
return (
11
<div>
12
<h1>{t('welcome')}</h1>
13
<Suspense fallback={<div>Loading...</div>}>
14
<DynamicComponent />
15
</Suspense>
16
</div>
17
);
18
}
19
389
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Conclusão
390
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Swagger
391
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
O que é
392
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Swagger Editor
393
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Swagger UI
Cada barra colorida é uma rota da API. Nas barras podemos ver o
caminho da rota, o método utilizado e alguns dos parâmetros
necessários. Ao clicar em uma das barras ela se expande mostrando um
exemplo de como cada parâmetro deve ser preenchido e a sua resposta.
394
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Swagger Codegen
395
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Conclusão
396
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
[Link] 13
397
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Layouts
Server Components
398
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Streaming
399
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Data Fetching
400
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Turbopack
@next/image
401
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
@next/font
@next/link
O componente next/link não requer mais uma tag <a> como filho. Essa
funcionalidade já era uma opção experimental na versão 12.2 e agora
está habilitada como padrão. No Next 13, o componente <Link>
renderizará uma tag <a>.
Estrutura do Next 13
Ao criar uma aplicação com Next, iremos nos deparar com uma nova
estrutura de pastas e arquivos. Como já dito, agora temos o diretório
'App', mas além dele foi adicionado o arquivo 'layout', que agora será
utilizado para configuração de metadados. Vale informar que todos os
metadados compartilhados neste arquivo serão apresentados em toda a
aplicação, mas você pode criar metadados para páginas específicas.
402
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Componentes do Cliente
403
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Essas são apenas algumas das principais novidades do Next 13. Essa
versão promete melhorar a produtividade dos desenvolvedores e a
experiência dos usuários, permitindo criar aplicativos web mais rápidos,
interativos e eficientes.
404
Licensed to Thiago Arraes - thiaqo@[Link] - 012.311.244-31 - HP0355234876
Obrigado!
Quero expressar minha sincera gratidão por ter adquirido este ebook.
Foram meses de trabalho e dedicação para sua finalização. Tenho
certeza que este ebook foi de grande importância em sua vida
profissional, pois ele foi criado com muito amor, lofi e café.
404