Comece com React e Bootstrap em 2 dias. Dia número 1

Devo dizer imediatamente que o site funcionará mais rápido se você substituir o Bootstrap por CSS e JS puros. Este artigo é sobre como começar rapidamente a desenvolver aplicativos da Web bonitos e a otimização já é um problema separado que vai além do escopo deste artigo.

Primeiro, você precisa entender pelo menos um pouco de HTML, CSS, JavaScript, XML, DOM, OOP e poder trabalhar no terminal (linha de comando).

Onde conseguir materiais para estudo?
Para aprender HTML e CSS, recomendo htmlbook.ru
Para aprender JavaScript, recomendo learn.javascript.ru
Para aprender XML, recomendo msiter.ru/tutorials/uchebnik-xml-dlya-nachinayushchih
Você pode ler sobre o DOM na lição JavaScript learn.javascript.ru/dom-nodes
Para estudar OOP, recomendo o curso em vídeo proglib.io/p/oop-videocourse
Para explorar a linha de comando do Windows, recomendo cmd.readthedocs.io/cmd.html
Para estudar o terminal em um Mac, recomendo ixrevo.me/mac-os-x-terminal
Se você está trabalhando no Linux, o bash e os análogos sabem que, em último recurso, o homem ou a ajuda o ajudarão .
Para aprender o React, uso learn-reactjs.ru (que é uma tradução da documentação oficial do React: reactjs.org ).
Para estudar o Bootstrap, eu uso o bootstrap-4.ru (que é uma tradução da documentação oficial do Bootstrap: getbootstrap.com ).
Para fazer amigos Reagir e Bootstrap, encontrei um excelente artigo webformyself.com/kak-ispolzovat-bootstrap-s-react

Neste artigo, vou fazer um aperto no mínimo necessário para o trabalho e criar um cronômetro:



Instalação


Primeiro, precisamos de um gerenciador de pacotes. Eu escolhi o npm e está no Node.js
Então, primeiro, instale o Node.js no seu sistema operacional a partir do site oficial: nodejs.org/en/download . Você pode descobrir a instalação, então não descreverei o processo de instalação. Notei apenas que a instalação no Ubuntu é simples:

sudo apt update sudo apt install nodejs sudo apt install npm 

Por meio do terminal, verificamos se o Node.js e o npm foram instalados com sucesso:

 nodejs -v npm -v 

Se houver erros durante a saída, significa que algo deu errado e você precisa entender, e é possível reinstalá-los. Se vc é exibido com números e pontos, tudo está bem.

Instale Create-react-app para que você possa criar rapidamente estruturas de aplicativos:

 npm install -g create-react-app 

Em seguida, criamos a estrutura do aplicativo no React. Vamos nomear nosso aplicativo como novo aplicativo . Se você deseja criar um aplicativo para uma pasta diferente da pasta do usuário, vá primeiro para o terminal através do terminal usando o comando cd . Então, no terminal, basta digitar 3 comandos:

 create-react-app new-app cd new-app npm start 

Criamos o aplicativo novo aplicativo . Vá para a pasta do novo aplicativo . Iniciamos o aplicativo. Após essas linhas, o navegador com o aplicativo React deve iniciar no endereço http: // localhost: 3000



O terminal deve permanecer aberto, sem ele a página do aplicativo não será aberta. Se você de repente fechou - isso não importa. Basta usar o comando cd para ir para a pasta do aplicativo e iniciá-lo com o comando npm start

Agora instale o bootstrap

 npm install bootstrap 

Também é recomendável instalar as dependências jquery e popper.js, mas elas são necessárias apenas para a parte JS do Bootstrap. Eu tentei sem eles - a parte CSS do Bootstrap funciona bem, então as seguintes linhas no terminal são opcionais:

 npm install jquery popper.js 

Em seguida, é necessário fazer alterações nos arquivos do aplicativo, para isso, vá para a pasta new-app, onde o aplicativo está localizado, adicione a linha ao arquivo src / index.js , que deve ser o primeiro:

 import 'bootstrap/dist/css/bootstrap.min.css'; 

Se você usa jQuery, popper.js ou a parte JS do Bootstrap (janelas modais, animações etc.), será necessário adicionar mais três linhas na primeira linha:

 import $ from 'jquery'; import Popper from 'popper.js'; import 'bootstrap/dist/js/bootstrap.bundle.min'; 

Agora resta executar o projeto:

 npm start 

E, novamente, o navegador é aberto em http: // localhost: 3000 já com o aplicativo enobrecido usando o Bootstrap:


Também para depurar o React, você pode instalar a extensão " React Developer Tools " para o navegador. Os links atuais para a extensão do Chrome e Firefox e outros casos de uso estão listados no repositório oficial github.com/facebook/react-devtools
A instalação e a configuração inicial estão concluídas.

JSX, componentes e propriedades


Vamos ver o que o create-react-app gerou para nós - os arquivos de origem estão no diretório src. Primeiro, vejamos o arquivo index.js - existem várias linhas de importação. Fica claro pelas linhas o que eles estão fazendo, então não vou comentar.

A linha mais importante neste arquivo:

 ReactDOM.render(<App />, document.getElementById('root')); 

Desenha a página do aplicativo. Há um elemento <div> com id = root no arquivo HTML de origem. Este <div> exibe o componente App , desenhado pela função de renderização da classe ReactDOM . Nesse caso, o componente é desenhado em um formato semelhante ao XML, chamado JSX (sobre o qual mais tarde).

Agora vamos para o arquivo App.js , onde está localizada a implementação da classe App, que herda da classe React.Component .

 class App extends React.Component {     <b>render()</b>,     JSX: <div className="App"> <header className="App-header"> <img src={logo} className="App-logo" alt="logo" /> <p> Edit <code>src/App.js</code> and save to reload. </p> <a className="App-link" href="https://reactjs.org" target="_blank" rel="noopener noreferrer" > Learn React </a> </header> </div> 

JSX é muito semelhante ao HTML, mas há inserções de código JS entre chaves {}. E deve haver um elemento raiz, neste caso <div>.

Para entender melhor, apagaremos todo o código do método render () e escreveremos o componente mais simples:

 class App extends React.Component { render() { return <h1>, {this.props.name}!</h1>; } } 

Agora, vamos voltar ao arquivo index.js e corrigi-lo.

 ReactDOM.render(<App name="" />, document.getElementById('root')); 

Após salvar os arquivos, a página será atualizada no navegador. E agora vamos entender.

Conceitualmente, os componentes são semelhantes às funções JavaScript. Eles pegam dados arbitrários (chamados adereços) e retornam elementos React que descrevem o que deve aparecer na tela. Os componentes permitem dividir a interface do usuário em partes independentes e reutilizáveis ​​e trabalhar com cada uma delas separadamente.

Quando o React vê que um elemento é um componente customizado, ele passa todos os atributos JSX para esse componente como um único objeto. Esse objeto é chamado de adereços.

No exemplo, o parâmetro name é passado para o componente como um atributo da tag <App> com o valor " World ". Além disso, no método render () da classe App , como resultado de uma função dentro do JSX, que na verdade é um modelo HTML, colchetes {} indicam isso - a classe atual, props - o objeto do usuário, nome - o nome do parâmetro do objeto.

Construtor, Ciclo de Vida e Mudança de Estado


Além dos parâmetros armazenados em adereços, você pode armazenar o estado do objeto em state .

Vamos fazer um cronômetro. Nenhum parâmetro é necessário para o timer, então vamos remover os parâmetros em index.js :

 ReactDOM.render(<App/>, document.getElementById('root')); 

E agora no arquivo App.js, substituímos todo o texto entre importação e exportação :

 const INTERVAL = 100; class App extends Component { constructor(props) { super(props); this.state = {value: 0}; } increment(){ this.setState({value: this.state.value + 1}); } componentDidMount() { this.timerID = setInterval(() => this.increment(), 1000/INTERVAL); } componentWillUnmount() { clearInterval(this.timerID); } render() { const value = this.state.value return ( <div> <p>:</p> <p> <span>{Math.floor(value/INTERVAL/60/60)} : </span> <span>{Math.floor(value/INTERVAL/60) % 60} : </span> <span>{Math.floor(value/INTERVAL) % 60} . </span> <span>{value % INTERVAL}</span> </p> </div> ); } } 

Após inserir e salvar esse código, um cronômetro aparecerá na página e iniciará automaticamente.

Vamos analisar esse código. Antes da aula, uma constante foi anunciada, graças à qual você pode ajustar a taxa de atualização do timer.

Em seguida, dentro da classe, há um construtor obrigatório da classe, para o qual os props são passados. Em seguida, o processamento padrão do construtor da classe pai super (props) e a determinação do estado do valor por meio disso é o objeto atual. Este é o único lugar onde você pode definir diretamente o estado. Em outros locais, apenas a leitura está disponível ou a configuração do estado com o método especial setState () , que é usado no próximo método increment () para aumentar o estado do valor em um.

Em aplicativos com muitos componentes, é muito importante liberar recursos ocupados por componentes quando eles são destruídos. Precisamos definir um cronômetro sempre que o DOM for sorteado pela primeira vez. No React, isso é chamado de "montar / instalar". Também precisamos limpar esse timer toda vez que o DOM criado pelo componente for excluído. Em React, isso é chamado de "desmontagem / desmontagem".

Para isso, os métodos componentDidMount () e componentWillUnmount () são usados . Na documentação, esses métodos são chamados de " ganchos do ciclo de vida ". Por simplicidade, os chamaremos de métodos de ciclo de vida. O método componentDidMount () é acionado após a renderização do componente no DOM. Este é um bom lugar para definir um cronômetro. Limparemos o cronômetro no método componentWillUnmount () do ciclo de vida.

Observe como em componentDidMount () armazenamos o ID do temporizador diretamente neste, usando a função de seta Enquanto this.props é instalado independentemente pelo React e this.state tem um significado específico, você pode adicionar livremente campos adicionais à classe manualmente se precisar armazenar algo que não é usado para saída visual. Se você não estiver usando algo em render () , ele não deve estar no estado state .

Além disso, durante a execução da renderização () , o estado do valor é fixo no valor constante local. E então, usando a função matemática floor () , que arredonda o número para baixo, dividindo ( / ) e obtendo o restante da divisão ( % ), obtemos as partes do timer, que são exibidas na mesma linha após a palavra Timer. Você pode ver os resultados do nosso trabalho.

Aparência com o Bootstrap


Não é conveniente que o timer funcione imediatamente quando a página for atualizada. Gostaria que ele iniciasse e parasse quando você clicar nos botões apropriados. E eu gostaria que fosse no centro e grande.

Vamos começar com o design. Para fazer isso, adicione as seguintes linhas ao arquivo App.css :

 .container-fluid { display: flex; flex-direction: column; } 

Graças ao contêiner de borracha para contêiner adaptável do Bootstrap, que ajuda a criar um layout totalmente flexível para uma página ou bloco. Este contêiner é 100% largo. Vamos fazer um contêiner flexível , com a direção de alinhar os elementos verticalmente - para que ocupe todo o espaço e possa ser alinhado no centro.

Agora vamos finalizar o método render () no App.js para aplicar os estilos do Bootstrap e adicionar alguns botões. Para fazer isso, substitua o valor retornado pelo método pelo seguinte:

 <div class="container-fluid align-items-center"> <h1 class="display-1"></h1> <h1 class="display-1"> <span><kbd>{Math.floor(value/INTERVAL/60/60)}</kbd> : </span> <span><kbd>{Math.floor(value/INTERVAL/60) % 60}</kbd> : </span> <span><kbd>{Math.floor(value/INTERVAL) % 60}</kbd> . </span> <span><kbd>{value % INTERVAL < 10 ? '0' : ''}{value % INTERVAL}</kbd></span> </h1> <div> <button class="display-4"></button> <button class="display-4"></button> </div> </div> 

Na primeira linha, duas classes de Bootstrap foram adicionadas à raiz <div> : container-fluid (que escrevi acima) e align-items-center - que apenas alinha os elementos do container no centro.

Em seguida, dois <div> com a classe display-1 - essa classe é apenas para mostrar texto grande.

Em seguida, uma nova tag <kbd> foi adicionada aos números - que geralmente é usada para destacar as teclas que precisam ser pressionadas. Nesse caso, é ótimo para contrastar os números exibidos.

A expressão condicional é adicionada no último dígito, mostrando parte de um segundo, permitindo que dígitos de um dígito (<10) sejam exibidos no início de 0 e não para números de dois dígitos. Isso é necessário para que os números não se alterem a cada segundo. Para fazer isso, use o operador JavaScript ternário: condition? true: false

Então, em um <div> separado, coloquei 2 botões com a classe Display-4 - essa classe foi selecionada como o tamanho mais adequado para que os botões correspondam ao tamanho do temporizador. Eu inseri um caractere entre os botões   - Espaço inextricável para que os botões não se fundam.

Você pode iniciar, mas os botões ainda não funcionam. Vamos ensinar os botões a trabalhar.

Manipulação de eventos


Primeiro, adicione a chamada às funções correspondentes no código de saída do botão:

 <button class="display-4" onClick={this.stopTimer}></button> <button class="display-4" onClick={this.resetTimer}></button> 

Observe que em React, o manipulador de eventos onClick , não onclick , como em JavaScript, e a função chamada são indicadas entre chaves sem parênteses e indicando o objeto do qual o método é chamado, neste caso, isso .

Agora, definimos os métodos especificados stopTimer () e resetTimer () :

 stopTimer(){ clearInterval(this.timerID); } resetTimer(){ this.setState({value: 0}); } 

Mas isso ainda não é suficiente, e se você deixar assim, quando o botão for pressionado, um erro aparecerá, porque isso ao chamar a função será indefinido . Isso ocorre porque, em JavaScript, os métodos de classe não são vinculados por padrão. Normalmente, se você referenciar um método sem () depois dele, por exemplo, onClick = {this.resetTimer} , será necessário vincular esse método.

Vincule os métodos no construtor da classe adicionando 2 linhas:

 this.stopTimer = this.stopTimer.bind(this); this.resetTimer = this.resetTimer.bind(this); 

Ótimo, funcionou! Mas apenas o botão Parar pode ser usado apenas uma vez e, depois disso, os botões param de funcionar. E isso é lógico, porque ao chamar stopTimer () , desabilitamos a chamada de função regular chamando clearInterval () .

Os comentários sugeriram o uso de funções de seta. Tentei funcionar. Portanto, você não pode adicionar 2 linhas ao construtor, mas substitua as próprias funções pelas seguintes funções de seta:
 stopTimer = () => { this.timerID = setInterval(() => this.increment(), 1000/INTERVAL); } resetTimer = () => { this.setState({value: 0}); } 

Para resolver isso, faremos com que o botão "Stop" também funcione como "Run".

Primeiro, adicione o estado booleano parado ao construtor para entender em que modo o botão funciona:

 this.state = {value: 0, stopped: false}; 

Agora substitua completamente o conteúdo do método stopTimer () :

 this.setState({stopped: !this.state.stopped}); if(this.state.stopped){ clearInterval(this.timerID); } else { this.timerID = setInterval(() => this.increment(), 1000/INTERVAL); }; 

No início do método, altere o estado parado para o oposto via setState () .

Além disso, se o timer deve ser parado (ou seja, parado = verdadeiro ), desativamos a chamada de função regular via clearInterval () e, se o timer deve ser iniciado (ou seja, parado = falso ), iniciamos a chamada de função regular da mesma maneira que componentDidMount () .

Você também precisa corrigir o método increment () para que ele pare quando parado = true :
 increment(){ if(!this.state.stopped) (this.setState({value: this.state.value + 1})); } 

E, finalmente, alteramos o nome do botão, dependendo do estado parado, inserindo o seguinte em vez de "Stop":

 {this.state.stopped?'':''} 

Agora temos um cronômetro bonito e conveniente.

Em vez de uma conclusão ou uma cereja no bolo


Finalmente, gostaria de mudar o título padrão e o ícone da janela para o nosso.

Você pode alterar o título definindo document.title no método componentDidMount () , mas prosseguiremos e tornaremos o tempo de exibição do título da página preciso em segundos. Para isso, adicionaremos a configuração document.title ao método componentDidUpdate () especial:

 componentDidUpdate(){ const value = this.state.value; if (this.state.stopped) document.title = ""; else document.title = ": "+Math.floor(value/INTERVAL/60/60)+":" +Math.floor(value/INTERVAL/60) % 60+":"+Math.floor(value/INTERVAL) % 60; } 

Agora, o timer repete até segundos no título da página e, quando o timer é parado, apenas a palavra Timer é exibida.

O ícone é simples. Basta preparar uma imagem no formato jpg , bmp , gif , png , soltá-la na pasta pública (e não no src , no qual trabalhamos principalmente), nomeie, por exemplo, favicon.png e altere a linha no arquivo public \ index.html :

 <link rel="shortcut icon" href="%PUBLIC_URL%/favicon.ico"> 

por linha:

 <link rel="shortcut icon" type="image/png" href="/favicon.png"/> 

Por hoje, é tudo o que eu queria contar. No próximo artigo, falarei mais sobre o Bootstrap, que neste artigo tocou apenas um pouco. Além do Bootstrap, ainda existem tópicos importantes: listas, tabelas, formulários e pensamento no estilo React.

Por fim, o repositório no BitBucket, que possui todo o código deste artigo

Source: https://habr.com/ru/post/pt431826/


All Articles