Transcrições
1. Introdução: Bem-vindo ao bootcamp de reação completo. Oi, meu nome é Andrew e sou o desenvolvedor do React. Oi, meu nome é nosso Ash e eu posso UI UX designer. Você já quis criar um aplicativo semelhante ao Twitter ou Facebook? Prefere praticar ao invés da teoria? Se sim, você está no lugar certo juntos, vamos construir três projetos separados de complexidade diferente do zero, um jogo tic-tac-toe e um aplicativo de pesquisa de filmes
e, finalmente, uma conversa. Este curso é destinado a pessoas que estão ansiosas para desenvolver aplicativos web. Nós tecnologias que se tornam cada vez mais populares hoje em dia. Primeiro, discutiremos todos os conceitos básicos que você precisa saber antes de começar a reagir. Aqui vamos falar sobre nenhum GS, boas APIs de renderização do lado do cliente e do lado do servidor e ferramentas
essenciais para que você se sinta confortável em qualquer fase das abordagens de desenvolvimento. Logo depois disso, temos uma seção dedicada de JavaScript, mas descobrimos os recursos mais recentes e atualizados do idioma. Então nos movemos ligeiramente para reagir com a pequena parte da teoria. Neste ponto, você vai conhecer uma vez que Riak é feito e como ele funciona. A partir daqui, começaremos com nosso primeiro projeto, aquele jogo de tic-tac-toe. Ele tem uma interface moderna com animações legais e funcionalidade perfeita neste projeto, conheça primeiro reagir. Você aprenderá a criar componentes, estilos
dinâmicos em interfaces de usuário. Mas falaremos sobre gerenciamento estadual e eventos de ciclo de vida de componentes usando o Hooke. No final deste projeto, você será capaz de criar um aplicativo web simples que mostra o seu forte reagir básico, e você vai experimentar o fluxo de desenvolvimento em geral. O segundo projeto é chamado de bilheteria. Ele atua como um motor de busca para filmes e programas de TV. Você pode obter informações sobre qualquer filme ou AG. E além disso, você pode adicioná-los aos favoritos para revisá-los no futuro, nós esses projetos,
você se move em direção a um aplicativo React mais complexo ou você está trabalhando com APIs
externas e gerenciando cenários não primitivos usando ganchos 3i de traje. Além disso, você vai aprender sobre CSS e JS como uma alternativa para estilo e aplicação, vamos explorar o conceito de rotas dinâmicas e busca remota de dados. Você também entenderá como otimizar e analisar componentes Reagir usando ferramentas de reação integradas. No final desses projetos, vamos até transformar nosso aplicativo em um aplicativo web progressivo que funciona offline. Após a conclusão da bilheteria, você será capaz de criar um aplicativo típico React que requer conhecimento de reação mais abrangente e avançado. Nosso projeto final será um bate-papo com os recursos mais populares exigidos por qualquer aplicativo de bate-papo. Estes incluem logins de mídia social, gerenciamento de
contas, permissões baseadas , dados em
tempo real e muitos outros recursos legais neste projeto, você vai conhecer o Firebase em primeiro lugar. Aqui você dominará a autenticação do usuário e o gerenciamento de estado global. Nesta fase, reagir ganchos vai ser a sua principal arma para desenvolver um aplicativo React pronto para produção gerenciar estilos você mesmo nem sempre é desejável. É por isso que aqui vamos usar uma biblioteca de componentes de interface do usuário para utilizar um sistema de design pré-construído. Finalmente, desenvolveremos nosso próprio backend usando o Cloud Functions, e adicionaremos o recurso de notificações em tempo real ao nosso aplicativo de bate-papo. Espere, você não terminou. Você está pronto para ajudá-lo em qualquer fase
do curso e responder suas perguntas o mais rápido possível. Você está pronto para explorar, reagir juntos. Vemo-nos na aula.
2. Requisitos: Oi, meu nome é Andrew. Serei seu instrutor. Jogue Dick Koers. Deixe-me falar sobre os requisitos para que este tribunal comece a trabalhar com reagir. Primeiro, todo o conhecimento sobre HTML e CSS é essencial. Eu não serei nenhuma atenção extra explicando o que é dif tag. O mesmo vale para CSS. Espero que você saiba sobre classes e seletores, mas não fará nenhuma parada para explicar básico de
HTML e CSS. Mas você sempre pode fazer perguntas nos Comuns. Há definitivamente alguns momentos-chave fora HTML e CSS, e isso será explicado. Mas na maioria das vezes vamos trabalhar com JavaScript. Eu não espero que você seja um bom JavaScript ou tenha alguma experiência decente. Eu queria saber sobre programação em geral, você deve entender coisas básicas como o que está disponível ou uma guerra é um olhar de quatro. Você vai
se levantar hoje. Sintaxe JavaScript. Durante o curso, é bastante amigável coração para entender. As partes serão explicadas, então não se preocupe com isso. Há também uma seção especial dedicada Onley ao JavaScript. Ele cobre aspectos mais importantes fora da língua para garantir que você sabe o suficiente para começar com corrida
reagir, e eu tento fazer tudo o mais suave possível. Mas, no entanto, eu queria fazer tantas perguntas quanto você puder. E não seja tímido fazer perguntas tolas estavam sempre lá para te ajudar. Vamos resumir rapidamente. Você deve estar ciente de HTML CSS e algum conhecimento geral de programação. É isso. Vejo você no próximo vídeo.
3. Atualizações e problemas: Ei, neste vídeo, eu gostaria de fazer referência a um arquivo que irá informá-lo sobre as atualizações e mudanças que os seres humanos fazem durante o curso. Na web, tudo muda constantemente. E para acompanhar o conteúdo atualizado, criamos esse arquivo. Por favor, encontre atualizações e problemas arquivo pdf ponto
na seção de projetos e recursos dentro de você verá dois capítulos principais, atualizações
importantes e problemas comuns. Atualizações importantes afetam todos os que fazem o curso. Leia esse capítulo para evitar inconsistências durante os vídeos. Problemas comuns se referem a possíveis erros que você pode enfrentar e suas soluções junto. Consulte este arquivo em primeiro lugar quando você tiver algum problema. Na pior das hipóteses, leia o capítulo três. Queremos sempre mantê-lo atualizado. Somente. Boa sorte com os projetos.
4. Introdução à primeira seção: Ei, bem-vindo ao curso na seção Capa móvel Tudo o que precisamos saber antes de
começar com o desenvolvimento de reagir. Isso inclui ferramentas, um pouco de teoria e algumas outras coisas. Espero que goste deles. Vemo-nos lá.
5. Instalando Git + Bash (Windows): Ei, neste vídeo vamos instalar e obter o que é bom e por que precisamos dele? Vamos cobrir tudo isso no próximo vídeo. Este vídeo é sobre instalação. Vamos. Como sempre, primeiro abrimos Google e depois procuraremos e obteremos isso nos levará ao site oficial. Em uma nova guia que vou abrir, não carrega. E na guia atual, vou procurar o Git instalado no local. Isso nos levará a pelo menos ume.com. Então, por que precisamos disso? Se você verá discrepâncias na instalação do
Git ou se
você estiver perdido sobre a instalação do Git. Este é o último tutorial de insolação atualizado e atualizado. Eu recomendo esse. Então, se você estiver no macOS, linux, Windows, isso não importa. Basta navegar aqui e é muito fácil e direto. Tudo bem, agora vamos voltar aos downloads. Este vídeo é direcionado para usuários do Windows, mas se você é do Linux ou do macOS, está totalmente bem também. Então, se você estiver no Linux, basta clicar aqui
e, dependendo da sua distribuição, basta selecionar o comando. É muito fácil de fazer, ok? Se você vem do mundo macOS, você tem algumas opções. Você pode instalar adeus usando um gerenciador de pacotes como o Homebrew, ou você pode usar um instalador diretamente. Esse tutorial aqui, ele recomenda usar um instalador, que é a maneira mais fácil no macOS, ok? Como estamos no Windows, vamos clicar no Windows e obteremos o instalador. Novamente, se você estiver vindo de um sistema operacional diferente, ainda recomendo que você passe rapidamente este vídeo porque vamos abordar algumas questões importantes. Tudo bem, então abrimos o instalador e apertamos Next. O que precisamos aqui? Ícones adicionais. Isso depende de você, integração com o Windows Explorer. Portanto, esta é apenas a opção Windows. E queríamos selecionar o Git Bash aqui, e queríamos desmarcar uma boa GUI. Ninguém usa o bem para ir. Esta é uma ferramenta visual para representar um bom, certo? E o Git Bash é uma versão curta do terminal Unix chamada Bash. Portanto, esta versão curta está disponível no Windows no dia do Git Bash. E acho que isso é muito útil e conveniente. Então, no Windows, temos cmd e PowerShell, e vamos instalar o Git Bash e usá-lo em vez de CMD e PowerShell. Ok, então queríamos selecionar bom L de c. Então isso é apenas no caso de termos arquivos
realmente grandes e nosso bom projeto, essa opção nos permitirá colocar esses arquivos. Então, em um bom projeto basicamente, então queríamos manter associações. Não preciso de atualizações diárias e perfil do Git Bash para o Windows Terminal. Portanto, não tenho certeza sobre este, mas acho que isso está relacionado
ao novo Terminal Windows publicado recentemente. Ok, então eu também não quero isso. Então, em seguida, nesta etapa, vamos escolher um editor com o qual você se sinta confortável. Então eu sei que você ainda não sabe, mas, na
verdade, existe a possibilidade de
haver um conflito entre vários arquivos. E para resolver esse conflito, você terá que
passar manualmente por esses arquivos e editá-los. Então, quando esse conflito ocorrer, o
get abrirá um editor que você selecionar aqui por padrão. Ok, então escolha algo que você saiba como usar, por exemplo, o Visual Studio Code. Tudo bem, em seguida aqui. O que temos aqui, justificando, o nome da ramificação inicial em seu repositório também. Este é um complicado. Vamos selecionar, vamos selecionar, deixar, decidir. Mas o que se trata tudo isso. Bem, eu entendo, eu sei que você ainda não sabe, mas há esse conceito de ramificações em bom. Então, há cerca de um ano, boa comunidade e a comunidade do GitHub decidiram alterar o nome padrão do branch dois, principal logo antes de ser chamado de master. Agora é oficialmente chamado de principal, mas ainda há muitos projetos que continuam usando o master. Então, o que eu recomendo fazer é apenas escolher, selecionar, deixar, obter, decidir. Então, vamos clicar em Próximo. E aqui temos o ajuste do seu ambiente de caminho que desejamos selecionar a segunda opção Recomendada. Isso nos permitirá usar o Git de qualquer shell de terminal, seja CMD, PowerShell ou Bash, ou de qualquer outro software e shells que vamos instalar e usar. Então é por isso que a segunda opção é o que queremos. Nesta etapa. Não queremos mudar nada, basta manter um uso padrão que o OpenSSH empacotado receberá quatro. Suas conexões podem usar túneis SSH. Certo. É por isso que ele vem junto com o executável SSH, que vem do OpenSSH. Ok, em seguida, aqui, back-end de transporte https. Continue usando o OpenSSL. Não queremos mudá-lo também. Em seguida, aqui sobre terminações de linha. Bem, bom é uma ferramenta multiplataforma. No entanto, existem algumas coisas específicas que devem ser de alguma forma gerenciadas ou controladas para alcançar essa disponibilidade multiplataforma. E uma dessas coisas são finais de linha. O problema é que no Windows e em sistemas semelhantes ao UNIX, as terminações de
linha têm codificações diferentes, ok? E isso pode criar grandes problemas para conseguir projetos. Portanto, isso nos dará a capacidade manter nosso projeto multiplataforma sem problemas. Isso é uma coisa muito pequena, mas é muito importante porque se você selecionar a terceira opção e se você fizer algumas alterações para obter o projeto no Windows e, em seguida, abrir esse projeto em um sistema operacional diferente, você terá muitos problemas. Por que não queremos isso. Então, para o Windows, selecionamos essa opção. Em seguida, configurou o Emulador de Terminal para usar com o Git Bash. Ok, então o Git Bash será novamente nosso novo shell que usaremos como alternativa ao CMD e ao PowerShell. Então minty é aquela janela do terminal, ok, então se eu abrir o CMD, eu tenho essa janela padrão do Windows, basicamente a direita, como diz, a segunda opção aqui, janela de console padrão. Então, mentee é que esse software, basicamente que executa o shell terminal trans, projeta dentro dele. Então, será aquela janela que poderemos configurar, mudar sua cor e codificação e outras coisas podem ser ligações de teclas, tudo isso. Então, isso é só que, você sabe, janela que executa projéteis terminais. Certo? Então, queremos usar o mentee e, em seguida, escolher o comportamento padrão da boa pesquisa. Você ainda não sabe disso, mas vamos escolher o padrão. Essa é a opção preferida, quase sempre. E eu diria sempre. Em seguida, escolha um auxiliar de credencial. Aqui queremos selecionar o núcleo do Git Credential Manager. Isso é específico para o Windows aqui, mas ainda usa essa opção. O que ele faz, haverá momentos, quero dizer, sempre assim. Queríamos hospedar nosso bom projeto em algum lugar. Nós hospedamos no GitHub. E para nos autorizar ao GitHub, teremos que inserir nossas credenciais para um GitHub, nosso nome de usuário e senha. Portanto, para não respondê-las sempre que essas credenciais devem ser
armazenadas com segurança em algum lugar em um armazenamento em cache. No Windows, esse armazenamento em cache é chamado núcleo do Git Credential Manager. Então, é por isso que precisávamos não inserir nossas credenciais todas as vezes. Gostaríamos de enviar nossas alterações para o GitHub. Ok, em seguida, nesta etapa
queríamos habilitar o armazenamento em cache do sistema, limpezas simbólicas. Mantenha-o como está. Nós batemos em seguida e não precisamos nenhum recurso experimental. Então, basta clicar em Instalar. Removendo a versão anterior. Sim, quero dizer, para mim porque eu já o tinha instalado. Vamos esperar um segundo até que ele seja instalado e vamos ver o que temos. Certo, bom. Concluindo o assistente de boa configuração. Não quero que as notas de versão terminem. Agora, o bom está instalado. Como podemos verificar isso? Vamos para o CMD. E no cmd, queremos apenas digitar git space dash, dash version. E se você vir a versão instalada, parabéns, o get agora está instalado. Agora, isso está relacionado apenas aos usuários do Windows que instalaram, que selecionaram o Git Bash durante a instalação. Como podemos verificar manter o Bash? Bem, podemos executar git Bash diretamente de outro shell, de ver o Cmd, por exemplo. Então, se eu digitar Git Bash com traço dentro, verei que o Git Bash não é reconhecido. Bem, isso é para ser honesto, esperado. E para corrigir isso, temos que fazer novamente, uma pequena mudança em nossa variável de caminho. Então, o que precisamos fazer é iniciar o Painel e em busca com Tipo III e V. Em seguida, vamos editar as variáveis de ambiente
do sistema e vegetais vitamínicos. E, em Sistema, as bolhas procurarão o caminho. Clique duas vezes sobre isso. E aqui no final da lista você verá Arquivos de Programas C, bom, CMD ou qualquer caminho de instalação que você escolheu durante a instalação. Ok, então se abrirmos esse caminho, vamos para pastas. E vamos aqui. executáveis que temos aqui são bons,
bons GUI, tudo menos exceto o Git Bash. No entanto, se formos para obter a pasta aqui, temos o executável do Git Bash. Tudo bem? Portanto, para usar esse executável a partir do terminal, temos que adicionar o caminho da pasta à variável de caminho. Certo? Então voltamos aqui para essa lista. Clicamos em Novo e adicionamos Arquivos de Programas C. Bom. Então nós batemos OK, OK, OK. Agora vou reiniciar o terminal novamente. E agora, se eu digitar Git Bash, boom, estou dentro do shell do Git Bash e ele usa minty. Então, se eu clicar nas opções aqui, você verá esse logotipo de menta. Portanto, pode parecer muito parecido, mas na verdade usa como o console padrão do Windows. Mas isso é executado dentro do minty Terminal Emulator. Tudo bem, se você quiser, você pode configurar diferentes opções aqui, Seleção de
chaves, Terminal do Windows. Então, essas são todas as opções e apenas precaução, e este é o Git Bash. Agora, se quisermos digitar comandos Linux muito básicos aqui, podemos fazer isso, por exemplo, ls, para listar todos os arquivos nesta pasta. Ok, ótimo, e esta é a nossa entropia dos usuários C. Isso é meu. Será seu nome de usuário aqui. Se quiséssemos ir para um disco diferente, vamos digitar cd para
alterar o diretório e, em seguida, o nome do disco. Ótimo, então isso é sobre o Git Bash. Você também pode executá-lo a partir da janela de execução no
Painel Iniciar ou pressionando Windows plus r e digitando Git Bash. E você está lá dentro. Isso é basicamente, é, isso é tudo o que precisamos para configurar o Git, ok, Talvez mais uma opção seja o comando Git config, certo? Então, se formos a isso na lesão ao total, não importa quando para Windows, para Linux não importa. Então aqui precisamos configurar, usar nosso nome e e-mail, certo? Então, basta copiar esse comando aqui e colá-lo no terminal. E aqui insira seu nome. Pode ser o seu nome verdadeiro, ou pode ser o seu apelido, o que quer que você faça. Então pressione Enter para seu nome de usuário
e, em seguida, o mesmo para e-mail. Então, o que são esses? Eles ficarão visíveis nas mensagens de commit. Na boa história, abordaremos tudo isso,
mas isso é algo que outros usuários e você verão no histórico do seu projeto,
escolherão algo real, que é basicamente ele é instalado para Usuário do Windows, você obtém bashes instalados. No próximo vídeo, falaremos sobre isso em detalhes e como isso facilitará nossas vidas. Vejo você lá.
6. Altere o bucha de Git (somente Windows): Ei, antes de tudo, quero mencionar que este vídeo é apenas para usuários do Windows. Neste vídeo, gostaria de
abordar a aparência do Git Bash. Deixe-me mostrar o que quero dizer. Se eu iniciar o Git Bash. Não gosto do jeito que parece. Quero remover isso significa W 64, quero remover essa entrada B em,
no nome da minha máquina. Não preciso de tudo isso. Isso é totalmente opcional, mas tornará a experiência do desenvolvedor um pouco mais agradável. Então, vamos mudar isso. O que temos que fazer, temos que navegar
para obter a pasta de instalação no início. Então, para mim, vai ser C, Arquivos de Programas, bom. Dentro desta pasta, queremos ETC. E o perfil D aqui procurará um bom ponto prompt SH, e nós o abrimos com qualquer editor de texto. Vou abri-lo com o Sublime Text. E você verá isso. Sei o que vai ser completamente confuso e não sabemos o que está acontecendo aqui, mas não entre em pânico. Só queremos removê-los ou talvez substituí-los por outra coisa. Então, antes de tudo, para remover esse título Ming W6 vamos procurar algo com título, aparentemente. Portanto, esse prefixo de título de cifrão é exatamente para Ming W 64. Então, acabamos de removê-lo daqui. E também removemos os dois pontos, mas não removemos esse ponto e vírgula daqui porque isso faz parte
dessa cor representada como esta basicamente. Então aqui, deixe-me colocar meu apelido com uma seta e deixe-me salvar o arquivo. Agora, deixe-me reiniciar o Git Bash. Então, novamente, vou para a janela Executar Git Bash. E agora boom, eu vejo meu apelido e, e eu faço muito legal agora eu quero
remover tudo o que destaquei. Então eu procuro o sistema EMS. Acabei de remover essa linha completamente. Em seguida, removo o usuário no nome do host. E também o que eu gostaria de fazer, gostaria de destacar o caminho atual, que é exibido aqui. Então, se eu navegar para ver, eu tenho assim, mas eu queria colocá-lo entre parênteses. Então, a barra invertida w é o diretório de trabalho atual. Então eu quero colocá-lo dentro de suportes de caixa assim. Tudo bem, e uma aula, o que eu queria fazer, eu queria mudar o prompt
do cifrão para uma flecha talvez. Então aqui eu procuro esta linha. Tudo bem, prompt será sempre uma seta. Eu mudo, salvei o arquivo e agora vamos ver o resultado. Então, novamente, reinicio o Git Bash. E agora esta é a nossa aparição final. Se navegarmos para o disco D, nós o teremos assim. Muito legal. Então, novamente, isso é totalmente opcional e essa é minha preferência pessoal porque eu gosto da simplicidade e gosto da aparência. E para mim, do meu ponto de vista, parece muito, muito melhor do que era antes. Depende totalmente de você se você precisava ou não. Mas é isso. Isso é o que eu queria abordar. Vejo você no próximo.
7. Instale o Git (macOS): Ei, neste vídeo, vou mostrar como instalar o Git no Mac OS. Primeiro, navegue até o Google e digite git. Vá para o primeiro URL. Este é o site oficial. Clique em downloads e selecione macOS. Você verá algumas maneiras de instalar o Git. Vamos escolher aquele com Homebrew. Homebrew é um gerenciador de pacotes. Ele nos permite baixar software
distribuído com um único comando de terminal. Instale o Homebrew, copie o comando de instalação do site, vá para o Launchpad e execute o terminal, cole o comando e aguarde que ele seja instalado. Ele também pode solicitar sua senha. Agora que temos Homebrew, podemos instalar facilmente o Git, navegar de volta para obter o site e copiar homebrew instalado Git, abrir o terminal e colar o comando. Levará alguns segundos até que a homebrew seja instalada entre em seu sistema. Se diz que o get já está instalado, então você está bem. Provavelmente é por causa do Xcode. E é isso. Tchau.
8. Instalando VSCOde (Windows): Olá, Neste vídeo, instalaremos o VS Code e editor que usaremos durante todo o curso. Primeiro de tudo, por que o código VS Code ou Visual Studio? Acho que pessoalmente acho que este é um
dos melhores editores e IDE disponíveis para projetos JavaScript. Se você estiver confortável com qualquer outro editor, por exemplo, átomo para desenvolvimento, se você tiver alguma experiência anterior, sinta-se à vontade para usá-lo. Mas em treinamento, eu aconselho seu pseudocódigo de mísseis devido ao seu sistema plug-in e é apenas confortável. Ok, então vamos instalá-lo. O que temos que fazer é ir ao Google como sempre e digitar VS Code. E isso nos leva ao site oficial. Então eu sugiro abrir a página de documentos e não procurar a página. Então, na página de download, temos instaladores para três sistemas operacionais diferentes, Windows, Linux e macOS. Então, para o Windows, é bem direto, certo? Você clica no instalador e ele inicia o download, ok, para Linux e macOS, eu aconselho ir para
a página de documentos e, em seguida, dependendo do seu sistema operacional, vá para a seção apropriada. Então, para o Linux, também é bem simples. Dependendo da sua distribuição Linux, há cães que você pode ler e ver como você precisa instalar o NodeJS. Quero dizer, como exatamente você
vai fazer isso porque os comandos serão diferentes com base na sua distribuição. Certo, então apenas trate os cães. Confie em mim, isso é bem simples e basicamente o mesmo para Mac OS. Essa é uma maneira fácil. Você obtém o instalador e simplesmente arrasta-o para o seu launchpad. É isso. E o VS Code é considerado instalado. Ok, então, para o Windows, temos o instalador. Vamos lançá-lo. Este usuário pretendia correr para nos aterrar e disse: Oh, pague. Então, sim, quero continuar correndo. Certo. Eu fecho isso. Você não verá isso. Certo. Então, estou aqui. Fui aceitar. Você pode alterar o caminho se
quiser isso como instalação padrão. Isso também está escrito em cães. Você pode ler sobre isso aqui. Então, onde está? Certo, está aqui. Agora clicamos em Avançar. Em seguida. Agora, aqui precisamos selecionar dois caminhos selecionados por padrão, mas certifique-se de que ele esteja lá. Registre o código como um aditivo para tipos de arquivos de suporte. Sim, é aconselhável que seja selecionado. Isso é opcional e, se você precisar criar o item da área de trabalho, ok, clique em Instalar. Depois disso, levará algum tempo e boom, você verá o código VS em sua área de trabalho. Depois disso, você o inicia e você acaba em uma janela como essa, o tema será diferente, mas não importa. Vscode agora está instalado. Como configurar com código
SQL e como instalar plugins. Tudo será abordado no próximo vídeo. Vejo você lá.
9. Instale o código VS (macOS ): Olá, Neste vídeo, mostrarei como instalar o código VS no macOS, ir para a pesquisa do Google e digitar fiasco, depois clicar no botão Download e ele o levará para a página de download. Clique no instalador do macOS. Ele iniciará automaticamente o download para você, aguarde até que esteja pronto. E isso abriu o arquivo dentro, você verá o código VS. Eu posso atalho, basta arrastar e soltar o ícone nos aplicativos logo depois disso, VS Code é considerado instalado e você pode acessá-lo indo para o almoço, mas depois procure o VS Code, abra e verifique se está tudo bem. E isso é tudo. Veja no próximo.
10. Configuração de VSCode e extensões: Ei, neste vídeo, gostaria de falar sobre o código VS, como configuramos o VS Code e o que precisamos fazer para sentirmos confortáveis durante o desenvolvimento. Vamos. A primeira coisa que eu gostaria de
apresentar é a barra de pesquisa de código VS, porque é incrível abrir a barra de pesquisa. Eu pressiono Control P. E isso me traz aqui. Posso digitar qualquer coisa que eu quiser aqui, mas não dará resultados correspondentes porque ele tenta procurar defiles no projeto atual. Mas como não temos nenhum projeto no momento em que abri, ele não dá resultados correspondentes. O que eu quero digitar é a seta para a direita. Digitando a seta para a direita no início. Isso significa que eu quero usar comandos internos do
VS Code ou opções de código
VS talvez para navegar sombrio. Por exemplo, se eu digitar seta e, em seguida, configurações JSON, isso me dará preferências em aberto configurações castigadas. Deixe-me clicar nesse e isso me
leva às configurações do arquivo JSON. Portanto, o arquivo JSON de configurações é basicamente como arquivo de configuração do usuário de código. Aqui só precisamos digitar comandos
diferentes para configurar extensões,
configurar algumas ferramentas ou o que quer que seja. A primeira coisa que eu queria colocar aqui, deixe-me abrir o navegador. E aqui eu tenho esse arquivo, essa configuração de código. Você terá esse URL e talvez já como ele é compartilhado. Então, basta abri-lo. E a partir daqui, a primeira coisa vou
pegar a janela de confiança de segurança do IS. E vou colocá-lo aqui assim. E o que ele faz, ele desativa a janela de segurança, mas não entre em pânico. O que é janela de segurança? Bem, o código VS perguntará muitas vezes, você confia nesse ambiente ou confia nessa pasta? E confie em mim, isso é muito chato desativar essa janela. Basta copiar colar esta opção e você nunca verá essa janela. Mais uma vez. Se você estiver curioso, você sempre pode
comentar essa linha de código e vê-la você mesmo. Mas vou mantê-lo como está. Agora, por um segundo. Vou deixar a segunda opção e vou pegar a última opção daqui, que é sobre pregador. O que é pregador? Pre-clear é uma ferramenta que
abordaremos em detalhes no próximo vídeo. Preacher formará nosso código quando salvarmos arquivos, linha garante que quando clicarmos em salvar, nosso código será formatado. Nesta etapa, o VS Code basicamente já está configurado e você pode iniciar tentativas de desenvolvimento imediatamente. Mas uma coisa que quero
mencionar é o terminal integrado VScode. Então, se eu pressionar o terminal e clicar em novo terminal, ele abrirá o PowerShell para mim porque estou no Windows. Se você estiver no Linux ou no macOS, verá Bash para usuários Linux e macOS, tudo bem. Mas para usuários do Windows, desde que instalamos o Git Bash, vamos usar o Git Bash e não o PowerShell ou Cmd porque, por padrão, o VS Code e o Windows usam o PowerShell. Então, o que precisamos fazer? Precisamos voltar para esse arquivo e copiar essa configuração e deixe-me colocá-lo aqui no final. Então, o que ele fará, instruirá o VSCode a usar o Git Bash como terminal integrado. Não é diferente, como se você o
abriria fora do VSCode. É conveniente usar tudo em um só lugar, especialmente ferramenta como terminal. Copiei todas essas opções se o caminho for diferente para você, basta substituí-lo seguindo o mesmo padrão. E vamos fechá-lo e depois vamos abri-lo novamente. E vamos verificar se agora estamos usando o Git Bash. Dito isso, os usuários do Windows parabéns, estamos usando o Git Bash. Agora, a última coisa que eu quero falar neste vídeo, e eu diria que a mais importante
é as extensões VS Code. Tudo bem? Então, o que são extensões VS Code? Essas são ferramentas opcionais que ampliam VS Code com uma ótima funcionalidade. Para ir para Extensões, clicamos neste ícone no painel esquerdo. E aqui eu já tenho 33 extensões instaladas. É muito que eu sei, mas não entre em pânico. Não precisamos instalar todos eles. O que vou fazer agora, vou passar rapidamente pelas extensões que
acho necessárias para o nosso curso. E caberá a você se você deseja instalá-los ou não. Para vender e ampliar
na barra de pesquisa, basta digitar o nome da extensão. Por exemplo, melhor sintaxe C Plus Plus. Você clica na extensão, por exemplo, nessa e pressiona Instalar. Depois disso, ele será instalado. E pode pedir que você reinicie o código VS, mas é muito raro. E, a propósito, não preciso dessa extensão, então vou desinstalá-la. Então volto para Extensões Instaladas e vamos procurá-las rapidamente. A primeira extensão que eu quero
mencionar está disponível para a tag de nome. O que ele fará. Ele será apenas renomeado HTML, abrindo e fechando a tag à medida que digitamos HTML. Isso é muito útil. Eu recomendo este, riser de cor de pêra de
suporte. Eu acho que essa é uma
das extensões que deve instalar porque simplesmente destaca abertura e fechamento do colchete e decodificação. Isso é útil porque torna nosso código mais legível e distinguível. Eu recomendo esta extensão. Em seguida, temos snippets
ES 7 React redux GraphQL React Native. Esta é uma extensão importante. Vamos utilizá-lo
muito quando vamos escrever código React. Então instale-o. Vou mencionar essa extensão no futuro mais uma vez. Então temos ES fiapos. Vamos cobrir o ES lint em mais detalhes no próximo vídeo. Mas certifique-se de ter essa extensão instalada antecipadamente. Em seguida, temos a tag de correspondência de destaque. Assim como diz, ele destacará a tag HTML correspondente, assim como você vê nisso. Pré-visualização. Muito legal. Acho que é, é, é útil. Agora temos o IntelliSense para nomes de classes CSS. Bem, sim, é útil. Então, o que ele fará, ele adicionará preenchimento automático para nomes de classes
CSS definidos em nosso projeto, totalmente com você. Em seguida, temos Material Icon Theme. Ele apenas adicionará esse conjunto de ícones aos arquivos que veremos no Explorador de Arquivos aqui no painel esquerdo. Eu uso e recomendo a todos. Inteligência Npm. Este é importante. O que ele fará, adicionará preenchimento
externo para pacotes e bibliotecas que vamos importar para código, altamente recomendado. Em seguida, temos inteligência de caminho. Basicamente a mesma coisa, mas para arquivos locais. Portanto, preenchimento automático para importação de arquivos locais. Então temos pregador, pregadores, uma ferramenta que formatará nossos arquivos. Então, novamente, vamos cobrir isso em detalhes, então apenas certifique-se de que ele está instalado. E a última extensão será alternada por aspas. cotação de alternância é muito simples. Basicamente, apenas alterna as citações. Por exemplo, se for lido aqui, precisamos pressionar isso dependendo do seu sistema operacional para alternar aspas de simples para duplo, de duplo para backticks. Deixe-me demonstrar para você. Se você apenas pressionar esses botões em qualquer lugar, você terá Esta mensagem informando que a execução do Comando contribuído falhou. O problema é que você precisa usar esse comando somente dentro de aspas. Tenho que colocar meu cursor aqui dentro de um texto com aspas e depois usar a combinação para triplicar aspas. Eu uso muito pessoalmente e recomendo a todos. Acho que é isso. Eu cobri tudo o que eu queria. Mencionei todas as extensões que acho importantes. Eu lhe dei tudo sobre configurações, JSON, você sabe, sobre terminal integrado. Eu pessoalmente abro com controle mais ligação de chave
J, não daqui. E sim, é isso. Talvez mais uma coisa a mencionar seja o tema VSCode. Se você quiser que o VS Code pareça legal, procure um tema de extensão, ok, e escolha algo que você gosta. Eu pessoalmente gosto do tema Firefox. E eu já o tenho instalado. Então, vou clicar em Set Color Theme, Firefox, dark e boom. Agora tenho cores diferentes no meu código VS. Muito bom. Ele também tem um tema leve se você estiver interessado. Certo, acho que é tudo. Vejo você no próximo.
11. Trabalhando com Git - Parte 1: Ei, neste vídeo, vamos falar sobre, bom, vamos. Primeiro de tudo, o que é o Git? O Git é uma ferramenta de gerenciamento de projetos que
nos permitirá acompanhar todos os nossos arquivos de projeto. Por exemplo, faremos muitas alterações nosso código-fonte quando vamos desenvolver nossos projetos. Talvez leve um ano. Talvez demore dois anos para desenvolver esse projeto. Depois de um ano, provavelmente não
me lembrarei do que fiz no passado, como o medo atrás. E para ter esse histórico de projeto, o Bom existe. Isso nos permitirá ver quais mudanças fizemos, o que exatamente deu errado nesta etapa específica. Talvez gostássemos de mudar alguma coisa. Talvez gostaríamos de contribuir com outras pessoas e, para gerenciar tudo isso, o bem existe. Agora, vamos ver tudo isso na prática. Primeiro, criarei uma nova pasta de projeto. Já abro o VS Code. Agora precisamos abrir uma pasta de projeto. Vou clicar em File Open Folder. Em seguida, vou navegar até uma pasta onde quero criar outra pasta. Este será meu projeto de teste, e eu o abrirei no VS Code. Ótimo. Agora vamos abrir o terminal integrado. Vou pressionar Control mais j. E ele abrirá o Git Bash para mim. E, como você pode ver, ele já está na pasta do projeto. Ótimo. Agora, precisamos inicializar bem nesta pasta do projeto primeiro. Para fazer isso, precisamos digitar git nele. E você verá essa mensagem inicializada repositório git
vazio nesta pasta. E ponto importante aqui que ele criará um ponto de pasta oculta obter uma ordem para visualizar essa pasta oculta, precisamos digitar ls menos a. Ele mostrará todos os arquivos e pastas
na pasta atual mais pastas ocultas. Tão bom. E podemos realmente navegar para essa pasta usando cd para alterar o diretório. E então podemos digitar ls novamente para visualizar todos os arquivos e pastas. E você pode ver um monte de coisas aqui, mas não estamos interessados nelas. Ponto importante aqui que, se
vamos excluir esta pasta, todos os nossos bons detalhes do projeto serão excluídos. Então, se eu navegar de volta para a pasta principal, usarei CD e dois pontos, e agora vou excluí-lo. Então, vou digitar uma RAM do que nosso F e nome da
pasta para excluir todos os arquivos e pastas dentro do bem, e obter a própria pasta. Agora você pode ver esse título mestre e
mestre desapareceu aqui. Isso significa que agora o get é totalmente excluído desta pasta. Agora deixe-me digitar git nele novamente. E boom, bom, agora é inicializado mais uma vez. Ótimo. Agora, e esse título mestre aqui? O que é isso? Este é o nosso ramo atual. Vamos falar sobre filiais mais tarde. Agora mesmo. Não se concentre nisso. Estamos interessados em obter o que ele faz. Então, quais são os benefícios? Primeiro, vamos criar um arquivo aqui. Vamos chamá-lo de algum ponto de arquivo TXT. Aqui vamos digitar olá. Talvez este seja o nosso arquivo principal do projeto, muito despejo, mas fará o truque. Agora, para usar o bem, podemos digitar git status em primeiro lugar para entender o que está acontecendo neste
momento específico em um bom projeto. Então você ainda não pode ver commits. Atualmente, estamos no branch master e
temos vários arquivos não rastreados para serem mais específicos. Para um arquivo, alguns file.txt, nada adicionado ao commit, mas arquivos não rastreados presentes em um bom projeto arquivos podem estar em três estados diferentes. primeiro estado é um estado não rastreado, segundo estado é o estado do estágio. terceiro estado é quando os arquivos são confirmados. Então, neste momento, estamos em estado não rastreado. O que isso significa? Isso significa que seja detectado que
temos alguns novos arquivos em nosso projeto, mas eles ainda não fazem parte desse bom projeto. Para adicionar esses arquivos, para que eles saibam que queremos rastrear esses arquivos para incluí-los como parte de nosso bom projeto, precisamos adicioná-los ao estado do palco. Para fazer isso, precisamos digitar exatamente como diz aqui, git add file. Então, podemos digitar git, adicionar um pouco de file.txt. Pressionei tab para preenchimento automático. Então eu apenas digito algum arquivo, algum F, depois pressione Tab e ele permitirá completar o nome do arquivo para mim. Mas também posso fazer git add dot para adicionar todos os arquivos nesta pasta ao estado do palco. Portanto, o ponto representa todos os arquivos no diretório atual. Vou usar esse comando porque ele é mais curto. Git add dot. Agora você pode ver a cor alterada para azul aqui. E o que está acontecendo. Vamos digitar git status novamente para ver o que ainda não temos commits, alterações a serem confirmadas. Agora você pode ver que temos um novo arquivo, alguns file.txt. Ótimo. Isso significa que nosso arquivo está no estado do palco. E como estamos usando o VS Code, VS Code tem integração com o Git e a desintegração é uma ferramenta realmente poderosa. É por isso que aqui no painel esquerdo temos esse ícone com um número dentro dele. Vamos clicar nisso. Portanto, essas guias representam obter integração. Assim, você pode ver que temos dois suspensos aqui, mudanças e alterações
preparadas. Você pode ver que agora nossa soma file.txt dentro das alterações preparadas. Então você pode ver à esquerda o que era antes, e à direita com verde, o que foi adicionado, já que é um novo arquivo, não
vemos nada e vermelho à esquerda. Agora, se você está lutando com todos esses bons comandos ou eu não sei Por algum motivo, é
difícil para você se lembrar de todos eles. Você sempre pode usar a integração com o Git aqui. Então, se eu clicar em menos aqui, ele excluirá esse arquivo
do estado do palco e ele o
reverterá de volta para o estado não rastreado. Agora, se eu digitar git status, o terminal novamente, você pode ver arquivos
não rastreados, alguns file.txt. Agora, se eu quiser adicionar esse arquivo ao estado do palco, basta clicar no sinal de mais. Boom,
é, está em encenado novamente. Ótimo. Agora, qual é o estado do palco? Bem, esse estado de estágio é basicamente aquele estágio
pré-operacional em que os arquivos podem ser confirmados. Então, o que é um commit? Um commit é apenas um registro no histórico do
Git e representa as alterações feitas no projeto. Agora vamos confirmar esse arquivo em nosso bom histórico. Então, o que podemos fazer, podemos digitar git commit e , em seguida, precisamos digitar menos M para mensagem de commit. E vamos digitar alguns file.txt adicionados. Vou executar esse comando. E você verá o modo tratado, um arquivo alterado, uma inserção, ótimo. E todas as mudanças à esquerda desapareceram. Tudo bem. Agora, se vamos digitar git status novamente, você não verá nada para confirmar. Isso ocorre porque o commit é arma. Já está no passado. Good acompanha todos os nossos commits que fizemos no passado. Para visualizar o histórico do Git e o terminal, temos que digitar git log. Temos um commit que nomeamos edit some file.txt. Data é este e o autor, meu apelido e meu e-mail e commit hash no branch master. Digamos que eu queira adicionar novas alterações a esse arquivo. Vou apenas ir em frente e modificar esse arquivo. Vou digitar algo despejado e salvar o arquivo. À esquerda, você verá que temos novamente novas alterações no arquivo. E isso é o que adicionamos, isso é o que tínhamos antes. Agora, os mesmos passos. Precisamos primeiro adicionar essas alterações ou aquele arquivo
que foi alterado para o estado do palco, certo? E depois disso, poderemos confirmar esse arquivo. Porque agora, se eu vou fazer git
commit e digitar algo, você verá uma mensagem de erro. Bem, não é uma mensagem de erro, mas não confirmará nada porque bom só pode confirmar arquivos preparados. Por exemplo, se eu vou criar um novo arquivo, test.js e vou digitar, não
sei,
coisa muito básica em JavaScript, log do console. Olá. Vou voltar para essa guia. Vou digitar git status. Você verá que um arquivo foi modificado, um arquivo não é rastreado. Agora eu quero encenar todos esses arquivos. Vou fazer git add dot. E você verá que todos eles estão agora encenados. E se eu for digitar git commit, esses arquivos preparados serão adicionados ao novo commit. Tudo bem? No entanto, e se eu não quiser que todos esses arquivos sejam confirmados? Talvez eu tenha criado esse arquivo, mas ainda não estou pronto para confirmá-lo. Eu só quero comprometer essas mudanças no histórico. Então, o que vou fazer,
removerei test.js desse estado de estágio e deixarei apenas algum arquivo nesse estágio. Então, como eu disse antes, git confirma apenas arquivos preparados. Então, se eu for digitar git commit e
vou digitar algum file.txt editado. Vou executá-lo. Você verá que o teste permanece porque ele ainda não
está rastreado, não confirmado. E se eu digitar git log, verei agora que tenho que confirmar a nota. Agora, se eu quiser adicionar test.js, vou digitar novamente git add dot e depois git commit. E vou digitar edit, test. Sim, legal. Mais uma vez, boa sorte. E eu tenho meu histórico do Git lá. Isso é o que o bem faz. Ele nos permite criar esse histórico do projeto por meio de mensagens de commit. Mas, ok, isso parece útil, mas não vejo o ponto principal aqui para ver todos os arquivos, todas as alterações que você fez para obter projetos ou comandos diferentes, como um bom show, por exemplo. Assim, podemos digitar git show e, em seguida, commit hash para visualizar as alterações feitas neste commit específico. Então, vou apenas copiar isso e colocar uma boa mensagem de dinheiro do show. Temos esse commit. Essa é a diferença. No arquivo. Alguns file.txt, temos uma linha editada e a segunda linha editada. É isso. Então agora eu concordei que isso não é conveniente
ver tudo através do terminal. É por isso que existem muitas extensões
VS Code que podemos instalar para visualizar esse processo. Então, se eu digitar git na pesquisa de extensão, você verá muitas extensões diferentes como bom histórico, obter terras, bom gráfico. E todos eles ajudarão você a trabalhar com o bem. Eles permitirão que você visualize, reutilize e torne o desenvolvimento do kit o mais confortável possível. Eu pessoalmente não uso nenhum desses porque acho que essa integração é mais do que suficiente e o resto continuará no GitHub. Na segunda parte, vamos falar sobre o GitHub. Github está relacionado para obter o que é o GitHub. Você saberá tudo isso no próximo vídeo. Vejo você lá.
12. Trabalhando com Git - Parte 2: Olá, Bem-vindo à segunda parte da boa série. Neste vídeo, vamos falar sobre o GitHub. O que é o GitHub e por que precisamos dele? Vamos como lembrar, eu tenho o pequeno projeto bom da primeira parte em
que tenho dois arquivos e alguns commits no terminal,
se eu conseguir o log, poderei ver o histórico do Git desse projeto. Agora, a questão é o que acontecerá se eu for
excluir essa pasta do projeto de teste do meu PC, meu projeto vai desaparecer completamente? E a resposta para essa pergunta realmente será o GitHub. Ele virá em nosso resgate. Github é um serviço de hospedagem para bons projetos, assim como temos hospedagem para sites, GitHub é um serviço de hospedagem ou plataforma para bons projetos. Se eu for ao Google e procurar um GitHub, ele me levará ao site oficial. Se você ainda não tem uma conta do GitHub, sugiro criar uma já agora, neste
momento, já fiz login. Quero mencionar que existem alguns outros serviços de hospedagem populares para bons projetos, como o Git lab ou talvez o Bitbucket. A diferença entre eles será nos recursos e integrações que eles dão a você. Github é o mais comum. Tudo bem, agora, temos nossa conta do GitHub aqui, e gostaríamos de hospedar nosso bom projeto que temos localmente em nosso PC, no GitHub. Como podemos fazer isso. Então, primeiro precisamos criar um repositório remoto no GitHub. Se eu clicar no sinal de mais e no canto superior e clicar em novo repositório, ele solicitará meus novos detalhes do repositório. Um repositório é basicamente um projeto bem, que você coloca no GitHub. Então Repositório significa projeto, mas no GitHub, então nome do
meu repositório será meu projeto. Deixarei a descrição vazia a
visibilidade do repositório de que pode ser repositório
público e privado. Se você escolher público, seu repositório ficará visível para todos, mas somente pessoas autorizadas poderão
contribuir com esse repositório se ele for privado, ninguém jamais conhecerá e verá esse repositório. Então, vamos escolher privado e,
em seguida, vamos clicar em Criar Repositório. Então, nesta etapa, criamos um novo projeto no GitHub. Agora, precisamos associar a hora Local good project que
temos em nosso PC com um repositório remoto no GitHub. Podemos fazer isso de duas maneiras, seja por HTTPS ou através do túnel SSH. Ssh é uma opção disponível, mas o GitHub recomenda HTTPS porque é mais simples e fácil de configurar, vamos usar HTTPS. Você já pode notar que GitHub sugere algumas etapas como podemos associar nosso código local ou projeto
local ao repositório remoto. Vamos seguir o segundo passo para enviar um repositório existente porque nosso projeto local bom pode ser chamado de repositório Git local. Então, vamos apenas copiar o primeiro comando
daqui e colocá-lo no terminal. Então, o que o git remote adiciona origem? Vamos primeiro executar esse comando e vamos ver o que vai acontecer. Nada é impresso e isso é totalmente bom. Mas agora nosso bom projeto local sabe sobre esse repositório remoto. Podemos verificar se digitando git remote dash v, você verá origem e verá URL do
repositório que copiamos daqui. Ele também está disponível aqui. Agora, vamos dar uma olhada mais uma vez neste comando. Portanto, temos git remote add. Este é o comando para associar nossos repositórios. Origin é o nome de um alias que atribuímos a esse URL porque
é mais fácil sempre se referir a apelido ou a um alias em vez de URL o tempo todo, que era origem. Este é o nome mais comum. Certo. Agora, o que precisamos fazer para aplaudir nossos arquivos locais para a hospedagem, precisamos fazer git push do que o alias que
associamos ao nosso URL do repositório, que será origem e o nome do branch que queremos implantar. Então git push origin master. Se abrirmos novamente e o Git Hub, veremos que ele sugere um bom branch main e, em seguida, git push origin main como lembro Eu já mencionei que confusão há
cerca de um ano que a comunidade
quer mudar nome da ramificação padrão do mestre para o principal, mas vamos continuar usando o master agora. Então, vamos usar git push origin master em vez de git push origin main. Vou executá-lo. E você verá que a nova ramificação foi criada nessa taxa de URL. Vamos voltar ao GitHub, atualizar a página e o boom, podemos ver que tudo está visível aqui. Então, o que podemos fazer no GitHub. Github, podemos ver nossa boa história completa. Podemos ver todos os arquivos e podemos ver no momento que
este comando para esse arquivo foi criado, ok,
Então, três horas atrás foi o último commit para esse arquivo e para esse arquivo também para testes, sim, podemos clicar em Arquivos para visualizar o conteúdo. Na verdade, podemos clicar em commits para ver quais alterações foram feitas nesse commit. Então, para que algum arquivo editado seja comprovado, modificamos ou removemos essa linha e adicionamos essas duas linhas. Verde é o que foi adicionado. Vermelho significa algo que foi removido. Vamos voltar ao repositório aqui. Também podemos ver um bom histórico
completo clicando nesse botão. E podemos ver que temos três commits. Podemos navegar
no repositório neste momento, no histórico. Se clicarmos, podemos ver neste momento que havia apenas um arquivo. Vamos voltar ao repositório principal novamente respondendo à pergunta principal, por que precisamos do GitHub? Precisamos do GitHub para colaborar com outras pessoas ou para tornar nosso projeto portátil. O que quero dizer é que suponha que
perdemos acidentalmente essa pasta do projeto de teste em nosso PC local. Por algum motivo, ele simplesmente não existe. No entanto, nosso projeto existe no GitHub. Então, o que podemos fazer, na verdade não podemos carregar nosso projeto do GitHub e colocá-lo em nosso PC local clicando neste botão verde, temos algumas opções aqui. Podemos baixar zip ou podemos clonar. Então, se clicarmos em Download Zip, e se vamos abrir esse zip, você verá todos os arquivos dentro. Então, essa é uma maneira. A segunda maneira é clonar esse repositório usando a CLI. Então, vamos escolher a conexão HTTPS. Vamos copiar esse URL. E agora suponha que meu projeto de teste aqui não exista no PC. Eu o perdi. Então, se eu quisesse recuperá-lo ou recuperá-lo, farei git clone e, em seguida, o URL que copiei. Então ele copiará, criará uma nova pasta chamada meu projeto e colocará todos os arquivos dentro. Se eu for inspecionar minha pasta do projeto, você verá algum file.txt e testará, sim. Mas também se eu vou para minha pasta Project e se eu fizer, infelizmente F, para visualizar arquivos ocultos, haverá outra pasta Git aqui. Então isso ocorre porque quando você clona um repositório, ele já virá com uma boa pasta com a configuração do Git. Imagine que o projeto de teste nunca existiu nesse PC. Eu clono o repositório usando HTTPS e git clone. E agora minha configuração do Git já está concluída. Eu posso simplesmente navegar até
a minha pasta Projeto e tudo já está lá. Configuração para mim. Agora posso continuar a fazer novos commits, fazer algumas alterações
e, em seguida, fazer o upload para o GitHub novamente, deixe-me excluir minha pasta do projeto. Na verdade, não preciso disso. Vou navegar de volta. Agora. Como posso realmente continuar a desenvolver depois de ter meu projeto no GitHub? Essa é uma boa pergunta. Bem, assim como antes, se eu precisar introduzir novas mudanças no projeto, continuarei fazendo minhas alterações. Talvez eu adicione outra linha com olá dois aqui e salve-a. Agora, como você se lembra, eu tenho mudanças não rastreadas. Se eu digitar git status, você verá que o arquivo foi modificado. Então, novamente, preciso adicionar esse arquivo ao estado do palco. Vou colocar git add dot. Você verá aqui,
ele aparece agora em mudanças
preparadas e agora eu posso me comprometer. Então git commit adicionou hello two. Agora, se eu digitar git log, poderei ver o novo commit na parte superior. Agora eu tenho quatro commits, mas se eu voltar ao GitHub, não
vejo isso aqui porque GitHub e Git, eles não estão magicamente sincronizados entre si. Sempre que você fizer novas alterações no seu PC, elas são locais. Eles estão disponíveis somente no seu PC. E se você quiser vê-los na hospedagem, você precisa enviá-los para hospedagem. E para fazer isso, novamente
usamos o comando git, push, Good Push e o nome de LES e nosso alias. Podemos verificar se com git remote dash v, nosso Ls é origem, o que leva a este repositório, que está correto. Então, vou fazer git push origin e depois dominar o nome da ramificação. Agora vejo que minhas alterações foram carregadas. Eu atualizo a página. E outro comitê foi adicionado aqui há
um minuto, o que está correto. Se eu clicar nessa mensagem de commit, você verá que essas duas linhas para editar exatamente o que acabei de fazer. E mais uma vez respondendo à pergunta principal, o que o GitHub faz? Por que precisamos disso? Github é necessário para a colaboração entre pessoas e para tornar nosso projeto o mais portátil possível. No próximo vídeo, falaremos sobre filiais e como as pessoas estão colaborando usando o GitHub. Vejo você lá.
13. Trabalhando com Git - Parte 3: Olá, bem-vindo à terceira parte da boa série. Na última parte, implantamos com sucesso nosso bom projeto local no GitHub. E sabemos o que é o GitHub. É uma plataforma de hospedagem para colaboração e usamos o GitHub para tornar o projeto
superior o mais portátil possível. Nesta parte, vamos descobrir esses principais conceitos de bons ramos frios. E vamos falar sobre como podemos
colaborar no GitHub. Vamos. Primeiro de tudo, vamos falar sobre filiais. Este misterioso ramo mestre esteve aqui desde o início. Mas o que isso significa? Se vamos digitar git branch no terminal, veremos que você terá apenas master, mas podemos criar quantas ramificações quisermos. Então, branch é apenas aquela outra cópia do nosso projeto. Vejamos isso por meio de um exemplo. Então, vamos criar uma nova ramificação. Para criar uma nova ramificação, temos que digitar git checkout do que
menos b e, em seguida o nome da ramificação que queremos criar, vamos chamá-lo de meu recurso dash. Você pode ver mudar para uma nova ramificação. Meu recurso, novamente, digito git branch. Eu tenho mestre e tenho meu recurso e um conjunto de mestre. Eu vejo meu recurso agora, isso ocorre porque esse é meu branch ativo neste momento. Então, o que você vê aqui é sua ramificação atualmente ativa. Agora, qual é a diferença agora, essas duas ramificações são iguais, mas suponha que eu queira desenvolver um novo recurso no meu aplicativo, mas não quero tocar no meu código principal. Meu código principal permanece inalterado, mas eu queria desenvolver um novo recurso. É aqui que entram os ramos. Então, meu branch master contém meu aplicativo mais recente para o código implantado na produção. Funciona agora. E, ao mesmo tempo, eu queria desenvolver um novo recurso. Então eu crio uma nova ramificação chamada meu recurso, e agora começo a desenvolver nesse novo ramo. Suponha que eu esteja no meu branch de recurso, eu crio um novo commit. Meu novo recurso será um novo log do console, que será Olá três. Tudo bem? Agora eu confirmo essas alterações. Primeiro eu empurro para o estado do palco e depois faço um novo commit. Eu chamo isso desenvolveu meu novo recurso. Ótimo. Se eu fizer git log para visualizar o histórico, posso ver meu histórico anterior e, em seguida, meu novo commit, desenvolver meu novo recurso. Incrível, mas como isso é útil? Agora, se eu precisar, por algum motivo,
voltar para o meu código principal e ver o que estava lá. Agora sou capaz de alternar entre ramificações. Então eu coloquei git branch para ver o que branches fazem metade e, em seguida, posso fazer git checkout master para alternar entre branches, mas desta vez sem sinalização B menos. Agora mudei para branch master. E você pode ver como essa alteração que o dr. fez no meu ramo de recursos desapareceu. Isso ocorre porque essa alteração faz parte da minha ramificação de recursos. Ele não tem relação com o master porque se eu colocar um git log, você verá que eu não tenho esse commit que o libertei no meu branch de recurso, no branch master, é completamente diferente. Então, como você pode ver, Master e meu recurso são algum tipo
de cópia do meu projeto que existem ao mesmo tempo, eu posso manipular essas ramificações para desenvolver diferentes recursos. Agora, como posso realmente utilizar esse conceito de ramificação para torná-lo útil para mim ou para pessoas com quem eu colaboro. Então, suponha que existam 10 pessoas que trabalham no mesmo projeto e para convidar pessoas para um repositório e precisam ir para configurações, gerenciar o acesso. E aqui você geralmente convidará colaboradores. Portanto, as pessoas
que têm acesso a esse repositório privado poderão fazer alterações nesse repositório. Mas se tudo,
se todas as pessoas que trabalham em um projeto vão empurrar para o mesmo ramo principal ou ramo principal. Isso vai ser um pouco uma bagunça. Queremos torná-lo o mais estruturado, surgido quanto possível para manter nossa boa história limpa, legível e sustentável. E para fazer isso, utilizaremos ramos. Suponha que nosso código principal esteja no branch master, que tem o último commit adicionado olá para Eu sou outra pessoa sentada em algum lugar lá fora. Sou colaborador e crio uma nova ramificação, meu recurso que já criei e fiz algumas alterações. Quero enviar essas alterações para o GitHub e quero mesclar essas alterações no código principal, que está localizado novamente na ramificação principal. Então, o que eu preciso fazer, eu preciso primeiro empurrar esse ramo. Para o GitHub. Para fazer isso, farei git push origin porque este é o nosso alienígena para o repositório. Lembramos que git push origin, meu recurso. Vamos esperar um segundo. E agora ele é empurrado e até sugere que
criemos uma pull request para meu recurso no GitHub visitando. Vamos falar sobre isso em um segundo. Mas se voltarmos ao GitHub, já
vemos que meu recurso tinha push recentes há menos de um minuto. Compare e pull request. Se eu atualizar a página, agora aqui verei duas ramificações. Se eu clicar aqui, tenho o branch master padrão e tenho suas ramificações, meu recurso atualizá-lo há minutos por mim e principal ramo do CEU horas atrás por mim. E aqui posso ver se eu passar o mouse, verei um commit à frente do mestre. Agora, para enviar as alterações que tenho no meu branch de recurso para o master, preciso criar uma pull request diretamente no GitHub. Uma pull request é essa solicitação do desenvolvedor quando você pede aos mantenedores
do projeto que mesclem sua ramificação na ramificação principal. Então, basicamente, você quer contribuir e
gostaria de empurrar essas alterações para o código principal. Vamos clicar em nova pull request. Vamos nomeá-lo desenvolvido. Meu novo recurso deixará um comentário que, ei, acabei de fazer essa grande mudança. E aqui nós selecionamos isso. Queremos enviar, queremos mesclar minha ramificação de recursos no master. Esses são todos os commits que eu fiz naquela ramificação. Posso criar tantos commits quanto possível. Por exemplo, se eu adicionar outro commit, talvez console.log, olá para, novamente, eu encenar essas alterações, eu as confirmo novamente, nova alteração. Novamente, eu empurro, Good Push origin, meu recurso. A ramificação será atualizada. Mesmo que eu já tenha criado uma pull request, ainda não a
criei. Mas, de qualquer forma, então vou clicar
em criar , puxar, solicitar. E vamos ver o que temos aqui. Então, primeiro vemos a capacidade de verificação de mesclagem porque pode haver conflitos nessas alterações. Mas como não temos conflitos, está tudo bem. Então, veremos nossos pull requests aqui. Então, agora o que vai acontecer? Eu sou aquela pessoa que sentada ali criando essa pull request, então
entra o líder do projeto ou mantenedor do projeto e essa pessoa
responsável pela pull request vai aqui e vê que, Ei, essa pessoa queria mesclar essas mudanças. Então ele clica nessa pull request. Ok, ótimo, aquele cara fez uma grande mudança. Oh meu Deus. Quero mesclar essas alterações. Então essa pessoa mescla essa pull request. Então ele seleciona uma das opções aqui. Deixe-me clicar em merge pull request e vamos ver o que vai acontecer. Então, mescle pull requests dessa pessoa,
essa ramificação desenvolveu meu novo recurso, confirme mesclagem, mesclagem, solicitação de pesquisa, ramificação de exclusão
bem-sucedida e fechada. Vamos clicar em que o branch foi excluído, pull requests, merge. Se eu voltar ao meu projeto aqui, posso ver as pull requests de mesclagem do Sherlock 16, meu recurso, e agora faz parte de um bom histórico. Se eu clicar em commits, verei que primeiro tenho esses dois commits que tive no meu branch de recurso. E além disso, tenho outra pull request de mesclagem de commit. Agora, todas essas alterações que estavam na minha ramificação de recursos foram mescladas no código principal e estão disponíveis aqui. É assim que as pessoas geralmente contribuem por meio de pull request um, todas essas alterações estão no GitHub. Teremos discrepâncias porque temos sete commits no branch master, no repositório remoto, no GitHub em nosso projeto local, ainda
estamos tendo meu branch de recurso. E se formos ao master usando git checkout master. E se fizermos git log, veremos que o último commit aqui é adicionado hello two, enquanto aqui está, mesclar pull requests para um. Para corrigir isso, precisamos baixar as alterações mais recentes do GitHub em nosso código local para sincronizar o histórico. Para fazer isso, o comando é muito semelhante ao git push, mas em vez de git push, usaremos git pull. Então, novamente, obtemos pull do que as áreas do repositório e, em seguida, o nome da ramificação a ser extraída. Então, queremos tirar o mestre da origem. Vou executá-lo. E você verá isso ótimo, algo aconteceu. E como você pode ver, agora, todas as minhas mudanças estão aqui. O último commit introduzido, olá quatro e eu, e agora tenho olá no meu código. Muito legal verificar se eu faço git log novamente. E você vê que eu tenho vários pedidos de bomba de Sherlock 16, a
propósito, para sair desse estado quando, quando uma boa história transborda, você pode simplesmente digitar q e ele o levará para o terminal. Tudo bem, eu diria que provavelmente é isso, é
assim que as pessoas usam o GitHub para colaborar. O modelo seria um pouco diferente se for um repositório público e você quiser
contribuir para um projeto de código aberto. Mas não vamos cobrir isso nesta série. Isso é mais do que suficiente para entendermos como o Git funciona e como as pessoas colaboram umas com as outras. Então, novamente, vou repetir o fluxo mais uma vez normalmente. E se você quisesse criar uma nova mudança e estiver trabalhando em um projeto. Primeiro, você cria uma nova ramificação usando git checkout menos b e o nome da ramificação, pode
ser qualquer coisa. Tudo bem, então essas cópias, essa nova ramificação será criada a partir da ramificação que estava ativa no momento em que você executar esse comando. Portanto, essas ramificações agora conterão todos os commits que você teve ao executar este comando, ok, você continua desenvolvendo o branch de conduta, faz quantos commits precisar para concluir o recurso. Em seguida, você envia esse branch para o GitHub usando um bom Push. Em seguida, ele aparece no repositório. Em seguida, você vai para suas pull requests e cria uma nova pull request para mesclar essa ramificação que
acabou de publicar no GitHub no código principal, na ramificação principal. E então uma pessoa responsável virá e verá que, Ei, aquele cara quer mesclar esse ramo no código principal. E quando essa pull request for mesclada ou aceita, suas alterações serão mescladas no código principal. Depois disso, todos que estiverem trabalhando em um projeto, eles serão obrigados a extrair as últimas alterações
do branch principal usando o comando git pull. E é isso. Este é o fluxo básico de parabéns de colaboração do
Git e do GitHub. Acho que este é o nosso acabado para uma boa série, e eu vou vê-lo na próxima.
14. Instalando o Node): Olá, Neste vídeo, estamos prestes a instalar o Node.js no Windows. O que é NodeJS e por que precisamos disso é explicado no próximo vídeo. O que precisamos fazer é abrir qualquer navegador e acessar o Google. E o Google não procurará GS. O primeiro link será o site oficial. Aqui temos duas versões a serem baixadas, LTS e versão atual. A versão atual é a versão mais recente disponível para download, e o LTS é a versão estável mais recente. Não precisamos complicar demais. É por isso que pegamos LTS. Clique nesse e abra o instalador. Espere um pouco e clique em Avançar. Sim, eu aceito Próximo, mude o caminho se você precisar. Em seguida, nesta etapa não precisamos de GS, NPM e caminho de atitude. Em seguida, nesta etapa temos ferramentas para módulos
nativos e queremos selecionar essa opção. O que é isso e por que precisamos disso? Assim como diz, alguns módulos npm precisam ser compilados a partir do CC plus plus ao instalar. O que isso significa? Isso significa que existem algumas bibliotecas, módulos ou pacotes que instalaremos durante nosso desenvolvimento que exigem alguns binários nativos específicos para o sistema operacional, no nosso caso, janelas. Portanto, as ferramentas que compilarão esses músculos lisos são ferramentas de compilação
Python e Visual Studio. Então, essa opção apenas
os instalará se eles estiverem faltando agora, certo? Clique em Avançar e pressione Instalar. Não vou clicar em Instalar porque já não tenho GS instalado. Mas para você, isso é o que vai acontecer. Quando você clica nesse botão, você verá uma nova janela CMD aparecerá. E ele verá algo como vamos fazer e instalar esse pedido que exigiremos esse número de espaço. Basta fechar essa janela e depois disso, você verá que outra janela será aberta, que é a janela do PowerShell. E haverá todo o registro de instalação. Então, espere algum tempo até que esteja pronto e então você está bem. Nenhum JS é considerado instalado. Agora vamos verificar isso. Como fazer isso. Clique no painel Iniciar e procure cmd. Então abrimos isso. E no CMT nós digitamos espaço do nó, traço, versão traço. Pressione Enter e você verá a versão que acabou de instalar. Pode ser possível que, ao digitar nó dash, versão dash, você verá algo como nó não é reconhecido como um comando interno ou externo. Portanto, temos que encontrar outra maneira de verificar nossa instalação. Para fazer isso, precisamos voltar para iniciar o Painel do que para o painel de controle. E então vamos procurar programas e recursos, ok? Aqui precisamos verificar se não temos GS na lista. Portanto, se você não tem GS na lista aqui, ele lhe dá aviso não reconhecido como um comando extra interno. Então você precisa fazer um pequeno ajuste na configuração do sistema. Então, o que você precisa fazer é clicar novamente no painel Iniciar
no tipo de pesquisa ENV e selecionar editar as variáveis de ambiente do sistema. Em seguida, clique nas variáveis de ambiente. E aqui, em variáveis do sistema, você deve encontrar a variável de caminho. Clique duas vezes sobre esse. E na lista você não verá os Arquivos de Programas C. Sem JS, que é meu caminho de instalação sem jazz. Então, porque você não tem isso aqui na lista, você vê que nó não é reconhecido, ok? Então, o que você precisa fazer, você precisa clicar em Novo e adicionar seu caminho de instalação sem GS. Portanto, se você não modificou a opção na instalação, seria Arquivos de Programas C, NodeJS também. Então, clique em Novo, cole o caminho aqui, ok? Ok, ok, então basta reiniciar o terminal. Em seguida, tente o nó dash, a versão dash. Mais uma vez. Depois disso, você deve ver a versão. E é basicamente isso. Parabéns, você acabou de instalar o NodeJS no Windows. Vejo você no próximo.
15. Instalando o macOS (macOS): Oi, Neste vídeo, mostrarei como instalar o NodeJS no macOS. Vamos. Como sempre, você acessa o Google primeiro e digita NodeJS, vá para o primeiro URL, que é o site oficial, depois navegue até a página de downloads e clica no instalador do macOS. O download começará automaticamente. Abra o arquivo baixado. Você verá o assistente de instalação clicar em Continuar, depois aceitar os termos, depois verificar o caminho de instalação e clique em Instalar. Ele solicitará sua senha e tudo bem. Aguarde a instalação do GS logo após o processo de instalação, você não terá GS e NPM em seu sistema para verificar a instalação. Vamos para o terminal, vamos almoçar mal. Em seguida, procure o terminal para verificar o nó do tipo
NodeJS traço V, que significa a versão. Ele deve imprimir a versão que você instalou. E da mesma forma, também
precisamos verificar o NPM. Então digite npm dash v, e é isso. Vejo você no próximo.
16. NPM, Parte 1: Olá, bem-vindo a conhecer o vídeo de introdução do GS. Agora vamos falar sobre o que não é GS. Por que precisamos dele e como somos capazes de usá-lo? Vamos primeiro, o que não é GS sabe GS é o ambiente de tempo de execução JavaScript. Isso significa que é algo que nos permite executar JavaScript. E você provavelmente vai pensar, por que não precisamos de GS? Porque temos JavaScript em
execução no navegador e esse é o ponto. Hoje em dia, somos capazes de executar JavaScript fora do navegador com a ajuda do NodeJS, podemos usar JavaScript para escrever aplicativos móveis. Podemos usar o JavaScript para escrever aplicativos de desktop. Basicamente, podemos fazer qualquer coisa com JavaScript agora. Graças à nota, sim, porque nos permite executar JavaScript fora do navegador. Por exemplo, se eu abrir o navegador aqui, clico em Inspecionar e, em seguida, vou para o console. Portanto, esse é o ambiente do navegador. Sou capaz de escrever qualquer JavaScript que eu quiser aqui. Por exemplo, se eu quiser digitar console.log 5 mais 2, ele imprimirá seis para mim. Isso é ótimo, mas isso está dentro do navegador. Se eu quisesse executá-lo em outro lugar, eu não teria permissão para fazê-lo. Mas com a ajuda de nós, sim, poderei fazer isso. Vamos para o código VS e
deixe-me criar uma nova pasta de projeto. Vou para a pasta Meus Projetos, e aqui vou colocar o teste GS. Selecionarei essa pasta. E agora vamos criar um novo arquivo aqui, vamos chamá-lo de test.js. Antes de escrevermos qualquer coisa, primeiro
vamos garantir que não temos JS instalado. Somos capazes de acessá-lo. Para isso, abrirei meu terminal integrado. E para acessar o NodeJS, só
preciso digitar nó. Depois que eles executarem o comando node, entrarei no ambiente Node.JS. Então, aqui, poderei executar JavaScript. Por exemplo, a mesma coisa que eu fiz no log
do console do navegador 2 mais 4. Muito incrível. Esta é a prova de que o JavaScript foi executado fora do navegador. Mas isso não é muito conveniente para nós
sempre escrever JavaScript dentro do terminal. Então, para sair desse modo, que pressionará Control mais C várias vezes. Ótimo. E agora, em vez disso, vamos escrever alguns arquivos JavaScript que mais tarde executaremos
sem JS antes de entrarmos em arquivos, eu só quero mencionar que todos os arquivos,
todos os arquivos JavaScript que são executados dentro do ambiente Node.JS será um módulo. Um módulo é um arquivo JavaScript autônomo. Isso significa que não se sabe sobre o mundo
exterior apenas o que está escrito por dentro. Vamos primeiro criar talvez Sou audível? Const cinco é igual a cinco. E agora vamos consolar o log de pontos 5 e pressione Salvar. É isso. Acabamos de criar nosso primeiro roteiro. Agora vamos executá-lo para executar um arquivo, temos que digitar nó e, em seguida, o nome do script que gostaríamos de executar. Então, isso vai ser o teste GS. Eu executo esse comando e você pode ver cinco no console porque eu apenas consolo o log 5. Se eu for remover essa linha, vou comentá-la. E vou tentar executar o script novamente. Nada será impresso. E isso é óbvio porque não fazemos nada lá dentro. Agora, vamos tornar nossa tarefa um pouco mais difícil. E se tivermos dois arquivos para módulos? Deixe você criar um segundo ponto aqui, e vamos colocar uma string aqui. Talvez meu nome, eu imprima Andrew. E o que eu quero fazer, quero de alguma forma compartilhar informações entre esses dois módulos. Então eu queria passar meu nome
do segundo gs para o teste. Sim. E eu sou capaz de fazer isso por meio de importação e exportação. Então, para exportar algo de um módulo, usamos o módulo. Então, nossos especialistas do que exportamos um objeto. E neste objeto, colocarei minha variável de nome assim. Então eu posso fazer isso realmente assim. Meu nome, então chame meu nome. Mas em JavaScript podemos usar uma abreviação. Podemos simplesmente colocá-lo assim e funcionará muito bem. Agora meu nome é exportado do segundo gs. Vamos tentar importar isso. Se eu voltar para Ts, gs, deixe-me remover tudo isso. Vou colocar um const que
vou nomear minha exportação algo como. Importou meu nome, seja o que for. E para importar o que eu exportei daqui, preciso digitar obrigatório. E por dentro exigem, eu coloco caminho para esse módulo, que será apenas o segundo GS. Não preciso especificar a extensão. Então, coloquei ponto e barra aqui para especificar que esse arquivo está localizado nesta pasta. Agora, o que vou fazer, simplesmente o log do console importou meu nome. Eu salvo o arquivo, volto para o terminal
e, novamente, nó, teste, GS. Boom, o que eu vejo, eu tenho um objeto. E esse objeto contém minha chave de nome. Exatamente o que eu exportei do segundo, sim,
na verdade, podemos renomear isso para o segundo módulo importado. E então eu posso fazer referência ao segundo módulo importado ponto meu nome porque este é um objeto e tem chave meu nome. Eu salvo, executo o script novamente e entrei impresso no console. É assim que o NodeJS funciona simplesmente criando módulos
diferentes que compartilham dados entre si. Esse sistema com uma exigência e com exportações de
módulo é chamado GS comum, que é escrito assim. Vírgula gs. Este é um sistema de exportação de importação nativo em Node.JS. No entanto, neste momento, comunidade
NodeJS está trabalhando ativamente e usando o sistema que é chamado de módulos ECMO Script. Portanto, esses módulos fazem parte do ambiente do navegador e, no momento, são experimentais em um ambiente Node.JS. Portanto, eles são ligeiramente diferentes das exportações de exigências e módulos, mas são mais fáceis e intuitivas de usar. Vamos experimentá-los. O que você acha para usar moléculas
ACML Script no ambiente Node.JS, temos que adicionar outra extensão aos nossos módulos. Então, em vez de js, precisamos usar o MGS, que será módulo GS, MGS e renomear esse arquivo também, vai ser mgs. Então, em vez de obrigatório, vou comentar essa linha
pressionando Control Slash. E, em vez disso, usarei Importar. Então, como exportamos um objeto, colocarei novamente colchetes encaracolados. E vou especificar que preciso importar meu nome. É importante especificar
o mesmo nome porque se eu
for especificar algo diferente, ele não existe no objeto exportado, certo? Então vou colocar meu nome do segundo módulo. Ótimo. E agora vou registrar meu nome no console. E no segundo MGS, em vez das exportações de módulos, simplesmente
digito exportar meu nome. É isso. E parece muito,
muito mais limpo que o CommonJS. Agora vamos tentar um teste de nó executado. Sim, e nós teremos, não é possível encontrar o módulo aha IC. Isso ocorre porque eu provavelmente tenho que especificar a extensão. Deixe-me experimentar. Sim, exatamente. Portanto, há mais uma desvantagem com o módulo usando scripts ECMO no estado atual do NodeJS, tenho que sempre especificar a extensão com CommonJS, posso admitir especificar a extensão quando a Importar módulos diferentes como esse, mas com o módulo de scripts ECMO, eu tenho que fazer isso. O resultado é o mesmo. Vou executar o script. Eu tenho Andrew, mas você pode ver agora ele
usa o módulo de scripts ECMO em nosso projeto. Quando faremos todas essas coisas de desenvolvimento, usaremos o ambiente Node.JS e vamos utilizar
os módulos Achmat Script. Você pode ver que este é um exemplo muito simples. Ele usa scripts únicos aqui, nada complicado. No entanto, obviamente precisamos de algo mais complexo e esse é o nosso tópico para o próximo vídeo. Vejo você lá.
17. NPM, Parte 2: Ei, bem-vindo à segunda parte da introdução do NodeJS e à última parte que
discutimos o que é não sim, e como podemos executar scripts únicos. Neste vídeo, vamos falar sobre o NPM e como podemos usar o npm para gerenciar dependências de projetos e projetos. Vamos. Primeiro de tudo, o que é npm? Npm significa Node Package Manager e já vem com o NodeJS. Portanto, se você não tiver JSON instalado, você já tem o NPM para verificar
se dentro do terminal, basta digitar npm. Há uma versão dash e ela imprimirá a versão do NPM atualmente instalada. Agora, como podemos usar o npm ou o que ele faz por nós? Bem, o problema é que em projetos JavaScript reais, existem dependências ou pacotes de projeto. Portanto, essas são essas bibliotecas, módulos
diferentes da Internet ou ferramentas
diferentes que instalamos em nosso projeto. E npm é a ferramenta que nos permitirá fazer isso. Então, para instalar esses pacotes, mas primeiro, como inicializar o npm dentro da nossa pasta do projeto. Para fazer isso,
temos que usar o comando npm init. E depois de executar esse comando, ele solicitará algumas coisas, como nome do pacote, versão e outras coisas. Basta ignorar isso pressionando enter o tempo todo. Quando o comando for concluído. Na rota do projeto, você verá pacote de arquivo package.json Jason é
aquele arquivo manifesto que descreve nosso projeto dentro, podemos ver o nome do projeto, talvez a descrição da versão do projeto. Se vamos colocar as luzes do
autor e ver se temos algum script e algumas outras seções sobre
as quais falaremos em um segundo. A questão é: qual pacote JSON faz para nós? Como isso pode ser útil? Bem, vamos para o navegador. Vamos procurar o NPM no Google e
vamos acabar no site oficial do npm. Npm tem o registro NPM. Então Node Package Manager é uma ferramenta que nos
permite gerenciar pacotes dentro do nosso projeto. Mas de onde vêm esses pacotes? Eles vêm do registro NPM. O registro NPM é aquele oceano de diferentes pacotes, ferramentas e bibliotecas que podemos instalar em nosso projeto usando npm. Então, neste site, você pode procurar pacotes diferentes. Existem milhões, bilhões de bibliotecas
diferentes que podemos usar. Mas, por enquanto, vamos procurar o que eu
preparei , que é cowsay. Vamos clicar nesse. E agora podemos ver a página oficial para estes pacotes nessa página, podemos encontrar sua documentação, como podemos instalar esse pacote,
o que ele faz, como podemos usá-lo e todas as outras coisas. Podemos ver que ele tem para dependências. O problema é que os pacotes publicados no registro do NPM têm dependências, e essas dependências também são pacotes publicados. E esses pacotes também podem ter Dependências. Dependências, dependências e dependências de dependências são chamadas de dependências de pares. Nessa página, também podemos encontrar algumas informações sobre o assunto, como a versão, quantos downloads semanais ele tem o autor publicado pela última vez e algumas outras coisas. Vamos ler a documentação. O que vemos aqui? Primeiro de tudo, o que esse pacote faz? Bem, este pacote é basicamente muito simples. Seu único propósito é apenas imprimir essa vaca no terminal. Então, vamos ver a parte de instalação, npm instalar menos g cowsay. Vamos copiar esse comando e vamos colocá-lo em nosso terminal. Vamos ver o que vai acontecer. Assim, podemos ver que algo está acontecendo. Podemos ver que a instalação já foi bem-sucedida. Podemos ver os pacotes Editar 41 e a versão que instalamos, que é 1.5. Por que 41 pacote? Assim como mencionei anteriormente, pacotes têm suas próprias dependências, e essas dependências têm suas próprias dependências. E, eventualmente, temos essa árvore de dependência. É por isso que, no final, temos 41 pacotes no total. Temos o npm instalado cowsay. O que ele fez? Bem, ele acabou de instalar o cowsay em nosso sistema como um pacote global. Como um pacote global porque nós menos o sinalizador g para verificar se
podemos digitar npm list menos g, então dash, dash depth é igual a 0. Vamos executar esse comando e vamos ver o que é impresso. Já tenho alguns pacotes instalados aqui globalmente, mas na sua lista você verá cowsay. Então, o que isso significa? O que isso nos dá? Isso significa que agora podemos usar o pacote como CLI globalmente em nosso sistema. Vamos ver o parque de uso, Cowsay JavaScript. Vamos copiá-lo. E vamos tentar executá-lo no terminal. Eu tenho uma pequena vaca bonita aqui dizendo JavaScript. Então isso é exatamente o que esse pacote faz, e podemos usá-lo como um CLA em nosso terminal. E isso não importa de onde ele está disponível globalmente. Se eu abrir outra instância do Git Bash aqui, ainda
poderei usar cowsay. Porque novamente, instalamos o cowsay como um pacote global. Isso significa que podemos usá-lo em qualquer lugar. Existem dois tipos de pacotes, ou eu diria duas maneiras de instalar um pacote. Primeiro, podemos instalá-lo globalmente, assim como você vê aqui. Portanto, quando um pacote é instalado globalmente, ele não é limitado a nenhum projeto, é instalado globalmente em seu sistema. A segunda maneira é instalar um pacote como dependência do projeto. Quando um pacote instalado como dependência de projeto, em
primeiro lugar, ele não está disponível globalmente. Ele se torna disponível apenas naquele projeto em que foi instalado, vamos primeiro desinstalar o cowsay como um pacote global
e, em vez disso, vamos instalá-lo como uma dependência do projeto. Então, primeiro vamos digitar npm instalar menos g cow sake. Você verá no final removido o grau 41 do pacote. Agora, para instalar o cowsay como uma dependência de projeto, temos que fazer o npm instalado cowsay, mas desta vez sem sinalizador de menos g, vamos executar esse comando e vamos ver o que vai acontecer. O que há de novo no File Explorer lateral. Então, primeiro, se abrirmos o pacote Jason, veremos a nova seção de dependência. Então, como o pacote Jason é nosso arquivo de
manifesto, ele conterá, ele
listará todas as dependências que instalamos. Então, instalamos apenas um cowsay de
dependência dessa versão. Agora também vemos package.json. E package.json aparece sempre que você instala qualquer finalidade package.json de dependência.json é procurar versões
das dependências instaladas e dependências de dependências. Dessa forma, podemos evitar problemas
diferentes com resoluções de versão. E também temos pasta de módulos de nó. pasta de módulos de nó é aquela pasta em
que todos os pacotes foram instalados. Se
abrirmos essa pasta, veremos vários pacotes diferentes aqui junto com cowsay. Estes são aqueles 41 pacotes que vimos foram instalados. Eles estão aqui em módulos Node. Se quisermos excluir essa pasta, eles serão excluídos. Agora, vamos voltar para cowsay e vamos ver como podemos realmente usar esse pacote. Então, se rolarmos para baixo, podemos ver o uso como um módulo. Lembre-se de que eu disse a eles que todos os arquivos em Node.JS, nossos módulos são iguais aos pacotes. Como os pacotes no registro NPM também
são arquivos JavaScript, isso significa que existem módulos. Então, vamos ver como podemos usá-lo como um módulo. E olhando para esse trecho de código, posso dizer que este exemplo usa require, que significa que ele usa o sistema de importação CommonJS. Mas agora sabemos que há CommonJS e também há módulos ECMO Script. Então, em vez disso, vamos usar módulos atmosféricos. Então, vamos copiar esse exemplo. E vamos colocá-lo dentro do nosso teste mgs. Mas em vez de exigir, eu uso na importação do meu script. Então, vamos digitar cowsay de importação de cowsay. E aqui eu tenho que especificar o nome do pacote, onde o nome da dependência do pacote JSON. Não preciso especificar o caminho que não preciso referenciar módulos de nó. Eu só preciso digitar o nome da dependência, que vai ser cowsay. Agora, vamos excluir isso e vamos excluir isso, e vamos salvá-lo. E vamos tentar executar esse script. Vou digitar o nó test.js. E vamos ver, novamente temos aquela vaca dizendo que sou um Moodle, mas agora cowsay faz parte do nosso projeto. Quando o instalamos globalmente, era independente. Era apenas uma ferramenta em nosso sistema que podemos usar através do terminal. Mas desde agora cowsay faz parte do nosso projeto, estamos limitados a cowsay neste projeto específico. Se eu for remover a pasta de módulos de nó, vamos avançar e excluí-lo completamente. E se eu vou tentar executar esse arquivo novamente,
você verá que não conseguirá encontrar pacote cowsay porque acabamos de excluir todos os arquivos necessários para executar o cowsay. Então, para reinstalar os pacotes listados no pacote Jason listado em nosso projeto, temos que digitar o npm instalado sempre que não
tivermos pasta de módulos de nó, mas precisamos instalar os pacotes. Acabamos de digitar npm install. Então, o que ele vai fazer, ele vai olhar dentro do pacote Jason. Ele procurará a seção de dependência e instalará pacotes ausentes. É isso. Agora você pode ver novamente no pacote 41, se eu executar o script novamente, a vaca estava lá. Incrível. Vamos inspecionar o pacote JSON e vamos encontrar a seção de scripts aqui. Quero falar sobre esta seção agora, o problema é que nos projetos, existem alguns scripts específicos de projetos. Portanto, esta seção é chamada de scripts NPM. Portanto, geralmente scripts específicos do projeto são definidos por meio de scripts NPM. Já temos um script de teste definido aqui, mas vamos removê-lo e vamos definir nosso próprio script. Pode ser qualquer coisa, podemos nomear o que quisermos. Por exemplo, meu script de teste. E aqui precisamos digitar o que o script fará. Por exemplo, se no terminal
imprimir algo na saída, eu usaria o comando echo, echo, hello e hello é impresso. Então, bem, aqui podemos definir a mesma coisa. Por exemplo, meu script de teste executará echo hello, por exemplo, no código hello. Agora, para executar esse script NPM, tenho que digitar npm run e o nome do script, que será meu script de teste. Depois de executarem esse comando, esse comando procurará o pacote JSON nesta pasta, e ele olhará dentro desta seção de script, e ele encontrará meu script de teste, e então ele simplesmente executará o que estiver escrito aqui. Vamos experimentá-lo. Você pode ver que eu tenho Hello, basicamente o mesmo resultado. É isso, por que pode ser útil. Bem, há algumas
situações em que podemos ter um roteiro
muito, muito longo aqui. Imagine que seja assim. E agora, em vez de escrever tudo isso, o tempo todo, podemos simplesmente executar o npm, executar meu script de teste, e isso fará a coisa. É isso. Vamos falar sobre scripts NPM mais em detalhes uma vez que vamos lançar um projeto React real por enquanto, vamos deixá-lo vazio. Mais uma coisa que quero mencionar aqui é que as dependências
do projeto podem ser de dois tipos. Na verdade, existem dependências regulares que usamos em nosso código-fonte, e pode haver dependências de desenvolvimento. Portanto, as dependências de desenvolvimento também fazem parte do projeto, mas não são referenciadas dentro do código-fonte. Eles são usados apenas para desenvolvimento. Portanto, esses pacotes que vamos instalar para desenvolvimento serão pregadores e ES lint. E vamos instalá-los como dependências surdas. Falaremos sobre eles nos próximos vídeos. Eles serão usados para facilitar nosso desenvolvimento, mas são opcionais. Se vamos remover dependências de desenvolvimento, o projeto ainda poderá ser executado. No entanto, se removermos essa dependência daqui, se vamos remover módulos de nó, o projeto não poderá ser executado porque depende do cowsay. Portanto, se removermos dependências de desenvolvimento, o projeto ainda poderá ser executado. Mas se removermos a dependência principal, o projeto não será executado porque agora a dependência está faltando porque nosso projeto depende disso. Mas as dependências de desenvolvimento são apenas dependências para nosso ambiente de desenvolvimento. Ele não tem influência direta no código-fonte. Vamos falar sobre isso mais uma vez uma vez que vamos falar sobre pregador na gasolina. Mas, por enquanto, acho que é suficiente. Todos os projetos JavaScript são gerenciados assim usando npm, os pacotes de registro NPM, você terá o JSON empacotado em sua pasta raiz. Você terá dependências
instaladas a partir do registro do NPM. Então você fará referência a essas dependências em seu código-fonte. No final do dia, quando você tiver que
desenvolver o projeto ou precisar construir o projeto, você terá scripts NPM definidos aqui no pacote Jason. E é isso. É assim que todos os projetos JavaScript se parecem. É isso para o NodeJS. E eu vou te ver no vídeo ES fiapos e pregadores.
18. O que são prettier e ESLint?: Ei, neste vídeo eu gostaria de
falar sobre pregador em ES lint. Quais são essas ferramentas? Por que nos importamos e como eles vão nos ajudar? Vamos descobrir isso juntos. Então, a primeira coisa que quero mencionar que neste vídeo, vou reutilizar o mesmo projeto que
criei no vídeo de introdução do Node.JS. Como você se lembra, ele contém apenas uma dependência, que é cowsay, e nós a usamos dentro apenas do MGS. Vamos começar. Pregadores uma ferramenta que
vai formatar todos os nossos arquivos. Ele tem apenas um propósito para formatar arquivos. Ele ganha o conflito predefinido. Então, vamos descobrir como podemos usar o pregador. Se formos ao Google e procurarmos um pregador, você acabará no site oficial. Vamos para a documentação oficial de instalação e vamos segui-la. Primeiro pregador instalado localmente. Vamos copiar esse comando e vamos colocá-lo dentro do terminal. Portanto, a sinalização save-dev dentro do comando significa
que esse pregador de pacotes será instalado como uma dependência de desenvolvimento. Se vamos abrir package.json, veremos uma nova seção aqui, dependências de
desenvolvimento, que são dependências do desenvolvedor. E veremos pregador aqui. Agora. Vamos continuar com os cães. E aqui criamos um arquivo de conflito vazio. Mais uma vez, vou copiar o comando. Coloque-o no terminal, e ele criará um pregador vazio RT JSON para mim, cada pregador de ferramentas e Eastland, requer um arquivo de configuração para entender o que queremos dessa ferramenta. E podemos ver todas essas opções de conflito para pregador dentro da documentação no link Opções. Se vamos aqui, veremos diferentes opções aqui que podemos usar a imagem interna RC Jason, por
exemplo, tab com. Então, vou usar a largura da guia daqui. Só vou copiá-lo, colocá-lo dentro da configuração. E podemos ver que o padrão é dois. Então deixe-me colocar 10 aqui e vamos ver o que vai acontecer. Salvei o arquivo. Volto para testar o MGS. Pressiono Control S para salvar o arquivo. E boom, você vê que o recuo mudou. Agora. Ele usa a largura da torneira de 10 linhas vazias. Você provavelmente está pensando como é automaticamente como formatar esse arquivo. O problema é que o que acabamos de instalar dentro do nosso projeto sob dependências de desenvolvimento, instalamos o pregador como uma ferramenta, mas fora da formatação, como vemos, recurso está disponível através do VS Code extensão que você já
deveria ter instalado até agora. Se você não fez isso, vá para a guia Extensões. Procure pregar aqui. Esta é a extensão e
instale-a e verifique se ela já está configurada. Se você não fez isso, para assistir ao vídeo
VS Code Configuration de projeto para projeto, você deseja reutilizar o pregador. Você não quer sempre especificar opções diferentes aqui. Confie em mim, haverá apenas alguns. Então, por esse motivo, vou compartilhar com vocês esse presente e você poderá simplesmente copiar e colar conflito de pregador
que eu uso em todos os lugares. Então deixe-me colocá-lo aqui e deixe-me salvar o arquivo. Como você pode ver, eu uso cinco comandos e isso é suficiente para que um pregador funcione. Você pode ver se eu vou salvá-lo. Ele usa esse conflito agora. Incrível. Então, respondendo à pergunta, por que precisamos de pregador? Primeiro de tudo, você precisa entender que o pregador é uma ferramenta opcional, mas é altamente recomendável que você tenha pregador dentro do seu projeto JavaScript. A razão para isso é porque queríamos tornar nosso código o mais legível e sustentável possível. E o pregador nos ajudará com isso. Qual deles você prefere? Essa formatação estranha? Porque por algum motivo você não terminou o recuo manual ou prefere um código muito limpo alcançado com o pregador? Acho que será a segunda opção. Por fim, considere uma situação em que você tem muitos arquivos dentro do projeto e eles não estão formatados. Pregador. Então, o que fazer neste caso? Bem, a primeira opção é, claro, ir
para todos os arquivos, pressionar Control S para salvar cada arquivo manualmente
e, em seguida, o pregador se formará neles. Mas isso não é muito conveniente. Seria melhor criar um script que formate todos os nossos arquivos de uma só vez. E esse script usaremos pregador, e é aqui que entram os scripts NPM. Vamos criar um script NPM que usará o pregador para formatar todos os nossos arquivos dentro do projeto usando o pregador RC JSON. Então, se voltarmos à documentação do pregador, vamos para a página de instalação. Vamos rolar para baixo e aqui podemos ver agora formatar todos os arquivos com pregador e temos esse comando e px pregador dash, traço ponto direito. Deixe-me copiá-lo. E vamos voltar para os scripts do NPM. Então, aqui vamos definir e você o
script NPM que vamos nomear o formato. Dentro desse roteiro, vou colocar n px, pregador, traço, ponto direito. No entanto, nós realmente não precisamos e Px aqui, você pode ler o que é n px neste alerta amarelo. Temos certeza? Então n px é basicamente uma ferramenta que é fornecida sem JS que permite executar pacotes diretamente
do registro NPM sem instalação. Se eu não instalei o pregador e então usaria n px pregador dash, dash Reidar. Funcionaria porque o NP x usará pregador sem instalação
diretamente do registro do NPM, mas não precisamos dele. Temos pregador instalado. E quando escrevemos pregador aqui dentro do script NPM, ele usará o pregador instalado dentro dos módulos de nó. Vamos experimentar esse comando que acabamos de definir. Vou voltar ao meu terminal e
executarei o formato npm run. Você verá que algo está acontecendo. E agora alguns arquivos são afetados, basicamente todos eles. Vamos sacudi-los. Portanto, temos esse arquivo formatado, esse arquivo formatado, esse arquivo formatado. Então, basicamente, tudo agora está formatado usando um pregador. Vamos voltar ao pregador RC Jason, e talvez vamos mudá-lo para 10 tablets. E vamos executar novamente o comando npm run format. E você verá que todos os arquivos agora estão formatados contra o conflito de pregadores que acabamos de definir. É isso. Agora você sabe o que o pregador faz e por que precisamos dele? Vamos resumir rapidamente. Preacher é uma ferramenta que formatará arquivos dentro do nosso projeto atual, mais bonito tem um arquivo de configuração que é pregador de pontos RC JSON. Podemos usar o pregador por meio dos scripts NPM ou podemos usar o pregador por meio da extensão VS Code que instalamos. Então essa extensão, a única coisa que
faz, só nos permite formatar arquivos. Quando apertamos o botão Salvar, se quisermos desativar essa extensão ou se não a tivermos, o
pregador não se formará em nossos arquivos quando clicarmos em Salvar, a única oportunidade para formatar o os arquivos serão através do nosso script NPM personalizado, que nomeamos formato. Mas com a extensão, é muito, muito mais conveniente. Agora, vamos passar para ES lint antes de saltarmos para Eastland, deixe-me voltar rapidamente à nossa configuração anterior aqui e executar novamente o comando format. Incrível. Agora, o que é Eastland? Eastland também é uma ferramenta opcional que nos
permitirá verificar
o JavaScript em relação a alguns problemas comuns, relação a algumas diretrizes de código predefinidas. Precisaremos do ES lint para verificar se
não temos erros muito simples em nosso código, como variáveis indefinidas, variáveis não utilizadas, ou talvez tenhamos algum pedaço de código que é usado forma errada e ES lint irá
deixe-nos saber sobre isso. Então, novamente, assim como com pressão, vamos ao Google e vamos procurar o ES lint. Vamos clicar aqui. Você pode ver que o ES lint é linear. Então, linear é uma ferramenta que realmente verifica o código contra erros. Vamos clicar em Começar
e, novamente, basta seguir a documentação. Então npm instale ES lint save-dev, copy. Vamos colocá-lo no terminal novamente. Dash, dash save dev flag garantirá que o ES lint será instalado como uma dependência de desenvolvedor no pacote Jason, novamente, dependências de desenvolvimento de água, dependências de desenvolvimento são as ferramentas que usamos no desenvolvimento ambiente. Eles não fazem parte do código-fonte. Então, se eu vou remover a Islândia e o pregador, meu projeto ainda poderá ser executado. Ótimo. Temos ES lint instalado. Agora vamos seguir a documentação. Então, ele nos sugere usar o comando init para inicializar o arquivo de configuração. Então, em vez disso, vamos criá-lo manualmente. Então, vou criar um novo arquivo aqui, e vou nomeá-lo ponto ES lint RC. Então esse será meu arquivo de configuração do ES lint. Para configurar o ES lint, temos que seguir exatamente o mesmo padrão que com o pregador. Você tem que criar um arquivo de configuração e temos que colocar alguns comandos para permitir Yes Lint entenda o que queremos dele. Vamos voltar ao site e aqui temos configuração. Então, vamos apenas copiá-lo. Mas vamos mudar algumas opções aqui. Vou colocá-lo aqui. Vou remover isso e acabamos com a seção de regras. Dentro da seção de regras na Islândia, RC, definimos regras ES lint que gostaríamos de usar dentro do nosso projeto contra o qual nosso código será verificado. Por exemplo, posso digitar uma regra chamada vírus não usado, e precisamos fornecer algumas opções aqui. E você pode ver isso até me dá editor de
preenchimento automático desligado e desgastado. Então, o que são esses? Então, se eu vou adiar, essa regra será desativada e meu código não será verificado em relação a essa regra. Se eu vou colocar como
uma opção para alguma regra de lint ES. Isso significa que quando eu for contra essa regra, ES fiapos me dará um aviso. E eu tenho uma terceira opção, que é erro. Isso significa que sempre que eu for contra essa função, Sim, o Lint produzirá um erro. Então, há algumas, digamos, regras
cruciais que eu quero ser relatadas para mim como outra. E há algumas regras menores que eu quero ser relatada para mim como avisos. Podemos encontrar todas essas regras dentro da documentação. Eu sempre sugiro que você olhe dentro da documentação. Você pode encontrar tudo lá para que você possa até ver as opções de erro de advertência aqui, exatamente o que é dito para você. Agora, podemos ir ao Guia do Usuário e podemos seguir as regras. Esta é uma referência de regras. Você sempre pode encontrar todas as regras aqui. Por exemplo, se eu vou procurar barras não utilizadas, você pode vê-lo aqui. Vamos procurá-lo. Sim, não permita variáveis não utilizadas. Então é isso que a regra faz, é isso que permite o uso de variáveis não utilizadas. Então, vamos experimentá-lo. Vou voltar ao meu código. E aqui o que eu tenho erro de análise, a entrada da chave é reservada. Bem, sim, primeiro precisamos deixar o ES lint entender que estamos usando a sintaxe JavaScript mais recente. Para fazer isso, vamos ao ES fiapos. Aqui, adicionamos outra opção que será opções de analisador. Então, dentro das opções do analisador, temos que fornecer a versão AVMA. E vamos colocar 2020 aqui quando eu salvar o arquivo e voltar a testar o MGS, e vejo outro erro dizendo que importação e exportação podem aparecer apenas no módulo do tipo
fonte proveniente do ES lint novamente. Então eu volto para yes Lind e posso fornecer outra opção aqui será o tipo de
origem, o grau do módulo. Agora não temos nenhum erro ou avisos, então não temos uma regra de vírus não utilizada definida que produzirá um erro sempre que formos contra isso, é
verdade, Vamos testar mgs. E aqui vamos criar uma variável de uso final. Talvez eu dê o nome de Olá. E o que vemos aqui? Vemos que ele é destacado com linha vermelha. Se eu passar o mouse, você verá o quão baixo é atribuído um valor, mas nunca usado. E vem, como você pode ver ES lint, nenhuma variável não utilizada. Se eu for voltar ao ES lint RC, e se eu for desabilitar essa regra, desabilite
a verificação contra essa regra. Você verá agora, eu não tenho nenhum aviso ou um somador. Então, vamos voltar aqui e vamos colocá-lo como um aviso. E podemos ver que é amarelo porque é um aviso agora. E se eu colocá-lo de volta, ele ficará vermelho. Incrível. Talvez vamos manter um aviso e vamos voltar à documentação. Então, vamos voltar para a página de instalação. E aqui podemos ver na parte inferior que
também podemos colocar a opção de extensões dentro do ES fiapos. O problema é que o ES lint tem muitas regras diferentes e escreve todas essas regras manualmente aqui o tempo todo. Isso não é muito conveniente porque nosso ES fiapos nosso vai ser bonito, muito longo. Isso não é conveniente. Então, para resolver esse problema, ES lint tem arquivos de configuração ou digamos que conflitos predefinidos que
podemos estender do ES lint vêm incorporados no conflito recomendado pelo ES lint. Então, vamos apenas copiá-lo e colocá-lo no topo. Agora, usamos o condenado recomendado. Se voltarmos a testar o MGS, veremos que temos console não está definido agora. Bem, isso ocorre porque o ES lint coisas que estamos executando dentro do ambiente do navegador. E para isso, temos que
especificar novamente que estamos correndo dentro do jazz. Então, para isso, temos que colocar as opções ENV aqui e especificamos que estamos dentro. Nota. E vamos dizer verdade, podemos realmente colocar muitas opções diferentes, como ES6, para especificar novamente que estamos usando a sintaxe JavaScript mais recente. E há muitas opções diferentes. E acredite em mim, você não precisa conhecer todos eles. Porque você sempre tem primeira documentação que você pode usar sempre que tiver problemas com a compreensão da Eastland ou pode simplesmente copiar e colar sim. Vincule conflitos de algum lugar e ajustado para suas necessidades. Este é muito básico. Vamos mantê-lo como está. Uma nota importante que eu queria
enfatizar é que você só pode ver amarelo pairando ou talvez você possa ver esse vermelho pairando por aqui. Quero dizer, relatórios diretos dentro do VS Code, graças à extensão. Então eu tenho a extensão ES lint instalada. Aquele que integra ES lint ao código VS. É por isso que aqui vejo esta linha vermelha. Se essa extensão fosse
desativada , o ES lint não me reportaria, assim como eu a vejo agora. Não ficaria vermelho. A única maneira que eu saberia sobre esse erro seria executar o comando ES lint, assim como fizemos antes com o pregador. Então, talvez vamos criar outro script NPM e vamos definir o comando para Eastland. Vamos voltar para package.json. Aqui eu vou colocar pode ser comando lint e vou chamar ES lint asterix dot JS ou como temos extensão MGS vou colocar e gs aqui, vamos executar para ES lint contra todos os arquivos com a extensão MGS. Vamos para o terminal integrado e vamos executar o script que definimos, npm run lint, e você
verá o ES lint relata um problema. Olá recebe um valor, mas nunca é usado. Portanto, isso é muito conveniente porque no código de produção, aparentemente não queremos ter e usar variáveis. E há muitos erros
e avisos diferentes que podemos receber. Mas acredite em mim, isso é para nosso próprio bem. Es lint nos ajudará a manter nossa base de código com menos erros quanto possível. Vamos utilizar muito o ES lint combinado com o pregador. No entanto, há um problema com ES fiapos e preacher. O problema é que algumas regras de pregador se sobrepõem às regras do ES lint. E para corrigir esse erro, precisamos navegar até ES lint. Se formos ao ES lint rolamos para o resumo aqui, podemos ver usar o pregador do condenado do ES lint para fazer o pregador e o link ES funcionarem bem juntos. Vamos navegar até o pregador de conflito enxuto ES. E vamos para a parte de instalação. Vamos copiá-lo. Vamos colocá-lo aqui. E novamente, dash, dash, save dev flag para instalar esse pacote como uma dependência de desenvolvimento. Se você vai olhar dentro das dependências de desenvolvimento, verá pregador de conflitos orientais agora. E vamos ver o que temos que fazer no pregador para
a extensa matriz em seu arquivo Eastland RC. Então, estende algumas outras configurações e pressão. Tudo bem, então vamos colocar, vamos copiar o pregador. Vamos voltar para o ES lint estende-se. E você pode ver pelo exemplo que ele usa uma matriz. Portanto, o ES lint suporta ambos. Vamos transformá-lo em uma matriz. E vamos colocar o pregador aqui. Bom. Sem esse pacote, sem esse pregador condenado da ESPN, você acabará em uma situação em que você terá erros de
Eastland e você não
entenderá por que você os está tendo. Este pacote garante que você não tenha conflitos. E vou ver que é isso. Isso é tudo o que eu queria contar sobre ES fiapos e
pregador para resumir rapidamente, o que é Eastland? Eastland é uma ferramenta que nos permitirá verificar nosso código,
nosso código JavaScript, em relação algumas diretrizes comuns predefinidas. Ele acabará por tornar nosso código menos propenso a erros, e garantirá que nossa base de código, o mais limpa possível. Preacher formatará nossa base de código para que ela se torne o mais legível possível. Só mais uma vez, vou dizer que essas ferramentas são opcionais, mas você verá pregador e ES lint em quase todos os projetos JavaScript porque as pessoas querem que seus projetos sejam legíveis e ser menos propenso a erros. É isso. Vejo você no próximo.
19. O que são Server, JSON, API RESTOS e GraphQL?: Ei, neste vídeo, eu gostaria de falar sobre servidores. O que é um servidor? O que é uma API? O que é uma API rest? O que é o GraphQL? Vamos descobrir isso juntos. Primeiro, vamos começar com o servidor. O que é um servidor? Um servidor, é apenas um computador em algum lugar na Internet. Ele executa algum software. E esse software
nessas aulas de computador para nossas solicitações recebidas. Por exemplo, quando eu navego para qualquer site, quando clico nesse link, meu navegador envia uma solicitação para esse servidor. Então, à esquerda, este é o meu navegador, e ele envia essa solicitação para esse servidor. Este servidor lida com a solicitação recebida e envia de volta arquivos HTML, CSS e JavaScript. Então, novamente, um servidor, é apenas um computador que executa algum software que de alguma forma lida com nossas solicitações recebidas e envia uma resposta de volta. Agora, e se eu não quiser receber sempre arquivos HTML, CSS e JavaScript, talvez eu só queira executar alguma consulta no site, como na barra de pesquisa. Preciso retornar HTML novamente? Não, você não sabe. Você só precisa obter os dados, o resultado dessa consulta na barra de pesquisa. Portanto, nesse caso, os dados devem ser transferidos em algum outro formato. Portanto, algum outro formato geralmente é formato
JSON ou formato XML. Mas o XML já está obsoleto, eu diria na web agora, todos usam o JSON. Então, vamos procurar JSON ou talvez até mesmo pela API de rest falsa gratuita de
espaço reservado JSON . Tudo bem, então primeiro precisamos descobrir o que é JSON. Só vou clicar em Executar script aqui. E recebo que este JSON é apenas o formato no qual os dados são transferidos pela Web. Ele pode ser usado não apenas na web, mas em qualquer outro cenário. É muito fácil
transferir informações neste formato. Parece muito semelhante a um objeto JavaScript. Agora, vamos voltar à nossa tela. Então, como ele se encaixa nesse cenário? Então imagine que estou aqui
no site e digito algo na barra de pesquisa, que está dentro do site. E eu quero recuperar meus resultados de pesquisa no formato JSON, eu enviaria outra solicitação para esse servidor, e esse servidor tratará minha solicitação, minha consulta. Ele procurará o banco de dados. Ele recuperará os resultados e enviará esses dados de volta para mim no formato JSON, que se parece exatamente com isso. Portanto, não há necessidade de HTML, CSS ou JavaScript. Portanto, esse tipo de servidor que hospeda arquivos HTML, CSS e JavaScript, geralmente chamados de serviços de hospedagem. Então, eles são usados para hospedar páginas HTML básicas. Eles apenas colocam seus arquivos, HTML e CSS em sua máquina, e eles apenas servem esses arquivos no computador. É isso. E quanto aos servidores de API? Então, o que é uma API, em primeiro lugar, API significa interface de programação de aplicativos,
e geralmente serve para servidores de API apenas porque, na maioria das vezes, os servidores de API servem
a esse propósito de intermediário entre você e banco de dados subjacente. Mas esse não é apenas o caso. Bem, eles geralmente são chamados servidores de
API porque são interfaces para tudo o que está por trás desse servidor. É por isso que eles são chamados de APIs ou interfaces ou o que ele os chamou. Vamos dar uma olhada neste espaço reservado JSON mais uma vez. Então eu envio uma solicitação para este URL. Só vou copiá-lo e colocá-lo aqui. Se eu acessá-lo, você provavelmente
verá isso em formato bruto assim. Este servidor atua como uma API rest porque segue o formato restante. Portanto, é uma API porque é uma implementação de servidor personalizada. Portanto, é aquele software personalizado instalado
no servidor que lida com minha solicitação para ele e envia de volta Jason, essa é a parte da API. Agora, o que é descanso? Descanso significa que ele segue o padrão de design restante na implementação do resto. Isso significa que o código do tipo de espaço reservado JSON do servidor que calma expõe vários endpoints que podemos
acessar para recuperar dados. Por exemplo. Vá para a barra para fazer a barra um. Este é todo id. Obtemos dados relacionados com o ID número 1. Se eu digitar sete aqui, você verá que agora tenho id de usuário um, id sete e dados diferentes. Se for quatro, serão dados diferentes. Se for algo assim, você não verá nada porque ele não existe o servidor API deles, este que estamos acessando agora é, na verdade uma API para o banco de dados subjacente que ele usa sob o capô. Certo, e segue o padrão de descanso. Você pode navegar até o site principal aqui. E você pode procurar outros pontos finais disponíveis nesse recurso. Por exemplo, você pode ver os recursos aqui. Podemos ir para postagens, podemos ir aos usuários, podemos ir para álbuns. E você pode ver que todos eles têm endpoints diferentes. Novamente, isso ocorre porque segue a implementação do resto. Imagine uma casa grande com muitas portas. Então, uma casa grande é o servidor, o servidor API. E essas portas são e pontos que você está acessando para obter dados. E esses dados são transferidos no formato JSON. Porque é muito simples entender esse formato. É muito leve e fácil de ler ou escrever, mas o resto não é a única implementação de servidor que pode existir na natureza. Há outro realmente popular agora, que é chamado GraphQL. E, obviamente, existem os outros. Então, mas agora no momento, principalmente dois tipos, API rest e GraphQL API. Graphql é ao mesmo tempo uma linguagem e, ao mesmo tempo a implementação do servidor, a arquitetura. Então, vamos procurar o GraphQL no Google ou talvez o GraphQL Explorer. Isso nos levará a esta página de documentos do GitHub GraphQL API. E vai, vamos acabar nessa página. Isso exigirá que eu faça login para usá-lo. Então, vou entrar com minha conta. Se você não tem a conta do GitHub por enquanto, tudo bem. Basta olhar o vídeo. Portanto, esta é a linguagem GraphQL. É assim que se parece. Para solicitar dados do servidor GraphQL, temos que enviar uma co-variação como o pai nesse formato seguindo a linguagem QL do gráfico. Então, se eu vou enviá-lo, você verá que eu recebo dados
neste formato e ele é o formato JSON, como você pode ver. Então, qual é a diferença entre gráfico e repouso? Bem, antes de tudo, como mencionei antes, API
rest tem vários endpoints. Por exemplo, barra todos. Onde está isso? Corte comentários, álbuns, fotos e tarefas. Para acessar dados, seu URL deve ser diferente para acessar recursos diferentes. Mas o GraphQL, é um pouco diferente. Se eu clicar em Inspecionar e ir para a guia Rede aqui, quando eu pressionar este botão de reprodução, você poderá ver o URL que está sendo acessado, que é barra do proxy de barra GraphQL. E se eu executar outra solicitação, o URL não será alterado. Bem, a implementação do servidor GraphQL tem apenas um ponto final através qual todas as solicitações passam para entender o que o usuário recusou, o que queremos do servidor. Enviamos essa covariação para o servidor. Se, por exemplo, navegarmos para referências e consultas em uma nova guia. Então, vamos procurar o usuário e ele espera um argumento. Vamos tentar essa consulta. Então, vou remover tudo isso. Vou digitar usuário, como diz aqui. E precisamos fornecer um argumento. Você fornece um argumento. Temos que abrir parênteses e colocamos esse argumento aqui. Login é o argumento do tipo string. Vamos colocar meu apelido aqui. Agora, em colchetes encaracolados, tem que
especificar que tipo de dados temos que receber. Então, ele vai ser login. Se eu colocá-lo assim. Bem, eu basicamente tenho a mesma informação, mas a consulta é diferente e nesse ponto é a mesma. Agora, você já viu a diferença? Bem, a diferença, a principal diferença sobre o GraphQL e a
API rest é que o GraphQL só envia dados que você pede, certo? Então, aqui eu peço apenas login na minha consulta. Portanto, essa consulta é chamada de esquema, esquema que você solicita do servidor. Tudo bem, então eu solicito esse esquema de apenas login e recebo apenas login de volta à API rest. Se formos a posts, pedi postagens. Não especifico quais campos quero recuperar da pose. Isso cabe ao servidor decidir para
que o servidor centralize o título e o corpo, e não podemos alterar isso. Tudo bem, se eu acessar postagens com esse ID, ele me dá título e corpo. Mas com o GraphQL,
posso especificar quais campos quero recuperar do servidor se navegarmos até os cães. Então, faça login, na verdade, essa consulta nos retorna usuário do tipo. Se abrirmos, o usuário tem muitos campos e podemos realmente usar a inteligência do GraphQL. Então, vou pressionar o espaço de controle. E aqui eu tenho espaço de controle biológico aqui talvez tenha nome aqui que eu tenha login. Então você pode ver que estou usando o idioma de consulta para especificar qual campo eu quero recuperar. E quando eu pressiono Play para enviar a consulta, você pode ver agora que tenho minha forma de dados personalizada especificada na consulta. Muito legal. Então, essa é a principal diferença. E você provavelmente pensará que o GraphQL é, Oh meu Deus, é incrível. Por que precisamos de APIs de descanso? O problema é tudo sobre implementação e sua complexidade. Graphql foi criado pelo Facebook alguns anos e tornou-se muito popular. No entanto, a API rest é uma solução mais madura e testada em batalha. Graphql é difícil. Não é tão fácil. É fácil consumir o Graph kill, mas para implementar o GraphQL, requer um bom conhecimento. A API Rest é mais simples, mais fácil de implementar e é mais intuitiva em comparação com parabéns do GraphQL. Agora você sabe o que é uma API. Vejo você no próximo.
20. VS de lados de clientes Renderização de lados do servidor (dinâmico e estático): Ei, neste vídeo, gostaria de falar sobre aplicativos
do lado do cliente e do lado do servidor. Por que nos importamos e por que é importante entender a diferença? Vamos primeiro. Deixe-me abrir minha pequena tela que preparei. No topo, temos três tipos principais de renderização na web. A primeira é a renderização no lado do servidor, que é um roteamento no lado do servidor. Em seguida, temos renderização no lado do cliente, que usa o roteamento do lado do cliente. E então temos uma abordagem híbrida, que combina ambos. A melhor maneira de entender a diferença entre esses três é observar os exemplos. E isso é exatamente o que vamos fazer. Se eu for ao navegador aqui, preparei dois sites, site
steam e o Netlify. Ambos são aplicativos de renderização no lado do servidor. E como sabemos sobre isso? Se clicarmos com o botão direito do mouse na página e acessarmos a fonte da página, aqui, podemos ver a marcação. Portanto, se virmos a marcação na origem da página, isso significa que a página é renderização no lado do servidor. Então isso é o que você vê aqui, foi retornado do servidor quando eu acesso esse URL. Além disso, cada página contém ataques met exclusivos. Isso significa que se eu for para uma página diferente e se eu inspecionar a origem da página dessa página, as metatags serão diferentes e a marcação será exclusiva para cada página no site. Agora, temos um segundo exemplo, Netlify. Ele também usa renderização no lado do servidor. Se eu inspecionar a página, tenho exatamente a mesma imagem. Tenho metatags exclusivas e tenho a marcação. Tudo bem? Mas Netlify é diferente. O problema é que o Netlify usa páginas
estáticas ou renderização estática no lado do servidor, enquanto o steam usa renderização
dinâmica no lado do servidor, qual é a diferença? A diferença é que, no caso da Netlify, todas essas páginas são apenas estáticas, elas não mudam. Isso também significa que todas as páginas do site da
Netlify têm seu próprio arquivo HTML. Se eu for para a página de
preços, a página de preços tem seu próprio arquivo HTML, assim como a página inicial ou qualquer outra página. Agora, e o vapor? Vapor, um pouco diferente. Ele usa renderização dinâmica no lado do servidor. Isso significa que esta página, por exemplo, página
do jogo, esta é apenas uma página de esqueleto. Ele tem o modelo que ele usa para renderizar jogos. Então, se eu for para qualquer outra página, você pode ver que ela parece exatamente a mesma. A única coisa que foi alterada são as informações na página, mas o layout é o mesmo. E esse layout é o esqueleto usado para inserir dados
dinamicamente nesse esqueleto. E isso é exatamente o que o vapor está fazendo. Então, para todas essas páginas de jogos, eles têm apenas um esqueleto. E esse esqueleto é reutilizado para inserir os dados dinamicamente. Ele é chamado de dinâmico porque toda vez eu envio uma solicitação para acessar essa página, o servidor cria dinamicamente marcação
HTML e, em seguida, ele me envia de volta para recusar. É por isso que cada página cada página é diferente. Ele tem marcação exclusiva porque foi criado ou montado
dinamicamente no servidor. Ao contrário das páginas estáticas, marcação
HTML não é montada
no momento da solicitação quando eu acesso esta página. marcação foi montada quando o aplicativo foi construído. Então, ele foi criado uma vez e agora toda vez que eu acesso essa página de preços, ele apenas envia a marcação estática porque ela não tende a mudar. Tudo bem, a desvantagem das páginas estáticas é que se precisarmos alterar algo em nosso conteúdo estático, temos que reconstruir o aplicativo, regenerar páginas HTML e depois carregá-las para hospedagem novamente. Então, agora eles são considerados atualizados. Com a renderização no lado do servidor, esse não é o caso. Você tem o esqueleto e os dados são inseridos dinamicamente. Isso significa que os dados recuperados
do banco de dados e, em seguida, com base nesses dados, o HTML é retornado. Você não precisa mudar nada. Você não precisa regenerar páginas ou fazer nada. Somente se você precisar alterar o layout ou o esqueleto. Somente neste caso, ele deve ser reimplantado para refletir todas as alterações nesse esqueleto. Vamos para o segundo tipo, que é renderização do lado do cliente, ou mais frequentemente chamados de aplicativos de página única como PA. Agora, quais são esses sites? Aqui eu também preparei dois exemplos. Telegram, versão web. E este site instantâneo que foi construído com o React a propósito. Então, se eu inspecionar o telegrama, Exibir fonte da página, posso ver que não tenho nada aqui. Se eu for para o body tag, está totalmente vazio. No entanto, se eu inspecionar elementos da página, a marcação estará lá. Então, o que está acontecendo aqui? Do servidor? Eu recebo esse arquivo HTML de urso apenas com pacotes JavaScript. E JavaScript é aquele que renderizará minha página, quem criará a marcação? Quem criará o HTML dentro do navegador. É por isso que ele é chamado de renderização do lado do cliente, porque o JavaScript é aquele que renderizará a página dentro do navegador assim
que tivermos esse HTML do servidor, essa é a diferença. Portanto, na renderização do lado do servidor, já
temos marcação montada e retornada do servidor antecipadamente. Mas com aplicativos de página única ou com renderização no lado do cliente, não temos isso. Temos um mínimo de HTML muito simples e o restante é montado dentro do navegador por JavaScript. É isso. Mas há uma desvantagem muito crucial sobre aplicativos de página única ou renderização no lado do cliente. É ruim para SEO, que significa otimização de mecanismos de busca. O problema é que, se você quiser que esta página seja classificada e rastreada pelo Google ou pelo Facebook, é sempre melhor renderizar no lado do servidor. Porque os rastreadores, o que o mar, eles vêem exatamente isso, esta página fonte. Eles vêem a marcação, eles veem ataques de Matt. E com base nessa marcação e nas metatags, eles podem executar e entender o que é essa página. No entanto, mas aplicativos de página única, rastreadores, eles não vêem nenhum desses. Eles não esperam que o JavaScript
no navegador monte e renderize a página. Eles só vêem essa tag de corpo vazio e esses ataques matemáticos básicos. Então, se você precisar de um bom SEO, use renderização no lado do servidor. Tudo bem, agora temos esse conceito de roteamento no lado do servidor e roteamento do lado do cliente. O que são esses? E aplicativo de página única. Você pode ver que, se eu navegar pelas páginas, a URL muda, mas minha página, ela não será atualizada. Isso é chamado de roteamento do lado do cliente porque foi tratado no cliente por JavaScript. Isso significa que o JavaScript é aquele que altera o URL. Javascript é quem renderiza a página. Certo? Ele não envia solicitações adicionais para o servidor. Tudo é feito dentro do navegador. Ao contrário do roteamento do lado do servidor, se eu for para qualquer outra página, você pode ver que ela está sendo atualizada porque o que eu faço basicamente, peço ao servidor que me forneça esta página. E essa é a diferença. Portanto, o roteamento do lado do servidor é quando você envia outra solicitação para o servidor e solicita esta página com aplicativos de página única com roteamento do lado do cliente. Tudo isso é feito dentro do navegador sem solicitações adicionais. Certo, ótimo. Agora, a terceira forma de renderização é chamada de abordagem híbrida. A abordagem híbrida é a melhor de dois mundos serem combinados. Temos renderização no lado do servidor e temos navegação no lado do cliente, roteamento do lado do cliente. Agora, um exemplo seria a documentação do Netlify. Então, se eu inspecionar a origem da página, posso ver a marcação e posso ver ataques conhecidos exclusivos. Muito legal. Mas se eu tentar navegar para qualquer outra página, você poderá ver as alterações no URL. No entanto, a página não atualiza. Assim, na primeira solicitação, quando você acessa este site inicialmente assim, ele enviará marcação já montada do servidor para você, o que significa que é renderização no lado do servidor. No entanto, depois disso, uma vez que a página é carregada, o JavaScript assume o controle e você terá essa sensação de gostar
no aplicativo ao navegar na página da Web. Muito legal, certo? Então, no momento presente, a abordagem
híbrida é muito, muito popular
porque, novamente, combina o melhor de dois mundos. Você pode ter uma boa otimização de SEO devido à renderização no lado do servidor, e você pode ter um aplicativo como se sinta com o roteamento do lado do cliente. Muito legal. Agora, quais são os contras e prós de cada abordagem? Então eu já mencionei isso, mas vou fazer isso de novo. O primeiro é o C0, que significa otimização de mecanismos de busca com renderização no lado do servidor, o COO é o melhor resultado porque você já significou ataques montados. Você já tem o conteúdo da página montado na marcação. E com base nessas informações, rastreadores, como rastreador do Google, Facebook, arrastões do
Twitter e outros trollers. Eles podem analisar sua página com base nessas informações e classificar sua página adequadamente com aplicativos de página única. Este não é o caso. Se eu inspecionar a página, só
consigo ver o mínimo muito nu. No entanto, existe uma solução moderna para resolver esse problema de aplicativos de página única. E a solução é pré-renderizar o aplicativo de página única. Isso significa que cada página no aplicativo de página única no aplicativo do lado do cliente será pré-renderizada em um arquivo HTML estático. Então, cada página terá seu próprio HTML. E quando você acessa esta página, ela lhe trará, ela lhe dará o HTML estático que foi gerado. Isso é o que a Netlify faz. Netlify é um serviço de hospedagem e eles pré-renderizam aplicativos de
página única para torná-los mais otimizados para SEO. Esta é uma ótima solução. Então, em seguida, temos um aplicativo como sentir. Portanto, os aplicativos de renderização no lado do servidor, ou mais especificamente, o roteamento do lado do servidor, não possuem esse recurso porque você pode ver sempre que
navega, a página é atualizada e você instantaneamente entenda que este é um site. No entanto, com o roteamento do lado do cliente, você recebe um aplicativo como sensação porque a página não é atualizada, assim como estamos navegando no aplicativo móvel. E o último ponto é, requer JS, aplicativo renderizado no
lado do servidor ou mais especificamente, páginas estáticas. Eles podem não significar JavaScript. Pode ser um conteúdo estático apenas com HTML e CSS, que não precisa de JavaScript. Mas aplicativos de página única ou aplicativos do lado do cliente sempre precisam de JavaScript porque tudo é feito pelo JavaScript. É como o núcleo dos aplicativos do lado do cliente. E se você desativar o JavaScript ou se ele não estiver disponível por algum motivo do que a apple simplesmente não funciona no treinamento. Vamos nos direcionar para criar aplicativos de página
única com o React. Espero que tenha sido claro e te vejo no próximo.
21. Atalhos de código VS: Oi. Neste vídeo eu vou mostrar meus atalhos que eu uso no código V s. Isso será útil para todos. Não se concentre no frio agora. Este vídeo é sobre atalhos. Começamos abrindo uma pasta de projeto para esse controle de espera que pressione K mais o, em seguida, selecione a pasta para abrir. E nós somos perspicácia. Agora precisamos de terminal para isso. Você pode pressionar o controle, além de inclinado ou controle mais J T aberto em riso muito terminal entre esconder e mostrar controle de imprensa
Estado mais Jay, Há muitas situações em que precisamos mover linhas de código ao redor para que basta segurar para fora e pressione setas picadas e inferiores ela moveu linhas Cordis apontando Seja, então precisamos gerenciar várias abas abertas para abrir arquivo em uma nova guia. Basta abrir esse arquivo a partir do Explorer ou pressione o controle mais B para barra Riesco Charge,
Em seguida, procure o arquivo e pressione enter para alternar entre guias. Segure e pressione números de 1 a 9. Ela abriu a torneira ordenada relevante a maior parte do tempo. Precisamos adicioná-lo. Algo em várias linhas. Seleção de várias linhas e ajude-nos a mover o curso ou para o lugar certo. Mantenha o controle, além de setas para cima e para baixo para estender a seleção com leões. Controle de liberação mais para fora e agora somos capazes de editar código no modo multi linha, segure, deslocamento e pressione prados para seleção de único caractere foram segurar controle e pressionar setas para mover carros ou para as palavras seguintes ou anteriores. Você pode combinar turno e cultural para selecionar toda a ala. Também podemos selecionar correspondência específica para edição de várias linhas, mover o seu curso ou para a ala ou selecionar alguns personagens, manter o controle e pressionar D. Uma vez ele irá selecionar o tribunal atual,
em seguida, manter o controle e Presidente de Ele irá adicionar ocorrências para a seleção que correspondem ao padrão. Também podemos criar várias abas para facilitar o controle de imprensa, além de barra invertida para dividir este coreano em vários toques. Na verdade, o mesmo pode ser aplicado ao terminal dentro do controle de pressão do terminal mais barra invertida para abrir várias instâncias. Isso que entre instâncias segurar e pressione a seta superior ou inferior e é isso. Estes são os principais atalhos que facilitarão o protesto do desenvolvimento. Você sempre pode personalizar configurações de carimbo Invesco estavam aqui em baixo. Vejo-te no próximo
22. Introdução ao JavaScript: Olá, Bem-vindo à seção JavaScript. Nesta seção, falaremos sobre recursos de sintaxe JavaScript
mais comuns. Não abordaremos o básico, porque
entenderemos tudo isso durante o processo, vamos anexar padrões mais avançados e mais comuns. Precisamos entender tudo isso para nos sentirmos confortáveis durante o desenvolvimento da criação. Espero que você goste. Vejo você no próximo.
23. Var VS Deixe VS Const: Oi, Neste vídeo, falaremos sobre diferentes tipos de variáveis que existem em JavaScript. Estes são var, let e const. Neste vídeo, entenderemos a diferença entre eles e qual tipo temos que usar nessa situação. Vamos. Então, como tudo isso vai ser organizado? Vou criar um único script que vou nomear o arquivo gs. E então vou executar esse script com exemplos através do terminal integrado usando o comando node file.js. Então bar, deixe e const. Qual é a diferença? Vamos talvez criar uma variável do tipo var e chamá-la de meu nome. Então eu vou apenas console.log essa variável. E então vamos executar o script. Você verá que Andrew é impresso, tudo funciona. Então, qual é o problema com essa variável? Eles lidam com var é que esse tipo de variável está incluído ao escopo de função mais próximo. Para entender que temos que criar essa variável dentro de uma função. Então, vamos criar uma função. Imprima meu nome. E dentro dessa função, vou colocar var. E então eu vou registrar meu nome no console. Agora, se eu vou executar o script, não te
verei nada porque bem, é uma função e eu tenho que chamá-lo, imprimir meu nome. Ótimo. Agora execute o script novamente. Você verá Andrew, o resultado é o mesmo. Se eu vou colocar o log do console fora do escopo da função, receberei um erro de referência. Porque meu nome é definido dentro do escopo da função. Ele não é visível fora dele. É por isso que temos um erro de referência. Ótimo, entendemos isso. Mais uma vez, qual é o problema com var? Como um triste, ele está incluído ao escopo da função mais próximo. Isso significa que não importa quantos escopos eu tenho dentro dessa função, ela será visível em todos os lugares. O que quero dizer é que se eu vou colocar muitos, digamos, se blocos aqui, se cinco for maior que um, então eu vou criar outro no blog
deles apenas para criar escopos, ok? Se 10 for menor que 20, se cinco for maior que três, não
importa o que eu faço aqui. Eu só quero criar tantos escopos internos quanto possível. E agora o que vou fazer, vou colocar var, meu nome dentro do máximo em seu escopo, e então vou tentar acessar meu nome dentro dessa função. O que você acha que esse código entra em funcionamento conforme o esperado e veremos a entrada no terminal. Vamos experimentá-lo. Vou executar novamente o nó do script file.js. E vemos Andrew, bem, isso é imprevisível. Queremos que essa variável se
comporte para não ser visível fora do escopo em que foi definida. Portanto, o escopo em que essa variável foi definida é esse bloco
if mais interno, se ele foi definido, digamos que neste bloco, neste caso, ele ficaria visível em todos os lugares dentro, mas não fora dele. Var é novamente, está incluído no escopo da função mais próximo. Não importa onde ou em que,
em seu escopo mais, defini variável do tipo var dentro de uma função, sua visibilidade sempre será escopo da função. E isso é ruim porque é imprevisível. Queremos sempre garantir que nossa variável esteja sempre visível somente dentro desse escopo onde ela foi definida aqui. Então, para corrigir esse problema, temos variáveis de tipo, let e const. Então, se eu vou colocar o LED aqui, e então vou tentar executar o script. Você verá um erro de referência. Porque agora let tem escopo para o escopo mais próximo,
na verdade, para o escopo onde ele foi definido. E o mesmo com const. Se eu vou colocar const aqui e executar este script, você verá novamente a mesma coisa. Meu nome não está definido erro de referência. Então, para corrigir isso, para corrigir o erro de referência, temos que referenciar meu nome neste escopo onde ele está disponível, o
que será esse. Vamos mover o log do console para esse escopo. E vamos tentar novamente. Você verá que a entrada é impressa. E agora isso é previsível porque sabemos que essa variável é definida dentro desse escopo e sua visibilidade termina sempre que saímos, se eu colocar o log do console nesse escopo, você verá novamente o erro de referência. Oh, deixe-me salvar o arquivo. Você verá um erro de referência porque isso sai do escopo. Onde meu nome está definido, certo? Esta é a diferença entre chumbo const e var let e const tipo de tigelas de fibra. visibilidade termina com o escopo envolvente, enquanto var termina com o escopo da função mais próximo. Então, se eu tiver outra função dentro de uma função, digamos que a função olá. E então vou definir a mesma coisa. Tudo isso dentro de Hello than var será visível somente dentro da função hello. Não será visível imprimir meu nome, mas sim para Hello. Tudo bem, acho que está claro. Agora, qual é a diferença entre let e const? Vamos esse tipo de variável que tende a ser reatribuída. Digamos que eu criei meu nome viável e, no futuro, quero reatribuí-lo. Talvez eu queira
agora o valor não Andrew, mas outra coisa. Então, o que eu faria, eu reatribuiria esse valioso. Então, pelo nome, agora se torna john. E se eu for consolar o log John, você verá na verdade John não entrar porque agora ele tem um valor diferente. Vamos digitar que pode ser reatribuído. No entanto, com const, não é. Deixe-me salvá-lo e executar o script. Você verá atribuição para variável
constante porque const significa constante, algo que não muda se eu criá-lo pelo dobro do meu nome e colocá-lo como entrada, significa que ela não mudará. Sempre será Andrew. Mais uma vez. Vamos pode ser reatribuído. Se você criou uma variável, meu nome
e, no futuro, se tiver
certeza de que vai renomeá-la, use lead porque o lead pode ser reatribuído se você não quiser que essa variável mude, Tem certeza de que qualquer valor que
você atribuir a essa variável permanecerá assim. Use const. Na prática, a maioria das variáveis terá o tipo const. E essas variáveis que
sabemos que vamos reatribuí-las. Vamos usar lat, mas de outra forma const, e nunca usamos var. Então, para resumir rapidamente, o fio é um tipo de dados de idável, que era a habilidade é o escopo de função mais próximo. Não importa como lá maioria definiria essa variável. Ele ainda estará visível no escopo da função. E, como let e const, let e const têm escopo para o escopo mais próximo onde estão definidos. Vamos esse tipo de variável que pode ser reatribuída e const é constante. Se você for criar uma variável constante, ela não será alterada mais tarde. No entanto, há mais um pequeno truque com const, e esse truque são objetos. Portanto, se Meu nome for um objeto,
esse objeto pode ser modificado, mas você não pode alternar o tipo de objeto para outra coisa. O que quero dizer é que, se meu nome, eu o defino como um objeto e depois quero mudá-lo para John. Terei designação para uma batalha constante. Mas se eu quiser dizer, modifique o objeto em si, por
exemplo, dê a ele uma nova chave. Por exemplo, meu nome ponto algo vai ser olá. E depois vou registrar meu nome no console. Você verá o objeto que tem uma chave, algo com valor Olá. Você tem que se lembrar disso. Portanto, neste caso, você não modifica
diretamente por tipo duplo, mas modifica o objeto em si. Agora você sabe a diferença entre diferentes tipos de variáveis. Vou dizer isso mais uma vez. Na prática, a maioria de nossas variáveis será do tipo const. E para aquelas variáveis que tendem a mudar, vamos usar o tipo LED. Nunca usaremos VAR. Vejo você no próximo.
24. O que é Array?: Oi, Neste vídeo, vamos falar sobre o mapa de pontos da matriz. O método do mapa de pontos da matriz está disponível em todos os arrays JavaScript. Ele é usado para iterar sobre a matriz de elementos e é usado para transformar cada elemento de matriz em outra coisa. É por isso que o mapa de pontos da matriz de nomes. Vamos ver isso em um exemplo. Em file.js. Vou criar uma nova matriz, que vou nomear Olá e deixar ser 4326. Agora, digamos que eu queira iterar sobre esse array. Eu quero que você simplesmente registre o log de cada elemento de matriz. De um modo geral, posso conseguir isso com a maneira tradicional de fazer isso usando o loop for, mas agora podemos usar um mapa de radar. Então, vou colocar o mapa de pontos de saudação. E uma vez que eu abra o código
VS do parêntese me dará a descrição. Você pode ver que o método do mapa de pontos recebe a função de retorno de chamada. E o segundo argumento é esse arco. Este arco é sobre o, esta palavra-chave em JavaScript. Não vamos tocar nisso. Estamos interessados em. A função de retorno de chamada. Callback é aquela função que está sendo passada como argumento para alguma outra função. Então, como vamos passar uma função para a função map, é por isso
que a chamamos, ligue de volta. Tudo bem, acho que está claro que vamos
usar muito o retorno da palavra. Então esse callback recebe três argumentos. O primeiro argumento é valor, depois temos índice e matriz. E vamos digitar a função. E se eu vou abrir parênteses novamente, verei valor, índice e matriz. Portanto, o valor é o valor do elemento atual. O problema é que o método do mapa de pontos itera sobre uma matriz. Portanto, esse retorno de chamada que passamos para o método do mapa de pontos será executado para cada elemento de matriz. Portanto, se tivermos quatro elementos no total nessa matriz, isso significa que essas funções de retorno de chamada serão
executadas quatro vezes para cada elemento e valor da matriz. O primeiro argumento no callback
será o valor atual que estamos iterando. Portanto, pela primeira vez que o callback será executado, o valor será, pela segunda vez, o valor será três, e assim por diante até o último elemento. O segundo argumento aqui é o índice, e será o índice do elemento de matriz atual. Então, para o primeiro elemento, será 0 porque os arrays em programação começam com índice 0. Então, será 0, 1, 2 e 3. Vamos chamá-lo de idx. E o terceiro argumento será o array. E será a mesma matriz
para a qual aplicamos esse método de mapa de pontos. Então, vamos dizer que é, e eu vou dentro desse callback dentro dessa função. Vamos, na verdade, console.log, valor, índice e array. E agora vamos tentar executar o arquivo de nó de script HGS. E o que vemos, então primeiro vai o valor. Como você pode ver para três a seis, vemos todos os nossos elementos de matriz, o que está correto porque, novamente, esse callback é executado para todos os elementos da matriz. A segunda coluna que vemos é o índice desse elemento. Então, para tem índice 0, isso é o que você vê no terminal. E o último elemento terá índice três, porque, bem, este é o último elemento e sabemos que matrizes começam com índice 0, o que está correto. E o terceiro valor será a própria matriz na qual esse método de mapa de pontos foi aplicado. Mas esse não é o verdadeiro poder do método de plotagem de pontos. Ele é usado para transformar cada elemento de matriz em outra coisa. E eles tomaram o método do mapa produz um novo valor. Ela produz uma nova matriz. Isso significa que eu posso escrevê-lo em uma variável. Então, vou colocar o resultado const igual a hello.mat. E então eu posso realmente o
resultado console.log para ver o que eu tenho. Se eu for executar esse script, terei uma matriz de quatro elementos em que cada elemento é indefinido. Por que é indefinido? Bem, o problema é que o método map espera que retornemos algum valor dessa função, desse retorno de chamada. E esse valor que retornamos será definido como um novo valor para o elemento atual. Por padrão, quando não retornamos nada de uma função, essa função retorna indefinida. É por isso que temos indefinido em todos os lugares. Vamos tentar colocar o retorno do retorno de chamada. Você consegue adivinhar qual será o valor? Vou executar esse script e agora ele vai ser 4, 4, 4, 4. Bem, novamente, essa função de retorno de chamada é executada para cada elemento de matriz. E para cada elemento de matriz, retornamos para, se eu vou colocar valor multiplicado por dois, você
pode adivinhar o resultado agora? Vamos ver. Agora temos 864 e 12. Basicamente o que
fizemos, apenas multiplicamos cada elemento de matriz por dois. Porque mais uma vez que o callback é executado para cada elemento de matriz. Pela primeira vez. Ele será executado para o primeiro elemento que é quatro, valor será para, valor será multiplicado por dois, retornamos oito,
o que significa que no valor de retorno para o método map para o primeiro elemento, temos o valor 8. Isso é o que vemos. O mesmo vale para o segundo elemento. Esse callback é executado. O valor será 3. 3 multiplicado por 2 é 6 para o segundo elemento. Agora temos seis, e assim por diante até o último elemento. E é isso. Este é o mapa de pontos de matriz de palavras usado para, vamos utilizá-lo muito, especialmente no React, mas teremos que mapear algum array para reagir a marcação. É por isso que é muito importante entender o método do mapa. É isso. E eu vou te ver no próximo.
25. O que é Array?: Ei, neste vídeo vamos
falar sobre uma redução redox,
assim como uma redução de ponto de
matriz de mapas de radar itera sobre elementos de uma matriz. No entanto, ele faz fundamentalmente uma coisa diferente se o mapa de pontos da
matriz for usado para
mapear cada elemento de matriz para algum outro valor, redução de pontos da
matriz é usada para compactar ou reduzir todos os elementos da matriz em um único valor. Vamos ver isso em um exemplo. Se voltarmos ao Arquivo GS, vamos criar uma nova matriz aqui, olá, que será sete. 6945, talvez. Ótimo. Agora podemos usar o método de redução de pontos da mesma forma que usamos o método map, que significa que podemos digitar hello dot reduce. E assim como no mapa de pontos, temos que fornecer uma função de retorno de chamada. Mas desta vez, a função de retorno de chamada receberá argumentos diferentes. Portanto, temos valor anterior, valor
atual, índice atual e array. Então, vamos tentar ver o que eles são. Então, fornecemos o retorno e abrimos parênteses novamente para o IntelliSense. E temos o primeiro valor anterior, valor
atual, índice atual e array. Assim como no mapa de pontos, a redução de
pontos executará esse callback para cada elemento de matriz. Isso significa que esse callback será executado cinco vezes para cada elemento. É por isso que sabemos o que será o índice e o array atuais. Assim como no mapa escuro, a
matriz será a mesma matriz que usamos para este método.radius. E o índice atual será
o índice do elemento iterante atualmente, que será 01234. Não precisamos deles. A única coisa que precisamos é o valor
anterior e o valor atual. Mas na maioria das vezes, valor
anterior não é frio valor anterior. É chamado de acumulador. O que é acumulador? Vamos conversar em um segundo. Eu só quero mencionar que o método de redução de pontos também espera um segundo argumento ao lado do retorno de chamada. O segundo argumento é o valor inicial e é opcional. Então, vamos colocar 0. Ótimo. Agora, o que é acumulador ou qual é esse valor anterior? O problema é que o
método de redução de pontos funciona comprimindo
ou acumulando cada elemento da matriz em direção ao resultado final. Isso significa que começamos com algum valor inicial com 0. Certo? Então, quando todos esses callbacks são executados para cada elemento de matriz, ele modifica de alguma forma nosso valor inicial. Tudo bem? E no final, na última execução de callback, temos o resultado. Isso significa que o
método de redução de pontos também produz um valor, mas em vez de uma nova matriz, ele produz uma única saída. Então talvez seja 15, não sabemos. Então, como é produzir um valor, vamos colocá-lo, vamos colocá-lo em uma variável. Portanto, o resultado const será hello dot reduce
e, no final, vamos apenas o resultado
console.log. Ótimo. Agora, se vamos tentar cancelar o acumulador de
log e ao lado dele, vamos
consolar o valor atual do log. E vamos executar esse script. O que vamos ver, a saída não é bastante óbvia. O que temos? Temos primeiro 0 e depois amplificação
indefinida, indefinida, indefinida. Para não nos confundir, na verdade
temos cinco registros de console
provenientes dos callbacks e o último para o resultado. Deixe-me colocá-lo assim. E nós o executamos. Sim, perfeito. Então, por que temos muitos valores indefinidos? Bem, na primeira execução, quando esse callback for executado para o primeiro elemento 47 acumulador será nosso valor inicial que fornecemos aqui. É por isso que vemos 0 valor atual será elemento atual, que é sete. É por isso que vemos 07. O que quer que retornemos desse callback ficará triste, pois o valor do acumulador para a próxima execução de retorno de chamada. Porque não retornamos nada dessa função. Por padrão, o valor de retorno é indefinido. É por isso que na próxima execução desse callback para o segundo elemento, que é seis, acumulador indefinido. Se vamos retornar um para cada acumulador R1 subsequente será sempre um, e o valor final também será um. Se eu executar o script, você pode vê-lo sozinho. Sempre temos acumulador definido como um, mas isso é muito despejado. Queremos realmente fazer algo com isso. Como podemos usar o ponto reduzido para fazer algo real, podemos realmente usar o método de redução de pontos para
encontrar a soma de todos os nossos elementos. Na verdade, podemos digitar acumulador mais valor atual. E é isso. Isso fará o truque. Vamos realmente salvá-lo e vamos ver o que é impresso. Vemos que o resultado é 31. Mas como acabamos com isso, vamos dividi-lo. Para a primeira corrida. Esse callback tem acumulador definido como 0 porque nosso valor inicial é 0, valor
atual será sete. Então, temos 0 mais 7. Isso é o que vemos aqui. Então, a partir desse callback retornará sete. Vamos digitar a primeira execução será um retorno sete. Isso significa que na segunda execução
desse callback para o elemento seis, acumulador será esse valor de retorno da execução anterior. Portanto, temos acumulador igual a 27 na segunda execução para o segundo elemento, e temos sete mais valor atual. Então temos 7 mais 6,
temos 13, o que significa que a
partir da segunda corrida, retornamos 13. Na terceira execução desse callback para os elementos nove, acumulador será 13 porque é isso que
retornamos do callback para a execução anterior. Quatro elementos, 613, É por isso que agora é 13. Então 13 mais
o valor atual será 13 mais 9 será 22. Retornamos 22. Para o quarto elemento acumulador é 2222 mais quatro será 26. Retorno 26. E para o último elemento temos acumulador 26. 26 mais cinco serão 31. E esse será o nosso valor final. Portanto, nosso valor final que temos na variável de resultado será o valor que retornaria
da última chamada
de volta do método de redução de pontos que é amplo. Esse primeiro argumento é chamado acumulador porque, assim como você observou agora, esse valor é acumulado em todos os retornos de chamada que temos no método de redução de pontos. É uma ferramenta muito flexível e, a princípio, é muito difícil
entender como os pontos reduzem funciona, mas confie em mim, é muito flexível. Outro exemplo seria quando temos que
produzir um novo objeto a partir dessa matriz. Por exemplo, queríamos ter esse objeto onde a
chave seria o índice
do elemento e o valor será desvalorizado. Então, por exemplo, o elemento 0 será sete, elemento um será 6, segundo elemento será 934 e depois cinco, certo? Então, suponha que
precisamos transformar esse array nesse objeto. Portanto, esse é o nosso resultado desejado. Na verdade, podemos usar pontos reduzidos para conseguir isso. Deixe-me remover esses Comuns e vamos ver como podemos abordar isso. Então, sabemos que precisamos receber um objeto no final. Então, antes de quando
calculamos a soma, sabemos que nosso valor final será um número. É por isso que colocamos 0 aqui. Mas agora, como será um objeto, vamos colocar um objeto vazio aqui. Este será nosso ponto de partida. acumulador para a primeira execução será um objeto vazio. valor atual ainda permanece o valor que temos dentro da nossa matriz. Então, agora, para alcançar esse resultado, temos que realmente mesclar valores dentro desse objeto. Como precisamos trabalhar com objetos, precisamos retornar um objeto desse callback porque esse é nosso acumulador. Nosso resultado final novamente é um objeto. É por isso que nosso acumulador é um objeto. Então, vamos retornar e temos que retornar um objeto. Portanto, para mesclar objetos, temos que digitar atribuição de ponto de objeto. Então, o primeiro é o alvo. E aqui vamos fornecer algum valor que será mesclado nesse objeto. Mas antes que possamos mesclá-lo, temos que realmente criar o objeto, certo? Então vamos colocar const, digamos que o elemento atual mapeado. E vamos colocá-lo como um objeto vazio primeiro. E então temos que criar essa única peça de valor que representará nosso elemento atual dentro do resultado final. Então, queremos que esse elemento atual do mapa seja esse objeto. Então, para o primeiro elemento, será 0, 7. Queremos que o elemento atual mapeado seja dessa forma e mesclaremos esse objeto em nosso acumulador. Então, precisamos de alguma forma conseguir que
possamos digitar elemento atual mapeado. Então, o índice do nosso elemento, temos que usá-lo. Então, agora podemos realmente colocar nosso argumento aqui e chamá-lo de índice atual. Coloque-o assim. Assim, podemos referenciar que o índice atual do
ponto do elemento atual mapeado é igual ao valor atual. E essa linha nos trará essa grade de resultados. Agora nós mesclamos esse resultado em nosso elemento atual mapeado do acumulador, e agora teremos o resultado desejado. Vamos verificar. Arquivo de nó gs. E hoje temos 0 elemento valor 7, primeiro elemento valor seis segundos, 9, terceiro, quarto, 45, grau. Tudo exatamente como eu queria. O que realmente aconteceu aqui? Vamos tentar e acumulador console.log. Bem, e como você pode ver, na verdade, este é um ótimo exemplo dessa saída. Você pode ver como o acumulador está
sendo acumulado em todas essas execuções de retorno de chamada. Então, primeiro, para a primeira execução desse callback, mantivemos nosso objeto vazio, certo? É por isso que vemos objeto vazio aqui. Então criamos esse elemento aqui, que é esse, e então o
mesclamos em um objeto vazio. Então é isso que retornamos da primeira corrida. Na segunda execução, nós mesclamos isso no primeiro objeto, que resultou nesse objeto com 76, e assim por diante até o último elemento. Então, no final, temos nosso resultado desejado. Muito incrível. redução de pontos é realmente poderosa e muito flexível. É crucial entender isso porque o Dr. US é bastante comum, não tão comum como o método do mapa de pontos, mas ainda assim é usado com muita frequência. Sei que é difícil de entender. Os pontos reduzem completamente quando você o vê pela primeira vez, mas confie em mim, apenas leve algum tempo, experimente com ele, jogue com os diferentes valores. Experimente você mesmo, talvez tente valores de registro no console. Tentei colocar valores diferentes em um raio, tentei retornar valores diferentes daqui. E você verá que depois de algum tempo você entenderá, você terá aquele momento aha. Tenho quase certeza. Acho que este é o método de redução de quatro pontos. Espero que tenha ficado claro. Tentei quebrar o máximo que
pude e o resto é sobre você. Vejo você no próximo.
26. Declaração de função VS Expressões: Ei, vamos falar sobre expressão de
função e declaração de função. Por que precisamos saber a diferença e quais são essas? Este será mais um vídeo teórico em vez do prático. Mas acho que isso é importante para entender a diferença, mesmo que B possa não ser necessário. Independentemente disso, no final do dia, isso fará de você um desenvolvedor melhor. Vamos. Então, se eu vou voltar ao Arquivo G, S aqui, vou declarar uma função. Vou chamá-lo de Olá, e por dentro cancelarei o log. Meu nome é Andrew. E abaixo eu vou criar um valioso olá para essa variável e para essa variável. Vou atribuir uma função. E por dentro vou imprimir. E você também. Agora, como você pode ver, os dois fazem a mesma coisa. Vamos chamá-los. Então, primeiro vamos chamar olá, e depois vamos chamar olá para o terminal. Vou executar o script e a saída. Bem, é basicamente o mesmo, certo? Então, qual é a diferença? A diferença é que o primeiro exemplo é uma declaração de função e o segundo exemplo é uma expressão de função. O segundo exemplo é, na verdade, uma expressão variável. Então, se eu vou colocar qualquer variável e dar um valor a
ela, ela será uma expressão. Então, o mesmo que podemos observar aqui. Basicamente, atribuímos uma função a uma variável. Diferente aqui. Aqui fazemos declaração de função. A diferença mais importante entre esses dois é que, com a declaração de função, não
importa onde definimos o tempo da função. Está na parte superior ou na parte inferior, mas com expressão de função e realmente importa. Vamos colocar os dois no final. E vamos chamá-los novamente. Vou executar esse script. E o que eu vejo, a primeira função, que é declaração de função, passou e posso ver a saída. Mas o segundo exemplo, erro de referência com
falha não pode acessar o hello tube antes da inicialização. A coisa é que hello two é uma expressão de função e o JavaScript só
criará essa função quando, na verdade, o JavaScript for para essa linha, declaração de
função será criada ou será içado para a costeleta. Em JavaScript, existe esse conceito de içamento quando as declarações de
função são, na verdade, como movidas para o topo antes que o código seja executado. É por isso que não importa onde os definimos. O código sempre, o idioma sempre verá esse código como se declaração da
função estivesse no topo, assim. Mas a expressão de função permanece onde foi definida. Assim como nas variáveis, podemos realmente referenciar a variável. Digamos oi, antes de ser criado. Então, se eu vou criar alto abaixo, e se eu tentar executar esse pedaço de código, darei o mesmo adder. erro de referência não pode acessar alto antes da inicialização. Então, como esta é uma expressão e o mesmo que vemos com olá, esta é uma expressão e não podemos acessar essa expressão antes de ser criada aqui no topo. Portanto, a única correção para isso é, bem, acessar olá depois de criarmos essa variável. Então, agora, se eu vou executá-lo, não
verei nenhum erro no mundo real em projetos JavaScript molar. Isso na verdade não é uma coisa. Você não observará esse comportamento no código. Bem, porque isso se relaciona principalmente com JavaScript simples e é sempre bom
conhecer e entender a diferença, certo? Mas em projetos modernos, como temos ferramentas que processam nosso código, essa coisa não ocorrerá, mas como eu disse, é bom e pessoalmente acho importante entender a diferença. Então, para resumir rapidamente, expressão de
função é quando você atribui uma função a uma variável, é mais fácil lembrar se você pode pensar nisso,
é que a declaração de função sempre começa com a função como a primeira palavra. E a expressão de função não tem função como primeira palavra porque a primeira palavra que temos const aqui, nós a atribuímos a uma variável e
as declarações de função são movidas para o topo, independentemente onde eles são definidos pouco antes do código ser executado. E é isso. Vejo-te no próximo.
27. Funções de arrow e argumentos de função padrão: Ei, neste vídeo, vamos falar sobre funções de seta e argumentos padrão. Vamos. Se eu vou navegar para file.js, vamos criar uma declaração de função simples que chamaremos de meu nome. E imprimirá Andrea, que é meu nome. E vamos criar um segundo exemplo que usa uma função de seta. E a função de seta é uma expressão de função em primeiro lugar, o que significa que ela será atribuída a uma variável. Então vou colocar const, meu nome, 2 é igual a parênteses, depois a função de seta, ou às vezes é chamada de função gorda. E depois desse corpo da função, vou colocar console.log e desenhar dois. Agora, se eu vou chamar meu nome, sabemos qual será o resultado. Mas se eu vou chamar meu nome para, será o mesmo? Vamos verificar. Nó file.js. E vemos que a saída está prevista porque,
bem, é apenas uma função, mas agora é uma função de seta. Então, qual é a diferença? A primeira diferença é que as funções de seta têm uma sintaxe
mais leve em comparação com as declarações de função. Bem, o problema é que vamos
usar muito as funções de seta, especialmente em JavaScript moderno. Eles são ainda mais preferidos do que as declarações de
função que começam com a palavra-chave function. Não há porque a sintaxe é mais leve, especialmente quando vamos
fornecer callbacks, dois métodos diferentes. É mais fácil fornecer uma função de seta. Então, se eu vou, por exemplo, usar o mapa de pontos da matriz, será mais fácil para mim fornecer uma função de seta. É mais leve escrever uma função de seta em vez de usar a função, depois parênteses. E agora parece que papai, pode até confundir algumas pessoas. Então, eventualmente, não importa qual deles, seja expressão de função ou declaração de função. Não importa porque, no final do dia, nosso código será processado
pelas ferramentas de construção que
cuidarão de tudo isso sob o capô. A segunda diferença tem algo a ver com essas palavras-chave em JavaScript. Não abordaremos esse caso de uso com a palavra-chave this. Mas eu diria que você realmente deveria ir ao Google e verificar você mesmo. Basta procurar por funções de seta, essas palavras-chave. E a terceira diferença é que as funções de
seta nos permitem usar uma sintaxe ainda mais curta do que essa. Quando precisamos retornar um único valor de uma função de seta, podemos omitir usando os colchetes encaracolados para especificar o corpo da função. Então, por exemplo, se meu nome retornar uma string, Andrew, podemos realmente escrevê-la assim,
o mesmo que teremos em meu nome. Então deixe-me escrevê-lo. Retorne Andrew, e não haverá diferença, certo? Mas com as funções de seta, podemos até torná-lo mais curto. Então, vou apenas copiar a string Andrew. Vou remover colchetes encaracolados. E eu vou colocar uma string, e agora nada será alterado, mas a sintaxe é muito, muito mais curta. Vamos verificar se meu nome realmente retorna uma string, Andrew, já que ele retorna um valor, vou gravá-lo em outra variável. Vamos chamá-lo de m e depois console.log M. Ótimo. Então eu vou executar o script novamente e você verá angio, correto. Isto é o que retorna do meu nome para ele é muito importante entender que, se você for escrevê-lo assim, a função não retornará nada, que significa que ela retornará indefinida. Deixe-me executar este script e você verá indefinido. Bem, como essa não é uma sintaxe curta, isso é o mesmo que escrever isso, mas sem a palavra-chave return. Portanto, é importante entender que, se você precisar ou se quiser usar sintaxe mais curta, lembre-se
sempre de excluir colchetes encaracolados. E também é importante entender que a sintaxe
mais curta retorna apenas um único valor. Se você precisar fazer alguma ação dentro de uma função, você não poderá usar a sintaxe curta porque, nesse caso, você não tem onde realmente escrever seu código. Então, neste caso, você é obrigado a fazer alguma operação aqui, certo? Certo, seu código personalizado e, em seguida, no final, você retornaria um valor assim. Portanto, não há diferença se você fizer isso com a palavra-chave return ou se você faz isso com a sintaxe mais curta é o mesmo. É assim você escreve o código sempre que possível, tente usar uma sintaxe mais curta porque bem. É mais curto. Há uma coisa que eu quero mencionar sobre essa sintaxe curta é quando você precisa retornar um objeto. Então, quando temos uma situação, quando precisamos retornar um objeto, por
exemplo, nome, entrada. Portanto, esse objeto eu quero retornar dessa função de seta. Bem, com a palavra-chave return, parece assim. Mas como vai
parecer sem a palavra-chave return, os objetos também
terão colchetes encaracolados e o corpo da função também tem colchetes encaracolados. Se vamos colocá-lo assim. Você verá erro de sintaxe porque bem, isso é errado JavaScript coisas que isso é função, mas não é um objeto. Para realmente corrigir esse problema, você precisa envolver o objeto de retorno entre parênteses assim. Então, dessa forma, ele entenderá que você
deseja retornar um único valor que deseja usar uma sintaxe mais curta e está retornando um objeto para verificar se permite executar o script. E vemos que agora temos nosso objeto retornado. Ótimo, tão bem, que se sentam sobre as funções de seta. Vamos utilizá-los muito. Vamos falar sobre argumentos de função padrão. Bem, esse é realmente fácil. Há muitas situações em que precisamos
passar argumentos para nossas funções. Por exemplo, meu nome para a única coisa que a função fará. Ele irá registrar o primeiro argumento que vamos fornecer. E vamos chamar esse argumento de meu nome. Então, no lado receptor, temos meu nome e, em seguida, imprimimos meu nome é meu nome. Ótimo. Agora, se eu vou chamar meu nome para, deixe-me remover código desnecessário. Se eu vou executar meu nome para sem fornecer o parâmetro para esse argumento. Bem, neste caso, Meu nome será indefinido porque,
bem, nós não o fornecemos, certo? Não fornecemos nenhum valor para o meu nome. Para verificar se podemos ver meu nome está indefinido. E há muitas situações em que temos circunstâncias
diferentes em nosso código e variáveis. Eles não produzem valores esperados. Eles não produzem o resultado esperado, certo? Portanto, neste caso, queremos garantir que
sempre temos algum valor de fallback para
fornecer o valor padrão para esse argumento de função. Precisamos apenas colocar iguais e, em seguida, fornecer um valor padrão. Não sei, John. Tudo bem, agora, sempre que eu não passar nenhum valor para isso, meu argumento de nome, John, ocorrerá e será usado como um fallback. Agora vamos tentar executar o script e você
verá que meu nome é John, certo? Porque eu não passo nada. Isso foi apanhado e agora usa John e John são impressos. Se eu vou fornecer angio, John não será usado em vez de Andrew porque Andrew não é indefinido. É um valor que passamos para esse argumento, certo? Ou execute o script. Agora vejo que meu nome é Andrew. Tudo funciona muito bem. Então, se eu vou passar indefinido, o que será impresso? Correto? John? Para verificar se estamos sob script novamente, meu nome é John. Perfeito. Imagine as situações em que temos vários argumentos em uma função. Digamos que meu nome e minha idade, e eu vou imprimir meu nome é e minha idade será minha h. Se eu não fornecer nenhum argumento, Meu nome será indefinido. Meu h será indefinido. Para verificar indefinido, indefinido, perfeito. Agora, posso realmente fornecer um valor padrão para todos eles ou apenas para um argumento. Então, deixe que seja minha idade e, por padrão, será igual a 10. Então, agora, se eu executar novamente, você verá que meu nome permanece indefinido porque não temos nenhum valor de fallback. E minha idade é 10. Talvez. Vamos colocá-lo em John. Vamos derramar Andrew aqui. E vamos colocar indefinido para finalizar nossos pensamentos, vamos dizer direto e nosso conhecimento. Então, para o meu nome e você será pego, e para a minha idade, 10 serão retirados porque fornecemos indefinido. Isso é o mesmo que não fornecer um valor, certo? Se eu vou escrever, meu nome é Andrew e minha idade é Stan. Perfeito. Bem, é isso. Agora você sabe como vamos utilizar as funções de seta. Quais são esses? E agora você sabe sobre argumentos de função padrão. Vejo você no próximo.
28. Interpolação de corda: Oi, Neste vídeo, vamos
falar sobre modelos de string
ou, na verdade, eles são chamados strings de
modelo e interpolação de string. Vamos em file.js. Suponha que eu quisesse imprimir meu nome em uma frase. Quero dizer que meu nome é Andrew, meu h é 10. Para isso, vou criar três variáveis. A primeira variável será nome, que será Andrew. O segundo será h, vai ser 10. E o terceiro será o resultado que vou imprimir no console. Então, para fazer uma frase, terei que concatenar strings porque vou usar valores dinâmicos, que são nome e idade. Na programação. Em outras linguagens de programação, isso geralmente é feito usando o operador plus. Então, isso vai parecer que meu nome é mais nome. Isso produzirá entrada. Então, novamente, mais. E agora o ponto de corda que eu tenho que digitar minha idade é novamente, então mais h. E também temos que cuidar dos espaços. Aqui. Tenho que adicionar um espaço e aqui também. Ótimo. Agora vamos tentar
imprimi-lo e executar este script, nó file gs. Meu nome é Andrew May, h é 10 anos. Este é o nosso resultado desejado. Mas, como você pode ver, isso não é muito prático porque, bem, essa sintaxe, na verdade não é conveniente. E se tivermos muitas variáveis e
tivermos uma string muito longa, então ela se tornará ilegível. E se houver uma maneira melhor de fazer isso? Bem, na verdade,
isso é modelos de string, ou geralmente chamados de strings de modelo. Vamos tentar executar novamente essa linha de código usando o modelo de string. Então, vamos criar outros resultados variáveis para. E vamos usar o modelo de string. Para usar o modelo de string, temos que usar backticks. Então, para strings regulares, usamos aspas regulares, certo? Uma única reclose ou aspas duplas. Para modelos de string, usamos backticks. Então, vou alternar aspas usando a extensão de aspas de alternância que instalei no VS Code. Você pode encontrá-lo no mercado VS Code. Esta extensão alterna aspas, essa. Então eu estou pressionando a ligação de teclas para alternar aspas e eu paro em backticks. Backticks, a string é avaliada como está, como aparece no código. Então vou digitar, meu nome é espaço. E aqui eu queria dinamicamente, digamos injetar um valor. Para fazer isso, temos que interpelar esse valor em uma string. Os modelos de string nos permitem fazê-lo usando a sintaxe de cifrão e colchetes encaracolados. Então, quando colocamos o cifrão seguido de colchetes encaracolados, dentro de colchetes encaracolados, podemos colocar qualquer expressão JavaScript que produza um valor. Esse valor será interpolado nessa string, naquele lugar nessa string. Então, queríamos colocar nomes aqui. Meu nome é nome. Eu coloquei Dodd. Minha idade é de novo, o
cifrão seguido de colchetes encaracolados h. Vou salvá-lo. Vou registrá-lo no console ao lado do nosso primeiro resultado. E vamos comparar esses dois. Como você pode ver, eles são os mesmos. Mas a diferença está no resultado
da sintaxe para usar modelos de string e o primeiro usa apenas o operador plus e concatenar strings já resultaram. Essa sintaxe é muito melhor e mais abrangente, e essa sintaxe é preferida no JavaScript moderno. Ninguém realmente usa concatenação para concatenar strings, talvez muito raramente, maioria das vezes, você verá interpolação de string usando modelos de string com backticks. Como mencionei anteriormente, a string que aparece dentro dos backticks é avaliada como está. Isso significa que se eu vou
colocar muitos espaços vazios aqui, e talvez aqui, todos
eles serão incluídos na sequência final. Então, se eu colocar espaços em branco aqui, cadeias de caracteres
em branco, elas serão cadeias de caracteres em branco na saída. Vamos vê-lo. Você pode ver que o espaçamento está todo retido. Coloquei três linhas vazias aqui, elas aparecem na saída. Não podemos fazer isso com o operador plus. Se eu vou colocar espaços em branco aqui, terei erro de sintaxe. E se eu tentar executar o script, terei erro de sintaxe, token
inválido ou inesperado se quisermos
usar linhas vazias em nossa string e quisermos mantê-las, somos obrigados a usar modelos de string. Portanto, isso levará a sintaxe inválida. Vamos colocá-lo de volta como era antes. Tudo bem, Agora entendemos modelos de string, como mencionei anteriormente, dentro de colchetes encaracolados, somos capazes de colocar qualquer expressão JavaScript. E, como lembramos, a expressão é uma entidade que produz um valor. Portanto, temos o nome que é expressão disponível, ele produz a Andrew uma string. O que eu quero dizer é que não estamos limitados a apenas colocar variáveis aqui. Podemos colocar qualquer expressão JavaScript dentro. Por exemplo, vamos usar o operador ternário. Se 10 for maior que cinco, então vamos colocar a variável de nome. Caso contrário, usaremos a idade porque 10 é sempre maior que cinco, sempre
teremos nome. Então, vamos tentar ver. E temos Meu nome é Andrew, minha idade é 10. Ótimos trabalhos. Vamos mudar o operador. E agora teremos, meu nome é 10 porque bem, temos falso aqui, e é por isso que recebemos H no final. Então, podemos realmente colocar uma função de cada ano. Vamos criar const e pegar meu nome. E ele retornará John aqui, certo? E dentro de colchetes curly usando interpolação de string, vou chamar essa função. Nessa função me retornará a string. Vamos experimentá-lo. Vamos ver meu nome é John. Minha idade é 10, e é isso. Isso é tudo o que precisamos saber sobre modelos de
string ou literais
de string e interpolação de string. No final, você precisa se lembrar três coisas sobre modelos de string. Então, o primeiro é que eles usam backticks. Eles não usam aspas regulares. Se você vai colocar citações regulares aqui, isso não funcionará. interpolação de string não funcionará. Se eu verificar, você verá que terei
o cifrão e colchetes encaracolados serão impressos. Eu tenho que mudar minhas aspas para backticks, então a interpolação de string funcionará. A segunda coisa a lembrar é que dentro da interpolação de string, podemos colocar qualquer expressão JavaScript. Não somos limitados. E a terceira coisa a lembrar é que a string dentro dos backticks é avaliada como está. Isso significa que, se colocarmos espaços vazios aqui, eles serão incluídos na string. Eles não serão omitidos. É isso. Vejo você no próximo.
29. Destruição de objetos e matriz: Ei, neste vídeo vamos falar sobre objeto e array faz estruturação. Esses dois recursos são muito usados. Vamos verificá-los em file.js. Digamos que eu queria criar um objeto, deixá-lo ser carro. E ele terá as seguintes chaves. Cor, que vai ser vermelha, digamos Gears 5 e talvez tipo de motor. Vamos colocar diesel. Agora digamos que eu queira acessar as chaves desse objeto. Então, geralmente eu faria isso como carro, depois colocando DOD e, em seguida, o nome da chave que eu quero acessar. E se eu quisesse colocá-lo em uma variável, geralmente faria assim. Então, vou declarar uma nova variável chamada engine. E então eu colocaria carro e atenção. E se eu quisesse puxar todos esses objetos, criaria uma variável separada para cada um. Por exemplo, as engrenagens const serão engrenagens de
carro e o mesmo que faremos pela cor, certo? Podemos ver isso como três linhas de código separadas. Bem, isso não é muito conveniente no GPS moderno, podemos fazer algo mais simples, destruição de objetos. Então, em vez de fazer isso, deixe-me comentar. Podemos substituí-lo por uma linha. Então vamos colocar const, então vamos colocar colchetes encaracolados para especificar que isso vai ser objeto faz estruturação. Então vamos colocar iguais e o objeto que gostaríamos de destruir, que vai ser carro daquele objeto de carro, queríamos puxar o motor e as engrenagens. Digamos que não precisamos de cor. Então, em colchetes encaracolados, especifico quais chaves eu quero extrair desse objeto. Então, vai ser de cor. E então vou puxar as engrenagens. Essa única linha de código
substituirá Esses dois por cores e engrenagens? Se quiséssemos puxar o motor também, nós apenas digitaríamos o motor aqui. E, claro, é muito importante
especificar o nome da chave de forma muito estrita. Digamos que se tivermos engrenagens aqui por algum motivo e elas estiverem em maiúsculas, não
sabemos disso, certo? E nós destruímos as engrenagens, elas serão indefinidas porque bem, não existe nesse objeto. Talvez vamos tentar e registrar o console, a cor. Assim. Deixe-me rapidamente fazer isso engrenagens e também antigo. Certo. Deixe-me pobre Node arquivo GS e você vê o Colorado e engrenagens diesel de motor indefinido, já que temos engrenagens, objetos a partir de uma letra maiúscula, e nós destruímos engrenagens que não existem nisso objeto. Temos indefinidos, mas outros valores são. Tudo bem. Então, vamos colocá-lo de volta e vamos verificar se ele funciona. Incrível. Agora temos Gears 5, esse objeto está estruturando, pense, é uma ferramenta realmente poderosa. Isso é basicamente tudo o que ele faz. Ele apenas puxa chaves de um objeto. É isso. Isso é basicamente o mesmo que fazer isso com essas três linhas separadas. Eu diria que isso é apenas uma taquigrafia. Ele não traz algo novo. É só uma taquigrafia. Há mais uma coisa nesse objeto apenas estruturando é que, digamos que, com a primeira abordagem com essas três linhas, podemos facilmente renomear variáveis. Se eu quisesse especificar o motor do carro, eu apenas renomearia a variável de motor para motor de carro, assim mesmo. Muito fácil, certo? Mas quando o objeto está estruturando, lembre-se de que sempre temos que especificar chave estrita que
gostaríamos de destruir, pois outra forma discutível não existirá. A chave não existirá nesse objeto. Então, como podemos renomeá-los? Bem, para fazer isso,
digamos que, em vez do motor, queremos usar o motor do carro. Tenho que colocar dois pontos e , em seguida, o novo nome dessa variável. Então agora, do objeto do carro, eu puxo o motor e renomeei o motor para o motor do carro. O mecanismo não existirá como uma variável. Ele aparecerá como motor de carro. Se eu estiver indo para o mecanismo somente log do console, vamos ver o que teremos. Teremos um erro de referência. O mecanismo não está definido porque essa variável não existe. Puxamos a chave do motor, mas o nome da variável agora é motor do carro. Então, se vamos referenciar o motor do carro, isso não nos dará nenhum erro. Acho que está claro. Então, o mesmo com outras teclas, se você quiser renomear a cor, colocaremos a coluna e, em seguida, a cor do carro. E é isso. Muito fácil, certo? Como uma triste destruição de objetos porque é uma ferramenta realmente poderosa. Vamos usá-lo muito, especialmente no React. Vamos dar uma olhada em um exemplo real que vamos usar no React na verdade. Então, vou criar uma função, digamos que alguma função. E esta função de soma receberá um argumento, vamos chamá-lo de carro de arco. Vamos esperar que nosso carro seja um objeto. E podemos chamar alguma função. E nós forneceremos nosso objeto de carro para o nosso carro, certo? Vamos comentar rapidamente e vamos tentar e console.log, arg, carro assim. E veremos nosso objeto bem simples. Agora, digamos que quiséssemos
cancelar chaves separadas de log desse objeto. Então, novamente, a mesma imagem que acabamos de fazer. Então, nós referimos essas chaves
usando a sintaxe do nome da chave da porta do carro de arco. Por exemplo, cor de ponto de carro de arco. Certo? Lemos, se eu vou usar o motor, ele vai ser desleal se eu fornecer uma chave não existente, por
exemplo, rodas quadradas, certo? Vou ficar indefinido porque bem, essa chave não existe nesse objeto. Em vez de fazer isso, posso usar a reestruturação de objetos e posso
usá-lo diretamente dentro do parêntese. Então, a primeira maneira que podemos usar, na verdade essa linha de código, assim. E vai funcionar, certo? Assim como discutimos anteriormente. Mas, em vez disso, eu posso realmente mover esse objeto está estruturando diretamente dentro do parêntese. Então, vou copiar isso e colocá-lo aqui. E agora acabamos de remover ainda mais linha de código. Agora posso acessar diretamente cores e engrenagens críticas. Vamos verificar se
lemos e cinco, o que está correto. Bom. Vamos estender esse exemplo um pouco mais. E se eu fornecer um segundo objeto para alguma função? Então, aqui, suponha que eu forneça um segundo objeto. Talvez não seja carro, mas vou colocá-lo como um carro. Tudo bem? E aqui eu espero algum objeto, e espero que esse objeto de soma dois
tenha duas chaves, nome e idade. Então, posso referenciá-los fazendo alguns objetos para o nome do ponto ou a idade. Mas, em vez disso, posso novamente usar a destruição de objetos diretamente aqui. Então eu colocaria nome e idade. Usamos a destruição de objetos para os dois argumentos. Então, os argumentos são separados com a vírgula, certo? E as chaves que destruímos são especificadas em colchetes encaracolados
com bastante facilidade que alguma função é um bom exemplo porque teremos um pedaço
de código muito semelhante no React. Vamos combinar a
estruturação do objeto com argumentos padrão. Então, e se eu não fornecer nenhum argumento para alguma função? Deixe-me remover o segundo objeto daqui. E digamos que eu destrua cores e engrenagens. Vamos experimentá-lo. O que vou conseguir? Eu obterei a cor da
propriedade não pode destruir de indefinida. O que aconteceu? Bem, o problema é, como você se lembra, quando não fornecemos nenhum argumento para algumas funções, esse argumento
que esperamos para um par nessa função será indefinido. Então, o que estamos basicamente fazendo aqui, estamos tentando puxar essas chaves de um valor vazio, que basicamente não existe sob o capô, parece assim. Então, puxamos cores e engrenagens do indefinido. Mas, como você pode ver, essa sintaxe leva a um erro de tipo. Isso está incorreto. Portanto, neste caso, para realmente corrigir esse erro, podemos fornecer um valor de fallback. Então, vou colocar um objeto vazio, e agora vamos ver o que vamos ter. Vamos ter indefinido, indefinido. Bem, isso é esperado porque não
fornecemos nenhum valor para esse objeto. valor indefinido retorna para um objeto vazio. E a partir desse objeto vazio, interruptor chaves, cores e engrenagens não existentes. Bem, porque eles não estão definidos em um objeto vazio. Se eu vou colocar a cor verde e tentar registrar o console, você verá que o valor será verde e as engrenagens serão indefinidas, certo? Porque, novamente, nosso valor indefinido retorna para esse objeto. E a partir desse objeto, destruímos a cor nas engrenagens. Há mais uma desvantagem na verdade com essa abordagem. E se eu fornecer um objeto vazio aqui? Como podemos saber, um objeto vazio já é um valor definido, certo? Vou colocar um objeto vazio. Você consegue adivinhar o que vai ser cor e engrenagens? Correto? Vai ser indefinido. Indefinido porque agora a cor e as engrenagens, elas não existem nesse objeto. É por isso que temos indefinido. Indefinido. E se quisermos especificar valores
padrão para chaves de objeto separadas? A abordagem é a mesma usando o sinal de igual. Assim, podemos colocar cor por padrão será verde. Vamos colocar um objeto vazio para verificar isso em um segundo. E as engrenagens, por padrão, serão seis, certo? Agora, se eu vou executá-lo, você verá verde e seis. Muito incrível. Então, novamente, para estender esse exemplo, se eu remover o valor padrão para o objeto em si, mas eu mantiver valores padrão para chaves
separadas e vou
remover um objeto vazio aqui. Vamos tentar executá-lo. Mais uma vez. Não podemos ler cor da
propriedade indefinida porque, novamente, temos a mesma situação. Essas duas chaves são tentadas para serem destruídas de indefinidas, o que leva a um erro de tipo. Então, para corrigir isso, temos que fornecer o fallback. Isso é importante. Fornecemos o fallback para o objeto em si, e aqui fornecemos valores
padrão para chaves destruídas separadas. Mas posso concordar que essa sintaxe é um pouco confusa. Podemos realmente refatorá-lo para que pareça mais agradável. Eventualmente, acabaremos com mais
uma linha de código, mas está tudo bem. Entre parênteses, vou manter apenas o valor padrão para o objeto em si. E em vez de usar a estruturação, vou colocar o nome do argumento. Então, deixe que seja objeto de carro. E em uma nova linha, vou realmente colocar a reestruturação para o objeto, as engrenagens de cores
const são iguais ao objeto Car. Agora você pode ver que nós realmente separamos as preocupações entre parênteses. Nós especificamos apenas o valor padrão para o objeto em si e em uma nova linha, quando usamos essa estruturação, especificamos valores padrão para chaves separadas, tão simples quanto isso,
eu pessoalmente acho que isso é um dos recursos mais legais disponíveis no GIS moderno. Eu realmente gosto disso, mas também temos um raio estruturando ao lado do objeto. A estruturação, na verdade é muito, muito semelhante. Então, digamos que eu tenha uma matriz ou talvez me deixe realmente remover tudo isso. Vou manter alguma função, mas vou comentar. E abaixo, vou criar algum array. E vou colocar alguns valores como 5, 4, 3, 2 e 8. E da mesma maneira que aplico objetos reestruturados a um objeto, posso usar uma estruturação de raio para significar que usamos a destruição de objetos. Usamos colchetes encaracolados, mas para matrizes, vamos usar colchetes de caixa. Então, da mesma maneira, vamos especificar colchetes de caixa matriz de soma igual. Mas desta vez não precisamos seguir rigorosamente o nome das chaves. Isso se opõe? Temos nomes de chave, mas na matriz não o temos. Na matriz, temos pedidos. Então, quando aplicamos a destruição de objetos, não
importa em que ordem você destrói as chaves. Mas em uma raiva é estruturante. É importante. Mas você pode dar nomes que quiser para suas futuras variáveis. Por exemplo, eu gostaria de interromper seu, o segundo elemento dessa matriz. Então, para fazer isso, sou obrigado a primeiro destruir o primeiro elemento, a ordem que você especificar em uma estruturação de raio será a mesma os elementos vão
na matriz original para destructor o primeiro elemento, eu forneço o primeiro elemento. E agora eu destruí O segundo elemento, segundo elemento, que será 4. Então, o primeiro elemento será 5, o
segundo elemento será quatro. Como você pode ver, o pedido é retido. Primeiro elemento cinco segundos 4. Se eu vou colocar o terceiro elemento aqui, você
pode adivinhar o valor? Bem, sim, vai ser três. Vamos verificar isso. Registro do console, primeiro elemento, segundo elemento e terceiro elemento. Note o arquivo GS, o que vemos 5, 4, 3, exatamente os mesmos valores. Se eu, por algum motivo, quisesse emitir esse elemento, digamos que eu o use assim, certo? Const, segundo elemento. Bem, isso não vai funcionar. O segundo elemento agora será o primeiro elemento, que é cinco. Se eu consolar o log, você o verá, será cinco. Porque, novamente, a ordem é importante quando você aplica uma reestruturação porque os elementos, eles são ordenados, eles não têm nomes de chave. Você pode dar qualquer nome a essa variável, mas você precisa manter a ordem. Eu acho que finalmente está bem claro, eu diria que uma estruturação de raio é usada da mesma maneira que a reestruturação de objetos. Se você quiser fazer algo semelhante com uma estruturação
de raio entre parênteses quando estiver usando a função, ela funcionará. A diferença é apenas que, com a destruição de objetos, q são necessários para usar colchetes
encaracolados com a estruturação do raio, você usará colchetes de caixa e também a ordem. Lembre-se de que, em uma matriz, os elementos são ordenados e é por isso que você
precisa destruir todos os elementos anteriores. Se você quisesse destruir o número do elemento. E se eu quiser destruir o quarto elemento, sou obrigado a interromper seus três primeiros. Isso é inevitável enquanto em chaves de objetos, elas não são ordenadas. É por isso que você pode usar qualquer pedido. Quando destruir as chaves, é sobre objeto e uma estruturação de raio. Vamos usá-lo muito e espero que tenha ficado claro para você. Vejo você no próximo.
30. Espalha e desocupação: Oi, Desta vez vamos falar sobre o resto e espalhar os operadores. Esses dois são fortemente acoplados ao objeto em raça e são muito usados em js modernos. Vamos descobrir o que eles fazem. Se eu voltar ao File GAS, deixe-me talvez criar uma função e o topo que eu vou nomear alguma função. Ele vai receber o argumento número um, argumento número 2 e 4. Agora console religioso log arg1, arg2, perfeito. Abaixo, deixe-me chamar essa função e deixe-me fornecer olá como o primeiro argumento. O segundo argumento será n para o terceiro será 15 em diante, talvez apenas uma função de seta vazia, e então deixe ser apenas o número 5. Ótimo. Se vou executar esse script, verei que tenho Hello Andrea, dois primeiros argumentos. Agora, como podemos realmente alcançar o resto dos argumentos e como podemos acumulá-los em uma única unidade, em S e Google suportável, é por
isso que o operador restante existe. Ele acumula o resto, os argumentos sobre o resto de algo em um único barril. Então, no topo, vou colocar uma referência rápida para nós. Portanto, o operador rest acumula ou digamos valores falsos em uma única variável. Falhas. Ótimo. Então, para usar o operador restante, temos que colocar os três pontos e o nome da variável na qual o resto será escrito. Então, deixe que seja erast de arcos. Pode ser qualquer nome. Agora deixe-me tentar e console log o resto dos arcos. E agora temos 15 funções anônimas e 5, basicamente
vamos
o resto dos argumentos que não definimos. Então podemos ver nossos dois primeiros argumentos são olá e ONG, e o resto é 15, a função e cinco, ótimo, se eu vou remover o R2 aqui, você
pode adivinhar como o resto do RX vai mudar? Vamos experimentá-lo, certo? Então, agora temos Andrew
no início do que 15 funções e cinco. E é assim que o operador restante funciona. Ele só pega o resto dos valores e os
dobra em uma única variável, assim. Agora, vamos ver como podemos usar o operador restante dentro de objetos e matrizes. Deixe-me comentar isso. E eu vou criar um objeto, diria que vai ser pessoa e o nome será Andrew. Talvez a idade seja 10. E suponha que eu tenha objeto está estruturando aqui. E eu gostaria de pegar talvez o nome daquele objeto
pessoa que vou cancelar a bagagem. Podemos receber nota angio. Talvez vamos adicionar mais chaves lá. Digamos que jogos de hobby, perfeitos. Agora, e se eu quiser de alguma forma recuperar apenas a chave de nome e o resto das chaves, eu gostaria de dobrar em um novo objeto completamente novo. Nesse caso, novamente, posso usar o operador restante. Assim como na função, vou usar três pontos dentro do objeto que faz a estruturação e o nome do objeto no qual o resto será escrito. Então, deixe que seja o resto da pessoa. Agora deixe-me tentar registrar o console o resto da pessoa. E o que vou conseguir, vou conseguir um novo objeto com o resto das chaves que não destruí. Então eu destruí apenas o nome. E o resto é h e hobby. É por isso que no novo objeto, que é o resto da pessoa, vou ver H e hobby se
vou adicionar H aqui. Agora, o resto da pessoa
conterá apenas hobby porque este é o resto. O que resta? Vamos verificar isso. Jogos de hobby perfeitos. Se eu vou destruir o hobby também, você
pode adivinhar o valor agora? Certo? Vai ser um objeto vazio. Se eu vou remover todas as chaves, você
pode adivinhar o valor agora? Correto. Vai ser exatamente o mesmo objeto porque o resto, bem, são todas as chaves que não
destruímos desde que não ouvimos nada. O resto é basicamente tudo aqui. A mesma regra se aplica ao apagar. Deixe-me comentar isso. E na parte inferior, vou criar alguma matriz. E vou colocar 5, 4, 3, 10 e 8, certo? E vou aplicar uma reestruturação de ataque. Então const pântanos colchetes de alguma matriz, de alguns re, eu gostaria de pegar primeiro elemento e o resto. Gostaria de escrever em uma variável completamente nova. Então, novamente, vou colocar três pontos e o nome da variável, que será o resto de alguma matriz. Vamos verificar se vou
consolar registrar o resto de alguns raios. E eu vou pegar 4, 3, 10 e 8, que é o resto
da matriz que eu não destruí. Se eu vou destruir seu segundo elemento. Agora, o resto vai ser 3, 10 e oito porque bem, eu tenho dois primeiros elementos e o resto é 310 e 8. Se eu verificar isso correto, tudo funciona perfeito. Agora, não falamos sobre o operador spread, mas podemos ver que ele também tem os três pontos. Bem, o problema é que os operadores de resto e spread, eles têm a mesma sintaxe, mas eles são usados em contextos diferentes e é muito fácil perdê-los confusos. Como sabemos, o operador restante acumula ou falsa o resto de algo em uma única variável. Eles espalham o operador faz exatamente o oposto. Ele desdobra algum valor. Então deixe-me demonstrar isso para você. Então, suponha que tenhamos um objeto. Tudo bem, onde está? Vamos, vamos reutilizar esse objeto de pessoa. E digamos que eu tenha outro objeto que é chamado de outro objeto. E tem alguns campos, como o genoma da
IA, e o nome deles será Alex, e talvez o carro seja BMW. Ótimo. Agora, e se eu quiser mesclar esses dois objetos? Podemos usar o operador spread para conseguir isso. Então, abaixo, vamos criar um objeto completamente novo, que chamaremos de objeto mesclado. Vai ser um objeto vazio. E nesse objeto vazio, vamos primeiro espalhar o objeto da pessoa e depois vamos espalhar algum outro objeto. Então, primeiro espalhamos a pessoa e depois espalhamos algum outro objeto. Você pode adivinhar o que vai ser o vale do objeto Merced. Vamos verificar o objeto em marcha. E vemos que o novo objeto tem todas as chaves que temos pessoalmente e em algum outro objeto combinadas. Bem, como eu te disse antes, o operador spread desdobra valores. Então, neste caso, ele desdobrou primeiro o objeto da pessoa
e, em seguida, desdobrou algum outro objeto. Além disso, como você já pode notar, ele tem exatamente a mesma sintaxe, três pontos que o operador restante, mas eles têm a diferença subjacente que, novamente, o operador spread desdobra valores enquanto o operador restante os dobra. Vamos dar uma olhada em outro exemplo com objetos. E se, em vez disso, eu só vou mesclar diretamente algum outro objeto dentro da pessoa. Eu posso facilmente fazer isso assim. Algum outro objeto. E é claro que tenho que colocá-lo no topo. E agora não preciso de objeto mesclado. E agora nosso novo objeto pessoa conterá todas as chaves da própria tigela e de algum outro objeto. Isso é muito flexível porque agora você pode usar o operador spread para gerenciar objetos como quiser. Você pode mesclar objetos juntos. Você pode mesclar um objeto em outro. E há alguns outros casos de uso que permitem que você use
esse spread de alguma forma para desdobrar as chaves de um objeto em outro lugar. No nosso caso, o que acabamos de fazer, desdobramos todas as chaves
desse objeto no objeto Person. Se eu vou remover o operador spread, vamos ver o que será desvalorizado. Teremos algum outro objeto como uma pessoa de insight chave. E essa chave manterá o valor do objeto com chaves, outro nome e carro. Por que temos isso assim? Bem, essa sintaxe que você vê aqui é basicamente a abreviação de algum outro objeto, dois pontos, algum outro objeto. Essa é a chave, esse é o valor. Mas quando temos uma situação, quando a chave terá o mesmo nome que a variável que mantém o desvalor, que é algum outro objeto. Podemos usar a taquigrafia e isso funcionará. Perfeito. Agora vamos ver o operador de propagação no apagamento. Vou comentar isso. E eu vou incomum ao nosso conjunto de somas. Então, aqui temos o resto de algum array. Na verdade, vamos remover isso. E vamos usar esse exemplo. Y é, vamos criar uma nova variável e nenhuma matriz, e deixá-la ser 123. Bom. Agora, da mesma forma que acabamos de mesclar objetos e exatamente da mesma maneira que somos capazes de mesclar apagar, certo? Então aqui vou criar uma matriz completamente nova. Vou chamá-lo de resultado. E nesse novo array, primeiro
vou desdobrar o resumo, e depois vou desdobrar outro array. Então, no final, vamos concatenar os dois arrays. Resumo e não se esqueça de três pontos. E depois outra matriz com três pontos. Agora somos apenas resultados de log do console e eventualmente, receberemos dois arrays combinados. Incrível. Isso é espacialmente flexível com matrizes porque somos capazes desdobrar algum array em outro array em qualquer lugar. Significa que se eu vou apenas substituí-los, vou trocá-los, certo? Terei pedidos completamente diferentes porque agora outro array vai primeiro. É por isso que vejo 123 e o array resultante. Se eu for remover o operador spread de ambos. Agora, nossa matriz tem apenas dois elementos em que cada elemento é uma matriz em si. Certo? Então, temos uma matriz de dois elementos. primeiro elemento é uma matriz, segundo é uma matriz, mas isso não é exatamente o que queremos. Normalmente, não queremos esses arrays aninhados. Queríamos trabalhar com corrida
mais plana porque isso é conveniente e bem, isso é normal de se ver. Haverá muitas situações em que teremos que usar o operador spread em matrizes. E gostaríamos de seguir rigorosamente alguns pedidos com o operador spread, somos capazes de colocar quaisquer valores em qualquer lugar que quisermos. Assim como estou fazendo agora, certo? Então você pode adivinhar o valor, o valor resultante, se eu colocar essa linha de código, Deixe-me ver. Então, primeiro, terei outro array. Depois de todos os valores de outra matriz que é 1, 2 ,
3, vou ter 15, 16 e 12. Depois disso, terei todos os valores do resumo. E no final terei 16, 1 e 0. Muito legal. Eu acho que isso é tudo sobre os operadores de spread e rest. Vamos usá-los muito. Eles são muito, muito úteis. Então eu aconselho você a se sentir confortável com isso e praticar um pouco. Eles podem ser confusos, mas acabam sendo muito fáceis. Então confie em mim, leve algum tempo, acostume-se com isso e eu vou te ver no próximo.
31. Código sincronismo, Callstack e Loop de eventos: Olá, finalmente chegamos ao nosso tópico final em JavaScript, uma promessas de código de coletor e coletor e esperam assíncrono. Este é o tópico mais importante no GS moderno, o conhecimento desse tópico é essencial. Sem esse conhecimento, o desenvolvimento de JavaScript nunca se sentirá completo para você. É por isso que sugiro ficar o mais confortável possível com esse tópico. Para entender um código de coletor e coletor e promessas, você deve entender tópicos mais profundos, como o GPS funciona sob o capô, o que é loop de eventos e pilha de chamadas? Neste vídeo, vou tentar explicar em termos simples como o JavaScript funciona para
entender o conceito de promessas, soltar. O que você vê na tela agora é uma visão geral de alto nível de como o JavaScript executa o código. Esta imagem descreve como o GS é executado dentro do navegador. Para o NodeJS, será um pouco diferente, mas é bom usá-lo para nosso caso de uso. Então, no quadro amarelo, você pode ver partes do mecanismo JavaScript que são chamadas de pilha e pilha de chamadas. A pilha está no espaço alocado na memória onde todas as variáveis definidas vivem durante a execução do código. A pilha de chamadas é aquele local de throughput que o JavaScript decide o que executar. Em seguida, falaremos sobre pilha de chamadas e um momento. Fora do quadro GS, você pode ver APIs da Web, retorno de chamada, fila e loop de eventos. Tudo isso não faz parte do mecanismo JavaScript. Isso significa que eles são definidos pelo ambiente em que
o JavaScript é executado. Conhecemos dois ambientes de execução JavaScript primários, navegador e NodeJS. Por exemplo, as APIs da Web incluem coisas como API DOM ou Fetch API, que fazem parte do ambiente do navegador. Somente, as APIs da Web não são implementadas em Node.JS. Não temos recursos de manipulação de HTML como documento get element by ID e NodeJS. Esses são recursos implementados no ambiente
do navegador só sabem gs, no entanto, implementa algumas coisas das APIs da Web. Por exemplo, defina um tempo limite. Eles parecem exatamente os mesmos em ambos os ambientes, mas sob o capô, a implementação é diferente. Você já deve ter ouvido falar que o JavaScript é uma linguagem de encadeamento único. Mas o que isso significa? Isso significa que o JavaScript tem uma única pilha de chamadas. Como pilha de chamadas únicas significa que o idioma pode processar apenas uma operação por vez. Imagine uma porta simples. Poucas pessoas ao redor tentando passar
pela porta podem caber apenas uma pessoa de cada vez. Não pode caber às pessoas
ao mesmo tempo em que a primeira pessoa entra na porta. E se essa pessoa ficar
mais alta do que outras pessoas que tentam passar
pela porta terá que esperar porque não conseguem
entrar somente depois que a pessoa do estoque sair da porta, outras pessoas poderão continuar e passar pelo mesmo com o mecanismo
JavaScript se houver duas linhas de código indo uma após a outra, por exemplo, dois logs de console, sabemos que a primeira linha de código sempre será executada primeiro e somente após os acabamentos de primeira linha, segunda linha será executada. Isso significa que, se a primeira linha de código levar cinco anos para ser executada, a segunda linha de código aguardará todos esses cinco anos para que a primeira operação seja concluída, e somente depois disso será executada. Então, novamente, o JavaScript é uma única linguagem encadeada com a pilha de chamadas únicas. Devido a uma única pilha de chamadas, mecanismo
GS pode processar apenas uma operação por vez. A pilha de chamadas é um armazenamento temporário para todas as funções pendentes a serem executadas. E é organizado como uma pilha, uma estrutura que segue o último método de primeiro a sair. Por último, primeiro a sair significa que último elemento adicionado ao o
último elemento adicionado ao armazenamento sempre será removido primeiro, uma pilha de placas é um exemplo perfeito de último a entrar, primeiro a sair, imaginar uma pilha de placas. Você empilha placas umas sobre as outras. Depois de ter modelos uns sobre os outros, digamos que você precise remover a primeira placa da parte inferior. Você não pode simplesmente tirá-lo de baixo direito? Se você fizer isso, a pilha cairá e as placas se espalharão. A única maneira de você tirar isso jogado é remover todas as placas do topo,
uma a uma até chegar à placa desejada
na parte inferior, esse tipo de organização é chamado de pilha. A última placa adicionada
à pilha sairá da pilha primeiro. Assim, o nome é o primeiro a sair. O Java poderia chamar stack segue exatamente a mesma organização. Agora imagine um contêiner. Esse contêiner será a pilha de chamadas. À esquerda, há um simples pedaço de código. Vamos ver como o JavaScript protestaria contra esse snippet. Javascript divide o código em funções. Quando o JavaScript precisa executar uma função, a função é adicionada ao topo da pilha de chamadas. Toda vez que a função sai ou retorna, ela é removida da pilha de chamadas. Então, primeiro, o JavaScript vê console.log. Você está pronto? Ele é adicionado à pilha de chamadas do que executado e imediatamente removido. Depois disso gs, Cs, imprima minha biografia, ela é adicionada à pilha de chamadas dentro de imprimir minha biografia, GS primeiro vê, obtenha primeiro meu nome, que significa que foi adicionado ao topo da pilha de chamadas. Gs olha para dentro, Get FirstName e vê que esta função retorna um valor. Uma vez que a função retorna, GS, a remove da pilha de chamadas. A execução da impressão minha biografia continua. Agora gs, Cs função GetAge, a mesma situação. Gs olha dentro do GetAge, a função
retorna e é removida da pilha de chamadas. Depois, há console.log final. Meu nome é Andrew, minha idade é 10, adicionada e removida instantaneamente. Imprima minhas saídas biográficas e a pilha de chamadas está vazia. Agora, a execução do código principal ou do mainframe está concluída. A notória pilha máxima de chamadas excedida ou erros de estouro de
pilha ocorrem quando o tamanho da pilha de chamadas é inflado e o número ficou ridiculamente enorme que o mecanismo não pode processar esse número de operações dentro do pilha de chamadas. Porque o JavaScript tem uma única pilha de chamadas que é organizada de uma maneira que você acabou de ver. É chamado de bloqueio. Lembre-se, uma operação de cada vez, próxima função não será executada até o término anterior. Isso nos leva ao termo síncrono, que basicamente significa que a execução vai uma a uma como a vemos no código. O comportamento de bloqueio pode ser facilmente absorvido dentro do ambiente do navegador. Em qualquer página, clique com o botão direito do mouse, selecione, Inspecionar e, em seguida, abra a guia do console. Dentro da guia do console, podemos executar qualquer JavaScript válido dentro do navegador. Por exemplo, console.log. Uau produzirá wow impresso no console. Perfeito. Mas e o comportamento de bloqueio dentro do ambiente do navegador, temos a função de alerta e é um bom exemplo para demonstrar o comportamento de bloqueio. Então, vou digitar Alert alto. E quando eu pressiono Enter, o que acontece é que primeiro eu vejo o pop-up que diz alto, mas o que acontece sob o capô? Sob o capô, a função de alerta foi adicionada à pilha de chamadas e ainda não foi removida porque o alerta não
saiu e o alerta não retornou nenhum valor, o que significa que o alerta ainda
é dentro da pilha de chamadas e bloqueia a execução de todas as chamadas de função subsequentes. Vou registrar qualquer coisa no console. Quando pressiono Enter. Nada acontece porque atualmente, neste momento, alerta está dentro da pilha de chamadas e bloqueia a execução, e continuará bloqueando a execução
até que a função de alerta retorne ou saia. E isso vai acontecer o que eu vou pressionar, Ok, então vou pressionar console.log. Vou executar o log do console mais duas vezes e depois vou pressionar OK, vamos ver o que vai acontecer. Agora. Você vê como tudo acabou de descongelar sob o capô. A função de alerta foi removida
da pilha de chamadas e a execução continuou. É por isso que posso ver todos os meus logs do console S3 para os quais pressionei Enter anteriormente. Ótimo. Agora entendemos o código de sincronização. Como você pode ver, não é muito conveniente esperar
sempre a conclusão de uma operação. É aqui que um código de sincronização vem para o resgate. Quando o JavaScript lê um pedaço de código coletor, ele é processado, não executado, processado em segundo plano e, uma vez processado, ele é colocado em uma fila separada para espera, que aguarda a pilha de chamadas ficar vazio quando todo o código de sincronização é executado e a pilha de chamadas fica vazia, o código
assíncrono, que foi colocado na fila de espera, é empurrado para a pilha de chamadas e agora está sendo executado. Existem recursos de linguagem especiais que nos
permitem escrever código assíncrono. São promessas e retornos de chamada, cujas
implementações são expostas a nós pelo meio ambiente. Navegadores, APIs da Web processam o código em segundo plano e atrasam seu loop de eventos de execução neste sistema é algum tipo de observador para a pilha de chamadas e a fila assíncrona que aguarda, uma vez chamada pilha está vazia. loop de eventos extrai itens
da fila de espera e os coloca na pilha de chamadas. Esse conceito introduz um modelo de execução de código sem bloqueio. Isso não altera o fato de que a pilha de chamadas pode processar apenas uma operação por vez, mas permite executar o código de maneira sem bloqueio. Vamos considerar um caso com duas operações. Envie uma solicitação para um servidor e imprima hello no console. A solicitação levaria 500 milissegundos para ser concluída durante a impressão Hello
levaria apenas dez milissegundos se for com o log do console modal de sincronização teria que esperar 500 milissegundos para a solicitação que você terminar e só então olá é impresso. Com o modelo sem bloqueio, a solicitação seria processada forma assíncrona em segundo plano. Bem, o código de sincronização continua sua execução. Nós veríamos Hello ser impresso imediatamente após dez milissegundos e a solicitação em segundo plano, terminaremos sua execução em algum momento
no futuro após 500 milissegundos sob o capô, há na verdade, várias filas de espera. Um para temporizadores, um para sacos frios, 14 promessas, etc. Eles têm prioridades diferentes e certas ordens. Por exemplo, as promessas têm prioridade sobre retornos de chamada para não complicar demais isso, vamos imaginar que haja uma única fila para todo o código assíncrono. Um dos exemplos de código assíncrono são retornos de chamada. Callback é uma função que é passada como argumento para outra função. retornos de chamada não são assíncronos por padrão, mas aqueles expostos pelas APIs da Web são realmente. Por exemplo, vamos dar uma olhada no setTimeout. Ele está disponível em ambientes conhecidos gs e navegadores. Vamos dar uma olhada em dois exemplos. Um dentro do GS e outro dentro do navegador. Na verdade, não importa onde vamos usar o SetTimeout. Mas quanto mais melhor, não é? O primeiro exemplo estará dentro de nenhum GS. E já preparei esse
código simples com dois logs de console e setTimeout. Portanto, setTimeout espera que forneçamos dois argumentos, onde o primeiro argumento é o retorno de chamada que será executado após o número de milissegundos que fornecemos. Como segundo argumento, neste caso, eu forneço a 0 milissegundos, isso significa que a execução não será atrasada. Mas vamos ver como o código será executado. Você consegue adivinhar o resultado? O que virá primeiro? Vamos ver. Vou executar o script e veremos 1, 2, e só então o tempo limite é acionado. O problema é que setTimeout é assíncrono. Isso significa que o tempo limite, o retorno de chamada foi adicionado à fila de retorno de chamada em segundo plano. Vou fornecer 2504,52 segundos. Vamos ver como a imagem será diferente. Eu executo o script, vejo 12. Então eu vejo o atraso de 2,5 segundos. E só então o tempo limite do IC dispara sob o capô. Settimeout foi processado pelo código. Settimeout foi adicionado à pilha de chamadas,
mas o retorno de chamada e a execução do timer foram delegados às
APIs Node.js a serem processadas em segundo plano, setTimeout foi removido da pilha de chamadas. Isso significa que a execução continua. Em seguida, vemos o registro do console um na pilha de chamadas e removido instantaneamente. E o mesmo com o segundo log do console adicionado à pilha de chamadas e removido instantaneamente. E uma vez em segundo plano, o temporizador é processado após 2,5 segundos no futuro. Esses callback serão adicionados
da fila de retorno de chamada
em segundo plano para a pilha de chamadas e, em seguida, executá-lo. E não importa quantos milissegundos vou fornecer para o segundo argumento. Ele será sempre protesto de forma sem bloqueio, e será empurrado para a fila de retorno de chamada. E somente depois que a pilha de chamadas ficar vazia, o loop de eventos puxará esse callback
da fila de retorno de chamada em segundo plano e o enviará para a pilha de chamadas. Não importa quantos milissegundos eu forneça ou onde eu coloquei esse código, ele sempre protestará de forma assíncrona. Se eu colocá-lo no meio e eu fornecer 0 milissegundos, a imagem é a mesma. Vamos dar uma olhada no segundo exemplo. Você pode ver um HTML de índice muito básico, que tem um único elemento de botão com id, btn. Então, dentro do script, acabei de puxar esse botão usando a API DOM, seletor de créditos
documentados, hashtag, meu btn. Em seguida, para esse elemento de botão, anexo um ouvinte para o evento onClick e para o evento onClick na função
BET e clique será acionado. Agora ele está vazio, mas vamos adicionar algo dentro do log do console hello. E deixe-me realmente abrir esse index.HTML dentro do navegador. Clique com o botão direito do mouse em revelar Clique duas vezes nele e boom, aqui vamos nós. Clique com o botão direito do mouse E abro a guia do console, pressiono clique em mim e vejo olá é impresso assim como definimos dentro do manipulador para o evento onClick. Perfeito, vamos realmente copiar e colar o código que não tínhamos em GS para o manipulador. Agora, o comportamento será o mesmo que dentro do não, GS. Vamos verificar isso. Volto ao navegador, atualizo a página. Pressiono o botão e, como posso ver, primeiro vai 1, 2, e só então o tempo limite é acionado, mesmo que seja colocado entre os logs do console. Se eu colocá-lo no trabalho e se eu vou colocar, digamos dois segundos. Eu atualizo a página. Eu clico na parte inferior, um a dois segundos se passaram em disparos de tempo limite do IC. Bem, a imagem é a mesma. Então, o que acontece é que, uma vez que o JavaScript lê
setTimeout, setTimeout está sendo adicionado novamente à pilha de chamadas,
mas o retorno de chamada e o timer onde delegaram desta vez para as APIs da Web dentro do navegador. Isso significa que eles estão sendo processados em segundo plano. A execução continua. Settimeout é removido da pilha de chamadas. Registro do console adicionado à pilha de chamadas, executado e removido. E o mesmo com o segundo registro do console. Quando o código for concluído, o mainframe ou o código principal for concluído, loop de
eventos verificará constantemente a fila de retorno de chamada. Então, o di callback é adicionado à fila de retorno de chamada. E, em seguida, o loop de eventos vê isso e empurra esse callback para a pilha de chamadas. E depois disso, a chamada sai pela culatra. Mas vamos ver isso com o exemplo de bloqueio. E se eu for colocar alerta em vez de log do console, vou digitar alerta alto. E vou remover o segundo log do console. E agora a pergunta é definirá o tempo limite para ser processado em segundo plano
assim que o alerta começar a bloquear o loop de eventos, vamos ver. Eu atualizo a página. Pressiono o botão, alerto disparos e agora ele bloqueia o loop de eventos. Mas não vejo nada dentro do console. E se eu for pressionar o botão OK, somente depois disso, o código começará a processar o retorno de chamada. Porque setTimeout aparece após a linha de alerta. Se vamos colocar setTimeout antes da linha de alerta, a imagem será diferente. Para atualizar a página. Clique no botão Me novamente. Alert começa a bloquear o loop de eventos, mas agora SetTimeout já delegou o processamento desse callback para APIs da Web. Isso significa que, enquanto o alerta bloqueia o loop de eventos, callback está sendo processado por APIs
da Web em segundo plano. E agora esse retorno de chamada está dentro da fila de retorno de chamada aguardando para ser empurrado para a pilha de chamadas. Se eu vou pressionar Ok, verei instantaneamente disparos de tempo limite. Certo? Mas se eu vou pressionar Ok, dentro desses dois segundos aqui, a imagem mudará,
atualizará a página, clique em mim, pressione instantaneamente Ok. E você pode ver que foi ainda menos de dois segundos porque, uma vez que eu clico no botão, isso é instantaneamente delegado às APIs da Web. E não importa por quanto tempo a linha de alerta bloqueará a execução. Isso já está processado em segundo plano. Ótimo. Então, em termos simples, podemos dizer que o código assíncrono é esse tipo de código que sempre é executado depois de todo o código síncrono. Para lembrar facilmente esse conceito, imagine duas colunas, uma para sincronização e 14 código assíncrono, digamos que gs comece a ler o código e depois classifica o código em zinco e as colunas de zinco. E quando chegar a hora de executar o código, basta colocar a coluna assíncrona abaixo da coluna do coletor. E aqui vai você. Esta é a ordem na qual o código será executado. Claro, isso é simplificado demais, mas dá a ideia básica. No GAS moderno, você verá promessas em todos os lugares. A base para promessas é o código assíncrono. É por isso que é tão importante alavancar esse conceito. Solicitações de servidor, operações
de banco de dados, operações de leitura de arquivos Por tudo isso, usaríamos promessas e código assíncrono. Espero que tenha sido claro e agora você tenha
entendido melhor como o GS interpreta o código. Da próxima vez, vamos falar sobre promessas e async aguardam. Veja outro.
32. Código de sincronização e sincronismo - - e Async Sync: Oi, Neste vídeo, finalmente vamos
falar sobre promessas e async aguardam. Vamos. Sabemos que a base para promessas é código assíncrono. Mas então o que é uma promessa? Uma promessa é um objeto e isso
produzirá algum valor em algum momento no futuro. De forma sem bloqueio assíncrona, uma promessa pode ser um dos três estados pendentes estado, estado resultados e estado rejeitado. Embora uma promessa esteja no estado pendente, isso significa que a promessa não resolveu ou ainda não produziu nenhum valor, uma promessa é resolvida. Isso significa que a promessa já produziu um valor. E quando as promessas rejeitadas, isso significa que essa promessa foi lançada e somada e não produziu nenhum valor. Tudo bem, vamos ver como é uma promessa muito básica, e vamos ver como podemos começar a trabalhar com eles. Então, deixe-me criar uma variável. Vou chamá-lo de fazer alguns. E dentro dessa variável vou chamar de construtor prometido. Para fazer isso, tenho que fazer uma nova promessa. E o construtor de promessa, tenho que fornecer o executor ou o retorno de chamada que inicializará a promessa. Então, vou passar um retorno de chamada vazio. E esse retorno de chamada que passo para o construtor sempre recebe dois argumentos. O primeiro argumento é algo chamado resolve. O segundo é rejeitar. Portanto, o primeiro argumento é a função que devemos chamar dentro do callback para produzir um valor dessa promessa. E quando chamamos de rejeição, obviamente lançamos um erro dessa promessa. Nós rejeitamos essa promessa. Então, por exemplo, vou chamar resolve. E como você pode ver pela inteligência, tenho valor que tenho que passar. Resolvemos uma promessa com algum valor porque a promessa produz um valor. Então, por exemplo, olá. Agora, vamos tentar usar essa promessa de alguma forma. Então lembre-se de que uma promessa, não
é uma função. Então, seria errado chamá-lo com parênteses como se isso fosse valioso fosse uma função. Basta fazer referência
à promessa para que ela funcione. Se eu salvar o arquivo e então eu executar o script, você verá que nada vai acontecer porque bem, não
imprimimos nada na saída. Mas se eu estiver indo para o log do console, faça alguns, neste caso, verei que o objeto promessa será impresso. É importante notar que o que você vê aqui é o objeto promessa. Portanto, é a promessa em si. Não é o valor que a promessa resolve. retorno de chamada que passamos para o
construtor de promessa é inicializado de forma síncrona. Isso significa que sempre que nos referimos a alguns, esse retorno de chamada será executado de forma bloqueada. No entanto, o valor que será resolvido a partir dessa promessa é resolvido de forma sem bloqueio. E para resolver um valor
dessa promessa de obter a string real hello, tenho que usar essa sintaxe de promessa especial chamada então ou apenas sintaxe venerável. É chamado às vezes assim. Então faça um pouco de DOD. E a partir da inteligência você pode ver que eu tenho três opções pegar finalmente, e
então, para resolver um valor dessa promessa,
eu tenho que chamar o método ponto, então,
no objeto de promessa e o método ponto-ponto 2D, Tenho que passar um retorno de chamada. E esse callback como primeiro argumento, receberá o valor do resultado dessa promessa, por exemplo, valor resolvido. E se eu tentar e consolar o valor do resultado do log, você verá que será nossa string Olá. Se eu executar o script, você verá que o Hello é impresso na saída, o que está correto. Agora, e a função de rejeição que recebemos como segundo argumento no inicializador. Então, vamos tentar e, em vez de Resolver, usar reject e, uma vez que eles o chamem, você pode ver um motivo de argumento opcional. Então, sempre que
rejeitamos uma promessa, rejeitamos por algum motivo, na
maioria das vezes, você rejeitará uma promessa com um erro e outras promessas que você vai
deixar dizer encontrar na natureza, todos eles rejeitarão com um objeto de somador. É por isso que, em vez de apenas passar a rejeição com essa promessa falhou. Mas a mensagem assim, em vez disso, passamos por um novo editor e a
mensagem será promessa, falha na nota. Agora, se eu vou executar este script,
você verá erro, você verá erro, promessa falhou e tratou aviso de rejeição de
promessa e nota
importante aqui que isso então chamada de volta nunca foi acionada porque a promessa rejeitada e não vemos nenhum valor de resultados. Isso significa que a promessa lança um erro e
não fazemos nada para lidar com isso. Sempre tente detectar erros das Promessas. Isso é realmente importante porque, caso contrário, você
verá mensagens como aquela rejeição de promessa não tratada, o que pode potencialmente travar o aplicativo. Então, para capturar essa rejeição dentro da promessa, temos que usar o bloco de captura que vimos anteriormente. Então, vou colocar o DOD e depois vou chamar o método catch. E por dentro eu também tenho que passar um retorno de chamada, pois o primeiro argumento que chama volta para o método catch
receberá o que rejeitarmos essa promessa. Então, como rejeitamos essa promessa com outro objeto, nova promessa falhou. Aqui. Primeiro argumento, vou receber o objeto. Então, vou apenas para o log do console. E direi que o adder ocorreu. E então vou imprimir a mensagem de erro. Ótimo, vamos tentar executar o arquivo. Você verá que não temos nenhum aviso de rejeição de promessa não tratado. E desta vez vemos nosso registro do console. Assim, sempre que rejeitarmos a promessa, toda a dança que definimos para resolver a partir dessa promessa nunca será executada porque a promessa lança um erro e esse erro ou rejeição é tratado pelo bloco catch. Outra ótima dica sobre promessas é aquela dança de pontos. Eles podem ser acorrentados quantas vezes quisermos, o mesmo com blocos de captura. Então, por exemplo, se aqui eu
vou colocar outro ponto novamente, você verá o esboço inteligente finalmente. E, novamente, chamo o método then, passo a chamada de volta. Desta vez, recebi valor, digamos, e eu tento consolar o valor de log em segundo deles. E você pode adivinhar qual será esse valor? Vamos tentar. E vemos que uma promessa falhou. Aha, ok, Então, em vez de rejeitar, vamos novamente usar o resolve para realmente dizer dar o controle para dançar pontos. Não precisamos lançar o adder dessa promessa desta vez. Então observe o arquivo GS, você pode ver o Hello primeiro impresso porque isso é o que fazemos na primeira chamada de volta e depois vemos que
o valor no segundo Dan é indefinido. A coisa é que quando você encadeia múltiplos e argumentos, o primeiro argumento no Dan subsequente será o valor de retorno do anterior, porque a partir deste primeiro, depois callback não garantirá nada. Segundo ponto, em seguida, o primeiro argumento será indefinido. Se eu vou devolver cinco aqui, valor aqui agora será cinco. Vamos tentar. E você verá o valor em segundos, então é de cinco anos. Então, se eu vou usar outro terceiro Duck Dan, e desta vez vamos dizer val três em terceiro, então será três, certo? Vai ser indefinido, certo? Porque a literatura nada do anterior. Então, se eu vou retornar 10, Val três vai ser 10. Espero que esteja claro. E você pode ter uma pergunta, por que precisamos encadear várias danças aqui? O problema é que, no mundo real, vamos
trabalhar com várias promessas ao mesmo tempo. E dentro de uma promessa, vamos chamar outra promessa algo como fazer algum ponto então, então dentro teremos algo como retornar outra promessa e novamente, e assim por diante. É por isso que é mais fácil passar o resultado de alguma lógica para outra, a fim de simplificar o código para que ele o torne mais legível. Sei que pode ser confuso porque
não há um exemplo real agora aqui. Mas acredite em mim, está totalmente bom. Você verá isso no futuro. Na verdade, vamos tentar criar um exemplo mais real usando promessas. Então, vou remover tudo isso. E, em vez disso, vamos criar uma promessa completamente nova de que vamos envolver a função setTimeout que já conhecemos. Gostaríamos de converter setTimeout para,
digamos, sintaxe baseada em promessa. Por exemplo, quero criar uma função, vamos chamá-la de peso, somar. Essa função eu passaria, digamos número de milissegundos, digamos 40000 por 40 segundos. E isso vai ser uma função que retornará uma promessa. E depois dessa função, uma vez resolvida, uma vez que a promessa for resolvida, esse retorno de chamada será executado. Por exemplo, log do console, quatro segundos se passaram. É algum tipo de substituição para setTimeout, mas usando a sintaxe prometida be. Então, como somos capazes de implementar isso. Então esta é a nossa maquete. Vamos apenas comentar, e agora vamos começar a escrever a promessa. Portanto, a soma de peso é uma função que recebe um argumento, que é o número de milissegundos. Então, vou criar uma soma de peso. Como uma função de seta. Essa função recebe um tempo limite de argumento em uma bagunça como essa. E essa função retorna uma promessa, que gera nova promessa para o construtor de promessa, eu passo o retorno de chamada. E esse callback recebe dois argumentos, resultado e rejeição. Mas como não encontramos rejeição aqui, vou usar o argumento de resolução. Então agora temos que
atrasar a execução de código dentro dessa promessa, podemos usar setTimeout. Então, vou ligar para SetTimeout. primeiro argumento novamente é o retorno de chamada que será acionado após número
fornecido de milissegundos como um segundo argumento. E para o segundo argumento, vou passar o argumento para peso alguma função em si, tempo limite na massa. E uma vez que esses frios foguem pela culatra, vou ligar para
resolver a partir dessa promessa. E é isso. Essa é a nossa implementação. Vamos comentar nosso uso dessa promessa e vamos ver como ela funciona. Arquivo de nota GS. Posso ver quatro segundos se passaram e vejo minha saída quatro segundos depois. Apenas para demonstrar a você como isso não será bloqueador, podemos realmente usar o mesmo exemplo de nossos vídeos anteriores, console de log do console 2. Não importa onde eu coloquei algum ponto promessa Dan, ele sempre será resolvido usando a sintaxe de ponto de forma não bloqueadora. Isso significa que ele sempre aparecerá depois de todo o código síncrono. Para verificar isso, novamente, talvez vamos torná-lo um pouco mais curto. Uma série 100. Você vê 12 e só então quatro segundos se passaram. E não importa se eu coloquei SetTimeout ou não aqui. Por exemplo, vou
resolvê-lo sem nenhuma lógica. Sempre estará no final porque uma promessa é sempre resolvida de forma sem bloqueio. Espero que esteja claro. Agora, vamos dar uma olhada em outro exemplo do mundo real usando a API Fetch que temos disponível dentro do navegador. Se, quando o Google, eu vou digitar o espaço reservado JSON, acabo no tipo de ponto de espaço reservado JSON code.com. Quando eu rolar um pouco para baixo, você pode encontrar esta seção com um exemplo. Então, vou copiar isso e colá-lo dentro do meu script NodeJS. Se eu tentar executar o arquivo, você verá Fetch não está definido porque novamente, Fetch está disponível somente dentro do ambiente do navegador. Ele faz parte das APIs da web de navegadores. Ele não é implementado nativamente em Node.JS. É por isso que esse pedaço de código
só funcionará dentro do navegador. Então eu copiei novamente, vou para o console do navegador, certo? E aqui eu executo o código. Então, vamos dividi-lo. O que está acontecendo aqui? Então, antes de tudo, o que buscado faz, nós fornecemos um URL para essa função, e essa função envia uma solicitação para esse URL e nos devolve a resposta. Essa busca de pontos é uma função que retorna uma promessa. É por isso que temos que usar a sintaxe pontual
Dense para resolver essa promessa. Então, o fetch envia uma solicitação para o URL de forma sem bloqueio em segundo plano. E quando a resposta para essa solicitação estiver pronta e o navegador estiver pronto para lidar com ela, essa
promessa será resolvida, essa chamada sai pela culatra e obtemos acesso ao objeto de resposta. E, como você pode ver, esse é nosso senso de carga útil para nós de volta do servidor. E esta é a promessa que estava pendente Uma vez que estava frio e uma vez resolvida com o primeiro ponto, então você vê que o estado prometido está agora cumprido. Como mencionei anteriormente, essa solicitação será processada de forma sem bloqueio. Isso significa que, se essa solicitação demorar até 10 segundos, então esse retorno de chamada dentro do primeiro ponto, Dan disparará após 10 segundos de forma sem bloqueio. Mas qual é essa resposta aqui? Vamos tentar reescrever esse exemplo um pouco. E em vez de chamar a resposta JSON, vamos apenas para o objeto de
resposta console.log que temos aqui. E, como você pode ver, o objeto de resposta tem algo amigo, amigo usado cabeçalhos. Bem, esse objeto de resposta representa a resposta do servidor. E nesse objeto temos o método JSON ponto que devemos chamar nesse objeto
para obter a carga no formato JSON. Então, se vamos acessar esse URL em uma guia separada, certo? Tudo isso está acontecendo como manualmente. Fazemos isso manualmente usando a caixa de pesquisa do navegador, mas para fazê-lo programaticamente, usaríamos fetch e, em seguida, chamaríamos o método JSON ponto disponível no objeto de resposta. Este, mas o método JSON também o Cerence nos é uma promessa. Mas como é uma única ação dentro dessa chamada de volta, o valor dessa promessa será resolvido automaticamente e será o valor de retorno dessa chamada de volta. O que está acontecendo aqui é que dentro do primeiro ponto , em seguida, response.data não é método chamado, essa promessa é resolvida e é retornada. A partir do primeiro ponto e depois callback porque esta é a abreviação das funções de seta, já
sabemos que o valor
de retorno do método Dodge JSON estará disponível como um primeiro argumento no subsequente então é por isso que aqui temos argumentos chamados JSON. Você pode nomear o que quiser, e então nós apenas o console bloqueamos. É por isso que, se formos executar esse exemplo, veremos nossa carga útil. Mas desta vez fizemos isso programaticamente em vez de ir ao navegador e apenas acessar o Euro. Agora tudo isso acontece programaticamente usando a API Fetch disponível no navegador. Ótimo. Eu diria que isso é tudo sobre promessas, mas há mais uma coisa. Também temos algo chamado async await. E async await é apenas uma sintaxe alternativa à sintaxe ponto e depois, já que vamos trabalhar com múltiplas promessas ao mesmo tempo, a sintaxe de
ponto ponto se torna realmente confusa em algum momento. É por isso que uma alternativa a essa sintaxe é assíncrona aguardar. Vamos ver como ele se parece, e vamos realmente tentar reescrever este exemplo com fetch usando async await. Então, antes de tudo, a sintaxe async await está disponível apenas dentro de uma função. Isso significa que, para usá-lo, temos que criar uma função. Então, vou criar uma nova função. Vamos chamá-lo de solicitação de envio. E para tornar a
sintaxe assíncrona aguardar disponível dentro dessa função, temos que marcar essa função como um coletor. Então, função assíncrona enviar solicitação, se fosse uma função de seta, Const, digamos enviar solicitação. Seria assim. Logo antes da função de seta, colocaríamos a palavra-chave assíncrona, mas vamos manter a sintaxe da função
regular para sabermos disso. Para resolver essa promessa, certo, temos que chamar o ponto Dan e fornecer um retorno de chamada dentro da sintaxe async await. Não usamos ponto, então usamos a palavra-chave aguardar. Aguarde. É por isso que o nome da sintaxe é chamado de async aguarda porque bem, são apenas duas palavras-chave, assíncrono para marcar função a ser usada com assíncrono, aguardar sintaxe e um peso para resolver a promessa. Só vou chamar o fetch. Deixe-me copiá-lo. Busque. E para esperar que essa promessa seja resolvida, eu tenho que colocar um peso na frente e isso substituirá o ponto, então com ele é chamado de volta na frente de uma espera, eu tenho que assinar o valor
do resultado dessa promessa de sobre a Apple, por exemplo, isso vai ser resposta igual a aguardar, buscar. E o mesmo faremos com o método JSON. Então, agora temos acesso ao objeto de resposta. E então vamos criar a nova variável JSON. E ele vai aguardar ponto de resposta JSON, que está disponível no objeto de resposta. Se você não for usar a palavra-chave await, a variável JSON será o objeto promissor, assim como você viu no início do vídeo. Isso não é o que queremos. Só queremos o valor do resultado dessa promessa se eu for remover a palavra-chave await, certo? E se eu passar o mouse sobre a variável, verei promessa porque esse é o objeto promessa. Mas se eu ficar aguardado, terei algum, o que significa que essa variável manterá qualquer valor, mas definitivamente não é um objeto promessa. Agora, vamos tentar registrar o console JSON. E esse pedaço de código substituirá completamente essas três linhas. Sim, é um pouco mais de linhas, mas essa sintaxe é mais fácil de ler. A sintaxe async await é construída sobre promessas, e sua intenção é fazer promessas para se
parecer mais com código síncrono regular. Porque você pode ver que podemos ler este pedaço de código linha por linha, ao contrário do ponto, então um nó a apontar aqui é a segunda linha de código, certo? linha número sete não será executada antes linha número 6 resultar, uma vez que usamos a palavra-chave
await, significa que se esta linha de código, ela, essa promessa leva 10 segundos para ser executada, o código não irá mais adiante. Ele aguardará todos os dez segundos até que a promessa seja resolvida, porque usamos a palavra-chave
await, ela aguarda a promessa. A promessa é resolvida e só então a execução continua. Espero que fique claro verificar se vamos chamar a função e vamos executar esse pedaço de código dentro do navegador. E você verá que teremos exatamente o mesmo resultado. Vamos ver nossa carga útil que recebemos do servidor. Tudo bem, acho que isso é tudo para este vídeo. E sei que foi muito difícil entender essa quantidade de informações. Foi muito confuso, mas acredite em mim, não
é tão complicado quanto parece. Vamos anexar o tópico mais
uma vez em nossos projetos React. E é aqui que te verei da próxima vez. Adeus.
33. Modos de ECMAScript: Ei, neste vídeo eu gostaria de falar sobre módulos
atmosféricos no ambiente Node.JS, já
sabemos que existe um sistema de módulo nativo chamado GS comum. Ele usa a sintaxe de exigência e de
exportações de módulos para importar e exportar algo de um módulo no ambiente do navegador, também
temos um sistema de módulo de navegador nativo que é chamado de script. Módulos e módulos atmosféricos usam sintaxe de importação e exportação. comunidade Nodejs envia módulos Ackman Script a serem implementados em Node.JS para
substituir o CommonJS porque os módulos Ekman Script são mais convenientes e mais abrangentes. E, eventualmente, criamos ferramentas que nos
permitem usar módulos ACML Script no
ambiente Node.JS sem suporte direto para módulos atmosféricos no ambiente
Node.JS, de qualquer maneira, e moderno JavaScript, você verá os módulos ECMO Script. E raramente, eu diria que você veria CommonJS. Agora, neste vídeo, gostaria de falar sobre importação e exportação de módulos
atmosféricos porque há alguns aspectos importantes que
precisamos entender sobre eles. Primeiro, vamos criar dois arquivos. Então, vou renomear file.js para file.js MGS para usar módulos de script ACML nativamente no ambiente Node.JS. Então vou criar um segundo arquivo chamado segundo MGS. E do segundo MGS, vou exportar algumas coisas. Então, primeiro vou criar uma variável chamada Cinco, e vou exportar cinco ao lado dela. Vou exportar const 10. E vou especificá-lo assim. Você vê a diferença? Então, primeiro criei uma variável, depois a exportei. E aqui está apenas uma linha única, basicamente a mesma coisa que no topo. Talvez vamos exportar outra coisa. Exportar const. Meu nome será Andrew. E no final, vou colocar o padrão de exportação e, desta vez, deixá-lo comprar exatamente assim. Então, como você pode ver, temos dois tipos de especialistas. Nomeamos exportações e temos uma exportação padrão. Portanto, um aqua Script módulos, existem dois tipos de especialistas nomeados e padrão. Pode haver apenas uma exportação padrão em um módulo e quantas você quiser exportações nomeadas. Agora, como podemos realmente importar todos esses. Se eu for ao File MGS aqui, preciso digitar importar algo do segundo MGS. Ótimo. Então, o que devo fornecer aqui para importar 5? Bem, o problema é que qualquer módulo tem seu próprio objeto de exportação, o objeto especialista para segundo MGS ficará assim. Então, primeiro exploramos cinco, certo? Que será nosso especialista nomeado porque bem, temos a Bíblia nomeada cinco e exportamos a variável chamada cinco. Então cinco serão cinco, então essa mesma largura,
10, e o mesmo com o meu nome. Essas são todas as nossas exportações nomeadas. Então, no final, temos a captura padrão de exportação, especialistas
padrão. Eles não têm nenhum nome. Isso porque eles são padrão. Você exporta apenas um valor. Você pode ver que eu não criei nenhum nome explícito para uma string nítida, certo? Ele não é atribuído a nenhuma variável, apenas
é exportado por padrão, módulos
atmosféricos realmente anexarão essa exportação padrão ao objeto de exportação
sob a chave padrão, assim como essa. Então, eventualmente, acabamos com um objeto como esse. Isso é o que exportamos do segundo mgs. Agora, se eu quiser importar 5, posso usar o objeto está estruturando. Por quê? Porque bem, exportamos um objeto. Então, novamente, cada módulo tem um objeto especializado
e, como é um objeto, podemos usar a destruição de objetos. É por isso. Aqui ao lado de importar, vou colocar colchetes encaracolados para essa estruturação. E vou importar 5, certo, especifiquei a chave que eu queria importar 5. Além disso, gostaria de pegar talvez meu nome, cinco e meu nome. Vamos console.log cinco e meu nome. E vamos executar o script para verificar isso. E vemos cinco e Andrew. O que está correto. No entanto, e a nossa exportação padrão aqui? Vamos tentar importar o padrão. Na verdade, menos destruição padrão. Se eu fizer isso, terei instantaneamente um erro de sintaxe. O problema é que não podemos simplesmente usar essa palavra-chave padrão reservada. Isso não é permitido para importar a exportação padrão, não
precisamos usar a estruturação. Em vez disso. Só temos que dar nosso próprio nome para o valor exportado. Então, deixe que seja minha vírgula de importação padrão e, em seguida, todas as exportações nomeadas. Portanto, se não precisarmos de todas as exportações nomeadas, só
poderemos importar a exportação padrão, o que será nítido. Então, vou remover essa parte estruturante e manterei apenas minha importação padrão. Agora, deixe-me tentar registrar o console minha importação padrão. Você verá nítido e não importa qual nome eu forneço para minha importação padrão. Não importa porque inicialmente, ele não tem nenhum nome de variável. Ao contrário de nossos especialistas
nomeados, todos eles têm um nome significativo. Nós a exportamos variável chamada cinco. É por isso que quando vamos importar essa variável, podemos renomeá-la, certo? Podemos simplesmente colocar 55 maiúsculas não existem no objeto exportado. Temos cinco, que são minúsculas. É por isso que temos que seguir rigorosamente as mesmas regras da destruição de objetos. Temos que usar os mesmos nomes que exportamos. Outro caso de uso seria quando precisássemos
importar tudo isso como um único objeto. Assim como você vê aqui, não
queremos separar como exportações nomeadas e exportação padrão, assim. Não queremos separá-los assim. Então, em vez disso, queríamos receber o único objeto inteiro. Portanto, neste caso, podemos importar asterix como e, em seguida, o nome do objeto. Então, deixe que seja o segundo módulo. E agora, se eu vou cancelar o segundo módulo de log, você verá que eu tenho, basicamente meu objeto de exportação. Tenho 5, 10, meu nome e padrão. E agora, para acessar o especialista padrão, preciso agora realmente referenciar a chave padrão, certo? Você verá afiado. Se eu precisar acessar 10, terei que usar 10. Então, o que
acabamos de fazer, importamos todo o módulo para aquele único segundo módulo, tigela de
massa, eu diria na prática, isso é menos comum na prática no mundo real. Na maioria das vezes, veremos uma exportação padrão
ou uma exportação nomeada. Eles são muito usados no mundo real. Na verdade, vamos ver assim 510 ou se um módulo tiver apenas exportação padrão, usaríamos somente essa importação padrão. E nós o usaríamos assim. Bem, é aí que basicamente você vai vê-lo. Não é tão difícil entender essa parte. Você só precisa sempre lembrar que existem dois tipos de exportação. Uma exportação padrão e uma exportação nomeada, há apenas uma exportação padrão para um único módulo que você não pode usar para exportar o padrão aqui. Se eu tentar fazer isso,
você verá que terei identificador de erro de
sintaxe padrão já foi declarado. Eu recomendo que você sempre se lembre de que cada módulo tem um objeto que está sendo exportado e todas as exportações nomeadas são mescladas nesse objeto. É mais fácil lembrar que você precisa importar esse objeto. Usar objeto é estruturação. Acho que os módulos ECMO Script são divertidos e eu realmente gosto deles. E espero que o U2 o veja no próximo.
34. ECMAScript ou JavaScript: Ei, isso vai ser curto. Eu só quero esclarecer a diferença entre um script e JavaScript. Você provavelmente viu muitos termos, como ES6 é cinco, ES 2015. Depois desse vídeo, você saberá a diferença. Para procurar a resposta, usarei o Google e vou digitar o script
ECMO ou GS. E o Google me dirá a diferença. Assim, como podemos ver no primeiro pop-up, a especificação de script ECMO é um blueprint para criar uma linguagem de script. E o JavaScript é uma implementação desse blueprint. E você pode ver diferentes variações
dessa declaração em todos esses links. Para resumir rapidamente essa instrução, posso dizer que o script ECMO é um conjunto de
cátions específicos que o JavaScript implementa. Isso significa que o roteiro AGMA é algum tipo de roteiro para um filme em que o filme é JavaScript, tão fácil quanto isso. Para obter mais informações, você pode navegar
até a página da Wikipédia para o script ECMO. Então deixe-me abrir essa página e
daqui podemos ver diferentes versões do acme scrape. A versão mais comum do script
ACML provavelmente é sim, 2015, que se chama ES6
porque era a sexta edição do script ECMO. Se você rolar para baixo, poderá ler o que exatamente foi feito nessa versão específica. E também há um termo chamado ES. Em seguida, como você pode ver, este é um nome dinâmico que se refere a qualquer que a próxima versão inclua no momento da redação. Agora sabemos que quem se refere ao JavaScript como script ECMO é uma pessoa certa. Porque agora sabemos que esses dois são basicamente a mesma coisa. Acho que é isso. Para obter mais informações, consulte a Wikipédia ou um Google. Vejo você no próximo.
35. O que é o React?: Ei, finalmente começamos a falar sobre o react. Esses vídeos futuros curtos
abordarão a teoria e os conceitos do React. Sinta-se à vontade para fazer referência a essas séries qualquer momento no futuro. Let's go React é uma biblioteca para criar interfaces de usuário. Ele pode ser usado para criar sites, aplicativos
móveis e até aplicativos de desktop. A maneira mais fácil de aprender a reagir é provavelmente começar do reagir na Web para criar sites. Neste vídeo, vou
falar do ponto de vista da web, o objetivo do react é criar interfaces de
usuário com algo chamado componentes. Para sites, é apenas reagir ou Reagir para a web. Para aplicativos móveis, é React Native para aplicativos de desktop que é chamado de elétron. React opera somente na camada de exibição. Isso significa que o react não força sobre como você deve criar seu aplicativo. React apenas força sua própria lógica e determina como você deve manipular os elementos HTML subjacentes. O resto é sobre você no passado. Aqui, por volta de 20 e 10, jQuery foi muito usado para manipular HTML por meio de JavaScript. Mas não há necessidade de usar o jQuery hoje em dia. Como o react é apenas para a biblioteca, ele pode ser integrado qualquer aplicativo existente para criar uma interface de usuário. Exemplos de sites do React são Facebook e Netflix. Discord usa o React para tudo para criar seu site, aplicativo
móvel e até mesmo o aplicativo para desktop é criado com o React. Muito impressionante, não é? React não é uma estrutura que é feita por outras partes do aplicativo, deve ser construída com outras ferramentas e bibliotecas. E você verá que, assim que entrarmos na codificação, princípio, o react foi usado para criar aplicativos de página única, apenas, sites que são totalmente gerenciados pelo JavaScript e destinados a preencher aplicativos móveis mais parecidos. Mas, por enquanto, a comunidade React, ela criou muitas ferramentas
e estruturas em torno do react. Portanto, hoje em dia somos capazes de
criar qualquer tipo de site com o React. Mas aí está, renderização no lado do servidor, aplicativo de
página única, páginas da Web estáticas ou talvez um aplicativo híbrido. E você provavelmente viu outras soluções por aí, como Vue, JS, svelte ou talvez até Angler. Todos eles são baseados em componentes e, eventualmente, alcançam o mesmo resultado. É muito difícil dizer qual deles escolher. Algo é mais fácil. Algo é mais difícil. Se você ainda teve dificuldades com a escolha, eu recomendaria escolher aquele com nome ou logotipo
mais atraente, tão simples quanto isso. Mas em nossos projetos, conheceremos o React. Fique atento porque só restam alguns vídeos teóricos antes de entrarmos na parte de codificação até a próxima.
36. Abordagem baseada em componentes: Ei, lá No vídeo anterior, mencionei componentes e abordagem baseada em componentes. Mas qual é o componente? Um componente é apenas um bloco de HTML que não pode ser reduzido no futuro. A abordagem baseada em componentes é quando um aplicativo está sendo construído com componentes, melhor pensar em um componente como uma tag HTML criada pelo usuário personalizada. Mas, além disso, os componentes também podem incluir lógica e estado. Por exemplo, um componente pode ser um botão que muda de cor. Uma vez clicado, o botão muda a cor de fundo. Podemos nomear esse componente como botão de cor. E mais tarde, em qualquer parte do código HTML, Use o botão Cor quantas vezes quisermos. Isso é basicamente o que fazemos com tags HTML. Os componentes não são diferentes. Faz sentido pensar neles
como blocos de construção para o aplicativo. A abordagem baseada em componentes forma uma árvore de componentes. No topo dessa árvore, há um componente raiz que aninha outros componentes no componente raiz do React é quase sempre chamado de aplicativo, ou outros componentes são aninhados no componente do aplicativo. Os componentes que estão no topo são chamados de componentes de nível superior. Geralmente, são páginas. Componentes que aparecem mais altos na árvore são chamados de pais. Uma vez que isso está abaixo são chamados de crianças. Vamos dar uma olhada na página oficial do Facebook. Facebook é o criador do React, e é por isso que é o melhor exemplo possível a ser observado. Vou tentar dividir o espaço em componentes para lhe dar uma ideia básica, vamos. O site inteiro em si é o componente App. Na parte superior, teríamos componente
Navbar e o Navbar no centro, há um componente de navegação e cada botão dentro é outro componente também. À direita, ele pode ser um componente de navegação perfilado, onde cada botão semelhante é o mesmo componente, mas reutilizado várias vezes. Experimente você mesmo e divida a lista suspensa abaixo em componentes abaixo da barra agora, pode ser um componente de página inicial. página inicial inclui três componentes. Barra lateral à esquerda, barra lateral à direita e alimentação no componente da barra lateral central inclui o menu. O componente Feed inclui a lista de postagens e a barra lateral à direita inclui outra coisa. Cabe aos desenvolvedores como estruturar e criar componentes. Certamente é possível
manter toda a marcação e toda a lógica em um único componente sem criar outros componentes. Mas então a ideia de abordagem baseada em componentes seria totalmente comprometida. E será o mesmo que não usar componentes. No final do dia, acabamos com uma árvore de componentes. E essa árvore sempre tem uma direção de cima para baixo. Se houver algumas alterações em um componente pai, todos os filhos desse componente também
serão afetados simplesmente porque fazem parte dele. Vamos concluir. O desenvolvimento com o React é baseado em uma abordagem baseada em componentes. aplicativo React pode ser visualizado como uma árvore de componentes. Os componentes são peças reutilizáveis do aplicativo. As vantagens dos componentes são reutilização e a consistência em toda a aplicação. Se o componente de postagem do usuário de usabilidade pode ser inserido em qualquer lugar do aplicativo era apenas uma única linha de código. Com consistência, o componente de postagem do usuário sempre se comportará exatamente da mesma forma, independentemente
da página ou do local onde ele é usado. Bem, é isso. É assim que todos os aplicativos modernos são criados hoje em dia com componentes. Espero que faça sentido. Cia.
37. Funções vs, aulas: Olá, In React. Existem dois tipos de componentes disponíveis para nós, resíduos
de classe e função. Eles diferem em sintaxe e na forma como
manipulamos dados dentro deles. Antes do React Hooks, não tínhamos outra opção senão criar competência usando classes no presente, a situação é um pouco diferente. Com o React Hooks, usamos funções para criar componentes. ganchos React estão disponíveis apenas em componentes baseados em funções, e essa é a razão pela qual as funções simplificam os componentes. A sintaxe é mais leve e mais fácil de compreender. Em nossos projetos, usaremos o React Hooks, o que significa que vamos trabalhar com componentes baseados em funções. Somente. Componentes baseados em classe se tornam cada vez mais usados raramente. No entanto, é possível que às vezes lá
fora você veja componentes baseados em classe, mas isso é totalmente bom. A equipe do React tem suas apostas no React Hooks e eles
acreditam que os ganchos são o futuro. Depois de terminar o último projeto, você poderá ler componentes
baseados em classe e não terá problemas na transição entre funções e classes. Espero que faça sentido. Vejo você no próximo.
38. Reagir sob a capa: Olá novamente. Vamos ver como o React funciona sob o capô. No exemplo de um aplicativo de página única, a melhor maneira de pensar em um aplicativo React como se fosse uma árvore de componentes no React, há uma coisa chamada ponto de montagem
em que o aplicativo React está sendo inserido, ou melhor dizer, montado por padrão, é uma tag div com ID rude. Na parte superior da árvore, há o componente do aplicativo, que é o invólucro para todos os componentes do aplicativo. Dentro do componente do aplicativo, existem componentes de nível superior. Dentro deles, coloque componentes aninhados e assim por diante até o componente muito aninhado. Se pensássemos nisso por um momento, é praticamente o mesmo a estrutura HTML DOM, não é? O Document Object Model ou DOM é a representação da página HTML na forma de uma árvore de tags. Dom é como os navegadores veem e interpretam a marcação HTML. Quando fazemos coisas básicas em JavaScript como Document.getElementByID id id. Esse objeto de documento faz parte
da API DOM que é exposta pelo navegador. React cria na memória representação da árvore de componentes chamada DOM virtual. É o mesmo que o DOM do navegador, mas é usado apenas internamente pelo react. Quando o aplicativo React que está sendo renderizado
na árvore de componentes de página está sendo traduzido da apresentação dominante
virtual para marcação HTML. Essa marcação HTML está sendo inserida no elemento de montagem na página da Web. Lembre-se de que tudo isso é feito por meio de JavaScript. Quando os dados são componentes precisam ser atualizados, react sempre opera com o DOM virtual em primeiro lugar. Ele toma o estado capturado anteriormente do DOM virtual, o
compara ao recém-criado com atualizações e calcula a diferença. Se houver alguma diferença, react calcula quais dados e componentes devem ser atualizados. E essas alterações são chamadas de renderizações 3D. Cada renderização basicamente representa estado DOM
virtual em um momento, o processo de cálculo da diferença entre renderizações é chamado de reconciliação. E o nome do algoritmo desse processo é React Fiber. Em termos simples, o React Fiber detecta o que deve ser atualizado entre as renderizações. Você pode ter uma pergunta, por que usar o DOM virtual? Não está adicionando um passo extra e mais complexidade? Bem, isso depende. DOM virtual muda ou mais leve porque estão todos na memória, ao contrário das alterações em um DOM real, quando a marcação HTML é alterada, navegadores geralmente recalculam o layout e repintam a página da Web. É melhor ter 100 atualizações no DOM virtual, que eventualmente resultará em uma única atualização real do dom e
repintura de patch maior do que aplicar todas as 100 atualizações diretamente no DOM real. Quando navegamos por um site sob o capô, o HTML é constantemente atualizado. React garante que essas atualizações sejam feitas da maneira mais eficiente possível. A ideia por trás da cúpula virtual é
reduzir o número de atualizações reais do DOM. Sei que pode ser difícil perceber essa quantidade de informações, mas está totalmente bem. Você não precisa saber todos os detalhes. Agora, sabemos como o React funciona internamente. Essa é aquela em que uma peça faltante sobre sua arquitetura, essas ervilhas é um fluxo de dados unidirecional, que é chamado de fluxo. Flux é o nome de uma arquitetura interna reage. Flux implica que os dados no aplicativo sempre fluem em uma direção de cima para baixo. Por exemplo, quando os dados dentro de um componente são atualizados, o componente e todos os seus filhos também são renderizados. Caso as crianças sejam atualizadas ou não, é o trabalho para o React Fiber mencionado anteriormente, o algoritmo que calcula exatamente o que precisa ser atualizado. Mas o fato é que as atualizações se movem de componentes pais para filhos. É impossível ter o fluxo de
dados indo de baixo para cima. Acho que você será capaz de sentir isso quando escrevermos código React. Tudo bem, vamos resumir sob o capô, o react usa sua própria representação HTML DOM chamada DOM virtual. O objetivo do DOM virtual é reduzir o número de atualizações reais do DOM. O algoritmo principal do React é chamado React Fiber e sua principal tarefa é calcular o que exatamente deve ser atualizado entre os re-renderizadores react arquitetura design é chamado de fluxo, o
que implica os fluxos de dados apenas em uma direção de componentes pais para filhos. Bem, esta é toda a informação sobre o React. Não se preocupe se isso foi confuso. Basta assistir novamente o vídeo ou
procurar mais informações, se necessário. Vejo você em seguida.
39. Placas e Bundlers: Ei, desta vez eu gostaria de falar sobre como podemos começar o desenvolvimento de um novo React Web App. Neste vídeo, não
considerarei plataformas online diferentes, como o CodePen, para desenvolver diretamente dentro do navegador. Porque essas plataformas são usadas apenas como playgrounds, ou geralmente apenas para
compartilhar rapidamente o código com a configuração básica. Para entender como os aplicativos JavaScript modernos estão sendo construídos, devemos entender o que nosso projeto Butler é um projeto Bundler é uma ferramenta que leva todo o código-fonte, scripts, estilos, imagens, processos, tudo isso, e crie um projeto construído. O projeto construído é uma versão minificada
do código-fonte otimizada para máxima eficiência. São toneladas de som do projeto Bundler são os mais comuns são Webpack, roll up e parcel. Todos os projetos JavaScript modernos são cobertos por essas ferramentas. Ótimo, vamos voltar à nossa pergunta principal, maneiras de começar a desenvolver um novo aplicativo React. Eventualmente se resume a três passagens. A primeira maneira de criar um aplicativo React é configurar e
configurar todas as ferramentas de compilação, como o pacote da web para React do zero. A segunda maneira é usar um modelo de projeto. Criamos ferramentas já configuradas para o desenvolvimento do React. E a terceira maneira é usar uma estrutura do React, como o próximo GS ou o Gatsby. Não há resposta correta sobre qual escolher. Tudo depende da configuração que você está procurando, preferências
pessoais, recursos especiais e assim por diante. Configurar tudo manualmente e configurar o Butler do projeto,
como o Webpack do zero, raramente
é visto hoje em dia. Quase toda vez que você
usaria um modelo ou uma estrutura. modelos, a propósito, são muitas vezes chamados de caldeiras, o que significa que sempre que você vê onde a placa de caldeiraria não surta, é apenas outra maneira de dizer o modelo de palavra. Existem muitas placas de caldeiras do projeto React
criadas pela comunidade diferentes , que são copiar um modelo e começar a desenvolver nada mais necessário. O boilerplate React mais conhecido provavelmente
é o aplicativo Create React, que é mantido pela equipe do React sob o capô, ele usa configuração de web back predefinida. Você pode se sentir tentado a usar somente o aplicativo Create React. Mas é importante lembrar que o aplicativo Create React
não é a única maneira de desenvolver aplicativos React no presente, existem muitas ótimas alternativas. Atualmente, ferramentas construídas bastante populares para front-end são VDD e snowpack. Outra maneira de lidar com o React é usar uma estrutura do React. Frameworks são super populares agora, especialmente em seguida, sim, mas eu diria que é melhor
começar a aprender reagir sem uma estrutura. Como estruturas para recursos e funções
específicas da estrutura CHES em nossos projetos, usaremos modelos já configurados e colinas construídas. Quais? Sente-se assim que entrar nos projetos, veja outro
40. 1 visão geral do projeto TicTacToe: Olá, pessoal. Bem-vindo
à seção Tic Tac Toe. Este será um rápido vídeo de introdução onde você poderá
visualizar o projeto. O projeto
será o jogo Tic Tac Toe, que você pode ver na
tela agora mesmo. Podemos clicar nos quadrados. Nós podemos jogar o jogo. Sempre que tivermos um vencedor, a combinação vencedora
será destacada. Teremos efeitos
ativos diferentes. Além disso, na parte inferior, estará a história do jogo ,
que podemos percorrer
e ver quais movimentos foram Se
clicarmos nos quadrados, poderemos
sobrescrever o histórico
caso precisemos do botão de
início do jogo, e eu diria que
é basicamente isso. Embora possa parecer simples. Ele tem muitos
conceitos básicos que
criarão uma boa base
para seu conhecimento de reação. Então, vamos começar.
41. 2 Criando e configurando novo projeto com o Vite: Olá. Finalmente
vamos começar a construir o primeiro projeto que
será o Tic Tac Toe. A ferramenta que
vamos usar para construir o Tic Tac Toe será o Vite. Este é o site oficial da Vite
que você pode ver agora. Você pode encontrá-lo no Google. Vou
clicar em “Começar” e vamos ver o que
exatamente o Vite faz. Basicamente, o Vite é uma ferramenta de front-end que
constrói o projeto. Pode ser qualquer coisa. Pode ser react, pode ser JavaScript bruto ou pode ser qualquer outra estrutura
compatível. Sob o capô, o
Vite usa o Rollup. Rollup é um empacotador de módulos. Rollup é basicamente
a ferramenta que constrói o projeto e o Vite é a
configuração em torno do Rollup. Vite é muito rápido e, na verdade, muito
popular no momento. Vamos examinar
a documentação e começar
a organizar
seu projeto da primeira semana. Isso exige que tenhamos a versão 14 e superior do
Node, mas tenho certeza de que você tem versão estável
mais recente
, que é 18 no momento. Podemos ver que podemos
criar um novo projeto com npm simplesmente
executando esse comando. Vou copiar esse comando
e vou para o CMD. Em todos os projetos,
vou usar o Git Bash
e, dentro do VS Code,
vou usar o Git Bash. No entanto, para este,
vou usar o CMD. Você pode usar qualquer outra concha. Eu escolho o CMD especificamente porque o Vite nos fará algumas perguntas e, quando Git Bash é executado como uma instância
separada, ele tem problemas de
interatividade, ao contrário do CMD. Depois de
executar esse comando, o Vite me fará algumas perguntas e, em
seguida,
criarei uma nova pasta do projeto. No entanto, vou
criar uma nova pasta de projeto dentro de nossa navegação atual
do terminal. No momento, dentro do CMD, eu navego para
ver meu nome de usuário. Esta é a pasta do usuário
e, uma vez que eu
execute o comando Vite, ele criará a pasta do
projeto aqui dentro desse diretório. Eu não quero fazer isso. Quero definir o caminho da pasta
do meu próprio projeto. Para isso, primeiro
preciso decidir onde gostaria de
colocar meu projeto. Para mim, vai
estar aqui dentro do D_web. Este é o lugar onde eu
gostaria de colocar meu projeto. Primeiro, preciso navegar dentro do terminal
até essa pasta. Dentro do CMD, vou
digitar o nome do disco para mudar a navegação para o disco D.
Se você estiver dentro do Git Bash, então você tem que
digitar cd d e dois pontos, se você estiver dentro de
qualquer outro shell, então eu tenho certeza que
gosto do shell Linux ,
como o Bash, ou talvez no Mac, tenho certeza de que você
nem precisa disso. De qualquer forma, estou dentro do disco D, depois vou digitar
cd, cd significa mudar diretório e vou
digitar cd_web. Eu sei que é _web
porque se eu digitar ls,
ls é um comando shell do Unix para listar todas as pastas dentro da navegação
atual. No entanto, como o CMD é um terminal
baseado em Windows, eu preciso usar dir, então dir é a
alternativa de comando a menos dentro do Windows
Power Terminal. Dentro de D, eu tenho _web. É exatamente por isso que eu navego, então vou digitar cd_web e boom, agora estou dentro dessa pasta e estou seguro
para executar o comando Vite. Vou executar
o comando copiado. Ele me pediu um nome de projeto, vamos
chamá-lo de tictactoe-vite. Eu pressiono “Enter”. Agora eu
preciso selecionar uma estrutura. Vamos escolher react e a variante será
JavaScript. Ótimo. Agora, o comando
foi bem-sucedido. Diz que o projeto de andaime em _web tictactoe-vite, concluído. Agora execute cd, npm install, npm run dev. Vamos fazer
isso no departamento. Vamos sair disso. Agora, o que vou fazer abrir o arquivo VS Code,
abrir a pasta e agora
vou até D web e selecionar tictactoe-vite como a
pasta do projeto dentro do VS Code. Quando entramos,
temos alguns arquivos aqui. A primeira coisa
que vamos fazer é
instalar dependências. Nós temos os arquivos criados. Já temos o pacote json com algumas dependências
listadas, mas não temos nenhuma
delas instalada. Para isso, vou abrir o terminal
integrado
dentro do VS Code, e aqui o que
vou fazer, vou instalar dependências
executando npm install. O Npm instalado sem
nenhum argumento, ele verifica o pacote json dentro da navegação
atual. Minha navegação atual é a pasta
tictactoe-vite. Ele procura o pacote json. Ele procura dependências
e dependências de desenvolvimento
listadas nela
e, se estiverem ausentes, se estiverem desinstaladas, npm as instalará. Vou escrever esse comando e vou esperar. Enquanto isso funciona, vamos ver que tipo de
dependências temos aqui. Por padrão, temos as
dependências react e react-dom instaladas. Esses são
pacotes principais do react, então react é o
pacote principal e react-dom é o pacote principal especificamente
para a web porque, bem, web usa o modelo dom. Dentro das dependências de desenvolvimento,
temos os tipos react, na verdade não precisamos
deles nos tipos react-dom. Isso é algo
para TypeScript. Não sei por que eles vêm. Então, temos o vitejs plugin-react e o
próprio Vite como ferramenta. Também vemos viteconfig.js aqui. Como o Vite pode ser usado para
construir qualquer projeto de front-end, ele deve ser detectado. Em primeiro lugar, o Vite vem com configuração
quase zero. Precisamos especificar,
precisamos configurar com, ok,
pegue meus arquivos de reação e, por favor, faça a mágica, e o Vite fará. Para isso, precisamos
instalar o plugin,
bem, que
já está instalado
e, dentro do
viteconfig, temos que
listar esse plugin do Vite aqui. Você vê que tudo
já está configurado para nós. Nós realmente não precisamos
fazer nada. Se você quiser ler mais
sobre a configuração do Vite, siga esse link aqui. É bem simples. partir de agora, se eu abrir
meu terminal novamente você poderá ver pacotes adicionados,
tudo está ótimo. Mais duas coisas aparecem aqui, módulos
package-lockjson
e node. Portanto, package-lockjson
representa a versão que acabamos de instalar. Ele captura a versão específica do pacote
que instalamos. Então, temos módulos de nós. Os módulos do Node são o
local onde
todas as nossas dependências
foram instaladas. Como temos essa pasta, agora podemos executar facilmente nossos
scripts e eles funcionarão. Antes de fazermos isso, vamos configurar
mais algumas coisas aqui. Vamos adicionar eslint
e prettier ao nosso projeto. Para fazer isso, precisamos
instalá-los primeiro. Vou executar o npm
install dash dash save-dev. Save-dev instruirá o
npm install a instalar os pacotes como dependências do
desenvolvedor, então npm install
eslint e prettier. Em seguida, precisamos criar arquivos
de configuração para esses dois. Você pode ver que, quando
o comando termina, eu faço com que prettier e eslint apareçam como
dependências do desenvolvedor no pacote json. Vou criar um novo arquivo.prettierrc
e o outro será.eslintrc. Agora, como vamos
configurar esses dois? Temos algo chamado Gist. Este link será
compartilhado com você. Dentro desse Gist, você pode encontrar
arquivos.eslintrc e.prettierrc. Essas são as configurações
que vamos usar. Vamos copiá-lo
daqui e colá-lo desse
jeito. Você pode escolher qualquer configuração
mais bonita que desejar. Essa é apenas minha
preferência pessoal que
escolhi especificamente
para este projeto. Você pode alterar qualquer
valor de acordo com suas necessidades. Então eslint config, eu também copiei de lá. No entanto, é mais
interessante do que mais bonito. Aqui fazemos algumas coisas. Estendemos o eslint recomendado, que é a configuração
incorporada ao eslint. Não precisamos instalá-lo. Em seguida, estendemos o tempo de execução do plug-in, react, recommended e plug-in react JSX, além de mais bonito. Na verdade, eles
vêm dos pacotes, então esses pacotes devem
ser instalados. Se voltarmos a esse Gist aqui, podemos encontrar
dependências de desenvolvedor, MD, eslint-config-prettier
e eslint-plugin-react. Se formos até aqui, precisamos instalá-los primeiro. Esses são os plug-ins
que estendemos e eles não aparecem
do nada. Eles precisam ser instalados. Vou apenas copiar o comando de
instalação do eslint-plugin-react
e instalá-lo. Exatamente o mesmo que
farei com eslint-config-prettier. O que esses dois estão fazendo? O eslint-config-prettier
garantirá que nossa configuração eslint e configuração
mais bonita
não colidam uma com a outra. Este pacote apenas garante
que não tenhamos nenhum mal-entendido
entre essas duas ferramentas. O ESlint-plugin-react é um pacote
bastante popular. Bem, basicamente uma lista de regras para projetos de linting
react. A configuração que
temos aqui abaixo, eu basicamente
a retirei da documentação da
página eslint-plugin-react. Você pode encontrá-lo aqui. Expandimos duas coisas
desse plug-in conjunto
recomendado de regras e
o tempo de execução do JSX. Tempo de execução do JSX, vamos
voltar a isso, o que é exatamente isso. Regras do Insights, eu desativei a regra dos tipos
react prop, que vem do pacote
plugin-react. A razão para esses tipos de adereços é algo que
não vamos abordar. No entanto, ele está incluído aqui, então nós realmente não precisamos dele. Isso só vai atrapalhar nosso processo de
desenvolvimento, então simplesmente desativamos essa regra
completamente e a desligamos. O resto é
como eu te disse, foi tirado daqui. Ótimo. Finalmente, talvez
tentemos executar o projeto. Dentro dos scripts,
temos três scripts
definidos por padrão:
dev, build e preview. O Dev executará
o servidor de desenvolvimento local, construirá o
projeto e fará uma prévia. Tenho
certeza de que ele pré-visualizará a versão final
de produção para nós. Ele servirá os arquivos
de compilação de produção. Vamos executar o script de
desenvolvimento, npm run dev. Depois de um segundo, você
verá essa mensagem. Agora, podemos realmente
acessar esse URL que nos permite
abri-lo dentro do navegador. Se eu for até aqui, você verá isso. Bem, este é o nosso
aplicativo React no momento. O que ele fez nesse caso foi criar um servidor local para nós
e nos expôs o link que podemos usar para acessar
o servidor de desenvolvimento. Este é o lugar
onde podemos ver o projeto localmente
e desenvolvê-lo. Vamos parar o
comando pressionando Control C várias vezes. Vamos testar e ver
a compilação do outro comando. Se eu for usar o npm run build, você verá
algumas coisas aqui. Vite cria a pasta dist
e, dentro da pasta dist, cria SVG, HTML
e, dentro dos ativos,
cria arquivos JS e CSS. O que esse comando faz é pegar todos os arquivos dentro da pasta de
origem e os criar em HTML, CSS, JavaScript e arquivos
secundários. Esse comando de compilação produz versão
final
de produção do nosso aplicativo. Posteriormente, podemos pegar a pasta dist e
implantá-la na hospedagem. Isso é
exatamente o que
faremos mais tarde neste projeto. Nós realmente não precisamos
inspecionar nada dentro da poeira. É otimizado, é minimizado e você pode ver que parece feio. Isso é totalmente
bom porque deveria ser
otimizado dessa maneira. Novamente, sob o capô, o
vite usa enrolamento. O roll-up é a
ferramenta que faz toda essa minificação, transpilação e o resto. Agora, vamos dar uma olhada, o que temos aqui
entre outros arquivos? A pasta de origem é a
pasta em que criaremos nossos arquivos de origem. Todos os componentes do React, todo
o código vai para o código-fonte. O resto da
configuração, eslint,
mais bonita, que não
faz parte do código-fonte, mas faz parte da configuração do
projeto, está localizada
na pasta raiz aqui
ao lado do pacote Jason. Além disso, temos HTML de índice aqui. Indexe HTML aqui, esse
será nosso ponto de entrada. É aqui que nosso
projeto começa. Voltaremos a isso mais tarde. O que vamos fazer agora é não
tocar em nada. Vamos abordar
isso no próximo vídeo. Por enquanto, vamos dar uma
visão geral do resto. Temos a pasta pública e
temos a pasta de origem. A pasta pública
é o local para os ativos
estáticos do nosso projeto. Eles são sempre servidos sob o caminho raiz
do nosso aplicativo. O que quero dizer é que vamos
executar o comando dev novamente. Se vamos acessar, vamos ver o que
temos em público. Temos vite SVG, então se
vamos acessar a barra, que é root vite SVG, vemos que o arquivo está sendo
servido aqui em vite SVG, então o caminho que você
tem para o arquivo dentro pasta
pública é
mapeado para o segmento de URL. Se eu vou criar uma
pasta, vamos chamá-la. Não sei, lol e podemos
mover o vite para dentro do lol, então vite SVG será
servido em lolvite.svg. Esse é o local para
arquivos que não deveriam ser transpirados, minimizados ou afetados pela ferramenta de construção. Eles permanecerão como
estão aqui em público, e podemos referenciá-los
em nosso aplicativo. A pasta pública
é bastante comum todos os projetos de front-end. Ótimo. Agora que sabemos o que
são todos esses arquivos, só
há uma coisa
que queremos fazer antes iniciar o desenvolvimento e
investigar esses arquivos. Queremos apresentar o
Git ao nosso projeto. O que precisamos fazer, primeiro
precisamos
inicializar, o Git aqui. Dentro do terminal,
vamos
digitar git init e aqui você pode ver que o Git agora está
presente, então o que
podemos fazer é adicionar tudo isso ao palco e depois
confirmar tudo. Apenas uma nota aqui. Há um novo arquivo
aqui chamado Gitignore. Gitignore é o arquivo
reconhecido pelo sistema Git e tudo o que está listado dentro do Gitignore será
ignorado pelo Git. Dentro dessa pasta,
temos muitos arquivos
secundários com os quais realmente
não nos importamos. No entanto, também temos aqui módulos
node e dist. Esses dois serão ignorados pelo Git e, se você
ver dentro do código do VS, eles nem serão destacados.
O que isso significa? Isso significa que, quando
enviarmos arquivos, todos os arquivos afetados serão adicionados como
parte do projeto Git, mas os arquivos listados
aqui não
serão reconhecidos pelo Git. Eles serão simplesmente ignorados e esses módulos de nós serão
ignorados porque, bem, nós realmente não precisamos deles. Esses são arquivos
gerados dinamicamente. Se quisermos, digamos, compartilhar nosso projeto
com outra pessoa, a pessoa
que baixar
todos os arquivos do projeto não
terá esses módulos e
nós porque
pesam muito
e ela realmente não precisa deles todos os arquivos do projeto não
terá esses módulos e nós porque
pesam muito porque podem ser
criados dinamicamente. Vou apenas
digitar npm install, os módulos
do Node serão recriados. Vou digitar npm run build e a pasta dist
será recriada. Na verdade, não precisamos muito do peso
deles, e eles podem ser
criados dinamicamente. É por isso que eles estão
listados no Gitignore. Vamos
adicionar tudo ao estado de estágio com
o git add dot, para que possamos ver
vários avisos aqui. Às vezes, está totalmente bem. O Git garante que nosso projeto
seja multiplataforma entre diferentes sistemas que têm codificações
diferentes, então
não precisamos nos preocupar com isso. Depois disso, confirmamos
todos esses arquivos estádios
com a primeira mensagem de confirmação
e, se digitarmos git log, vemos que temos o
primeiro commit aqui. Incrível. Agora, precisamos fazer o upload desse
projeto Git para o GitHub. O que vamos fazer é ir
aqui para o GitHub. Vamos clicar em
Novo repositório aqui. Nome do repositório, vamos ficar com o jogo TicTactoe-Game. Vou escolher esse
repositório para ser público. Vou torná-lo público
mais tarde, quando terminarmos isso, não
precisamos de nenhum
arquivo ReadMe inicializado com o novo repositório porque vamos
criá-lo nós mesmos mais tarde, ou talvez possamos fazer isso
agora, então vou criar um novo arquivo chamado README.md
e, por dentro, vou usar
a sintaxe Markdown. Essa é a sintaxe dos documentos, então vou
adicionar hashtags aqui. Não pense muito nisso. Vamos chamá-lo de jogo Tic Tac Toe. Eu o salvo e, como
é um arquivo novo, precisamos novamente
adicionar outro commit. Adicionado, README.md. Perfeito. Agora
temos dois commits. Ótimo. Não precisamos do ReadMe, não
precisamos do Gitignore
porque já
temos o Gitignore
adicionado automaticamente até o momento. Não precisamos de nenhuma licença. Eu clico em Criar repositório. Ótimo. Aqui dentro da configuração agora eu posso configurar e
posso realmente associar meu
repositório recém-criado no GitHub ao meu repositório local
no meu computador. Podemos seguir as instruções aqui. Se estivermos criando um repositório
completamente novo, se não tivermos nenhum arquivo, mas esse não é o caso. Precisamos escolher empurrar uma linha comum de
frente de um repositório existente. Vou apenas copiar
linha por linha aqui. Git remoto na origem. Depois de fazer isso, depois disso, posso digitar git remote-v e vou ver
que, na origem do alias, tenho esse repositório e, se eu copiar esse link e abrir em uma nova guia, ele me levará até aqui, que significa que o
link está correto. Em seguida, sugere que
digitemos git Branch-m main. Eu não acho que
vamos fazer isso. O problema com o GitHub e Git Community é que
eles não conseguem decidir qual é o melhor nome para
a ramificação principal padrão. Bem,
geralmente ela é chamada de master. Atualmente, estamos
na filial principal, mas as pessoas querem
simplificar as coisas. Em vez de dominar, algumas
pessoas querem ver o principal. Vamos
ficar com o Mestre. Afinal, isso não é
grande coisa. O que vamos
fazer é que agora
associamos o projeto ao repositório remoto, que fará o upload
para o GitHub digitando git push origin master. Origin é o alias
que aponta para o repositório e
master é o nome da ramificação de destino
no repositório para onde
vamos enviar nosso código atual. Eu faço esse comando. Você pode ver que algo aconteceu e se eu for
atualizar a página aqui,
vou ver todos os projetos aqui
e o arquivo ReadMe
que criamos. Algo parecido. Parabéns a todos. Criamos e configuramos
os projetos Tic Tac Toe. Nos vemos no próximo vídeo. Finalmente, começaremos a
criar o aplicativo e poderemos ver quais são
os componentes. Tchau tchau.
42. 3 extensões Eslint e Prettier: Olá, aqui está apenas um lembrete rápido
sobre ESLint e Prettier. Como queremos ter certeza de
que essas ferramentas estão
integradas ao nosso VS Code e vemos
tudo em tempo real, vemos os destaques e formamos um arquivo
ao salvá-los, precisamos garantir que as
extensões estejam instaladas. Vá até a parada de extensão aqui e certifique-se de ter a extensão do
formatador de código
Prettier instalada aqui, bem
como a extensão ESLint. extensão ESLint
garantirá que você destaque
quaisquer problemas de ESLint, portanto, avisos ou erros
que tenhamos no código, a extensão
cuidará disso. extensão Prettier
garantirá que os arquivos sejam formatados de acordo com o
conflito quando estiverem seguros. No entanto, para a
configuração do Prettier, precisamos
de um pouco mais de configuração, para isso, você precisa acessar
as configurações JSON no VS Code. Abra as configurações do usuário JSON
e, aqui dentro,
queremos ter certeza que temos o
formato do editor em save true, bem
como o formatador
padrão do editor e
o JavaScript, formatador padrão do editor. Tudo isso está descrito
na página Extensões. Basta abrir essa página diretamente no código VS, basta percorrer,
copiá-la, bem como
copiar o formato do editor salvá-la e colocá-la dentro suas configurações JSON,
assim mesmo. Depois disso, quando você
salvar os arquivos, eles serão autoformativos. Para a extensão ESLint,
não precisamos de nenhuma configuração, ela simplesmente funcionará. Te vejo.
43. 04 O que são componentes e adereços do Reagir: Olá a todos, vamos finalmente
descobrir o que temos
dentro da pasta de origem. Vamos primeiro ver como o Vite resolve tudo
para a pasta de origem. Se eu vou executar o npm run dev
, o Vite serve o
servidor de desenvolvimento e nós temos isso. Tudo isso é criado e
definido dentro da fonte. Mas como a Vite realmente
resolve isso? Se olharmos dentro do package.json e examinarmos
o script dev, o script dev, o que
ele realmente faz, ele apenas chama o comando Vite. No entanto, um argumento opcional para o comando
Vite é o
caminho para index.html, que serve como entrada
para que o Vite entenda que, ei, esse é o nosso ponto de entrada. O Index.html que temos aqui é a entrada
e, por padrão, quando o Vite é chamado
sem nenhum argumento, ele procura index.html
dentro da pasta atual, o que está correto em nosso caso. Dentro do index.html,
temos uma marcação simples, então o Vite resulta nesse
index.html assim que o comando é iniciado, e ele vê que, ok, dentro do index.html, temos um script que
aponta para a fonte main.jsx. Source main.jsx é o
ponto de entrada para o aplicativo React, enquanto index.html é o ponto
para o próprio aplicativo. Bem, em um aplicativo, você pode realmente ter
vários aplicativos React, mas isso raramente é visto. Temos um script que
aponta para main.jsx. Temos um desenvolvedor com o ID definido como root, e temos ataques de
meta bastante padrão aqui. Na verdade, podemos mudá-lo
e chamá-lo de Tic Tac Toe. Depois de salvá-lo, você pode ver
no terminal que ele foi
alterado para página para carregamento. Se eu voltar, ele será
carregado automaticamente para mim. Eu não pressionei nada
e o título foi alterado. Muito incrível, não é? Se olharmos para dentro,
fonte main.jsx. Aqui,
finalmente conhecemos o React. Temos algumas coisas
importadas do React
e do react-dom/client. Essa importação do React do React, antes do React 17, era necessária em todos os arquivos em que
você escreve o código React. No entanto, a partir do React
18, isso é desnecessário. Você pode omitir a importação no React. Mas no nosso caso, como usamos o namespace React
para usar o modo estrito, ainda
precisamos
importá-lo apenas aqui, mas em todos os outros arquivos, não
precisamos digitar
import React from React. Isso foi necessário novamente
somente antes do React 17. Dentro do eslintrc, temos plugin jsx-runtime para configurar o eslint para entender que
estamos usando o React 18.
Por favor, não nos diga que
precisamos importar o React do React. Eslint sabe disso. Importamos o ReactDOM e, no objeto
ReactDOM,
chamamos createRoot. Para o método createRoot, passamos elemento de obtenção do
documento por ID root. Pegamos o elemento do index.html, que é apenas um elemento vazio, e esse elemento vazio é
chamado de ponto de montagem. Esse é apenas o elemento vazio. Pode ser qualquer elemento HTML válido que deve estar presente
dentro do HTML. Ele servirá como recipiente
para o aplicativo React. Para a árvore de componentes. Criamos raiz a partir
desse elemento HTML. Nós o obtemos novamente em index.html, os IDs devem corresponder se
eu for digitar algo diferente
que não corresponda à raiz, defina um index.html. Nada será
criado na página. Bem, isso é óbvio. Ótimo. Nós o colocamos de volta à raiz
e garantimos que tudo funciona. Uma vez que temos o objeto raiz, no objeto raiz,
chamamos o método render. Para o método render, precisamos passar
a árvore de componentes que queremos que esteja
presente na página. Bem, para o método de renderização, basicamente
passamos nosso aplicativo
React, nossos componentes React. O componente App quase sempre representa os principais
componentes dentro do aplicativo React. Quase sempre, tenho
certeza, é chamado apenas de App. React StrictMode,
é algo que foi
introduzido recentemente no React. Ele também vem como um
componente, mas o que
ele faz é apenas algumas coisas que nos alertarão sobre
possíveis problemas ou erros que possamos
ter no aplicativo React. Nós apenas mantemos isso assim. Não mudamos nada aqui. O que você vê aqui é nossa árvore de
componentes, sem mais nem menos. Todos os componentes sempre começam
com uma letra maiúscula. Você não verá um
único componente que comece com uma letra minúscula. Isso é impossível. A primeira regra de ouro é que os componentes estão
sempre em maiúsculas. Sempre, não importa o que aconteça. Temos o
modo React StrictMode e o componente App, e essa é nossa árvore de componentes. Agora, vamos finalmente dar uma
olhada no componente App. Dentro do componente App
, meu Deus, já
temos alguma coisa. Se passarmos o mouse, podemos ver qualquer erro de eslint proveniente da regra em branco de
destino react/jsx-no. Bem, tudo bem não
vamos fazer
nada sobre isso, vamos apenas remover
essa marcação de qualquer maneira , então não nos
importamos. Isso é bom. Esse eslint nos diz
que não é seguro
manter as tags Anchor sem atributos
específicos. Perfeito. Então, simplesmente
não o tocamos. Isso é um componente. função do aplicativo que você vê aqui
é um componente chamado App, então é um componente do aplicativo e já temos algumas coisas criadas aqui, mas
vamos removê-las,
não precisamos delas. Vou remover isso,
vou remover algo
que você disse e sobre o qual não sabemos nada, logotipo do
React, App.css. Talvez possamos manter o App.css. Podemos então remover o resto. Em vez disso, podemos simplesmente digitar olá remover o nome da classe. Temos um único div, olá e fechamos div, nós o salvamos. Em seguida, vamos
remover a pasta de ativos. Não precisamos disso.
Vamos remover o index.css. Não precisamos dele
dentro do main.jsx. Vamos remover a referência
ao index.css, pois acabamos de
remover esse arquivo. Temos apenas main.jsx, que importa o componente App, e dentro do componente App
temos o App.css. Ótimo. Um componente é apenas uma função que
retorna a marcação JSX. O que você vê aqui é HTML,
mas, na realidade,
nos bastidores, ele é traduzido para JavaScript. Tudo o que você escreve
aqui é JavaScript. Essa marcação HTML
aqui é chamada de JSX. Se eu não estiver errado e se
me lembro corretamente, é a combinação de
JavaScript e XML, não
tenho certeza
disso, mas de qualquer forma, essa marcação é chamada de JSX. Se você puder ver, também
temos a extensão.jsx. Poderíamos ter usado a extensão just.js em vez de
jsx, mas o fato é
que, como o Vite é uma ferramenta
de front-end ele também
precisa detectar
exatamente onde temos a marcação
React e onde exatamente temos o JavaScript
normal. Isso exige que nomeemos
todos os nossos componentes ou todos os nossos arquivos
onde temos marcação
jsx com a extensão.jsx. É por isso que você vê main.jsx porque temos a
marcação JSX dentro de um App.jsx, porque bem, esse é um componente e definitivamente terá uma marcação JSX interna. Novamente, um componente é apenas uma função simples
que retorna a marcação JSX, que se parece com HTML e basicamente, é traduzida
para JavaScript. Podemos digitar qualquer HTML válido aqui. Se eu vou digitar span tag, ou tag h1, e chamá-la de
título, eu a salvo depois volto, você pode ver
que ela está refletida aqui. Ótimo. Se eu for inspecionar a
marcação dentro do navegador, vejo div id root, que é novamente nosso ponto de
montagem para o aplicativo
definido dentro do index.html, e então nosso
aplicativo React é montado dentro do div, exatamente como você vê aqui. A marcação que definimos dentro do componente App,
div e title. simples quanto isso. Agora, também temos o App.css aqui. Como você já percebeu, para criar alguns estilos ou estilizar um aplicativo React, basta
criar um arquivo CSS. Escreva CSS normal aqui e importe-o dentro do componente. Simples assim. Nada de especial. Para atribuir classes aos
elementos que temos dentro da marcação, precisamos passar o atributo
className aos elementos,
não à classe, mas ao className, porque lembre-se de que,
embora seja uma marcação HTML, ela é traduzida para
JavaScript nos bastidores. Isso significa que ele é
processado pelo React. No React, em vez de
passar apenas a classe, passamos o atributo className. Dentro do
atributo className, especificamos quais nomes de
classe esse
elemento deve ter. Vamos passar algo aleatório. Vamos passar a classe de cartão
que é definida dentro do CSS. Vamos apenas fazer o
cartão e depois salvá-lo. Se inspecionarmos, você pode
ver agora
que esse div tem uma classe de
cartão com o CSS definido aqui. Funciona exatamente assim. Não há nada de especial nisso. Então, vamos
criar nossos próprios componentes. Dentro do código-fonte,
vamos criar uma nova pasta chamada Componentes. Dentro dessa pasta de componentes, criaremos um novo arquivo, que chamaremos
de Square.jsx. Aqui, vamos criar uma nova função chamada square
e, por enquanto, ela
retornará um div simples, olá. A partir desse arquivo,
vamos exportar o quadrado padrão, assim mesmo. Agora, acabamos
de criar um componente quadrado e queremos usá-lo
dentro de outro componente. Na reação, você usa componentes dentro de
outros componentes. Tudo é um
componente do react. Voltamos ao aplicativo JSX, e aqui vamos importar quadrado dos componentes ao quadrado
e, aqui dentro, vamos apenas digitar
quadrado e fechar automaticamente. Você pode ver quando você
quer usar componentes, você os usa como elementos HTML. No entanto, novamente, a primeira regra é que eles
estão sempre em maiúsculas. Basicamente, os componentes
são muito semelhantes às tags HTML reutilizáveis, mas são componentes com sua própria lógica definida internamente. Se acessarmos o aplicativo novamente, você verá que o olá está
sendo adicionado aqui. Este é o nosso componente
e a
marcação dentro do quadrado
é sobre olá. Se eu mudar para outra
coisa, isso será refletido aqui. simples quanto isso. Agora, você sabe que qualquer atributo HTML pode receber alguns argumentos para passar
algumas informações, para passar alguns dados
para esse elemento. Por exemplo, temos tag de imagem. A tag de imagem espera
dois atributos, source e alt, caso a imagem não seja carregada. Vamos prosseguir e
tentar especificar esse vite.svg como a fonte dessa tag
de imagem. Como o vite.svg é
servido sob root, porque lembre-se
daquela pasta pública mapeada para segmentos de URL, vou apenas
especificar vite.svg, salvá-lo e você verá que funciona. Ele nos aponta para vite.svg,
que está correto. Os componentes também têm atributos, mas todos esses
atributos são totalmente definidos por nós dentro da definição do
componente. Esses atributos
são chamados de adereços. Assim como os elementos HTML
têm atributos, os componentes têm solicitações para passar alguns dados dentro desse componente. Temos componente quadrado. Se abrirmos o componente quadrado, são apenas dados estáticos aqui
, apenas mostram olá. E se eu quisesse exibir
o componente quadrado e alterar o
que será exibido no interior? Digamos que possamos duplicar componentes
quadrados, assim mesmo, e
teremos vários componentes quadrados,
por exemplo, olá,
olá, olá. Mas e se eles precisarem de algumas informações
dinâmicas em tamanho, alguns dados dinâmicos como olá 1, olá 2, 3, 4, etc? Para fazer isso, precisamos
passar adereços. Props é apenas o objeto que o componente recebe
como primeiro argumento. Simples assim. Se
quisermos cancelar os adereços de registro, abrirmos o console e se eu
atualizarmos a página, você verá vários registros
do console aqui. Por que temos vários? Porque executamos o
componente quadrado várias vezes. Para cada componente, o registro
do console é impresso. No momento, é um objeto vazio. Não é indefinido, é um objeto vazio. Tudo o que passarmos para o
componente como um suporte, aparecerá abaixo do objeto
props aqui. Assim como passamos
atributos para elementos, passamos adereços para componentes. Digamos que, para este último componente
quadrado, vamos passar o adereço. Novamente, será totalmente personalizado. Vamos chamar isso de valor. Vamos passar a Sequência 5. Voltamos aqui, eu atualizo a página, dentro do console do navegador,
podemos ver o valor 5. Foi cancelado e
bloqueado duas vezes. Bem, isso é errado, que foi
cancelado duas vezes. Acho que o motivo pode
ser o modo estrito aqui. Deixe-me tentar
rapidamente e removê-lo. Se eu atualizar, agora tenho apenas um
log do console. Isso é estranho. O problema é que, quando o
componente é atualizado, ele é atualizado internamente. Quando o componente é atualizado, o JavaScript é executado novamente e a lógica interna do componente é executada novamente. Por alguma razão, o componente ósseo estrito
força o componente a renderizar novamente o JavaScript
dentro do componente para ser executado e vemos um registro
do console do mesmo componente
várias vezes. Vamos manter isso assim. Temos o valor 5. Para o resto dos componentes
que temos aqui, ainda
é um
objeto vazio porque bem, não
passamos
nada dentro dele, mas para o último componente, passamos o valor 5, passamos o suporte. Ótimo. Acho que está claro que, como não
passamos nada aqui, para esses componentes,
é um objeto vazio, mas aqui passamos o valor 5. Agora, dentro do objeto props, temos o valor chave
com a string de valor 5. Dentro da definição
do componente quadrado, agora
podemos usar esse valor aqui. Como é um objeto, ele está disponível
em props.value. Vamos consolar explicitamente o log props.value e
atualizar a página, vemos undefined e
five, porque, novamente, para todos esses componentes
que não passam value prop, valor será indefinido, mas para o último componente, o
valor será a string 5. Ótimo. Agora, dentro da marcação JSX, podemos exibir expressões
JavaScript. No momento, se eu digitar alguma coisa ou se eu quiser, vamos ver, exibir o valor desse adereço como um texto dentro do meu componente
em vez de olá, para que pareça dinâmico. Eu provavelmente
digitaria props.value. Mas isso vai funcionar?
Vamos tentar ver. Se eu abrir minha página, vejo props.value como um texto
porque não funciona. É só uma corda. Mas se quisermos avaliar props.value como um JavaScript
dentro de nossa marcação JSX, precisamos usar colchetes. Simples assim. Dentro
de colchetes, podemos inserir qualquer JavaScript válido e ele será avaliado e, eventualmente interpolado na
marcação que escrevemos. Se voltarmos aqui, veremos apenas cinco. Mas onde estão
os demais componentes? Se inspecionarmos a marcação, estará simplesmente vazia. Por estarem vazios, eles não ocupam nenhum
espaço na página. Mas o último componente, que foi renderizado,
tem cinco exibidos em seu interior. Exatamente o que
passamos aqui como suporte? Se seguirmos em frente e
passarmos outra sequência aqui, como olá, valor será meu nome. O valor será alguma coisa. Vamos remover este, salvá-lo e voltar. Você pode ver que tudo está sendo exibido
assim que passamos. Dessa forma, usando adereços, podemos passar as informações
para o componente. Aqui está uma dica rápida, pois sempre
sabemos que o primeiro argumento para a função componente
será o objeto props. Podemos usar a desestruturação
em vez de escrever adereços... algo o tempo todo. O que vou fazer é aplicar a desestruturação diretamente nos argumentos
da função. Como desestruturamos o valor da chave do objeto adereços, vou
pegá-la assim. Agora parece muito mais limpo e não precisamos
escrever adereços. algo. Dessa forma, podemos passar quantos adereços
quisermos dentro do componente. Além disso [NOISE], podemos passar outro adereço
especial predefinido chamado children. Crianças é algo
que você passa dentro do componente
como sua própria marcação. O que quero dizer com isso é que se você olhar dentro do
componente quadrado agora. É fechado automaticamente. É e por dentro
passamos diferentes adereços. No entanto, também podemos
escrevê-lo assim. Quadrado e feche-o
em uma linha separada. Então, lá dentro, podemos passar
algo como div, olá. Talvez outro título
diga, isso é título. Nesse caso, esse componente
agora não é mais fechado automaticamente. Eles permanecem fechados automaticamente
, mas é como um componente normal que não se
fecha automaticamente e, por dentro, passamos a marcação. Tudo o que passamos dentro do componente dessa
maneira. Essa marcação aqui,
olá, esse é o título. Ele estará disponível dentro da definição
do componente. Como adereço infantil, é um nome de chave reservado
especificamente para isso. Se eu vou prosseguir aqui
e registrar crianças no console. Se abrirmos o console novamente, você verá que, para o
restante dos componentes em que não passamos
filhos, ele é indefinido. Mas para o primeiro componente, se você abri-lo, há
algumas coisas estranhas aqui. Esse é o JavaScript
que está sendo realmente usado
por trás da marcação JSX. Podemos pegar as
crianças e renderizá-las. Podemos usá-lo como um slot. Em outras bibliotecas,
é chamado de slots. No reator, é
chamado de crianças. Você passa alguma marcação dentro do componente e
, em seguida, o componente interno, usando-a quando criança, pode decidir onde
exatamente ela será renderizada. Dentro dessa marcação, vou digitar, as crianças
serão renderizadas abaixo. Dentro da div,
vou interpolar crianças porque, novamente, se eu vou
passar crianças
assim, elas serão
consideradas crianças em sequência. Mas como children é uma
variável dentro dessa função, precisamos
interpolá-la na marcação JSX. Simples assim. Agora, se olharmos dentro do nosso HTML, temos coisas diferentes aqui. Para o primeiro componente, temos algo, então temos filhos que
serão renderizados abaixo. Então temos div, que são filhos que
passamos para o
componente dentro dele. Nós passamos olá lá
e este é o título. Isso é
exatamente o que vemos aqui. Esse HTTP do HTML é interpolado dentro do componente
quadrado. Está disponível para crianças. Foi exposto
como adereço infantil. Novamente, você não pode mudar. Sempre fica assim. É um adereço
reservado para crianças. Nunca muda e
sempre permanecerá assim
, não importa o que aconteça. Para o resto de nossos componentes, nada será renderizado. Você verá que
será uma div vazia. Sempre que você tenta exibir, ou digamos o que quer que seja, você tenta interpolar o nulo indefinido. Dentro da marcação JSX, ela não será renderizada
porque, bem é considerada um valor vazio, não será exibida. Se eu for continuar e tentar exibir
null por dentro, nada estará lá. Será apenas uma div vazia. O mesmo acontece com
indefinido e falso. Todos os valores falsos não serão
avaliados como algo. Eles serão simplesmente omitidos. Assim, podemos
criar componentes. Legal, não é? No próximo vídeo, vamos criar um componente
de placa. Vamos criar um componente
de raiz
quadrada e
tentar incluir algumas funcionalidades
no aplicativo. Te vejo lá.
44. 05 Como aplicar estilos de CSS: Olá. Vamos
continuar criando o aplicativo. Na última vez, discutimos
os componentes, como podemos criar componentes, como podemos transmitir crianças, quais são os componentes, como podemos exibi-los, etc. Agora, vamos começar e
dar vida ao nosso aplicativo. O que vamos fazer agora é criar
a marcação que
será usada em nosso jogo. Voltamos ao aplicativo JSX. Vamos remover
tudo daqui. Vamos remover
esse nome de classe por enquanto, removeremos a
importação do quadrado e criaremos um novo componente dentro
da pasta de componentes, que chamaremos
de JSX. Ele representará nosso
conselho e colocaremos toda a lógica relevante
dentro desse componente. Novamente, vou
criar uma função de palavra. Por enquanto, vamos
exibir div como olá
e, a partir desse arquivo, vamos explorar
esse componente da placa. Então, dentro do aplicativo JSX, vamos importar a placa
da placa de componentes. Em seguida, vamos executá-lo aqui como um
componente de fechamento automático. Agora voltamos ao navegador, vemos olá, que
vem do componente da placa. Agora, dentro do quadro, vamos definir
o marcador inicial. Vamos dar a ele
um quadro de nomes de classe. Ainda não é tratado em nenhum lugar, nem em arquivo CSS, nem em qualquer lugar. Vamos apenas marcá-lo
com o quadro de nomes da classe. Lá dentro, vamos
criar linhas porque
se você se lembrar de como nosso jogo vai
ser um tic-tac-toe e tem que ser isso,
digamos, uma
estrutura semelhante a uma linha dentro do HTML. Vamos
criar três linhas. Teremos três divs. Cada div terá um quadro de nomes de
classe , uma
linha e, dentro de cada linha,
teremos três quadrados. Será basicamente apenas
uma grade, três por três. Dentro de cada linha, vamos
usar o componente quadrado. Vamos importar
quadrado a quadrado. A propósito, isso./ representa a pasta
atual onde
esta placa de arquivo JSX neste caso, a localizou. Se eu digitar. /, representa essa pasta de
componentes. Isso significa que tudo o que eu
digitar mais adiante será resolvido
nessa pasta. Eu importo default,
export, este,
um nome, seu quadrado interno, e tudo isso é importado
desse arquivo quadrado aqui. Dentro de cada linha,
vou correr o quadrado três
vezes, sem mais nem menos. Eventualmente, parece
algo assim. Se eu atualizar, ainda teremos a
marcação do último vídeo, mas vamos removê-la e usar apenas
o valor prop. Mas ainda precisamos passá-lo dentro de cada instância de raiz
quadrada que executamos. Vou passar
o valor zero aqui. O valor será um. A propósito, no último vídeo, eu passo o valor como uma string. Simples assim. Uma string pode ser passada
sem colchetes, mas se você tentar passar cinco e quiser que seja um número
em vez de uma string, você terá que
usar colchetes. Novamente, colchetes em
qualquer lugar da marcação JSX permitem que você use qualquer expressão
JavaScript válida em seu interior. Zero como número é uma expressão
JavaScript, e podemos passá-la
como uma propriedade de valor, e será apenas o
número 0 ou o número um. Se você quiser que seja uma string, basta digitá-la
assim e será uma string. Uma expressão que é
avaliada em string. Mas se for uma corda, você pode passá-la assim. Se passarmos números, teremos que usar colchetes. Valor 0, valor como esse. Deixe-me copiar
tudo rapidamente e
deixá-lo assim até as oito. Você pode ter uma pergunta
por que começa do zero. Bem, eu não te disse, mas vamos abordar
em breve como vamos
representar o tabuleiro, como vamos administrar isso, e precisamos representar
quadrados de alguma forma. Podemos
representá-los por índices. Um aumento na programação
começa do zero. Como vamos usar um
aumento para gerenciar um jogo de tabuleiro, os índices começarão do zero. É por isso que, por enquanto, fornecemos índices aos nossos quadrados e eles começam do zero
porque serão elementos da matriz. Voltamos aqui e vemos isso. Bem, se inspecionarmos o HTML, isso é exatamente o que escrevemos. Agora, vamos torná-lo um
pouco mais estiloso. Voltamos ao quadrado JSX e nossos quadrados
serão clicáveis. Em vez de div, podemos renderizar
um botão com o tipo button e dar a ele
um nome de classe de quadrado, que
definiremos em um momento. Agora, parece que sim ,
e não é tão
ruim, não é? Mas vamos aplicar
nossos próprios estilos aqui. Se voltarmos a ser convidados aqui, exatamente nesta página, onde você pode ter todas as
informações fornecidas, se você rolar aqui, temos
styles.scss aqui. Bem, SCSS é para arquivos Sass. Sass é um pré-processador CSS
que vamos usar. O que é um pré-processador CSS? É basicamente apenas uma
linguagem construída sobre CSS e tem seu
próprio conjunto de recursos. Eventualmente, quando
escrevermos esse SCSS de pontos, ele será compilado
em algo CSS de pontos e funcionará
como um CSS normal. Mas tem a desvantagem
de suas próprias características,
por exemplo, como a nidificação. Em CSS normal, não temos
permissão para aninhar seletores. Temos que escrevê-los em linha, como o rapper da história dos pontos, depois o
espaço e depois a história dos pontos. No SASS, tudo
pode ser aninhado. Podemos ter variáveis
e coisas diferentes. Você pode procurar no Google por SASS, Syntactically Awesome
Style Sheets. Você pode abri-lo,
clicar em “Learn SASS” e acessar esta
página muito rapidamente. Não é muito longo, é bem curto, abrange
e mostra todos os recursos do
SASS, por exemplo, variáveis. Ao usar o cifrão, você pode ter variáveis em CSS. Muito legal, e você
pode se aninhar. Você pode ver se você
escrever essa marcação SASS, ela se traduz nesse CSS, então vamos usar o SASS. Para fazer isso, precisamos instruir Vite. Precisamos dizer ao Vite que,
em vez do CSS normal, também gostaríamos de usar o SASS, e o Vite tem suporte para SASS. Se voltarmos à documentação do
Vite e
clicarmos em “Pesquisar”,
procurarmos SASS aqui e
abrirmos o primeiro link, teremos a seção de
pré-processador CSS, e o Vite fornece
suporte integrado para arquivos SCSS. Então, para fazer isso, habilite o suporte necessário
para instalar o compilador SASS. compilador SASS está disponível
como pacote npm chamado SASS. Você pode ver esse comando aqui. Se eu digitar npm SASS, colocarei o primeiro link. Esse é o pacote
que nos permite compilar
o
SASS em arquivos CSS. Então, só precisamos instalá-lo
e, na verdade, a Vite cuidará
do processo de transpilação. Eu só vou copiar esse
comando, abrir o terminal, parar o comando
pressionando Control C, então nosso servidor diff quebra, então eu vou instalar o SASS. Dash D é basicamente
o mesmo que dash, dash save-dev. Só um atalho. Ele instalará o SASS como
uma dependência do desenvolvedor
e, se você examinar
o pacote JSON agora, verá o SASS
nas dependências do desenvolvedor. Ótimo. Agora, precisamos
primeiro executar o npm run dev para iniciar o servidor
novamente e podemos seguir em frente e realmente
criar arquivos SASS. Dentro da pasta de origem,
vou criar Styles.scss e o que
vou fazer? Vou até o convidado e vou copiar tudo daqui e colocá-lo
dentro do estilo CSS. Você não precisa entrar em
muitos detalhes aqui. Essa é a marcação final
que teremos em nosso aplicativo porque esses
vídeos não são sobre CSS. Se você precisar mudar alguma coisa ou se quiser
trazer algo novo aqui, você está livre para fazer isso. Por favor, mude, brinque com isso, vamos
usar essa marcação. Dentro desses estilos,
temos uma cláusula do conselho definida. Em seguida, dentro do tabuleiro,
aninhamos a classe da linha do tabuleiro
e, dentro da classe da linha do tabuleiro, aninhamos a classe quadrada. baixo do capô, se
você abrir o SASS novamente, aninhamento compila
esses seletores aqui, então basicamente a placa e a linha interna do tabuleiro serão compiladas para algo assim, e o quadrado será compilado
para algo parecido. Isso é muito
conveniente, eu acho. Temos classes de linha
e raiz quadrada de tabuleiro e quadro, então o que vamos fazer é importar o arquivo
SASS de pontos para nosso aplicativo. Não precisaremos mais do CSS
do app dot, então simplesmente o excluímos. Em seguida, vamos para o componente do aplicativo
e, em vez de
importar o CSS do aplicativo, vamos importar
estilos, pontos CSS, e isso funcionará. Agora temos classes de
tabuleiro, linha de tabuleiro e
quadrado aqui. Vamos para quadrado, atribuímos a classe quadrada, que será
resolvida para esse CSS. Dentro do tabuleiro, temos um tabuleiro e uma fileira de tabuleiros, que serão resolvidos
para essas classes. Agora, voltamos ao aplicativo e pronto, você pode ver, parece exatamente assim. No entanto, você pode ver que algo está errado ou algo
está errado, na verdade é nossa marcação então precisamos
alterá-la um pouco. Se acessarmos o aplicativo aqui, forneceremos
o componente que envolve toda a
nossa marcação. Vamos dar a
ele a classe de aplicativo aqui que definimos
exatamente assim. Assim, podemos dar a ele um nome de
classe de App. O que ele fará é nos fornecer a caixa flexível básica
com a configuração da coluna. Se voltarmos aqui, você pode ver que agora
temos nossa grade final, que tem
essa aparência. Muito legal. Isso é tudo sobre estilo. Agora você conhece mais um truque como você pode estilizar
seu aplicativo usando o SASS. Se você já conhece algum outro
pré-processador como o Less, você também pode ler na documentação do Vite como
conectá-lo ou caneta. O SASS é bastante popular em todas as soluções comuns
em aplicativos. Eu acho que é muito legal
e muito conveniente. Agora, na verdade, começamos com interatividade, mas
acabamos com estilos. Acho que, por enquanto, vamos
acabar com estilos
e, na verdade, no próximo vídeo, falaremos
sobre interatividade. Acho que você não se importa. Como já trabalhamos
muito aqui, introduzimos o SASS, criamos componentes quadrados
e de placas e temos nossa
bela marcação aqui, vamos realmente
confirmar tudo. O que temos aqui?
Removemos o CSS do aplicativo, modificamos o pacote JSON e excluímos alguns arquivos. Então, vamos adicionar tudo
ao estado do palco. Vou digitar “Git
add dot” para que tudo apareça sob alterações faseadas e vamos apenas
confirmar tudo, e vamos nomear o
commit como SASS instalado e criar componentes
quadrados e de placa ,
básicos, algo assim. Mensagem de confirmação muito estranha, mas acho que funcionará. Nós comprometemos tudo. Para que tudo apareça no GitHub, precisamos
implantá-lo porque, novamente, precisamos lembrar
que, se você fizer alterações, elas permanecerão localmente no seu PC. Se você voltar para o
GitHub agora, nada mudará porque todas as suas
alterações ocorrem localmente, então você precisa implantar
na hospedagem do GitHub toda vez que
introduzir novas alterações localmente, então git push origin master. Eu faço isso e refresco, e agora temos tudo de bom. Incrível. Como prometi, o
próximo vídeo
será sobre interatividade, então nos vemos lá.
45. 06 Reagir o estado com o useState hook, reaja eventos: Olá de novo. Neste vídeo, conforme prometido, falaremos
sobre interatividade. O que quero dizer com interatividade. interatividade é algo
que acontece quando o usuário interage
com a página da web. Quando eu clico no botão,
algo deve acontecer. Um evento ocorre e algo
é atualizado na tela. Isso se chama interatividade. Agora veríamos como
podemos gerenciar isso no React. Em JavaScript bruto, em JavaScript
simples
sem nenhum React, você tem um arquivo JavaScript. Normalmente, você captura
elementos com a API DOM, algo como documento
obtém elemento por ID. Você pega um botão, depois escreve button.add
event listener, e esse ouvinte, você anexa alguma função que será executada quando você
clicar no botão. Mas, em reação, é praticamente o mesmo. Parece diferente, mas é quase o mesmo, então
vamos abrir o JSX aqui. Só por exemplo, vamos criar um botão e
vamos jogar com ele. Eu removi a placa por enquanto. Onde está o componente por
enquanto? Não precisamos disso. Temos o editor eslint
aqui, sem variáveis não utilizadas. Ele produz um erro
em vez de premiar, vamos realmente
colocá-lo em execução para que
seja menos variável. No eslint, eu simplesmente
não vou usar carros não utilizados e queria emitir um aviso, então agora ele
será laranja em vez de vermelho e não nos
incomodará muito. Então, eu vou
criar um elemento de botão e
vou chamá-lo,
clique em mim, por favor. Agora, o que eu quero
fazer nesse botão, talvez eu queira
atualizar algo ou cancelar algo, registrar algo e ver algum valor
no console do navegador. Como podemos fazer isso? Para cada elemento, para cada tag HTML
usada dentro da marcação JSX,
você pode passar um
manipulador de eventos para que tenhamos eventos, evento clique, evento de mouse, diferentes tipos de eventos e sempre que digo manipulador de eventos, me refiro à
função que será executada quando esse evento ocorrer. Por exemplo, vamos pegar
esse elemento de botão. Se eu tentar passar atributo que começa com um a
partir da inteligência, posso ver uma lista bem longa de eventos
diferentes disponíveis
para esse elemento. Onsubmit, onResize, onMouse, over onKeyUp, etc. momento, estamos interessados
no evento onClick, então vou apenas fazer onClick e,
para esse atributo
no elemento do botão preciso passar
um manipulador de eventos, uma função que será
executada quando o clique ocorrer, então
vou passar uma função vazia aqui e dentro dessa função, vou fazer console.log, “Olá”, então se eu salvar, eu volto para o aplicativo. Agora, sempre que eu
clicar no botão, você verá olá
ser impresso toda vez que eu clico
nele para que ele realmente funcione. Em JavaScript simples, todos os manipuladores de eventos sempre
recebem o objeto de evento como o primeiro argumento, portanto,
essa função aqui em JavaScript
simples sempre recebe um objeto de evento que
representa o evento. Vamos tentar cancelar o
registro desse objeto aqui. Vamos ver se
há alguma diferença. Então, se eu clicar no botão aqui, posso ver olá e depois
vejo o objeto de evento,
então esse objeto de evento
é um invólucro em torno do
objeto de evento nativo que você normalmente
obteria com
JavaScript simples, mas em react, isso é algo chamado evento
sintático, então
é basicamente apenas um invólucro em torno do evento
nativo com
poucas propriedades de reação. Se você inspecioná-lo, você tem uma pilha de
propriedades diferentes aqui, bem
como um
evento nativo que pode ser acessado apenas
com o evento event.native. Dessa forma, se você precisar, você pode obter um objeto de evento
JavaScript nativo. Mas, na maioria das vezes
, tem apenas o suficiente para
se referir a um evento sintético. Na maioria das vezes, ele contém as informações que você
está procurando, caso precise usá-las
, portanto, nesse caso,
não precisamos de nenhum
objeto de evento. Estamos interessados em
fornecer alguma interatividade ao aplicativo, então agora vamos experimentá-lo e
ver como podemos fazer isso. Digamos que temos um contador. Deixe-me seguir em frente e
criar uma variável. Vamos chamá-lo de “Let counter, que começa com um”. Agora, o que eu quero
fazer é
exibir esse contador aqui e
sempre que clico no botão, gostaria de
aumentar o valor de um,
2, 3, etc. Dentro do
manipulador de eventos OnClick, na verdade, vamos tentar mover essa função aqui para o aplicativo para que
fique mais bonita. Parece mais
atraente e fácil ler, então podemos criar essa função aqui
e chamá-la onBtnClick e eu
vou copiá-la daqui,
colá-la aqui e, para
o atributo onClick, vou passar btnClick. Assim, digamos que
dentro desse manipulador de eventos, eu gostaria de aumentar o contador aqui, então, em vez do log do console, talvez vamos mantê-lo. Vamos dizer que contador é
igual a contador mais um. Nada de especial. Agora, podemos ver que ele
realmente foi aumentado? Vamos para frente e para baixo. Vamos exibir o valor do contador , então vou
usar colchetes para interpelar novamente o
valor em apenas seis porque ele tem
um contador variável. Eu o guardo. Eu volto
aqui, vejo um. Só que nós temos isso
inicialmente, ótimo. Se eu tentar clicar
nele, nada acontece. Mas por que isso? O problema com essa
abordagem é que o React não segue exatamente as mesmas
regras do JavaScript simples. Então, se você estivesse usando JavaScript
simples e tentasse escrever uma lógica muito
semelhante, teria
funcionado,
mas não com o React. No React, sempre que você precisar um valor que mude ao longo de
algum período de tempo, depois de,
digamos, que durante o período de interatividade apenas
desvalorizou as mudanças, você precisa torná-lo um estado. Portanto, no React, um valor que
muda deve ser um estado. Em apenas um segundo, agora
podemos criar
nosso primeiro estado. Mas antes de fazermos isso, deixe-me explicar rapidamente por que isso não funciona. Vou abrir o
Paint e
escrever rapidamente como o React
lida com isso. No React, existe o
conceito de re-renderização. Uma nova renderização ocorre basicamente quando o componente está sendo
repintado na página da web. Quando usamos state,
state sempre aciona um
componente para renderizar novamente, e o estado na próxima
renderização será atualizado. Mas, se criarmos variáveis como essa e
tentarmos atualizá-las, isso não fará nada. A razão para isso é
porque quando
tentamos mutar a
variável desse jeito,
isso não acionará a renderização
do componente novamente. O ciclo de vida de um componente é
, na verdade, baseado em novas renderizações. Quando atualizamos a página, o componente está sendo
montado na página. Isso significa que está sendo
renderizado pela primeira vez. Então, digamos que esse quadrado aqui represente uma única renderização. O componente está
montado na página, foi renderizado e exibido. Agora, pelas regras do React, se eu quiser atualizar
algo na tela, se eu quiser atualizar algo
dentro desse componente, preciso acionar uma
nova renderização para isso. Aproximadamente nesta foto
, ficará assim. Essa nova renderização se
traduzirá em uma nova renderização diferente. Esses são quadros e comutadores do
React sobre eles. Então esta é nossa primeira renderização. Digamos que atualizemos o estado. Novamente, o estado será o valor que muda ao longo de
algum período de tempo. O estado foi atualizado, atualização de
estado aciona
uma nova renderização e agora temos um componente
que foi renderizado novamente. Novamente, com variáveis, se vamos
usá-las desse jeito, não
funcionará. O motivo dessa atualização de
variável é que essa linha número 9 não aciona uma nova renderização
e isso é um problema. Permanecemos neste primeiro quadro e tentamos atualizar esse
contador mais um aqui, e isso não faz nada,
não aciona uma nova renderização, que significa que precisamos usar estado para todos os
valores que sabemos que serão alterados
ao longo de algum período de tempo após alguma interatividade. Cada renderização aqui, então esta é a primeira renderização, a
segunda renderização, elas oscilam uma
da outra, elas não sabem nada uma
sobre a outra. A primeira renderização não sabe que
haverá uma segunda renderização
e, assim como a segunda
não sabe se houve
uma primeira renderização
ou uma renderização anterior, elas oscilam uma
com a outra. Tudo isso é gerenciado
internamente pelo React, mas o ponto principal
aqui é que precisamos saber que,
para atualizar algo, precisamos acionar um
componente para renderizar novamente. Sempre que um estado é atualizado, ele aciona a renderização
de um componente novamente. Agora, se quiséssemos que esse contador fosse atualizado
e funcionasse conforme o esperado, a partir do React, precisaríamos explorar algo
chamado useState. No topo, vou apenas
importar useState e aqui estou usando a
importação nomeada do React. O que é useState? No React, existe um conceito
de React Hooks. O que é um gancho? Hook é basicamente apenas
uma função que
nos permite manipular o ciclo de vida do
componente. O que é o ciclo de vida do componente? O ciclo de vida de um componente
é apenas um período de tempo em que algo está acontecendo dentro
do componente. Ele está sendo montado, atualizado, está sendo desmontado, então esse é o ciclo de vida do componente. Podemos usar o React
Hooks para
manipular de alguma forma o ciclo de vida desse
componente. Portanto, useState nos permite criar um valor que será alterado
ao longo do ciclo de vida de um componente. Como podemos usá-lo.
Dentro do nosso componente, precisamos apenas chamar
useState como uma função. Novamente, todos os React
Hooks são funções. A propósito, todos os React Hooks
sempre começam com o prefixo de uso. Portanto, essa é a
convenção no React. Sempre que você vê algo usado, é definitivamente um React Hook. Chamamos isso de função
e, como primeiro argumento, precisamos passar
o estado inicial. Qual será o
valor padrão para esse estado? No nosso caso,
queríamos dar a ele um valor
inicial de um, então vamos passar apenas um. Agora, essa função useState sempre
retorna uma matriz. useState sempre retorna uma
matriz de exatamente dois elementos. Vamos seguir em frente e
chamá-lo de valor de retorno por enquanto, e vamos tentar registrá-lo no
console, escrever diretamente dentro
do componente. Vamos ver o que temos aqui? Então, eu atualizo a página e aqui eu tenho,
como eu disse, uma matriz de exatamente
dois elementos. O primeiro elemento será valor
do estado neste
momento na renderização atual, e o segundo valor dentro
dessa matriz será a função de atualização
que precisamos
chamar para atualizar esse estado. Deixe-me mostrar o que quero dizer. Na maioria das vezes, você
verá que vamos usar
uma reestruturação porque sabemos que useState sempre retorna uma matriz
de exatamente dois elementos, para que possamos aplicar
uma reestruturação com segurança. O primeiro elemento será nosso estado e o segundo, uma função que precisamos
chamar para atualizar o estado. Eles são chamados de estado e função de
atualização de estado, e podemos chamá-los como
quisermos. Nosso estado
será chamado de counter, e a função de atualização para definir o estado será
chamada de setCounter. Agora vou remover esse
contador de esquerda igual 1 um. Vou remover esse
contador de linha mais 1, nós realmente não precisamos dele. Vamos tentar
consolar nosso contador. Na verdade, não
precisávamos cancelar o registro, já o
temos aqui. Se eu salvar,
atualizo a página, ainda
temos uma aqui. Esse é o nosso estado inicial. Agora, se quisermos
atualizar o estado, precisamos chamar a função de
atualização de estado, setCounter. Entre o clique
e o clique, queremos aumentar o valor. Então, o que podemos fazer. Podemos chamar setCounter
e, internamente, só precisamos passar um novo valor para esse estado. Por enquanto, vamos colocar um valor
estático. Digamos que 10. Eu salvo,
volto para o navegador, agora clico no botão e você vê que o valor
foi alterado para 10. Dentro do console importa
que você veja olá aqui. aconteceu é que quando
você clica no botão, setCounter foi chamado, ele atualizou o estado
de um para 10. Em seguida, sua renderização ocorreu novamente. Se voltarmos a esse
pequeno diagrama aqui, o que aconteceu é que esse componente
foi renderizado na página. Clicamos no botão, atualizamos o estado e essa atualização de estado
acionou a nova renderização. O segundo quadro aqui representa nossa renderização atual,
onde o estado atual é 10. Por que vemos o registro do console aqui? Na verdade, vemos o
log do console aqui porque o
temos dentro de OnBtnClick. Mas e se colocarmos o log do console aqui fora do OnBtnClick. Vamos tentar novamente. Eu
atualizo a página. Primeiro, vemos dois registros
do console, mas bem,
isso é esperado porque,
como você se lembra,
eu disse no
vídeo anterior sobre o React StrictMode,
era intencional que ele
renderizasse isso é esperado porque,
como você se lembra, eu disse no
vídeo anterior sobre o React StrictMode, era intencional que ele o componente duas
vezes para detectar erros, mas esse não é o ponto, ou talvez esse seja o ponto. Deixe-me remover o
React StrictMode por um segundo. Eu atualizo a página. vemos um registro do console Olá, vemos um registro do console porque o
componente é montado, a lógica interna do componente é executada, vemos o log do console. Ótimo. Mas agora, se eu clicar no botão,
vemos que o valor é atualizado, o componente é renderizado
e vemos olá pela segunda vez. Vemos isso porque, novamente, em cada nova renderização, a lógica dentro do
componente está sendo executada novamente. Javascript é executado novamente quando o componente é renderizado novamente, então o estado é
persistido porque o useState é um recurso
interno do React. Bem, ele é totalmente
gerenciado no React, então o valor que muda ao longo do período
é gerenciado pelo React. É persistido. Tudo é legal. Mas vemos o registro do console
aqui porque, bem, isso é algo
que trazemos para o componente e a
lógica é executada novamente, então é por isso que a vemos
pela segunda vez. Se estivermos prestes a atualizar
o estado novamente
na próxima vez que o componente
for renderizado novamente, você verá outro olá, etc. Você verá olá toda vez que o componente
for renderizado novamente. Mas o que acontece se eu
clicar no botão novamente? Veja, eu
clico mais uma vez e não vemos mais
nenhum olá. O React é inteligente o suficiente para detectar que o estado permanece o mesmo, então o valor permanece o mesmo. O React é inteligente o suficiente para não atualizar o componente
o tempo todo novamente, novamente. Ele não executa
recálculos o
tempo todo se o
valor do estado for o mesmo. Vamos prosseguir e tentar aumentar
o contador. Podemos fazer o contador mais
1, desse jeito. Agora, se eu atualizar a página, clico no botão,
vejo 2, vejo olá, porque novamente o componente
é renderizado novamente. Eu clico no botão novamente, e agora o olá, vemos 3 e assim por diante e assim por diante. No entanto, nessa abordagem de
atualização de estado dessa forma, quando precisamos definir um novo valor
para esse estado e queremos calcular o novo valor
do estado a partir do valor do estado atual, precisamos usar uma abordagem ligeiramente
diferente. Em vez de fazer
um contador mais 1, podemos realmente passar retorno de chamada
alternativo para
a função de atualização de estado. função de atualização de estado pode
receber um dos dois argumentos. Ou um novo valor de estado, como você viu, então 5, 10, novo valor que
definirá o cenário, ou podemos passar o retorno de chamada para
essa função de atualização de estado
e, dentro desse retorno de chamada, primeiro argumento será value, que representa o estado atual. Digamos que contador de corrente. Tudo o
que retornarmos desse retorno de chamada será
definido como o novo valor. A partir desse retorno de chamada, agora
podemos retornar contador
atual mais 1. Será o mesmo e, do ponto
de vista do usuário, nada será alterado,
mas internamente, essa é a abordagem correta
quando você precisa calcular o novo valor do estado a
partir do valor do estado atual ou
anterior. Como esse é o contador e gostaríamos de
aumentá-lo, precisamos saber o estado
atual do contador. Sempre que você tiver
essa situação, sempre use a abordagem de
retorno de chamada. Se quiséssemos apenas
configurá-lo como um número aleatório, não
precisamos dele
porque não precisamos do estado
atual para
calcular o novo estado. Voltamos ao
aplicativo. Eu refresco. Novamente, como eu disse, do ponto de vista do usuário,
nada mudou. Com algo assim, você pode manipular
elementos na página. Com base nesse conhecimento básico simples e
básico, conhecimento básico simples e
básico, todos os aplicativos React estão sendo
construídos desse jeito. Você tem vários estados. Você pode criar quantos
estados quiser. Você pode
manipulá-los como quiser com diferentes eventos
no evento de clique, mouse, quando
algo é aberto, algo é
fechado, tudo é gerenciado com
estados como esse. Acho que para este vídeo, isso será suficiente. Agora você conhece os eventos do React que podem ser transmitidos. Para esse atributo, você
pode passar qualquer manipulador de eventos para executar alguma função
quando algum evento ocorrer. Esse manipulador de eventos
sempre recebe um objeto de evento como primeiro argumento,
caso você precise dele. Se você não, bem,
simplesmente não o use. Se você precisar atualizar
algum valor na página, no contador de cores, no texto, seja o que for, temos um
estado para isso. As variáveis não funcionarão porque o React
não funciona dessa maneira. React é baseado no
conceito de rerenderização
e, para manter
o valor nas renderizações, precisamos usar o estado. Podemos fazer isso usando
o use state hook. ganchos no React são apenas
funções que você chama durante o ciclo de vida do
componente para manipular dados
dentro do componente. Algo parecido.
No próximo vídeo, veremos como podemos usar esse conhecimento e como
podemos aplicá-lo em nosso jogo. Vamos criar o estado do
jogo e manipular quadrados
para
que, quando clicarmos neles, isso de alguma forma atualize
o estado. Nos vemos lá.
46. 07 Criando estado de tabuleiro de jogo: Oi. No último vídeo,
falamos sobre interatividade, sobre estado, o que é estado, como isso pode nos ajudar. Neste vídeo, podemos
continuar com o estado, mas desta vez vamos
aplicá-lo em nosso jogo. Do vídeo anterior
, algumas
coisas mudaram aqui. Vou referenciar
essas mudanças muito rapidamente e tenho a
configuração do eslintrc desatualizada. Não coloquei nenhum
papel de vars não utilizado como aviso. Na verdade, vamos adicionar
outro commit para isso. premiação de bares reduz o aquecimento. Ok, isso vai funcionar muito bem. Agora, vamos continuar
com a interatividade. Então, se formos
para o tabuleiro, aqui, criaremos
nosso estado de tabuleiro, que basicamente
representará nosso tabuleiro de jogo. Mas a questão é: como vamos fazer isso? Se você se lembra, uma vez mencionei que
será uma matriz. É por isso que temos nove elementos aqui e todos
eles começam com zero. Eles simplesmente começam com
zero, nem todos. Então, eu vou
abrir a tinta aqui. Eu vou te dizer
exatamente como podemos representar o estado do jogo com uma matriz. Será uma matriz
de nove elementos. Então, por padrão, será uma matriz vazia com
nove elementos. E por padrão, cada
elemento será nulo, ok. Então, por padrão, inicialmente
teremos uma matriz
de nove elementos, cada elemento será nulo. Então, quando vamos
clicar em um quadrado. Portanto, nossos quadrados
serão representados por índices dentro dessa matriz. O primeiro quadrado
terá índice zero, segundo quadrado
terá índice um, dois e assim por diante. Quando
clicamos em um quadrado, digamos que clicamos
no quadrado com índice um, ele mudará seu valor
de nulo para x
ou zero com base em quem
clicou naquele quadrado. E desse jeito,
vamos administrar o estado. Então, eventualmente, teremos uma matriz
de nove elementos, cada elemento pode ser nulo se o quadrado não
for clicado, ou x, ou zero se o
quadrado foi clicado. Vamos prosseguir e,
internamente, primeiro
importaremos useState do react. Dentro do quadro, vamos
criar um novo estado, que podemos chamar de quadrados. Defina quadrados,
será useState. Agora, inicialmente, precisamos
criar uma matriz de nove elementos e cada elemento
por padrão será nulo. Para isso, podemos usar apenas JavaScript
simples aqui, então não podemos chamar um construtor de
matriz com nove como comprimento de matriz. Em seguida,
chamaremos o método de preenchimento de pontos e
preencheremos a matriz com nulos. Eventualmente, ele
produzirá uma matriz de nove elementos em que
cada elemento é nulo. Agora, como podemos
realmente associar cada quadrado a cada componente
que representa um quadrado? Neste momento, passamos por 0,1,2,3 e 4. Então, em vez disso, vamos
passar quadrados zero. Portanto, como o quadrado
é nosso estado, sempre será uma matriz que pegou o
primeiro elemento dessa matriz. Então, para o segundo quadrado, podemos pegar o segundo
elemento e assim por diante. Precisamos fazer isso
para cada quadrado. Vamos seguir em frente e fazer
isso para cada quadrado. Então, nós o salvamos. Voltamos ao aplicativo. Este site não pode ser acessado. Isso porque eu não conheci
o servidor de desenvolvimento. Então, npm run dev. Eu volto aqui e agora podemos
ver que nossos quadrados estão vazios. Bem, isso é esperado
porque temos valor nulo. Nós aprovamos valores nulos. E se você se lembrar, se tentarmos exibir null, ele não será avaliado. Isso resultará em
nada e em HTML. Agora, o que podemos realmente fazer? Você pode ver que precisamos
atualizar o estado de alguma forma, atualizar quadrados, atualizar o estado quando
clicamos em um quadrado, como podemos fazer isso? Portanto, permanecemos informados, mas temos toda a lógica sobre o componente
quadrado dentro do componente
quadrado. O que podemos fazer é usar adereços. Assim, podemos definir
alguma função aqui dentro da placa que
gerenciará a lógica, e podemos passar essa função como um suporte para o componente quadrado. Então, novamente, nós apenas
passamos alguns dados, algumas informações para os componentes. Então, aqui, o que
vamos fazer? Vamos criar
uma nova função chamada handle square click. Essa função
receberá um argumento. Vamos
chamar essa função com uma posição de argumento. Será o
0,1,2,3,4,5,6,7 e 8 será o índice do quadrado. E dentro dessa função,
faremos alguma coisa. Por enquanto,
vamos apenas mantê-lo vazio. Então, como eu disse, vamos usar prompts
para passar dados para o quadrado. O que queremos fazer quando
clicamos nesse quadrado, esse
clique quadrado da alça ficará frio. Então, o que podemos fazer? Podemos passar OnClick
ou Squared Click , qualquer que seja o nome que
você deu a esse adereço. Vamos chamá-lo apenas de OnClick. E para esse adereço OnClick, vamos passar e
construir um clique quadrado. Mas o problema é que, como passamos essa alça ao
quadrado, clique aqui, e se a passarmos dessa maneira, pegaremos esse OnClick aqui dentro do quadrado, e precisaremos chamar essa função de
quadrado dentro de quadrado e passar a posição como
argumento porque
manipula quadrados clique
recebe argumento de posição. Então, quando chamamos essa função, precisamos passar essa posição. Mas o problema é que o quadrado realmente
não precisa
saber nada sobre isso. O que queremos fazer idealmente, queremos apenas pegar a função
onClick aqui
e, para o atributo onClick, queremos passar essa
função dessa forma. E a Square não fará
nenhuma lógica sobre isso. Tudo será
gerenciado aqui a bordo. Então, para fazer isso,
o que podemos fazer com a propriedade
onClick aqui, podemos passar uma função, e essa função chamará handleSquareClick com a
posição que precisamos. Então, eventualmente, parece
algo assim. Podemos até simplificar isso
e remover o corpo funcional. Agora parece mais conciso
e parece assim. Por que precisamos passar uma função que chama
outra função? Por que podemos chamá-lo assim? Bem, o problema é
que, como você se lembra, quando
os componentes são montados na página, o
JavaScript dentro do componente é executado
e, com essa sintaxe, alguns JavaScript são usados linha por linha, e assim que
o JavaScript usa luz, ele verá que chamamos essa
função aqui nessa linha. Então, o que ele fará é chamar essa função de escrever
imediatamente. E qualquer que seja a disfunção que
retornaremos , receberá o valor
da propriedade onClick aqui, já que nossa função não
retorna nada, ela será indefinida
e, eventualmente, onClick here inside square será indefinida. Nada vai acontecer. Teremos essa
função chamada write straightaway e
undefined no final. Isso não é
exatamente o que queremos. Em primeiro lugar, o manipulador de eventos é uma função em primeiro lugar. É por isso que passamos uma
função, não outra coisa. Então, passamos uma função
que chama manipuladores rapidamente com os
argumentos de que precisamos. Bem, como você pode ver, precisamos fazer isso para
cada quadrado aqui, assim mesmo e passar posição
diferente, mas
você pode notar que há uma pequena
repetição aqui. Temos muitas coisas
que podemos simplificar aqui. Então, em vez de enquadrar valores, quadrados, depois índice de matriz, depois onClick e repetir
alças clicadas o tempo todo, podemos simplificar essa função. Podemos simplificar essa sintaxe
usando outra função. Então, o que podemos fazer aqui para evitar essa repetição?
Aqui dentro do quadro, podemos criar outra
função que podemos chamar de algo como
um quadrado de renderização. Esse RenderSquare recebe novamente posição que será a
posição que será um índice quadrado e,
dentro dessa função, podemos então retornar a marcação JSX. Vamos apenas copiar aqui. A partir de RenderSquare, agora
podemos retornar quadrado,
então, em vez de quadrados zero, vamos passar a
posição dos quadrados e handleSquareClick . Em vez de zero,
vamos passar a posição. Eventualmente, algo assim. Agora, dentro do JSX,
usamos colchetes para interpolar
o JavaScript nele. Como podemos interpolar
variáveis aqui, que são expressões
JavaScript exatamente da
mesma maneira, podemos chamar funções aqui
porque as funções
também fazem parte das
expressões JavaScript. Em vez de escrever quadrados todos eles desse jeito, o
que
podemos fazer é simplesmente abrir
colchetes, chamar RenderSquare e passar índice
zero para dentro. Assim que o componente saltar, essa função
será chamada com zero como argumento, que será a
posição dentro dela. Ele retorna a marcação JSX e
essa marcação JSX será interpolada no local onde essa função foi
bem chamada, basicamente aqui. Exatamente o mesmo que
faremos com o resto dos nossos quadrados. Eu só vou
copiá-lo duas vezes. Eu removo isso porque
não precisávamos mais dele e farei exatamente o mesmo
com o resto dos nossos quadrados, então 3, 4, 5, 6, 7, 8. Agora, novamente, chamamos a função
quando o componente é montado, essa função
retorna a marcação JSX e essa marcação JSX será inserida no local em que
essa função é chamada. Se você acabou de referenciar
essa função dessa forma, nada acontecerá. Se eu voltar, vamos
ver o que acontece. Bem, vemos algumas coisas estranhas aqui e se tentarmos ver, temos apenas dois quadrados aqui. O que estamos fazendo agora basicamente tentar
exibir a função em si. Não é o que a função retorna , mas a boa
assinatura da função e reação não funciona
dessa forma. Se você
tentar exibir os objetos como estão, não conseguirá fazer isso. Primeiro você precisa
convertê-las em cadeias de caracteres, mas não
é isso que
vamos fazer agora. Isso é um pouco avançado e
voltaremos a isso no futuro. Chamamos essa função, passamos um argumento e verificamos se
tudo funciona. Basicamente, refatoramos
levemente
nosso componente, mas ele
faz exatamente o mesmo. Ele renderiza o valor no
índice que especificamos aqui, valor da nossa matriz de quadrados, que é o estado. Dentro do handleSquareClick,
precisamos fazer alguma lógica aqui, então alguma lógica para
exibir quadrados de alguma forma. Para atualizar o estado do quadrado, precisamos chamar a função de atualização de
estado em nosso caso ao
indexar seus quadrados. Isso é exatamente o que
vamos fazer. Como nosso estado é uma matriz que será alterada
ao longo do período de tempo e nosso novo estado de matriz
que
calcularemos precisa ser calculado
a partir do estado atual, usaremos a versão de
retorno de chamada do estado definido. Vou passar o retorno de chamada
aqui e o
primeiro argumento será o estado quadrado neste
momento. Vou
chamá-lo de CurrentSquares e precisamos de
alguma forma manipular estado
CurrentSquares e obter novo estado de quadrados
com valores atualizados. Um ponto aqui que eu não mencionei no
vídeo anterior é que
não podemos alterar a variável de estado.
O que quero dizer com isso? Se usarmos useState e
tentarmos pegar esses quadrados e tentarmos
fazer algo assim, quadrados em alguma posição são
iguais a algo. O que fazemos aqui é manipular
diretamente esse estado em vez de usar
essa função de atualização de estado, isso não funcionará. Isso é proibido desta forma, estado não será atualizado. No React, ele
não funciona dessa maneira. Precisamos chamar a função de atualização de
estado o tempo
todo
para fazer isso,
então, novamente, isso não funcionará. Chamamos setSquares e,
dentro de Setsquares, também
temos
currentSquares, que
representa o estado de cada vez. Se tentarmos alterar novamente
o estado diretamente aqui, isso não funcionará. Isso simplesmente não funcionará. Não é assim que o React funciona. Precisamos chamar a função e
retornar um novo valor. O React não se
trata de alterar valores diretamente. O React trata de retornar novos valores, se isso
fizer sentido para você. A partir do setSquares, precisamos retornar um novo valor. O que podemos fazer para percorrer todos os nossos quadrados e, de
alguma forma, atualizá-los, podemos usar o
método Array.map e o método Array.map
não altera o estado, mas retorna
um novo valor de matriz. É por isso que é
seguro fazer isso. Um retorno currentSquares.map, então vamos
percorrer nosso estado quadrado. Nosso primeiro argumento
será o valor que
analisamos no momento, então
será nosso SquareValue. Então temos o índice
do quadrado. Vamos chamar isso de just pos. Como já temos uma posição
nesse escopo de função, se tentarmos chamá-la de posição, teremos colisão de variáveis. Nós apenas continuamos fazendo as pazes. Sempre que eu retornasse do.map
para o elemento atual, ele associará um novo
valor para esse elemento. Aqui, a lógica
será bem simples. A posição que
passamos para essa função é a posição na qual
basicamente clicamos. Para não nos confundir, vamos renomeá-la para a posição
clicada e aqui, indexar dentro de Array.map, vamos chamar posição. Vamos dizer se a posição
clicada é igual à posição do quadrado que examinamos Nesse caso,
retornaremos X por enquanto a partir do.map. Caso contrário, se o
quadrado que será
repetido no momento não for
o quadrado em que
clicamos, simplesmente retornaremos o
mesmo valor quadrado. Agora vamos
salvá-lo, parece que,
quando formatado pode ser um pouco confuso
porque temos uma função que chama a função e, dentro da função,
temos um retorno de chamada, basta se acostumar com isso, então
voltamos ao aplicativo. Agora vamos tentar
clicar em um quadrado. Eu clico no meio e boom, nada acontece. Por que isso? Vamos tentar no console registrar
o estado quadrado aqui. Vamos ver o que temos. Temos uma matriz de taxa de
nulos e, se eu clicar, nada realmente acontece. Vamos ver o que pode
estar errado aqui. A parte errada aqui
é que você pode ver o componente quadrado não
foi salvo. Isso porque, bem,
tudo o que acabei de escrever aqui não
foi salvo, então as alterações basicamente
não foram confirmadas. Eu o salvei e
agora deve funcionar. Eu clico no quadrado
e você vê agora
que eu tenho X aqui e se você vê aqui, o estado foi atualizado. Agora, como cliquei no
quadrado com índice 4, 0, 1, 2, 3, 4, clicamos nesse quadrado e dentro dessa matriz
atualizamos o elemento no índice 5
e definimos seu valor como
X, e definimos seu valor que tem
exatamente o que precisamos. Se clicarmos em
todos esses quadrados, você verá que todos os quadrados
serão preenchidos com acesso, que é
exatamente o que queríamos, e vemos todos esses
registros do console novamente o tempo todo. Porque, como
atualizamos esse estado, componente renderiza novamente a
lógica interna e vemos o log do console toda
vez que a lógica é executada novamente. Ótimo. Algo assim, somos capazes de administrar nosso estado. Por enquanto, acho que
isso será suficiente. No próximo vídeo, apresentaremos nossos jogadores. Na verdade, teremos
o jogador atual, então poderemos
diferenciar quem clicará nesse quadrado
a seguir. Será X ou zero, então agora você pode
ver que temos apenas X, o que não é
exatamente o que estou procurando. No próximo vídeo,
vamos abordar isso. Quando clicarmos nesse quadrado, ele será X ou
zero. Te vejo lá.
47. 08 Adicione jogadores X e o: Olá. No vídeo anterior falamos sobre esses
quadrados de estado
e, na verdade, conseguimos colocar X dentro do quadrado
quando clicamos nele. Neste vídeo, vamos
adicionar mais funcionalidades,
então, quando clicamos
no quadrado, podemos realmente
exibir x ou zero. Em outros termos,
teremos um jogador. Antes de
introduzirmos novas mudanças, muitas mudanças foram feitas até agora em relação
ao vídeo anterior. Adicionamos essa funcionalidade
quando clicamos no quadrado, exibimos X dentro deles. Bem, vamos prosseguir e
realizar essas mudanças. Vou apenas digitar git add. e vou chamar essa
mensagem de confirmação chamada,
digamos, exibir X ao
clicar em um quadrado. Vamos iniciar o servidor novamente. Incrível. Agora, vamos adicionar basicamente uma
funcionalidade de player. O player é algo que mudará ao longo
do ciclo do componente. Isso significa que
vai ser um estado. O que vamos introduzir
é um novo estado, e o estado
será o jogador. No entanto, não faremos nenhuma
complicação sobre isso. Será apenas um valor booleano
simples, que nos dirá quem será
o próximo jogador. Vamos chamá-lo de
algo como IsxNext. Se for verdade,
definimos o estado como x, caso contrário, será
zero, simples assim. Internamente, podemos
criar um
novo estado e renomeá-lo como isXNext, e as funções de atualização
definem isxNext
e, por padrão,
ele será falso. Como já temos praticamente tudo o
que
precisamos, vamos
modificar essa linha 12. Aqui, retornamos x. Está codificado aqui. Mas, em vez disso,
vamos apenas introduzir outra condição
simples, se não for o caso.
Nós vamos perguntar. Se for xNext, o valor que
associaremos ao quadrado
clicado será X, caso contrário, será zero. Logo após atualizarmos o estado de
setSquare, também
atualizaremos o setISXNext, vamos alterná-lo,
pois é um booleano. Vou chamar setISXNext
e, como precisamos ativá-la e ela ordenará que ela
seja ativada, precisamos saber a alternância
booleana atual, precisamos saber a alternância
booleana atual,
que neste momento é verdadeira ou falsa, e simplesmente a inverteremos. Novamente, vamos usar
a versão
de callback do set state updater. Vamos pressionar o callback. CurrentIsXNext ou
vamos simplificar. Vamos chamá-lo como
P ou prev para o anterior, ou vamos
sem complicações, seja qual for o currentIsXNext. Para alternar esse booleano, só
precisamos aplicar
negação na frente, sem mais nem menos, e pronto. O que ele fará, ele
assumirá o estágio booleano atual. Será verdadeiro ou falso, se for falso, aplicamos
negação ao falso, ela se tornará verdadeira
e, se for verdade, aplicamos negação, ela se
tornará falsa. Basicamente, inverta o booleano e fazemos isso depois de atualizarmos o estado dos quadrados
definidos. Fazemos isso,
voltamos ao nosso aplicativo. Clicamos e agora
temos zero primeiro. Agora clicamos mais, temos o X e vamos direto, e você pode ver que ele está
alternado e invertido, e tudo
funciona conforme o esperado. No entanto, se eu clicar
no quadrado novamente, você poderá ver algo
jogado aqui. O problema é que, quando
clicamos no quadrado, a lógica é executada novamente e
ela atualiza
o quadrado no índice na posição em
que clicamos. O que queremos acrescentar
aqui, outra condição. Se o quadrado já tem valor, se não for nulo, simplesmente
não executamos essa lógica. Aqui estão as
alças internas superiores, clique no quadrado, podemos perguntar se os quadrados ainda, clickedPosition,
o valor é verdadeiro. Valor verdadeiro significa não nulo. Nosso valor quadrado pode
ser nulo, X ou zero. Se esse valor for verdadeiro, significa que não é nulo. Nesse caso, simplesmente
retornamos dessa função. A palavra-chave return
sai da função e não vai
além. Nós o salvamos. Vamos ver, o nosso
vai parecer. Eu clico em quadrados e
tento clicar no quadrado novamente e
nada acontece porque, novamente, ele verifica a condição
e sai da função. Muito legal.
Algo assim, adicionamos um jogador ao nosso jogo. Nosso próximo passo será exibir a
mensagem na parte superior, quem será
o próximo jogador. No entanto, vamos fazer
isso no próximo vídeo. Por enquanto, vamos
comprometer nossas mudanças atuais. Vou nomear esse commit. O que fizemos, vamos revisar. Basicamente, apresentamos
um jogador aqui. Introduziu o jogo a um jogador. Ao clicar em um quadrado, mostre x ou zero. Nós nos comprometemos com isso, implantamos. Eu escrevi errado. Push Origin Master. Só fiz isso porque fiz algo nos bastidores
quando desligo o vídeo. Desculpe-me, você
não deveria ter isso. Vou usar a
primeira bandeira desse jeito, e agora tudo está no GitHub. Por favor, não se importe com essa parte, você não a terá. Ótimo. Nos vemos
no próximo vídeo.
48. 09 Mostrar mensagens do próximo jogador e do vencedor: Oi. No vídeo anterior, conseguimos adicionar a
funcionalidade do jogador ao nosso jogo. Neste vídeo,
continuaremos e
exibiremos a mensagem aqui
no topo da grade,
que diz: o próximo jogador é
e se tivermos um vencedor, mostraremos o vencedor. Neste vídeo,
abordaremos tudo isso mais o cálculo do vencedor. Em primeiro lugar, o que
queremos fazer? Precisamos decidir
o que exatamente
queremos colocar na marcação
da mensagem. O próximo jogador é x ou zero. Bem, queremos fazer
isso dentro do App jsx. Aqui, apenas uma simples tag H2 que
diz que o próximo jogador é,
por enquanto, alguém. Se eu voltar, fica
assim por enquanto. No entanto, já
temos um problema. O que precisamos usar aqui para mostrar quem
será o próximo jogador. Como você pode ver, toda lógica e estado residem dentro do componente da
placa. Isso significa que não está disponível
para o mundo exterior. O único componente
que conhece quadrados, todo o
estado e toda essa lógica é o próprio componente da placa e você pode passar
os dados necessários desse componente para
seus componentes secundários. Por exemplo, como
fazemos com o quadrado. Se quisermos ter
acesso a esse estado ou dados fora da diretoria,
isso é impossível. Temos duas opções aqui. A primeira opção é realmente
mover
a mensagem do próximo jogador dentro do componente do
tabuleiro. Talvez o coloque aqui. Temos todos os dados de que
precisamos no escopo
desta mensagem para que possamos
realmente obter algo dela e, eventualmente,
exibi-la. Temos o próximo jogador, esta
ou a segunda opção é mover parte dessa lógica
para o componente principal. Por exemplo, para o componente do aplicativo
e, em seguida, passe as informações
necessárias para o componente da placa por meio adereços e, em seguida, pause outra informação
necessária para enviar uma mensagem aqui. Se tentarmos visualizá-la, se abrirmos a tinta,
teremos uma imagem como essa. Temos um componente de aplicativo
que renderiza componente
da placa e,
dentro do aplicativo, renderizamos a mensagem. Por enquanto, ele não faz parte do aplicativo, mas ainda faz parte do aplicativo,
não faz parte da placa. O estado é gerenciado aqui
dentro do componente da placa. Como a mensagem
não faz parte do quadro, ela não tem relação com ela. Ela vive como uma folha separada, então isso significa que
é impossível ter acesso ao que
está acontecendo dentro do navio. A primeira opção que
mencionei é tornar a mensagem parte do componente do quadro aqui. Se formos a bordo e
colocarmos uma mensagem aqui, poderemos acessar os dados, que
possamos gerenciá-los aqui. Essa é a primeira opção, mas não vamos fazer isso,
queremos que a mensagem faça
parte do componente do aplicativo. segunda opção é
elevar a lógica, elevar o estado para o
componente pai, que é app, e depois passar os dados necessários
para os componentes correspondentes usando adereços. A lógica ficará dentro do
aplicativo e, em seguida, passamos os dados para a placa por meio de adereços e seguida, passamos outros
dados para a mensagem, novamente usando adereços no futuro. Por enquanto, não é um componente, mas a ideia é a mesma. Compartilhamos dados no componente de
patentes. Abrimos o quadro e, a partir do
quadro, vamos
pegar o estado e
movê-lo para o componente do aplicativo. O mesmo que faremos com
a importação. Vamos colocá-lo dentro do aplicativo e também lidar com o clique quadrado. A partir de agora, ele estará ativo e será gerenciado
dentro do componente do aplicativo. Eu copio isso aqui. Eu o coloquei dentro do
aplicativo. Simples assim. Nós salvamos o tabuleiro, mas você pode
ver que, dentro do tabuleiro, não
temos mais alça de clique
quadrado. Se passarmos o mouse, a raiz
quadrada do identificador não está definida porque nunca foi
criada em nenhum lugar aqui, o mesmo acontece com quadrados. componente da placa agora tem
esses valores indefinidos. Bem, isso significa que precisamos
ter acesso a ele de alguma forma e
faremos isso por meio de adereços. Como agora temos quadrados e manipulamos o quadrado, clique
aqui dentro do aplicativo, podemos passá-los para o componente
da placa com adereços. Vou passar
quadrados aqui desse jeito e lidar com o clique quadrado
exatamente da mesma maneira. Agora, dentro do tabuleiro, posso
aplicar o link
de destruição pegar quadrados e
manipular o clique quadrado. Agora, se eu salvar os dois arquivos, abro meu aplicativo novamente. Tudo funciona como antes, mas agora o estado
vive dentro do aplicativo e todos os dados necessários são passados aos
componentes da placa por meio de adereços. Ótimo. Isso significa que agora
a mensagem que exibimos no componente do aplicativo tem
acesso ao estado. Podemos exibir a mensagem. Nossa lógica será bem simples. Vou criar
uma nova variável aqui e vou te dizer o porquê. Chamamos isso de mensagem ou,
digamos, mensagem de status. Aqui vamos fazer isXNext, retornamos x string, caso contrário, retornaremos zero string e mensagem de
status, já que
ela estiver disponível, nós a
interpolaremos em JavaScript. Vamos dizer que o próximo
jogador é {Mensagem de status}, ou digamos que, em vez
de mensagem de status, vamos chamá-lo de próximo jogador. O próximo jogador é o próximo jogador. Nós o salvamos e temos próximo jogador zero.
Incrível. Nós clicamos. Na verdade, era zero, e você vê que
mudou e
continua e tudo
funciona conforme o esperado. No entanto, você pode
ter uma pergunta: por que exibimos
como uma variável aqui? Por que não criamos oito
estados para isso, talvez? O fato é que esse próximo
jogador é algo chamado estado derivado ou
computado, e por que não criamos outro estado para
isso usando o estado de uso? estado derivado ou computado
é o valor derivado do estado mais recente. Como temos
isXNext como um estado e sabemos que toda
vez que o componente é executado, a lógica interna é executada,
o que significa que essa
linha de código será novamente
em cada renderização de cada
componente. O problema é que quando o
componente é renderizado novamente, o estado é atualizado. Isso significa que, para a renderização
atual, o estado que temos
aqui estará atualizado. É o
estado mais recente que temos. Como essa lógica é executada novamente, ela sempre usará o estado
mais recente aqui isXNext. É por isso que realmente não
precisamos criar outro
estado para isso. Acabamos de criar um valor derivado do
último valor do estado. Bem, pode parecer
um pouco complicado, mas se você pensar bem, não
há nada de
sofisticado nisso. Já temos algum
valor que muda e,
na verdade, derivamos algo
desse valor. Nada mais do que isso. É por isso que não precisamos
criar outro estado de uso, não
faz nenhum
sentido fazer isso. Agora temos a mensagem que diz quem será
o próximo jogador, mas vamos mais longe
e mostrar o vencedor. Sempre que temos um vencedor, gostaríamos de mostrar. O vencedor é esse
cara, o próximo jogador X. Se voltarmos para o convidado que foi compartilhado com
você no início, e se você procurar
por calculatewinner.js, você tem uma função
aqui, calcule o vencedor. Vamos copiar essa função. Vamos voltar ao nosso
aplicativo e, dentro do código-fonte, vamos criar um novo arquivo
e chamá-lo de winner.js. Se você notou,
não nomeamos esse arquivo com a extensão dot.js6 porque esse arquivo não
tem nenhuma marcação js6. É apenas um JavaScript normal. partir daqui, do arquivo js, vamos exportar a
função calculatewinner. O que ele faz, pega
nossa matriz de quadrados, que, novamente, se você se lembrar, é uma matriz em que armazenamos
nossos valores quadrados; nulo, X ou zeros, e a partir dessa
matriz, calcula o vencedor. Se não houver vencedor para quadrados
de algodão, ele retornará nulo. Se houver um vencedor, ele retornará X ou zero, o que ocorre na linha 15. Como isso funciona? Como a função funciona? Aqui temos
uma matriz de linhas definida, que basicamente representa todas as combinações vencedoras possíveis
no jogo tic-tac-toe. Por exemplo, 0, um e 2 é a combinação 0, 1 e 2, portanto, se você
tiver X em uma linha. Você pode verificar todas as
combinações possíveis que você vê aqui. Novamente, é apenas um conjunto de todas as
combinações vencedoras possíveis. Então, o que
fazemos aqui é usar o simple for-loop. E nós os examinamos. Examinamos cada combinação
vencedora. Estou dizendo que é muito simples. Comparamos nossa
matriz atual de quadrados com a combinação
vencedora. Se tivermos essa combinação
vencedora em nosso estado de quadrados e
nossa matriz de quadrados, então apenas retornaremos o vencedor. Aqui usamos a
desestruturação da matriz na linha 13. As linhas na posição dos olhos
representam essa matriz. partir dessa matriz,
empacotamos o primeiro, segundo e terceiro elementos e os chamamos ,
b c. Por exemplo,
para essa matriz , a será zero ,
b será um, dois será c.
Então, usando essa lógica if, vemos se há algum vencedor. Se você está realmente interessado
em saber como isso funciona, tente realmente colocar
os valores nessa fórmula, digamos, você mesmo. Um pouco de lógica aqui. Voltamos ao aplicativo
e podemos fazer isso simplesmente
executando essa função dentro do componente do
aplicativo. Como precisamos passar pelo estado
quadrado e calcular, o vencedor
produzirá como vencedor. Não precisamos
criar outro estado. Essa variável vencedora que
temos será,
novamente, o estado
derivado do estado quadrado. Eu vou seguir em frente aqui,
talvez ainda por cima, eu vou
criar a variável vencedora. O que vou fazer é
importar o calculatewinner. Isso se chama export, então eu o importo com
colchetes do vencedor. Eu chamo essa função aqui e por dentro eu passo
nosso estado quadrado. Eu terei um vencedor aqui. Vamos tentar fazer o registro
e ver o que temos. Eu abro o console. Dentro do console, eu tenho nulo porque, bem, não
temos nenhum vencedor. Quando eu
jogo, nulo, nulo. Vamos criar um vencedor. Se eu clicar aqui agora, terei a combinação
vencedora, e você verá que ela produz zero
aqui, porque agora, bem, temos um vencedor, que é zero. Nesse caso, precisamos
exibir. Vamos em frente. Já temos o próximo
jogador, é o próximo jogador, mas vamos
modificar um pouco essa mensagem. Ou talvez não a toquemos. Aqui, vamos
criar outra variável que chamaremos de
mensagem de status neste momento. Aqui, vamos
perguntar se temos vencedor, então vamos dizer, vencedor é vencedor, a variável que temos. No entanto, precisamos usar o modelo de
string aqui para
aplicar a interpolação de strings. Vou transformar essa
string em um modelo de string substituindo
aspas singulares regulares por marcas invertidas. Isso me permitirá
usar a interpolação
usando o cifrão
e os colchetes, então o vencedor é o vencedor. Caso contrário, se
não
tivermos nenhum vencedor, usaremos a próxima mensagem de jogador que já
temos aqui. Em vez de mostrar que o próximo
jogador é o próximo jogador, desta vez vamos mostrar
apenas a mensagem de
status. Eu escrevi errado. Será uma mensagem de
status. Agora, vamos
ver o que temos aqui? Então, temos apenas o próximo jogador,
o próximo jogador. Eu entendo. Em vez disso, precisamos dizer que o
próximo jogador é o próximo jogador. Se voltarmos, o
próximo jogador é zero. Vamos jogar o jogo. Vamos criar um vencedor. Agora vemos a
mensagem: o vencedor é X. Ótimo porque temos um vencedor. Legal. No entanto,
aqui está um problema. Se você tentar jogar o
jogo, se continuar, ainda
podemos clicar em quadrados, mas isso pode ser facilmente corrigido. Já temos a lógica
para sair da função se
clicarmos no mesmo quadrado duas ou três vezes apenas
várias vezes. Aqui, vamos apenas estender essa condição e
contaremos. Se clicarmos no mesmo quadrado duas vezes ou se
tivermos o vencedor, sairemos da função. Tão simples quanto isso. Vamos tentar. Eu joguei o jogo. Nós temos o vencedor agora. Se eu clicar em qualquer um dos quadrados, não
executarei nenhuma lógica porque saímos daqui porque isso produz
talvez falso, talvez verdadeiro, não importa, mas aqui definitivamente
é verdadeiro. Temos a condição de saída. Simples assim, estamos quase
terminando nosso jogo. A única funcionalidade
que adicionaremos aqui
será o histórico do jogo. Poderemos navegar
pela história do jogo. Vamos acompanhar
nossos movimentos que
fizemos e poderemos
viajar entre eles, mas vamos gerenciar
isso no próximo vídeo. Por enquanto, essas
mudanças são suficientes. Na verdade,
vamos colocá-los no Git porque apresentaremos
muitas coisas diferentes aqui. Vou abrir o terminal, adicionar
tudo ao palco
e nomear todas essas mudanças como,
vamos ver, vamos ver, uma visão geral. Primeiro, retiramos
o estado do conselho. Ele apareceu dentro do componente do aplicativo e depois exibimos
o vencedor. Bem, isso é muito. Vamos contar,
elevar o estado para o componente do
aplicativo e mostrar a mensagem de
status para o usuário. Sem mensagem de status para o
usuário, calcule o vencedor. Não vamos complicar
com as mensagens. Acho que isso será suficiente. Eventualmente, implante
tudo no GitHub. Nessa nota profunda, vamos adicionar este vídeo. Te vejo na próxima.
49. 10 Mostrando o desenho do jogo: Olá. Neste vídeo, continuaremos
falando sobre, na verdade, as mensagens que exibimos
para o usuário aqui. O único ponto que
perdemos no vídeo
anterior, em que
exibimos a mensagem de status, é o sorteio do jogo. E se terminarmos o jogo, mas eventualmente não tivermos
nenhum vencedor? Nesse caso, gostaríamos mostrar outra mensagem
ao usuário dizendo que, digamos, x e zero empatados, então há um empate. Para fazer isso, precisamos aplicar
mais lógica aqui. Mas vamos
fazer isso dentro um componente que
vamos criar
especificamente para a mensagem de status. Dentro dos componentes,
vou criar um novo arquivo, que
chamarei de mensagem de status. Esse será
o novo componente. A partir daqui, vou
criar um componente de
mensagem de status de exportação. Mensagem de status. Assim por enquanto, será um div,
que diz olá. Além disso, preciso
exportá-lo daqui. Então, dentro do App JSX, vou importar quadrados
de componentes quadrados. Opa, desculpe-me, não uma mensagem de status quadrada. Então, aqui, em vez da mensagem de status
H2, vamos exibir o componente da mensagem de status
assim. Então, removemos isso. Agora, a
mensagem de status deve
estar em algum lugar dentro do componente da mensagem de
status. No entanto, não
temos nenhum dado aqui, é por isso
que novamente
usaremos adereços para passar todos os dados necessários
para o componente de mensagem de status. Temos a próxima camada e mensagem de
status aqui, que a moverá diretamente para o componente de mensagem de
status. Não temos ISXNext e não temos
nenhum vencedor aqui. É por isso que
esperamos que o vencedor seja aprovado e o
ISXNext seja aprovado. O cálculo do vencedor
é feito aqui. No entanto, o fato
é que também
precisamos detectar quando não temos quadrados vazios e não
temos um vencedor? Precisamos escrever essa lógica. Para exibir o sorteio, precisamos saber
se todos os quadrados estão ocupados com alguma coisa e ainda
não temos um vencedor, para obter esse valor, aquele booleano
que indica que precisamos
acessar nosso estado de
quadrados novamente. precisaremos dele na mensagem de
status. Vamos passá-lo aqui também. Teremos o vencedor, ISXNext e os quadrados ficarão aqui. Passe tudo como adereços. Então, aqui,
quando eu renderizo um componente de mensagem de
status ,
vou passar o vencedor , vou passar isxNext e vou passar quadrados. Ótimo. Agora, aqui vamos usar algo chamado renderização condicional. Bem, na verdade você
não sabe disso, mas já aplicamos renderização
condicional
aqui na linha 3-5. renderização condicional é simplesmente exibir algo
com base na condição. Por exemplo, aqui, se eu abrir colchetes dentro do JSX e
escrever, digamos, uma condição simples,
cinco é menor que 10. Nesse caso,
exiba div, que diz cinco a menos que 10. Caso contrário, exiba outro div que diga outra coisa. O que você vê aqui é chamado de renderização
condicional. É basicamente isso
que fazemos aqui. Em vez de simplesmente
usar strings aqui, podemos escrever uma marcação JSX, assim mesmo, e tudo eventualmente ficará
assim. Mas não precisamos de marcação JSX, precisamos de cadeias de caracteres simples, então mantemos isso assim. Agora, que tal desenhar? Qual é a lógica
para exibir o sorteio? Precisamos saber que temos todos os quadrados ocupados no grid
e não temos vencedor. Para obter o booleano que indica
se não
temos quadrados livres
no quadro, criaremos
outra variável porque, novamente,
será um estado derivado. Vamos dizer que
não há mais movimentos. Serão quadrados. Cada
método é o método que pode ser chamado de apagar. Ele retornará
verdadeiro ou falso. Nós repassamos a chamada para todos. Esse retorno de chamada é executado para cada elemento dentro da matriz de
quadrados. Se cada retorno de chamada, se para cada elemento o
retorno de chamada retornar verdadeiro,
então, eventualmente, o
valor final será verdadeiro. Se pelo menos um
retorno de chamada retornar
false, o valor final
será falso. Esse é basicamente o nome de cada. O callback tem exatamente
os
mesmos argumentos do método map. Primeiro, temos o elemento
que
será o valor quadrado no nosso caso. Isso é suficiente, não precisamos de índice e não
precisamos da matriz em si. Simplesmente verificamos se o
valor quadrado não é igual a nulo. Nós verificamos isso. Se todo
valor não for igual a nulo, toda
a condição
retornará verdadeira. Se pelo menos uma raiz
quadrada não
for nula, toda a estrutura,
toda a condição, retornará false. Isso é exatamente o que
estamos procurando. Agora, simplesmente vamos
e temos o div, e podemos aplicar várias
condições aqui. Se tivermos um vencedor
, poderemos mostrar algo. Aqui está o truque: como
também podemos aplicar a
renderização condicional. Se tivermos um vencedor, podemos usar uma
extremidade lógica e, em seguida, podemos exibir qualquer
JSX que quisermos. Isso também é
renderização condicional e é uma alternativa para escrever isso. Se tivermos um vencedor, mostre isso, caso contrário
, exiba nulo. Se você se lembrar, nulo será avaliado como nada e eventualmente, nada
será exibido, mas pode ser entediante
escrever isso todas as vezes, é por isso
que as pessoas geralmente escolhem essa maneira de escrever as coisas. Mas você precisa ter cuidado. Essa coisa aqui, quando você
verifica a condição, deve
ser um valor booleano. Se não
for um valor booleano , mas for
algo verdadeiro,
por exemplo, como zero, ele exibirá zero. Zero é
considerado um valor falso, mas não é um booleano. Portanto, a forma como o
operador and funciona, somente quando essa condição
retorna exatamente falsa. Precisamos ter certeza de que esse valor seja
booleano se você quiser usar essa abordagem
com um fim lógico. No nosso caso,
o vencedor já é um booleano, então não precisamos fazer isso. No futuro, você
definitivamente se
deparará com essa situação, quando
se lembrar disso, especialmente quando
for lidar com uma corrida e dados
provenientes de APIs. Nossa lógica é
ser a seguinte. Se tivermos um vencedor, queremos mostrar o
vencedor como vencedor. Vou apenas
copiá-lo e colocá-lo aqui. Então, podemos aplicar outra
renderização condicional aqui e dizer que, se não
tivermos um vencedor e não tivermos nenhum movimento
, podemos exibir outra
coisa. Se eu salvá-lo, ele
será formatado automaticamente. Vamos acabar com uma
estrutura como essa. Então, teremos outra
condição quando não tivermos um vencedor e
não tivermos nenhum nodo
se movendo para a esquerda. Mas essa coisa não parece feia, mas pode ser muito impraticável e às vezes
muito difícil de ler. Em vez de fazer isso, podemos escrevê-lo de uma forma
mais legível. Então, se você se lembra do que
fizemos no componente da placa, criamos a função quadrada do
renderizador a partir da qual retornamos a marcação JSX. Aqui, podemos aplicar exatamente
a mesma abordagem e escrever as condições para renderização condicional
dentro dessa função. Aqui vamos contar. Algo como renderiza uma mensagem de
status, ok? Essa função não
aceitará nada como
argumento porque, bem, não lidamos com
nenhum argumento aqui. Temos acesso a todos os dados que temos
no escopo superior. Aqui, vamos apenas perguntar. Se tivermos um vencedor
dessa função, retornaremos
vencedor é vencedor. Então vamos
perguntar se não temos
vencedor e não temos mais jogadas, isso significa que temos
um empate, nesse caso, exibimos zero e x de altura. Caso contrário, tecnicamente, podemos adicionar outra condição, como se não
tivéssemos um vencedor e não tivéssemos mais movimentos nesse caso, os jogos
continuam e mostramos próximo jogador é o próximo
jogador, desse jeito. No entanto, podemos torná-la como uma declaração de retorno padrão dessa função, porque
não faz nenhum sentido
aplicá-la se, porque esta é a última e definitivamente, ela será acionada somente quando essas duas falharem, então não precisamos realmente
verificá-la aqui ou podemos fazer isso, vamos continuar assim, vamos verificar essa
condição e em No final se não tivermos nenhuma condição que
nos satisfaça, nesse caso não
retornaremos nada caso algo dê errado para nós. No entanto, isso nunca acontecerá. Vamos embrulhá-lo em div. O próximo jogador será
o próximo jogador, não
precisamos de nenhum cifrão,
na verdade não precisamos mais de nada disso,
temos apenas uma mensagem de
status de renderização e, temos apenas uma mensagem de
status de renderização e em vez de toda essa construção
estranha, podemos simplesmente chamar a função de mensagem de
status de renderização. Agora, parece muito mais
legível, não é? Voltamos ao nosso jogo e
vemos que o próximo jogador é, o que é correto, vamos criar
um vencedor e tudo funciona conforme esperado, mas
vamos mais longe e na verdade, não temos nenhum vencedor
aqui, bem, isso é difícil. Isso não é difícil,
então, como você pode ver agora, todos os quadrados estão ocupados
com alguma coisa, mas você não tem nenhum vencedor e, eventualmente,
temos zero e x empatados, exatamente o que estávamos
fazendo, o que é ótimo. Agora, vamos estilizar
isso porque você pode ver que temos esses arquivos de estilos
aqui desde o início,
mas não fizemos muito sobre isso porque estávamos ocupados com
toda essa funcionalidade, então vamos seguir em frente e estilizar essa mensagem de status porque já
temos nossos estilos aqui. Se olharmos de
perto a história, lidaremos com
isso no futuro Temos a
classe de mensagem de status definida aqui, incrível, então vamos para a mensagem de
status aqui e para
esse elemento de encapsulamento para div. Vamos adicionar uma mensagem de status do
nome da classe, se salvarmos, já
temos essa, temos margem, talvez vamos
transformá-la em elemento H2, como era antes, mas na verdade nada realmente
mudará porque
temos o tamanho da fonte, que está definido aqui, ótimo. Agora vamos adicionar algo aqui porque,
como você pode ver, os elementos de extensão que aparecem como uma mensagem de status também
têm um peso de fonte normal, provavelmente eu pretendia
que fosse essa tag H2. Também temos classes aqui, texto verde e textos laranja, que podemos aplicar aos
nossos jogadores x e zero, então o que eu vou fazer é fazer assim, então, para esses zero e
x que temos aqui,
podemos envolvê-los em
elementos de extensão como esse, e a esse elemento de extensão, podemos realmente adicionar vantagens. X vai ser verde e
zero vai ser laranja, então adicionamos as tags verdes para x, para zero vamos adicionar
mais o nome do texto laranja, agora parece
assim, muito legal. Em seguida,
o que precisamos
fazer é, de alguma forma, condicionalmente, quando tivermos o próximo jogador, aplicar estilos condicionalmente. Bem, isso é algo novo sobre o qual ainda não falamos, então precisamos de alguma forma aplicar
condicionalmente as classes. Novamente, vamos
agrupar o próximo jogador em espaço e
exibir o próximo jogador aqui, mas agora também precisamos aplicar classes
dinamicamente
com base no player,
então, para abranger, vamos passar o nome da classe e, em vez de apenas
passar a string, vamos passar a expressão
JavaScript,
então, novamente, vamos
usar colchetes e aqui
estamos vou perguntar. Se for o Xnext, neste caso, aplicaremos a
classe verde de textos , caso contrário, aplicaremos
a classe laranja de texto,
então, como é um JavaScript, você pode usar qualquer método
disponível para alguma forma transformar,
aplicar, combinar, concatenar a string
e, eventualmente, ela será avaliada como a
string do nome da classe aqui, então vamos ver. próxima camada
é zero e, na verdade,
é laranja e,
à medida que jogamos, você pode ver as
mudanças de cor e as cores funcionarem, que funciona de forma incrível. Então, no final, também
temos o vencedor como vencedor,
então, a mesma lógica aqui, vamos aplicar ao vencedor. O vencedor é o vencedor, mas aqui desta vez
vamos perguntar se o vencedor igual a x, só então
usamos as tags verde, caso contrário, texto, laranja vamos verificar rapidamente, ótimo, o vencedor é x. Talvez uma coisa que
possamos adicionar aqui e que possa ser
útil para o futuro e para nós agora é que
você pode ver agora sempre quisermos exibir algo, é sempre envolto
em um elemento, neste caso na tag H2, em div, mas e se
eu quiser não descartar, não exibir nenhum div aqui? E se eu quiser apenas
exibir o vencedor é, como acontece com a tag
span, sem
agrupá-la em uma div,
porque se você abrir a marcação, ela é encapsulada na div, se eu não quiser fazer isso? Eu só quero mostrar que o vencedor é e span sem qualquer div, como diretamente dentro de H2. Nesse caso,
podemos usar algo chamado fragmentos do React, então o fragmento do React é basicamente
apenas um elemento vazio, então se eu remover o div e
digitar React.fragment, importar o React do
react porque agora usamos namespace
React é
basicamente um componente, mas é como um
componente vazio, apenas um espaço reservado. Se eu vou usar o
fragmento React em todos os lugares aqui, eu atualizo a página, jogo,
abro a marcação, aqui você vê que nada renderizado, exceto que o
vencedor é, desculpe-me, exceto que o próximo jogador está no espaço, eu não tinha nenhum elemento de
embalagem. Novamente, o fragmento do React representa
basicamente um elemento vazio,
mas o fragmento do React é uma
sintaxe muito ampla e é bom saber que
você sempre pode usá-lo,
no entanto, o fragmento do React tem uma sintaxe
mais leve. Se você removê-lo e manter
seus colchetes vazios, desse
jeito, esta é uma
versão curta do fragmento do React. Podemos remover o
namespace React
daqui e remover
fragmentos do React em todos os lugares, e apenas manter colchetes vazios
assim e funcionará, então isso também é um fragmento de reação, mas essa é uma sintaxe curta sem
dizer explicitamente React.fragment, sinta-se à vontade para usar qualquer um, eu prefiro usar essa sintaxe, menos código, melhor. Agora, terminamos definitivamente com as mensagens de
status, então vamos confirmar
nossas mensagens, desculpe-me,
confirme nossas alterações porque bem, fizemos muita coisa, falamos sobre renderização
condicional,
falamos sobre estilos condicionais,
estilos dinâmicos, nomes
dinâmicos de classes e
também exibimos a mensagem de
desenho, ótimo. Agora, eu já adicionei tudo
ao estado do stitch, desta vez vamos usar a interface
de usuário do VSCode, então eu clico no sinal de “mais”
aqui para organizar todas as alterações, agora elas estão todas em estágio e
podemos digitar uma mensagem
aqui e pressionar commit, mas eu prefiro
selecionar tudo manualmente, mas quero que seja preparado e seguida, digitar manualmente git
commit e determine. A mensagem de confirmação será essa jogada ou, sim, exibir mensagem de desenho, aplicar estilos ou componente
de
mensagem de status e pronto. No próximo vídeo,
começaremos com a história do jogo, falaremos sobre como
podemos realmente introduzir esse recurso da história do jogo
que podemos percorrer Isso vai ser
divertido. Nos vemos lá.
50. 11 Implementando histórico de jogos: Olá. Neste vídeo, falaremos
sobre a história dos jogos. No último vídeo,
falamos sobre o game draw para
exibir as mensagens
que aparecem aqui na parte superior. próximo jogador é:
temos um vencedor, temos um empate, o que é incrível, mas desta vez
vamos falar sobre história dos
jogos para
podermos clicar em qualquer jogada que fizemos e depois percorrer a história. Para conseguir isso, precisamos
realmente transformar nosso estado. Da forma como
gerenciamos atualmente um estado de jogo, fazemos isso usando quadrados
e estados isxNext. Tudo bem e
continuaremos gerenciando isso dessa maneira. No entanto,
mudaremos um pouco sua forma. Como a história é algo que precisamos lembrar porque seremos
capazes de atravessá-la, precisamos transformá-la de
alguma forma em uma matriz. Deixe-me abrir o Paint e mostrar exatamente
como vamos
representar o estado dos jogos. Por ser uma história, será uma série de elementos. Será uma matriz
e dentro dessa matriz, cada elemento será um objeto. Será basicamente uma matriz de objetos e cada objeto
nessa matriz terá duas
chaves, quadrados e isXNext. Cada objeto nessa
matriz representará o estado do tabuleiro de
jogo
no momento de nossa mudança. Para acompanhar os movimentos
que fazemos no jogo, nosso CurrentMove,
precisamos de um contador. Precisamos de alguma forma rastrear qual é o nosso CurrentMove para
que possamos viajar
nessa história. Se clicarmos em um item do histórico, digamos que vá para o Movimento Número 1, na verdade
iremos
para o Movimento Número 1 e nosso CurrentMove
será alterado. Para isso, precisamos de outro
estado para rastrear isso. Vamos ver como isso vai
parecer na realidade. Aqui na parte superior do aplicativo, vou criar um novo estado, que chamaremos de
histórico e setHistory, e isso precisa ser uma matriz. Por padrão, já temos um estado de
jogo vazio, assim como temos
aqui nas linhas 11 e 12. Vamos criar
uma matriz vazia com um objeto dentro
e, por padrão,
serão quadrados, que serão uma matriz de nove elementos preenchidos com nulos, e então isxNext será falso, assim como temos aqui. Podemos remover isso com segurança. Em seguida,
criaremos outro estado que representará nosso CurrentMove. Vamos em frente. Criamos currentMove
e setCurrentMove. Por padrão, nosso
CurrentMove será zero. Nosso contador será baseado em zero. Ótimo. Agora podemos ver que, como mudamos tudo, temos muitos erros aqui. Vamos mudar isso.
Como podemos obter estado
mais recente do tabuleiro de jogo que temos aqui? Podemos criar outra
variável que será nosso valor derivado dos estados history
e currentMove. Podemos chamá-lo,
digamos, de GamingBoard. Isso vai ser história
e nosso CurrentMove. Na verdade, ele nos
dará esse objeto para nosso CurrentMove. Agora, em vez de analisar
apenas quadrados aqui, vamos passar
Gamingboard.squares. Você pode ver que eu até tenho
o IntelliSense para isso. Incrível. Agora, handleSquareClick, vamos tocar
nisso em um segundo. Vamos para a mensagem de status aqui. No momento, analisamos dois
adereços, isXNext e squares. Agora tudo está combinado
em um único objeto. Podemos simplesmente passar o
objeto para a mensagem de status. O que vou fazer é analisar GamingBoard diretamente
para a mensagem de status. Vou remover
esses dois adereços. Vou abrir a mensagem
de status aqui. Agora, como eu analiso o GamingBoard, em vez de desestruturar o
isXNext e os quadrados, farei o GamingBoard. Vou desestruturar o
GamingBoard aqui. Agora, preciso digitar
GamingBoard.squares, GamingBoard.isxNext, e aqui também,
GamingBoard.isxNext. Mas, em vez disso, o que
farei, já GamingBoard é apenas um
objeto com duas chaves, quadrados e isxNext, vou aplicar outra
desestruturação aqui. O que vou fazer com o objeto
GamingBoard desestruturar quadrados e isXNext.
Um lembrete rápido. Isso é o mesmo. Essa única linha nos
substitui
sempre por escrever GamingBoard.squares
assim GamingBoard.squares
assim e GamingBoard.isxNext. Incrível. Lidamos
com a mensagem de status. Vamos lidar com
todo o resto. Para embarcar, analisamos quadrados. Agora temos GamingBoard.squares
e agora, de alguma forma, precisamos
lidar com HandleSquareClick. Bem, a lógica é que temos história e sempre que
criamos uma nova jogada, sempre que
jogamos, precisamos ampliar nossa matriz. Precisamos adicionar novos
valores a essa matriz. Dentro do HandleSquareClick,
vamos fazer isso. Primeiro, agora temos
GamingBoard.squares aqui. Então, em vez de definir quadrados, vamos fazer setHistory e voltaremos a
essa lógica em um segundo. Em vez de setisXNext, o que vamos fazer? Vamos apenas
incrementar nosso CurrentMove. Sempre que clicarmos em um quadrado, o movimento, o contador
será incrementado. Por isso, se você se lembra nosso exemplo de
vídeos anteriores sobre contador, esse é exatamente o caso. CurrentMove, e podemos
chamá-lo de currentMove inside. No entanto, já temos
esse nome aqui como nosso estado, então vamos simplesmente
chamá-lo de move. O movimento será movimento mais 1. Vamos apenas
incrementá-lo novamente. Move representará nosso estado atual
para CurrentMove. Dentro do SetHistory, em vez
de currentSquares, vamos
chamá-lo de CurrentHistory, e agora precisamos
estender o histórico de alguma forma. Em primeiro lugar, precisamos conhecer
nosso estado de jogo mais recente. Para fazer isso,
precisamos pegar o elemento mais recente da matriz
do histórico. Podemos fazer isso digitando. Talvez digamos que a variável lastGamingState será história, e vamos pegar
o último elemento
fazendo history.length menos 1. Dessa maneira, podemos pegar elemento
mais recente
da matriz histórica, que novamente será
um objeto dessa forma. Agora, o que
podemos fazer é calcular um novo estado que vamos adicionar
à matriz do histórico. Já temos a lógica aqui. Em vez de retornar,
vamos colocá-lo em uma nova variável chamada
nextGamingState. Em vez de currentSquares, vamos usar
LastGamingState.squares
e, em vez de isXNext, vamos fazer
LastGamingState.isxNext. Agora, para definir o novo
valor para o estado do histórico, precisamos retornar desse retorno
de chamada. A partir desse retorno de chamada,
o que vamos fazer, vamos concatenar
o que acabamos de criar aqui, NextGamingState, com nosso estado histórico
atual. Podemos usar o
método array.concat para isso. CurrentHistory.concat
e vamos apresentar um novo objeto aqui. Precisamos analisar um
objeto dessa forma. Squares
será o NextGamingState. Nós o chamamos de NextGamingState, vamos chamá-lo de NextSquaresState. Vamos
analisá-lo assim. IsXNext será,
novamente, o inverso de um
booleano, como fizemos antes, mas desta vez
vamos nos referir
ao nosso LatestGamingState que
temos aqui, então
LatestGamingState.isxNext. Vamos aplicar a
negação para inverter o booleano e agora tudo
funcionará magicamente. Vamos voltar
aqui e experimentar o histórico de registros do console
e o CurrentMove, ambos, para ver o que realmente
está acontecendo. Vamos ao
histórico de registros do console e ao CurrentMove. A propósito, estou registrando
os dois no console dentro do objeto. Só estou fazendo isso para
minha preferência pessoal. Dessa forma, é mais
fácil visualizá-los no console. Não há nenhuma
razão especial por trás disso. Você pode
registrá-los no console
desse jeito , um após o outro. Mas se você
os registrar no console como um objeto, é mais fácil visualizá-los. Voltamos ao
jogo, inspecionamos, vemos o console, abrimos esse objeto. Temos currentMove, zero, temos histórico,
que é uma matriz. primeiro elemento é esse objeto
com quadrados de nulos. Agora, vamos jogar
o jogo e ver como isso muda. Eu clico em algum lugar várias
vezes e, se eu os abrir, você pode ver que nosso próximo
movimento, o índice
CurrentMove aumentou e cada movimento seguinte, o
índice aumenta. Cresce. Inicialmente, era apenas uma matriz de nulos
dentro do primeiro elemento, depois jogamos o jogo, adicionamos isso à matriz do histórico, depois
jogamos novamente, adicionamos mais
elementos à história,
então, dessa forma, podemos rastreá-la. Agora, a questão é: como
podemos realmente exibi-lo? Como temos uma matriz, é muito fácil de fazer. Se voltarmos ao componente
do aplicativo, aqui precisamos
exibi-lo de alguma forma. O que eu sugiro é criar outro
componente dentro da pasta do componente, que chamaremos
de histórico. Esse será o componente da história de
Yan. Vamos exportá-lo por
padrão do histórico JSX. Por enquanto, será
apenas uma função vazia. Dentro do aplicativo, vou importar o histórico do histórico dos componentes. Vou rolar para baixo
e renderizar o componente histórico
abaixo do quadro. Eu o salvo e, agora,
dentro da história, queremos exibir de alguma forma todas
as etapas que fizemos. Na realidade,
parece assim. Quando você tem uma
matriz de elementos, geralmente
deseja que cada elemento represente algo
na marcação. Por exemplo, se tivermos uma lista de frutas representada
como uma matriz, digamos maçã ,
kiwi e
outra coisa em reação, geralmente
é assim. Você pega uma matriz de
elementos e mapeia cada elemento da matriz
para a marcação JSX. Essa string de maçã se
transforma em div, que exibe
essa string de maçã, e o mesmo para o
resto dos elementos. Para o componente de história, vamos passar nossa matriz
histórica como suporte histórico. Dentro da história, podemos sustentá-la usando a distração
do objeto adereço. A partir do componente,
retornaremos à marcação JSX, os elementos de encapsulamento
serão div e usaremos um elemento de lista
ordenada para isso. Aqui, precisamos mapear cada elemento de matriz em nosso
histórico para a marcação JSX. Vou abrir
colchetes para interpolar o JavaScript no JSX. Eu vou fazer history.map. Agora, sem nenhuma lógica
extra por enquanto, que exibirá div,
então, a partir de d.mapcallback, estou retornando também a marcação JSX
e estou dizendo olá aqui. Não importa a mensagem vermelha agora, podemos anexá-la em um segundo. Vamos salvá-lo e
ver o que temos. Nós temos olá. Jogamos o jogo
e você pode ver que
cada
elemento da nossa matriz está, e você pode ver que na verdade, mapeado para a
div correspondente dentro do HTML. Como temos seis elementos, cada elemento foi mapeado
para a div aqui. A propósito, acabei de perceber que também temos algo
errado porque
exibimos apenas aqueles
aqui. Vamos ver. De alguma forma, mudei a lógica. Vamos verificar rapidamente
se funciona. Ótimo. Eu estava falando que cada elemento da matriz é mapeado
para a div correspondente. Fizemos isso usando o
método.map. No entanto, você já percebeu que há um aviso
dentro do console
e, se eu passar o mouse aqui,
será o mesmo, faltando o adereço de chave para o
elemento no iterador. O problema é que quando
você usa.map dentro da marcação
JSX para mapear o elemento da
matriz para o JSX, você precisa sempre passar a propriedade chave para os
elementos JSX que estão sendo mapeados. A razão para isso
é porque o react precisa
acompanhar internamente cada elemento que você mapeou para a marcação
JSX, caso ele
seja alterado no futuro. A razão por trás disso é
que, como essa matriz é dinâmica, cada elemento JSX mapeado dentro dessa matriz deve ser representado de
forma exclusiva. Para ajudar a reagir
com representação
exclusiva, identificar de forma exclusiva
cada elemento da matriz, precisamos passar o
prop chave e o suporte chave deve ser exclusivo para cada elemento. No nosso caso, cada
elemento da matriz é um objeto, quadrados e chaves isNext, então não temos
nada de especial aqui. O que podemos fazer em casos simples simplesmente passar um índice de elemento de
matriz como chave porque ele
será exclusivo para cada elemento, porque para o primeiro
elemento será zero, para o segundo, um e assim por diante. Ele identificará de forma exclusiva o
elemento dentro dessa matriz. Será suficiente
para o nosso caso. Vamos pegar
esse índice aqui. Primeiro, temos o objeto, com os quadrados e isNext. Não precisamos disso, mas ainda assim, precisamos defini-lo
porque, caso contrário, não
poderemos
pegar o índice, que é o
segundo argumento. Como não
vamos usar objeto, que vai
chamá-lo de sublinhado, e vamos pegar o índice. Para a chave, vamos passar o
índice desse jeito. Se eu salvar, se eu atualizar, você pode ver que agora tudo
permaneceu o mesmo, mas não temos mais
problemas com a chave, porque agora cada elemento dentro da matriz é identificado de
forma exclusiva. Agora temos o índice aqui
e, na verdade, também podemos
interpelá-lo dentro do div e podemos
exibir esse índice. O que podemos dizer
aqui é que o movimento é o índice. Vamos ver, o que temos? Temos que o movimento é um, o
movimento é 2, 3 e 4. Ótimo. Parece
muito bom até agora, mas antes de tudo, não
queremos
mostrar que o movimento é zero. Queremos exibir algo como um novo jogo ou
iniciá-lo. Vamos aplicar a renderização
condicional aqui. Em vez de fazer isso,
vamos perguntar se o índice é igual a 0, então vamos exibir
texto de um novo jogo como este. Caso contrário,
abriremos os backticks e
diremos:
vá para mover a hashtag. Aqui, exibiremos o índice. Vamos ver como isso fica. Se eu atualizar a página, teremos um novo jogo por padrão. Se eu jogar, você pode ver que agora temos uma saída
muito mais limpa. No entanto, em vez de um novo jogo, talvez digamos assim, vá para o início do jogo. Na verdade, você pode ver que eles não
são nem um pouco clicáveis. Vamos converter esse div em
elemento de botão do tipo um botão, eu o salvo e agora
você vê que ele está quebrado. No entanto, se você se lembra, temos nossos estilos
em styles.css. Para essa história, podemos realmente aplicar esse conjunto de classes que
já estão escritas aqui. Primeiro, temos history-wrapper, que podemos atribuir ao
div history-wrapper. Então, temos a própria história. Este será nosso histórico de listas
não ordenadas. Então, dentro da história, cada elemento
li será estilizado. Bem, na verdade, certo, porque esquecemos
que tem que ser um elemento li. Em vez de botão,
vamos
digitar li aqui e
moveremos esse botão para dentro. Ainda temos essa
mensagem para a chave, porque eu disse que a
chave deve ser atribuída, deve ser passada somente para
o elemento de encapsulamento. O botão está dentro desse elemento. O elemento em si é uma mentira. Preciso passar a chave para o
elemento li. Agora eu o guardo. Também temos a classe
btn-move aqui. Podemos dar a esse botão
className btn-move. Vamos ver o resultado. Parece muito bom até agora. Você pode ver que parece
muito, muito melhor. Mas o fato é que
não podemos fazer nada agora. Precisamos de alguma forma adicionar
o recurso de travessia. A lógica, onde
vamos fazer isso será colocada
dentro do App jsx. Já temos o estado
CurrentMove, que representa em qual
etapa estamos atualmente. Aqui dentro, podemos criar uma função que
mudará nosso CurrentMove. Vamos chamar
essa função de moveTo. Esse MoveTo
espera um argumento. Vamos chamar isso de movimento.
O que isso vai fazer? Isso apenas atualizará o estado da mudança
que está sendo aprovada. Sempre que
os chamamos de MoveTo, nós, digamos cinco, ele
definirá MoveTo cinco. Agora vamos
passar essa função moveTo para a história como um adereço como esse. Dentro da história,
vamos pegar o MoveTo. Aqui, podemos anexar esse
MoveTo ao evento onclick. Para esse elemento de botão, vamos especificar o manipulador de eventos
onclick. Vamos passar
uma função que
chamará moveTo com o
índice desse movimento. Algo parecido com isso. Eu o guardo. Eu atualizo a página. Vamos jogar o jogo.
Temos vários movimentos aqui. Sempre que clico aqui, tenho que MoveTo não é
uma função,
porque eu novamente
não salvei o App jsx. Vamos tentar novamente. Eu jogo, clico em “Moves”
e você pode ver o estado do jogo
realmente muda. Funciona conforme o esperado. Mas, para torná-lo mais
fácil de usar, vamos destacar nossa mudança atual em que estamos atualmente. Voltamos ao código
e, aqui na história, podemos aplicar
classes dinâmicas novamente. Se examinarmos os estilos internos, temos uma classe ativa aqui que
pode ser dada ao btn-move. Já temos a classe btn-move, mas ela é estática
para todos os elementos. Agora, vamos
abrir colchetes. Vamos passar o
btn-move aqui. Vamos transformar
essa string em um modelo de
string para que possamos
aplicar a interpolação de strings, que nos dará a capacidade usar JavaScript
dentro dessa string. Aqui, vamos
fazer uma lógica muito simples. Se index ou, digamos, se
currentMove
for igual
a index, esse elemento estará ativo e esses
blocos serão aplicados. Vamos dar uma aula
ativa, caso contrário, vamos
dar uma aula vazia. Mas não temos currentMove aqui, então teremos que
recebê-lo corretamente novamente
e dentro do App jsx. Vou passar nosso
CurrentMove aqui em cima. currentMove é
igual a currentMove. Algo parecido.
Vamos economizar e ver. Bem, agora, na verdade está
sendo transformado em verde. Vamos inspecionar a marcação HTML. Temos btn-move
e temos uma classe ativa. Exatamente o que escrevemos
porque o índice do primeiro elemento é zero e
currentMove é zero por padrão, esse é nosso estado inicial. Jogamos o jogo e você pode ver como o className muda e o elemento mais recente sempre
tem uma classe ativa por padrão. Mas quando clicamos
em “Histórico” para percorrê-lo, você pode ver como o className
muda. Muito legal. Algo parecido. No entanto, vamos tentar jogar o jogo. Faça uma jogada e depois
continue jogando. Você pode ver que algumas
coisas estranhas estão acontecendo aqui. O problema é que nosso estado de
jogo não está sincronizado com a mudança para a qual
voltamos. Isso é problemático. O que queremos fazer
sempre que estivermos viajando pela história e, se
clicarmos no quadrado, queremos sobrescrever
o histórico. Agora, precisamos adicionar outra peça de lógica
aqui para conseguir isso. Precisamos detectar se
estamos percorrendo a história e, se
estamos atravessando, queremos sobrescrever. Caso contrário, queremos
mantê-lo como está agora. Vamos voltar ao histórico do App jsx
e do conjunto de insights. Vamos primeiro detectar se
estamos atravessando. Podemos fazer isso introduzindo a
nova variável IsTraversing. A lógica será a próxima. Se nosso currentMove mais 1 não for igual a
currentHistory.length. Em seguida, podemos tentar
registrá-lo no console e ver se isso é verdade e por que estamos fazendo o movimento
atual mais 1. Novamente, vamos consolar um CurrentMove e vamos o
console registrar history.length. Vamos chamá-la de duração de sua
história. Vamos ver por que precisamos
adicionar mais 1 aqui? Se eu abrir o “Console”
e jogar o jogo, você pode ver que a
duração do nosso histórico é sempre mais 1. Em seguida, o CurrentMove
que temos. Isso ocorre porque o
tamanho mínimo do histórico é aquele definido pelo nosso estado
padrão aqui, enquanto nosso CurrentMove é baseado no índice
zero. Para normalizar isso, precisamos
adicionar mais 1 ao movimento atual para que eles coincidam um com o
outro. Nós simplesmente verificamos. Se “CurrentMove”
for igual a qualquer tamanho que tenhamos, então sabemos que estamos
na última jogada e
não estamos percorrendo a história. Mas se não estamos em
nossa última jogada, então estamos atravessando
algo assim. Agora, de alguma forma,
também precisamos alterar nosso “LastGamingState”.
Porque sempre que estamos em nossa última jogada,
sempre
concatenamos, adicionamos ao histórico atual de jogos
até o final da matriz. No entanto, se
quisermos sobrescrever, queremos adicionar algo ao histórico, que está no
ponto dessa mudança. Não nos importamos com o movimento número três e com
o que quer que esteja abaixo dele. Só nos preocupamos com a
história neste momento. Precisamos escrever
a seguinte lógica aqui.
Precisamos modificá-lo. Podemos perguntar, se
estivermos atravessando, neste caso, pegue o
histórico atual no movimento atual. Caso contrário, pegue o
elemento mais recente desse histórico. A lógica com
“nextSquareState” não muda, e agora, aqui, em vez do
histórico atual concat, também
precisamos considerar uma matriz base diferente
à qual vamos associar novo estado do tabuleiro de jogo. Vamos criar
uma nova variável e chamá-la de algo
como base, talvez. Aqui, vamos perguntar novamente: se estamos percorrendo
neste caso, por favor, da história atual, corte apenas esses elementos aqui. “Vá para o início do jogo”, “vá para o
movimento 1”, “vá para o movimento 2". Nós dividimos do índice zero para o índice
do histórico
atual do último mais 1. Caso contrário, mantenha o
histórico atual como matriz base. Em vez do último, queremos
usar o último estado de jogo
e, em vez do
histórico atual, quero usar o base. Voltaremos a
essa lógica em um segundo. Parece assustador, eu sei, especialmente com
todos esses ninhos. Mas vamos ver a aparência
do nosso jogo agora. Viajamos pela
história, está tudo bem. Estamos em movimento número 3, e se eu quiser
sobrescrever a história, agora posso fazer isso. Você pode ver que basicamente
retiramos o resto da história
e a
substituímos por nossa nova mudança
aqui. Simples assim. Funciona perfeitamente. Agora, e a lógica aqui? Novamente, slice é usado para cortar alguns elementos
dessa matriz, da matriz de histórico atual. Nós dividimos do primeiro elemento para o
índice do histórico atual de mais 1. Nós apenas pegamos o índice de menos estado de jogo que
temos e adicionamos
um a ele porque, novamente, temos o
“CurrentMove” baseado em zero. Pode ser confuso,
mas
basta revisar isso algumas vezes
e fará sentido. Não é tão simples
à primeira vista, mas não há nada
muito complexo nisso, e você realmente não
precisa pensar demais nisso. Agora temos um histórico de jogos
e ele funciona incrivelmente bem. Somos capazes de viajar, podemos ignorar a
história sem problemas. Perfeito. Agora, parece que fizemos muito e,
na verdade, fizemos muito. Vamos remover esse log
desnecessário do console e ver se precisamos
adicionar alguma coisa aqui. Talvez possamos adicionar uma mensagem aqui, algo como a história
atual do jogo. Vamos ver como fica. Parece assim, o que é bom, e acho que isso será
suficiente para este vídeo. Vamos tentar comprometer
tudo o que
fizemos aqui. Isso é muito. Vou parar o aplicativo, vou adicionar
tudo ao palco, vou comprometer
tudo e
chamá-lo de edição do histórico do jogo. Basicamente, isso é
exatamente o que fizemos. Transformamos esse
estado em uma matriz. Modificamos nossa lógica e
ajustamos tudo
à nova forma de estado que
introduzimos com a história. GIT commit adicionou o
histórico do jogo.Incrível. Talvez, na verdade, vamos adicionar mais
uma coisa extra aqui. É completamente
desnecessário, mas nos
ajudará no futuro vídeo, e vou fazer um pequeno exercício
até o próximo vídeo. Vou iniciar o servidor
novamente e, o que farei, moverei essa matriz como estado inicial para fora
do componente. Vou criá-lo aqui e
chamá-lo de novo jogo. Coloquei tudo em letras maiúsculas
porque essa é a definição de
valor global constante que não vamos mudar, e vou dar a ela
essa matriz, desse jeito. Para o estado inicial,
vou passar um novo jogo. Na verdade, posso movê-lo para
dentro do componente, mas é melhor
mantê-lo do lado de fora. A razão para isso é
porque, se você se lembrar, sempre que temos
uma nova renderização de linha, o JavaScript interno é executado e
sempre que o JavaScript é executado, ele cria todas
as novas variáveis novamente, e como o novo jogo é
algo estático que
não precisamos recriar em cada
renderização de linha , podemos simplesmente
movê-lo para fora. Essa é apenas uma otimização muito
pequena, mas
nos servirá apenas para o GIT. Por que eles fizeram isso? No próximo vídeo,
o que
vamos fazer é adicionar um botão no qual clicamos e
que reinicia o jogo. Aqui está um pequeno exercício para
você até o próximo vídeo. Experimente e faça você mesmo. Crie um botão, exiba-o em algum lugar aqui
e, quando você clica
nele, ele realmente atualiza o
estado do jogo para o estado inicial. Novamente, você joga o jogo, clica no botão, ele atualiza o estado. Tente implementar
isso usando a nova variável de jogo que
criamos fora
do componente. Vou cometer isso
e dizer que mudei para novo estado de jogo fora
do componente do aplicativo, vou
enviar tudo para master e, no próximo vídeo ele nos ajudará a
implementar a redefinição do jogo. Tente se exercitar. Nos vemos na próxima.
51. 12 Adicionando o botão de reinicialização do jogo: Ei, como foi seu exercício
do último vídeo? Você conseguiu
fazer isso? Vamos ver. Neste vídeo,
adicionaremos um botão que redefinirá nosso
estado de jogo. Vamos embora. Então, aqui na marcação, bem no topo da história
atual do jogo, vamos adicionar
um elemento de botão do tipo botão e
vamos dizer que ele
iniciará um novo jogo. Então, quando clicamos
nele, ele deve fazer alguma coisa. Vamos colocar o manipulador
onClick aqui
e, para esse evento onClick, vamos especificar
onNewGameStart, e esse onNewGameStart
será uma função que criaremos
aqui e essa função, a única coisa que ela fará, apenas atualizará o estado. No vídeo anterior,
no final, movemos o novo jogo para a parte externa do componente
e isso nos ajudará agora. Agora podemos realmente ligar, definir o histórico e passar por um novo jogo, que é nosso estado inicial. Além do histórico, também
precisamos reiniciar o
contador da nossa jogada atual. Vamos seguir
em frente e chamar definir movimento
atual e colocá-lo de
volta para zero. Vamos ver. Se eu salvar, eu jogo o jogo, clico em “Iniciar novo jogo”. Tudo foi
atualizado agora. No entanto, não tem estilo e,
se examinarmos o estilo CSS, temos aqui a classe.btn-reset. Vamos continuar e usá-lo. Então, para esse botão, vou passar o nome da classe e vou passar btn-reset. Mas se você ver, ele também tem a classe
ativa aqui. O que eu queria fazer
quando apresentei essa classe ativa é que
sempre que tivéssemos um vencedor, esse botão se tornasse ativo. Então, vamos aplicar a
lógica dentro do nome da classe aqui. Como vamos
aplicar JavaScript, novamente, usamos colchetes
e, antes de tudo, esse será um
modelo de string com acentos. Vamos dar a ela a classe estática
btn-reset e, em seguida,
abriremos
as aspas de interpolação de strings e, dentro desses colchetes
para interpolação de strings, vamos perguntar. Então, se tivermos um vencedor,
por favor, dê a ele uma aula ativa,
caso contrário, mantenha-a vazia. Algo assim
e agora vamos ver. Então temos esse lindo botão aqui e se jogarmos o jogo, e vamos ter um vencedor, e sempre que tivermos um vencedor, esse botão fica ativo. Se percorrermos a história, tudo voltará a funcionar conforme
o esperado. Parece bom. Isso é tudo para reiniciar o botão. Como você pode ver, nada complicado, então vamos
em frente e nos comprometer. Vou adicionar
essas mudanças ao estado
do estágio e depois
vou me comprometer. A mensagem de confirmação será adicionada ao botão de reinicialização
do jogo ou
iniciará um novo jogo. Incrível. Eu envio tudo para o GitHub e vejo
você no próximo vídeo.
52. 13 Destacando o vencedor do jogo (combinação vencedora): Olá a todos. Neste vídeo, o que vamos fazer? Podemos exibir a combinação
vencedora caso tenhamos um vencedor, e também, mas
mudaremos a cor
dos quadrados porque
agora eles são pretos. Agora, talvez vamos
começar com as cores primeiro. Se formos para o quadrado
dos componentes, a lógica aqui
será praticamente a mesma que temos
dentro da mensagem de status. Se você se lembra, aplicamos o className
dinâmico aqui. Se o vencedor for X, o texto será verde, caso contrário,
será o texto laranja. As classes que
definimos aqui dentro dos estilos basicamente fornecem a cor ao elemento
definido pela variável SAS aqui. Aqui dentro do quadrado,
vamos simplesmente convertê-lo em expressão
JavaScript. Vamos
mudar as aspas de aspas duplas para acaspas. Vou perguntar se
nosso valor é X,
então vamos nosso valor é X, exibir o texto verde,
caso contrário, vamos
exibir o texto laranja. Simples assim,
nada complicado. Você pode ver agora
que tudo se
transformou em um lindo sistema de cores. Se clicarmos, se jogarmos, funciona. Ótimo. Agora, vamos pensar em como podemos realmente
destacar os quadrados vencedores. Para destacar os quadrados
vencedores, precisamos conhecer os quadrados. Precisamos conhecer seus índices. Precisamos saber que, se tivermos vencedor X para essa combinação
vencedora, teremos
quadrados vencedores e Índice 2. Então temos 0, 1, 2, 3, Índice 4 e Índice 6. Estes são nossos quadrados de ganhos. Calculamos o vencedor dentro da função
calcular o vencedor e retornamos apenas o
quadrado vencedor, somente seu valor. No entanto, a partir dessa função, também
podemos retornar quadrados
vencedores. Porque aqui comparamos todas as combinações
vencedoras possíveis. Já temos essas variáveis a, b e c,
elas estão estruturadas aqui, que representam índices vencedores,
a combinação vencedora. A partir dessa função de cálculo do
vencedor, podemos retornar um
objeto em vez de apenas nulo ou o vencedor. Podemos devolver um objeto com o vencedor e
os quadrados vencedores. Caso não
tenhamos nenhum vencedor, agora
retornaremos nulo. Mas vamos
transformá-lo em um objeto. Retornaremos vencedor ou nulo, e os quadrados vencedores serão uma matriz vazia. Mas caso tenhamos um vencedor,
devolveremos um objeto, o
vencedor serão quadrados c ou quadrados a ou quadrados b, não
importa. Mas para ganhar quadrados, retornaremos as linhas i ou podemos realmente
devolvê-las assim. Podemos criar uma nova
matriz e depois especificar
explicitamente que
estamos retornando a, b e c, ou podemos especificar
uma linha a linhas i. Agora voltamos para J6. Agora, esse vencedor é um objeto. Se eu destacar, também me
mostra um objeto. Eu posso usar essa
estrutura aqui. Da estrutura de ID do
objeto que retorna, chave
vencedora e quadrados vencedores. Vencedor e quadrados vencedores. Agora podemos passar esses quadrados
vencedores para o componente
do tabuleiro como um suporte
e lidar com essa lógica lá. Vou passar os
quadrados vencedores para o tabuleiro
e, dentro do tabuleiro, vou pegar os quadrados
vencedores e para aquele componente quadrado
que entraria aqui. Posso passar um adereço
que diz se esse quadrado é um quadrado
vencedor ou não
e, em seguida, aplicar alguma lógica
dentro do componente quadrado. No render square, vou
verificar se o quadrado
é um quadrado vencedor. Vou criar
apenas uma variável dentro do quadrado de
renderização e
chamá-la de quadrado vencedor. Os quadrados vencedores são uma
série de índices vencedores. Como 0, 1 e 2. Por exemplo, vamos
pegar essa combinação. Precisamos verificar se
a posição desse quadrado está dentro da matriz de quadrados
vencedores. Se isso for verdade, então sabemos que o quadrado faz parte da combinação
vencedora. Podemos simplesmente verificar os
quadrados vencedores. Inclui
esta matriz que inclui a posição
global do método. É isso. Então, podemos passar esse quadrado vencedor enquanto eu
desço para o componente quadrado. Se abrirmos o componente quadrado, vamos movê-lo aqui. Dentro do quadrado, desde que
passamos, está o quadrado vencedor. Pegamos esse quadrado vencedor
do objeto de adereços. Aqui podemos aplicar outro className dinâmico com
base nesse quadrado booleano vencedor. O método dot include retorna como um booleano, o que indica se essa matriz
inclui esse elemento. Já aplicamos o
sobrenome dinâmico aqui com base no valor. Podemos fazer exatamente o mesmo com
o quadrado vencedor. Vou apenas estender essa string com
outra interpolação e vou perguntar se
esse é o quadrado vencedor.
Por favor, aplique um pouco de className e algum className
será, se abrirmos estilos, CSS, dentro temos essa classe
vencedora. Essa classe vencedora
anexa a
animação de texto em escala definida aqui, que aumenta o
tamanho da fonte de forma infinita. Vamos voltar à praça. Se for um quadrado vencedor, atribuímos a classe vencedora. Caso contrário, anexamos
uma classe vazia. Vamos ver se funciona e depois disso,
faremos algo sobre esse slide, porque você vê que ele parece um
pouco confuso agora. Vamos ter um vencedor. Boom. Na verdade, funciona. Basta olhar isso. Temos
tudo pronto aqui. Muito legal, não é? Sempre que percorrermos a história, e se voltarmos aos últimos movimentos, a
animação estará lá. Se inspecionarmos a marcação, teremos a
classe vencedora anexada a cada quadrado que faz parte
da combinação vencedora. Muito legal. Agora vamos fazer algo com
essa corda porque, bem, ela parece um pouco confusa. Na verdade, não podemos fazer muito
sobre isso. Podemos dividi-lo em
várias variáveis e depois
combiná-lo, talvez algo como
colorClassName. Então, podemos simplesmente cortar
essa lógica daqui, colocá-la assim, então talvez possamos dizer algo
como WinningClassName, e então fazemos exatamente o mesmo. Nós apenas cortamos essa
lógica, colocamos aqui. Em vez de usar
essa lógica em linha, como fizemos agora, o que vai
passar a variável. Isso
será colorClassName. Interpolamos esse valor de
variável dentro dessa string e fazemos o
mesmo aqui, WinningClassName. Agora, parece muito mais limpo. Basicamente, separamos a
lógica em várias linhas. O que você preferir. Se você quiser
torná-lo um pouco mais limpo
dessa maneira, tudo bem. Se você gostou da
maneira bagunçada, fique à vontade para fazer isso. Algo assim, temos
a combinação vencedora, que foi
destacada na história do jogo. Ótimo. Acho que
no próximo vídeo, faremos os preparativos
finais e
daremos mais algumas coisas, talvez apenas
texto adicional, mais estilos. Finalmente, teremos
o aplicativo preparado para ser implantado em uma hospedagem. Incrível. Agora, antes de
terminarmos o vídeo, vamos remover comentários, registros do
console e confirmar tudo. Vamos dar uma visão geral do que fizemos
para modificar o cálculo quando o retorno retornou esse valor para um
objeto com duas chaves, quadrados
vencedores e vencedores, depois passamos esses quadrados
vencedores para o componente do tabuleiro. Dentro do tabuleiro, detectamos se o quadrado que
percorremos é um quadrado vencedor
e, com base nesse componente do
quadrado interno, aplicamos dinamicamente
nomes de classes para alternar a animação. Algo parecido.
Vamos e comprometer tudo. Git, adicione isso. A mensagem será
destacada com a combinação vencedora. Incrível. Vamos empurrar tudo. Até a próxima, nos
vemos lá.
53. 14 toque final: Olá. Neste vídeo, daremos
um toque final em nosso aplicativo antes da implantação. Bem, se usarmos nossos
estilos, na verdade, aqui, para o elemento corporal, aplicaremos essa fonte Roboto, mas na verdade não a
temos em nosso PC. Não o temos em lugar nenhum. De onde veio isso? O fato é
que não foi realmente aplicado. Vamos consertar isso. No convidado que
compartilhamos conosco, temos o HTML de índice aqui
com algumas propriedades. Se olharmos dentro do
nosso índice HTML, não
temos esse link para a folha de estilo
que temos aqui. A folha de estilo,
o que ela fará, baixará a
fonte Roboto das APIs do Google. Vamos apenas incluir
isso e, com essa linha, se atualizarmos o aplicativo, nada mudará porque
não executamos o servidor de desenvolvimento. Eu executo o servidor, eu
volto para o aplicativo. Agora, na verdade, temos a fonte
Roboto aplicada. Se eu remover essa linha, você verá as mudanças na família da fonte. Mas assim que não
carregamos a fonte que especificamos na
folha de estilo, tudo funciona. Ótimo. Agora vamos adicionar o
título ao nosso aplicativo na parte superior. Aqui dentro do aplicativo, logo acima do componente de
mensagem de status, exibiremos uma tag de título h1
simples e
informaremos o TIC TAC TOE. Para torná-lo mais atraente, podemos mudar a cor do TAC. Vamos envolvê-lo em um
elemento de extensão e dar a ele um nome de classe de texto
verde. Vamos salvá-lo. Agora parece muito melhor, e acho que
devemos realmente remover a propriedade font-weight bold título atual
do histórico do jogo. Podemos fazer isso
aplicando estilos embutidos. Bem, o que é ótimo. Nós não ouvimos isso, ou não o vimos antes. A única maneira de aplicarmos
estilos até agora no aplicativo foi usando
a propriedade de nome
da classe. Os nomes das classes são definidos
aqui dentro do arquivo SaaS. No entanto, e se não tivermos nenhum arquivo CSS ou arquivo SaaS? Como podemos aplicar estilos? Bem, sem o React
em apenas um arquivo HTML, podemos ter dois tipos de estilos. Podemos dar aos elementos um nome de classe ou transmitir estilos embutidos. O mesmo que podemos
fazer aqui no React. Para esse histórico do jogo, podemos passar a propriedade de
estilo e a propriedade de estilo
deve ser um objeto. Devemos especificar estilos
usando JavaScript, não com CSS, mas
com JavaScript. Vamos escrever CSS
com a ajuda do JavaScript, e isso é chamado de estilo
embutido. Queremos remover o
peso da fonte em negrito do elemento de título
que temos aqui. O estilo do elemento
terá o peso da fonte normal. Aqui, precisamos passar o
peso normal da fonte, desse jeito. Vamos ver se funcionou. Se inspecionarmos o elemento, posso ver o estilo e o
peso da fonte normais. Esses são estilos embutidos. O objeto JavaScript
que passamos aqui foi convertido para essa string
de estilo embutida. Você pode ver que eu
não especifiquei o traço entre as palavras de fonte e peso porque, ao
especificar estilos embutidos, é necessário usar a sintaxe
camel case. Se sua propriedade tem um
traço entre as palavras, ou tem espaços, seja o que for, você sempre a substitui por
uma caixa de camelo. Por exemplo, família de fontes. Você teria uma família de fontes
em forma de caixa de camelo. Algo parecido. aplicar
estilos embutidos em outro lugar. Se formos ao histórico de componentes, temos este botão aqui que representa esse
item na lista. Vamos torná-lo ousado
sempre que estiver ativo. Se abrirmos nomes de classes, vamos ver se está em negrito. Na verdade, é ousado. O que poderíamos ter feito se não
usássemos nenhum estilo, poderíamos ter feito o
seguinte se entrássemos na história. Aqui eu teria passado pelo
estilo e especifico, você pode ver
colchetes duplos aqui. primeiro colchete é
especificar que
usaremos JavaScript dentro e o segundo em seus colchetes
significa
que esse será um objeto para o qual
passaremos um objeto. É por isso que temos colchetes
duplos aqui. Propriedade de peso da fonte,
poderíamos ter perguntado, se o movimento atual for igual ao índice, ela estará em negrito,
caso contrário, normal. Se não tivéssemos essas classes, vamos removê-las e
ver se funcionou. Se eu aumentar o zoom, eu jogo o jogo, você pode ver que o elemento para qual essa condição
é verdadeira fica em negrito. Basicamente, nosso
movimento atual se torna ousado. Caso contrário, o
peso da fonte é normal. Não precisamos dele para
esse elemento específico porque ele já foi gerenciado
dentro do CSS. Você pode ver que o peso da fonte está em
negrito quando está ativo, então não precisamos de estilos
embutidos aqui. Acho que é isso. Eu diria que
terminamos nossa inscrição. Temos todas as funcionalidades, temos todos esses estilos. Tudo funciona perfeitamente
e tem uma aparência incrível. Sinta-se à vontade para modificar qualquer coisa, à
vontade para aplicar
seus próprios estilos, sinta-se à vontade para brincar com isso, estendê-lo ou talvez
mudar alguma coisa. Não há
requisitos estritos de que isso deva ser feito
especificamente dessa maneira. Você é o desenvolvedor aqui e é você quem decide. Se você precisar alterar
o título aqui, sinta-se à vontade para alterar o título. Se você quiser incluir
metatags extras dentro da cabeça, sinta-se à vontade para fazer isso. Nós terminamos aqui. Esse é o
estado final do nosso aplicativo. No próximo vídeo, falaremos
sobre implantação. Mas antes de terminarmos esse vídeo, vamos encerrá-lo e
comprometer tudo. Vou abrir o terminal; vou confirmar tudo. Vou especificar as
alterações que fizemos, então adicionamos a fonte
e adicionamos o título. Foi adicionado o título do jogo
TIC TAC e incluiu a fonte Roboto. Eu envio tudo
novamente para o GitHub. Como sempre,
nos vemos na próxima.
54. 15 Implantação para surtir: Olá. Nesta etapa, concluímos nosso precioso
aplicativo. Está lindo. Ele tem todas as funcionalidades. Agora, é hora de
compartilharmos esse aplicativo
com o mundo exterior. Queremos publicá-lo
na Internet para que possamos
ter o link real, o URL real que podemos
dar aos nossos amigos. Como podemos fazer isso. Existem vários serviços
diferentes que podem hospedar nossos arquivos estáticos
gratuitamente ou não gratuitamente. Vamos usar serviços
gratuitos. Mas a questão é: como exatamente isso acontece? Quando vamos executar o script de construção definido
no pacote Json, vite construirá nosso aplicativo
e produzirá arquivos estáticos, HTML, CSS, JavaScript e
imagens, se tivermos algum. Depois, podemos pegar essa pasta e entregá-la a um provedor de
hospedagem. Esse provedor de hospedagem exibirá
esses arquivos em algum lugar seus servidores e os exporá publicamente por meio de um URL
gerado automaticamente. Um dos serviços
que podemos usar para hospedar nosso aplicativo gratuitamente, hospedar nosso HTML, CSS JavaScript gratuitamente, ele sempre será gratuito
e é muito simples. O serviço se chama Surge. Você pode acessá-lo
acessando surge.sh. O legal do
Surge em sua simplicidade é que você não precisa de nenhuma configuração extra. O que você precisa fazer
é instalar apenas o pacote
global surge e, é instalar apenas o pacote
global surge em seguida,
usando o comando Surge, você pode implantar o
aplicativo dessa forma. Vamos seguir em frente e fazer isso. Surto global de instalação do NPM. Vou
colá-lo no meu terminal. Ele instalará o pacote de sobretensão
global. Diz, uma vulnerabilidade crítica de
gravidade. Bem, você não precisa
se preocupar com isso. Sempre que você vê
vulnerabilidades, isso pode ser bastante comum, especialmente com pacotes globais. Bem, esse é o
problema do pacote. O que podemos fazer sobre isso e quais são as
vulnerabilidades? Vulnerabilidades no código que baixamos
desse pacote e ele pode ser malicioso. Mas você não precisa
levar isso a sério. Na maioria das vezes,
no mundo do NPM, pacote é atualizado
talvez uma vez por dia, talvez duas vezes por dia. Mas nem sempre é possível
acompanhar as mudanças,
com as atualizações. Você pelo menos verá uma vulnerabilidade
crítica uma vez. Suas opções são, primeiro, não fazer nada e
atualizar para a versão mais recente e esperar que o
autor do pacote tenha corrigido a vulnerabilidade. A segunda opção é
não usar esse pacote. No nosso caso, não podemos fazer muita coisa e é por isso
que concordamos. Agora, temos o pacote
de pesquisa global instalado e ele diz que precisamos executar
o comando de pesquisa. Se eu fizer isso, ele solicitará que eu faça login
ou crie uma conta. Vou apenas
inserir meu endereço de e-mail e depois inserir minha senha. Eu já tenho uma conta, então ela me conectará. Mas, no seu caso, isso
criará uma nova conta para você. Agora, isso me incentiva
a iniciar o projeto, mas eu realmente não preciso de
nada no momento. Então, vou
fazer o Controle C para interromper a
publicação do meu aplicativo. Primeiro, precisamos construí-lo. Vou executar o script npm
run build e o vite produzirá a
versão mais recente do nosso aplicativo. Ótimo. Agora está lá. Parece minimizado, aglificado e tudo mais. Agora, queremos pegar
a pasta Dist e implantá-la para pesquisar. Então, usamos o
comando de pesquisa e, em seguida, especificamos o
caminho para a pasta
que queremos implantar em relação à
nossa navegação atual. Como nossa
navegação atual é tictactoe-vite, nossa pasta está localizada
nessa pasta no
mesmo diretório. Não precisamos
ficar loucos com isso. Só precisamos
especificar o nome da pasta que queremos implantar. No nosso caso, essa é uma
pasta chamada Dist. Se eu fizer isso, eu apenas
executo o Search Dist. Ele me pede um domínio. Portanto, sempre que você implantar no Surge, ele sempre será
implantado em um subdomínio. Sempre será algo
dot surge dot sh. Você não pode alterar a parte do surge.sh, mas pode escolher um subdomínio exclusivo que não está sendo
usado até agora. Por padrão,
o surge gera automaticamente um subdomínio
que está disponível, mas você pode alterá-lo. Talvez vamos
chamá-lo de tictacgame.surge.sh. Eu escolho esse nome. Mas, no seu caso, você
terá que
criar seu próprio subdomínio,
porque se tentar implantar
em um subdomínio que já foi
usado por
outro usuário do Surge, você terá permissão
negada ou algo assim. Isso fará com que sua
solicitação seja abortada. Portanto, certifique-se de escolher algo único e continue com isso. Eu escolho tictacgame.surge.sh. Eu implanto e agora ele está publicado em
tictacgame.surge.sh. Agora eu posso pegar esse
link e ir até lá. Como você pode ver agora, meu aplicativo está ativo. Tem link HTTPS. Isso significa que o
certificado SSL está presente. É gerenciado pela Surge. Não precisamos nos preocupar com
isso. Tudo funciona. Agora você pode pegar esse link
e compartilhar com seus amigos. Basta olhar isso.
Quão legal é isso? Ótimo. Agora, para referência
futura, talvez
queiramos simplificar
o processo de implantação. E se eu quiser
mudar alguma coisa e depois reimplantar novamente
exatamente no mesmo domínio? Então, neste caso,
o que eu preciso fazer fazer minhas novas alterações, introduzir novas
alterações no aplicativo. Em seguida, vou executar o
npm run build novamente para produzir uma nova
pasta dist atualizada e, novamente, terei que executar o surge dist
e entrar no mesmo domínio. No entanto, quero
torná-lo o mais simples possível. Então, por que não
criamos outro script dentro do pacote Json
e o chamamos de deploy. Vamos seguir em frente e criar um
novo script de implantação. Isso fará duas coisas. A primeira coisa é que ele
executará o comando build, npm run build, e logo em seguida, usando
a lógica e o operador, podemos encadear o comando que será executado após o npm run build. Então, queremos executar o surge dist e o domínio
que temos até agora. Surge, o nome da pasta
que queremos implantar, dist e, em seguida, o domínio. Sim, posso passá-lo para o comando surge como
argumento e funcionará. O Surge entenderá
que queremos implantar esse nome de domínio. Portanto, podemos eliminar o HTTPS e manter apenas
o nome de domínio assim. Agora, se eu tentar
mudar alguma coisa, talvez dentro do aplicativo, vamos verificar rapidamente se funciona. Então, vamos mudar tic
para outra coisa, e agora eu executo npm run deploy. Você verá que ele
pega o comando build
e, logo em seguida,
pega o comando surge. Ele foi implantado,
diz que foi publicado em
titacgame.surge.sh. Se eu atualizar. Agora, você vê novas mudanças. Legal, certo? Tudo bem. Vamos reverter tudo
aqui e reimplantar novamente. Novamente, produziu uma nova construção. Novamente, ele foi implantado e publicado novamente
nesse subdomínio. Incrível. É isso. Agora você tem nosso aplicativo online. Você pode ir em frente e
compartilhá-lo com o mundo. Vamos confirmar nosso
script de implantação que introduzimos, git commit adicionou o script de implantação. Então, parabéns, construímos
esse jogo muito legal aqui sem
muito esforço. Nós o publicamos
no serviço Surge. Então, agora ele está disponível na Internet e sempre
será gratuito. Ele será hospedado gratuitamente para sempre e agora
podemos nos orgulhar disso. No próximo e último
vídeo sobre o Tic-Tac-Toe, vamos resumir
exatamente o que
aprendemos durante esses vídeos, quais conceitos entendemos, o que podemos fazer
agora com nosso conhecimento. Nos vemos lá.
Parabéns pela implantação.
55. 16 resumo: Olá de novo. Neste vídeo, vamos resumir rapidamente o que exatamente aprendemos
até agora durante o jogo
tic-tac-toe. Vamos embora. Se olharmos nossa estrutura, já
podemos dizer que
sabemos como usar o Vid. Conhecemos as ferramentas de front-end
que podem construir nosso projeto. Se examinarmos o pacote JSON, podemos ver que
também aprendemos sobre hospedagem e como podemos hospedar
o aplicativo gratuitamente. Você pode escolher no Google qualquer serviço de hospedagem que permita
hospedar arquivos estáticos, HTML, CSS
e JavaScript e ver como aplicá-los caso precise de uma
alternativa para pesquisar. Nós conhecemos os
serviços de hospedagem agora. Se olharmos dentro da pasta de
origem e se olharmos dentro do JSX principal, podemos dizer que
usamos o React 18. Essa é a API dos cabeçalhos do React 18 e é
diferente do React 70. Aprendemos como usar a versão
mais recente do React aqui. Se olharmos dentro do App JSX, podemos ver uma lógica diferente aqui. Já sabemos o que é estado, como podemos gerenciar o estado, como podemos atualizar o estado e por que ele é necessário. Também sabemos qual é o
valor derivado desse estado e por que realmente não
precisamos criar
outro estado para gerenciar
esses cálculos, como vencedor ou talvez
como um tabuleiro de jogo. Também sabemos que a atualização de
estado ou função pode ser
chamada de várias maneiras, seja com o
retorno de chamada sempre que precisarmos definir um novo estado a partir do valor
do estado atual ou apenas com uma chamada
normal sem
retorno de chamada, apenas o valor. Nós conhecemos a marcação JSX agora. Sabemos como
aplicar nomes de classes. Conhecemos estilos embutidos
apenas com o objeto de estilo para que possamos escrever CSS usando JavaScript. Sabemos como
aplicar estilos dinâmicos
simplesmente usando modelos de string
e um pouco de JavaScript. Sabemos como passar adereços. Os prompts são basicamente os atributos dos
componentes que você pode usar para passar dados
para o componente. Aprendemos sobre renderização
condicional. Sabemos que podemos renderizar marcação
JSX com
base em alguma condição e podemos fazer
isso de várias maneiras. Podemos fazer isso em linha usando o operador AND
diretamente dentro do JSX, ou talvez possamos criar uma função auxiliar e
escrever a lógica interna. Vamos ver o que mais
temos aqui. Se olharmos para dentro da praça, já
conversamos sobre isso. Se olharmos para dentro da história, ainda não conversamos sobre isso. Também sabemos agora
que podemos pegar uma matriz e mapear cada elemento da
matriz para a marcação JSX. Caso precisemos
exibir listas, usamos o método de mapa de pontos. O método de mapa de pontos mapeia
cada elemento da matriz para a marcação
JSX se
o usarmos dentro do JSX. Sempre que fazemos isso, lembramos que sempre
precisamos passar a chave para o elemento de encapsulamento
porque
o React precisa identificar cada
elemento mapeado dentro do JSX. Eu acho que é isso. Já aprendemos muitos
conceitos sobre o React. Confie em mim, todos esses conceitos
que você experimentou formam a base necessária para criar
qualquer coisa com o React. Tudo o que você vê aqui está presente em qualquer outro aplicativo
React. Se você se sentir flexível
com isso e puder aproveitar isso, isso é incrível. Isso significa que, no
futuro, você não terá problemas para criar
nenhum tipo de aplicativo. Parabéns. Com essa boa nota, vamos encerrar o projeto
tic-tac-toe. vejo na próxima vez.
56. 17 Extra: Olá, pessoal. Na verdade, esqueci um
pequeno detalhe sutil para adicionar ao nosso aplicativo. Isso é sobre estilos. É sobre esses círculos
que vemos em segundo plano. Não os vemos
agora porque, bem, não os
adicionamos, mas eu esqueci de fazer isso. Dentro do Style CSS, você tem a classe BG balls, que cuida dos círculos de
fundo. Só precisamos criar
um elemento vazio em algum lugar dentro da marcação do aplicativo. Digamos que uma div vazia. Damos a ela um
nome de classe de bolas BG. Se atualizarmos a página, veremos que os círculos aparecem
em segundo plano, são responsivos
e têm uma aparência muito bonita. Desculpe por isso. Não se esqueça de reimplantar o
aplicativo e omitir essa alteração. Vou seguir em frente
e adicionar círculos de fundo. Em seguida, o NPM execute deploy. Os scripts de implantação que
definimos internamente [inaudível]. Tudo bem, até mais.
57. Visão geral do aplicativo do Box Office: Olá, bem-vindo
ao Box Office. Neste vídeo, gostaria de apresentar rapidamente o projeto, o que isso vai ser. No momento, você está
vendo a bilheteria. Este será um aplicativo de busca de filmes
e atores. Você poderá
pesquisar filmes ou atores, e os dados que você procura serão obtidos da API. Por exemplo, na entrada, vou digitar
algo como garotas
e, quando pressiono “Enter” ou
pressiono o botão de pesquisa, vejo os resultados. Todos esses resultados
serão obtidos
do servidor de API externo, que está disponível publicamente. Poderemos estrelar shows. Quando clicarmos em um programa, veremos aquela animação legal. Para que o usuário entenda que
esse programa agora está marcado como favorito, podemos clicar em Leia mais
e, nesse caso, uma nova página
será aberta em uma nova guia. Aqui poderemos ver todas as informações que
recuperamos da API; detalhes, temporadas, elenco, tudo sobre o programa. Aqui, voltamos para sua página inicial botão
Aqui, caso
precisemos voltar. Vamos fechar essa guia. Agora, como
estrelamos programas aqui, eles estarão disponíveis
em outro lugar. Eles estarão disponíveis na
guia Iniciar. Quando navegamos aqui, todos os programas que selecionamos anteriormente agora aparecem
aqui nessa página. Mesmo que eu feche o navegador, feche a guia ou atualize a página, nossos programas ainda estarão lá. Eles não são armazenados
em um banco de dados, mas são salvos no armazenamento do
navegador, especificamente
no armazenamento local. Vamos voltar para o Início e você pode ver que a
entrada ainda está lá. O mesmo acontece com a entrada, assim como os programas que marcamos estrela são salvos em algum lugar
dentro do navegador, o mesmo que fazemos com
a entrada aqui. Se eu atualizar a página, a entrada ainda estará lá. Além disso, temos essa
caixa de rádio aqui, botões de rádio, se mudarmos para atores e
depois procurarmos algum nome, por exemplo, como James. Em vez de shows, agora veremos os atores. Novamente, a mesma API,
mas ao contrário dos programas, os atores não têm sua
própria página porque
não recebemos muitas
informações da API. Isso é suficiente, apenas
cartões para pessoas, para atores, e esse aplicativo também
é um aplicativo web progressivo. Isso significa que nosso
aplicativo agora pode ser instalado como se fosse
um aplicativo nativo, esteja em um
desktop ou dispositivo móvel. Por exemplo, aqui
no canto superior direito, tenho esse botão de instalação
e, se eu clicar
nele, ele solicitará que eu instale este site como se
fosse um aplicativo. Se eu clicar em Instalar, logo em seguida,
serei, digamos, redirecionado ou aberto em uma nova janela que funciona
sozinha e esse
será meu aplicativo. Logo depois disso, se eu
voltar para minha área de trabalho aqui, vejo isso, agora posso. Este é meu atalho
para o aplicativo. Se eu fechá-lo e
abri-lo novamente, será aberto em uma guia separada e
funcionará exatamente da mesma maneira. Muito legal. Eu
diria que é isso, esse é o nosso aplicativo, vai ser muito divertido. Nos vemos lá.
58. 02 Criando o projeto com o Create React App: Ei, aí. Como você
se sente depois do tic-tac-toe? Pronto para continuar? Desta vez, vamos
trabalhar no Box Office, um aplicativo web onde
podemos pesquisar diferentes filmes e
atores. Vamos embora. Para o Box Office, vamos
usar o Create React App. É um clichê muito popular do
React, que nos permite
criar arquivos de projeto. No tic-tac-toe, usamos
uma ferramenta chamada Vite. Desta vez, vamos
usar o Create React App. Create React App é
como o Santo Graal de todos os modelos para aplicativos
React. A razão por trás
disso é porque Create React App é
mantido pela equipe do React. É o que podemos chamar de modelo
oficial do React. Você tem uma pergunta,
por que escolhemos Create React App quando
usamos o Vite no tic-tac-toe? A resposta para isso
é muito simples. Só porque
não há nenhuma razão real
por trás dessa decisão. Seja qual for a sua escolha,
você ficará bem. Mas, para fins de nossa negociação, queremos explorar o maior número possível de
opções e ver o que podemos fazer e o que podemos alcançar usando modelos
diferentes. Todos eles serão
praticamente iguais. Eles podem ser
diferentes
dependendo do quanto você pode usar
com a personalização. Mas, no geral, eles são
muito parecidos. No momento, estou no site
oficial do modelo do Create React
App. O que podemos fazer é
ir para Começar. A partir daqui, já temos a seção Quick Start, onde podemos simplesmente copiar esse comando. Mas nosso aplicativo de bilheteria será algo chamado
de aplicativo web progressivo. Vamos falar sobre aplicativos web
progressivos. O que é isso? Por que é legal e por que precisamos dele
ou talvez não precisemos dele? Vamos abordar tudo
isso mais tarde no Box Office, mas precisamos tomar
uma ação específica antes de criar
o aplicativo. Mais tarde, podemos usá-lo. Se rolarmos para baixo
e formos para Modelos, podemos ver que podemos executar o comando Create React App
com o sinalizador de modelo. Se formos para o Uso Avançado
ou para o desenvolvimento, deixe-me ver onde está, criando seu aplicativo, criando
um aplicativo web progressivo. Se formos para essa seção aqui, ela nos dará esse
comando que podemos executar com o modelo
conforme especificado, que será
um aplicativo web progressivo. Isso é
exatamente o que vamos copiar e usar
para criar novos arquivos de projeto. Então, o que
eu vou fazer é ir para a pasta onde eu gostaria de
ver meu projeto. Esta vai ser a pasta de
embrulho que eu tinha no vídeo anterior. A abordagem é a mesma. Você precisa executar esse comando na
pasta em que
gostaria de ver a pasta do seu projeto. Eu vou abrir o Git Bash, você abre seu terminal. Pode ser qualquer coisa. Não teremos problemas de
interatividade se estivermos no Windows
com o Git Bash. Vou para o disco d depois para a pasta do aplicativo. Aqui, vou colar esse comando
em vez do meu aplicativo aqui. Vou escolher o modelo
Box Office, o modelo Create React App PWA. Quando eu pressiono enter, o comando será iniciado. Levará alguns minutos para criar
todos os arquivos necessários. Ele não apenas criará arquivos, mas instalará todas as
dependências do pacote Jason, então esse comando
pode demorar um pouco. Enquanto estiver no processo de
instalação, vamos falar sobre a diferença
entre o Vite e o
Create React App. No tic-tac-toe, usamos o Vite. Vite é basicamente uma
configuração em cima do pacote de módulos
com o Create React App. É quase o mesmo. Create React App
é uma configuração em cima de um
bundler de módulos chamado Webpack. Embora o Vite possa ser usado para
qualquer biblioteca de front-end, para qualquer projeto de front-end, Create React App
visa apenas o React. Vite usa roll-up. Create React App usa o Webpack, e ambos são configurações em cima
desses buflers de módulo. Não há muita
diferença no que escolher. A resposta é que é muito
subjetivo o que escolher. Pessoalmente, prefiro o Vite, mas o Create React App tem
seu próprio conjunto de benefícios, por exemplo, eles têm esse
suporte progressivo a aplicativos web pronto para uso, o que é ótimo e
se adapta perfeitamente que é ótimo e
se adapta perfeitamente às necessidades do nosso projeto. Deixe-me voltar aqui
para o terminal. Eu posso ver que tudo
foi instalado. Eu posso ver a mensagem de sucesso e a
mensagem de boas-vindas. Se eu abrir minha pasta aqui, tenho o Box Office e
dentro dos meus arquivos de projeto. Agora, vou abrir o VS
Code e, dentro do VS Code, vou abrir
esse laboratório de pastas. Isso vai ser bilheteria. Aqui temos algumas
coisas que são um pouco diferentes das que tínhamos
antes no tic-tac-toe. Vamos falar sobre
isso em um segundo. Antes de prosseguirmos, vamos abrir o convidado que
você compartilhou com você. A partir daqui, vamos
configurar o Prettier e o ESLint. A configuração será
praticamente a
mesma do tic-tac-toe, mas
um pouco diferente. Primeiro, vamos copiar
a configuração do ESLint. Vou criar o eslintrc. Copie tudo aqui, o mesmo que farei com Prettier. No ESLint, o que temos aqui? Exatamente a
mesma configuração do tic-tac-toe, mas também temos
o plugin aqui, React Hooks, e apenas
algumas regras definidas aqui. Em seguida, precisamos
instalar dependências. Assim como antes, precisamos
instalar a configuração ESLint Prettier. O plugin Prettier
que estendemos, que precisamos instalar o plug-in
ESLint React e
também o plugin React Hooks. Vou copiar
esses plug-ins aqui. O
comando de instalação será eslint-config-prettier, eslint-plugin-react e
eslint-plugin-react-hooks. Além disso, preciso instalar
as ferramentas em si. Preciso instalar o
Prettier e o ESLint. Ótimo. Agora, vamos
aguardar a instalação. Eu já tenho seis vulnerabilidades de alta
gravidade. Bem, então o que
vou fazer a seguir. Em seguida, vamos
inspecionar o que exatamente
temos no pacote Jason. Vamos começar com os scripts. Assim como eu disse, o Create React App é
uma configuração sobre empacotador de
módulos subjacente do Webpack. Essa configuração oculta é exposta a nós por meio do pacote de scripts
React, que é distribuído
por meio do NPM. Assim como temos o beat
distribuído por meio do NPM, temos scripts React. É por isso que, em nossos scripts, temos scripts do React iniciando, construindo, testando e ejetando. Quais são esses scripts? No Tic-tac-toe,
temos o script de desenvolvimento, que executa o servidor de
desenvolvimento local para nós. Aqui, é chamado de início. Bem, geralmente
é chamado de início, mas faz exatamente o mesmo. Ele lança o servidor
de desenvolvimento local. Em seguida, temos o script de
construção, novamente, para criar uma compilação de produção, script
de teste que executa testes. Vamos tocar isso
em um segundo e ejetar. O Eject nos permite
cancelar a configuração dos
scripts do React e personalizar a configuração nós mesmos
na medida em que precisarmos. Então, temos muitas
dependências relacionadas à caixa de trabalho. O que é isso? Tudo isso está relacionado à criação de
um aplicativo web progressivo. Vamos falar
sobre isso mais tarde, não
tocaremos em nada disso. Sinais vitais da web, vamos
abordar isso em um segundo. Os scripts React são o pacote
com a configuração. Dependência do React
e biblioteca de testes, também
abordaremos isso
em um segundo, e nossas dependências de desenvolvimento
que acabamos de instalar. Incrível, agora, se olharmos dentro da pasta pública, o propósito dessa
pasta é exatamente o mesmo do feed. Quaisquer arquivos que colocamos aqui são mapeados para o segmento de URL
em nosso aplicativo. Aqui temos o índice HTML
dentro da pasta pública. Se no feed o tínhamos
na pasta raiz, aqui o temos em público. Essa é a primeira, digamos, grande diferença entre o
feed e o aplicativo Create React. Aqui temos algumas
coisas que são diferentes. Primeiro, temos esse
URL público, variável global, esse URL público
será enviado pelo webpack. Quando nosso aplicativo for compilado, webpack processará o HTML do índice e substituirá
esse URL
público pelo caminho raiz do nosso aplicativo. No nosso caso, ele será traduzido para
algo assim. Só favicon, e pronto. Agora também temos o elemento raiz no qual o aplicativo
será montado. Praticamente o que
tínhamos no tic-tac-toe. Então temos o arquivo de manifesto. O arquivo de manifesto é editado em relação algo relacionado à criação
do Progressive Web App. Basicamente, ele controlará o atalho que será
usado para abrir nosso aplicativo. Vamos abordar
isso quando
voltarmos ao Progressive Web App, não
pensamos
nisso agora. Agora, o que temos
na pasta de origem? Na pasta de origem,
temos uma configuração muito básica. Na verdade, vamos executar
o script Start para iniciar o servidor
de desenvolvimento. Vamos ver, o que temos aqui. Se eu voltar aqui, demoro algum tempo
para abrir o aplicativo. Enquanto ainda está abrindo, vamos ver o que temos
dentro do índice que ele abriu. Vamos ver a
aparência do aplicativo e
voltaremos aos arquivos. Você pode ver que leva alguns minutos e já
temos um problema instantâneo aqui. O React é definido, mas
nunca usado dentro do App.js,
porque, como eu disse, no React 17 e anteriores, você sempre tinha que
importar o React do react sempre que usasse o
JSX dentro dos arquivos. A partir do React 18,
isso não é necessário. Usamos uma
opção de plug-in específica aqui jsx-runtime, que nos dirá que não
precisamos dela. É por isso que o removemos. No React 18, isso não
é necessário. Agora, este é o nosso aplicativo, é assim que parece
agora , nada muito especial, uma configuração
bem básica. Vamos explorar os arquivos. Vamos começar com o Index.js,
nosso ponto de entrada, e aqui temos algumas coisas que nunca vimos antes. Em primeiro lugar, temos
ReactDOM.createRoute, documento. Obtenha elemento por ID raiz, que é o elemento que
pegamos do índice HTML. As identidades devem coincidir. É aqui que o
aplicativo será montado. Novamente, temos um modo estrito que renderiza nosso aplicativo com uma configuração
bastante básica, mas também temos o registro do Service
Worker e relatamos sinais vitais na web. O que são esses? Registro de Service Worker
e Service Worker GS. Esses são os arquivos
que farão nosso aplicativo web um aplicativo web
progressivo. Não queremos realmente
pensar neles agora. Isso é algo que
usaremos mais tarde. Nós apenas os mantemos e, por enquanto, simplesmente
ignoramos o que temos aqui sobre o registro de Service
Worker. Novamente,
falaremos sobre isso mais tarde. Mas também temos relatórios de sinais vitais
da web aqui. Se olharmos para dentro, sinais vitais
da web,
é isso que importamos. Aqui, é apenas uma função
simples que importa algo chamado
web vitals e depois
disso, chama um conjunto de
funções aqui. O que é um web vitals que
está sendo importado aqui? Este é o pacote que
temos aqui. Web Vitals. Se voltarmos ao registro do NPM, dentro do registro do NPM, podemos pesquisar
esse pacote onde está vital e ver o que
exatamente ele faz. Resumindo, o web vitals
é um pacote, é
basicamente um conjunto
de funções que você vê no
relatório web vitals. Essas funções nos permitem
medir o desempenho
de nosso aplicativo. Que tipo de desempenho? O desempenho é baseado em diferentes métricas que podemos coletar quando nossa página é carregada. Você pode ler sobre
eles em detalhes aqui na
página oficial do pacote do NPM. É muito útil quando
você deseja obter a máxima otimização e velocidade
máxima em seu aplicativo. Como funciona, é que
dentro do índice, sim, chamamos esse relatório de web vitals
e aqui como um retorno de chamada, que é definido novamente aqui
na entrada de desempenho aqui. O retorno de chamada que
passamos aqui
será chamado em cada métrica. Se passarmos,
cancele aqui. Isso significa que todas as nossas métricas de
desempenho serão canceladas. Deixe-me realmente salvá-lo e ver o que
exatamente eu preciso. Se eu voltar para o aplicativo, vou para Inspecionar. Se eu olhar dentro do console, posso ver
métricas diferentes aqui. Console registrado como objetos
com valores diferentes. É exatamente isso que o pacote web
vitals faz. Ele mede o desempenho e fornece métricas.
Nada mais do que isso. Nós realmente não precisamos disso. Talvez, mas vamos
usá-lo mais tarde, mas não agora. Portanto, podemos mantê-la como uma função
simples aqui. Vamos ver o interior do App.js. Na verdade, uma boa
pergunta aqui seria por que temos todos os arquivos extensão
with.js
em vez de JSX? Porque no Tic-Tac-Toe,
em todos os lugares usamos.jsx. Bem, o Vite exigiu que usássemos a
extensão.jsx e o Vite funciona de forma a
pegar todos os arquivos com extensão
JSX e entender
que isso é o React. Aqui, como o Create React App é voltado apenas para aplicativos React, isso não é um
requisito porque ele entende que
tudo será React. Mas no Vite, era
diferente, pois o Vite também pode ser usado para
outras bibliotecas. Também vamos nomear nossos
arquivos como extensão with.js. Vamos renomeá-los
no próximo vídeo. No momento, não
excluiremos nada daqui. Dentro do App.js, temos o arquivo de
logotipo importado aqui. Eu só quero fazer uma anotação
rápida aqui porque podemos fazer com que nossos
ativos estáticos, como imagens, fontes, algo
que
é estático e não
requer nenhum processamento, não
requer nenhum processamento, sejam colocados em público e depois referenciados a partir do código-fonte. Mas aqui é importado. arquivo SVG é uma imagem. Ele foi importado como se
fosse algum script ou módulo. Então, tudo o que é importante
aqui é passado como fonte. Se olharmos para HTML, desculpe, aqui temos uma imagem
que aponta para o URL. Você pode ver que é como se fosse
gerado automaticamente ou algo foi feito com esse URL. Exatamente. Nos
bastidores, o que o Webpack fez, para que o pacote
React escrevesse a configuração, ele entendeu que
queremos importar a imagem. Em seguida, ele processou a imagem e gerou automaticamente
o URL para ela. Então, basicamente, foi
processado pelo Bundler. Você pode ter uma pergunta sobre o porquê. Por que precisamos mantê-lo separado? Por que alguns arquivos, algumas imagens
importamos da
fonte e outras que mantemos em público? Na verdade,
não há nenhuma razão especial por trás disso, eu suponho. A diferença é
que esses arquivos são processados pelo Bundler. Esses que estão
dentro da pasta pública não
são processados
pelo Bundler. Poderíamos ter movido esse
logo.svg para o Public. Então, dentro do App.js, nós apenas referenciaríamos
logo.svg, certo? Se eu salvá-lo, eu atualizo, tudo permanece o
mesmo e você pode ver logo.svg é servido na rota do
aplicativo
porque o temos dentro da pasta pública e os segmentos de URL são
mapeados, como você lembra. Ele é colocado dentro da fonte, depois é
importado desse jeito
e, em seguida, na fonte especificada. Dessa forma, você
pode carregar imagens. Diz que isso não pode ser resolvido. Provavelmente, isso ocorre porque
eu preciso reiniciar meu aplicativo para que ele possa realmente
retomá-lo. Vamos fazer isso por precaução para garantir. Mas acho que isso é tudo
o que precisávamos fazer. O que podemos fazer aqui
para resumir isso,
o que acabamos de criar até agora, precisamos também no Git fazer o upload desse projeto
que acabamos de
criar no GitHub e adicionar outro commit porque
instalamos novas dependências. Vou iniciar o
aplicativo. Você pode ver que estava funcionando bem e o
URL foi bem-sucedido. De qualquer forma, você pode ver que o Git
já está nele aqui. Quando criei o modelo, quando executo o npx Create React App, ele inicializou automaticamente o
Git dentro dessa pasta. Se eu digitar git log, já
tenho um commit
inicial aqui. O comando cuidou disso. No entanto, como
introduzimos nossas próprias mudanças, vamos confirmá-las. Vamos ver o que temos aqui? Temos App.js, index.js. Vou remover todas
as alterações que fizemos aqui porque realmente
não precisamos delas. Vamos fazer tudo
no próximo vídeo. Estamos interessados apenas
em nossa configuração ESLint que adicionamos e na configuração
Prettier, na qual
adicionamos package lock e package.json porque
instalamos as dependências de desenvolvimento. Ótimo. Tudo
está dentro do palco. Vou apenas
confirmar tudo e chamá-lo de Prettier e ESLint instalado e
configurado. Incrível. Agora é hora
de enviarmos esse projeto
para o GitHub. Vamos embora. Na minha conta do GitHub, vou criar um
novo repositório no canto superior direito. nome do meu repositório será Box Office App. Vou torná-lo privado. Não quero adicionar nenhum Read Me. Eu já tenho gitignore. Se olharmos dentro do gitignore,
assim como antes, temos os módulos
do node a pasta Build ignorada. Se no Tic-Tac-Toe, tivemos uma compilação gerada dentro
da pasta do disco, Create React App gera
uma compilação dentro da pasta Build. Na verdade, vamos criar o repositório e depois
executar o comando build. Em seguida, faremos o upload de tudo. Eu clico em Criar repositório. Então, novamente, siga exatamente
o mesmo procedimento. Eu copio git remote add origin
na URL do meu repositório. Eu o coloco dentro do meu terminal, eu executo esse comando. Então eu faço git remote
minus v para verificar se a origem do
alias aponta para o
meu repositório do GitHub. Incrível. Então eu vou fazer
git push origin master. E agora, se eu atualizar meu
repositório do GitHub, ele estará lá. Incrível. Vamos tentar executar o script de construção no final só para ver se
ele realmente funciona. Npm execute a compilação conforme
definido em package.json. Onde estão nossos roteiros? Aqui, e vamos ver,
diz criar uma versão otimizada
de produção. Bem, temos o React
definido, mas nunca usado. Isso é exatamente o que
tínhamos, na verdade. É muito irritante que nenhum vars não utilizado
produza um erro. Porque você pode ver
que isso interrompe a construção porque o ESLint produz um
erro para nenhum vars não utilizado. Vamos prosseguir e, especificamente para essa regra, se eu não estiver errado, fizemos exatamente a mesma coisa no Tic-Tac-Toe para não usar carros não utilizados. Vamos contar, por favor,
avise-nos em vez
de um erro. Um aviso, é só um aviso. É só uma mensagem para avisá-lo. Isso não quebra a
construção nem nada. Você pode ver que agora ele ficou amarelo e minha construção
foi concluída com sucesso. Vou apenas
manter como está, não
vou modificar o App.js. Deixe-me remover as
alterações que fiz. Aqui você pode ver a pasta Build apareceu e, se olharmos para o terminal, temos a saída de que
o projeto foi construído, supondo que ele esteja hospedado
na rota e depois em um
conjunto diferente de comandos, e se olharmos
dentro da compilação, podemos ver que esta é nossa compilação
de produção. Temos apenas arquivos estáticos. Temos HTML, CSS, JavaScript, imagens e
arquivos Json e até TXT. Temos licença para
um prestador de serviços. Agora, pegaremos
a pasta Build e a enviaremos para hospedá-la. Novamente, isso é o que
vamos fazer no final. Você pode ver isso funcionar.
Parece perfeito, não é? Agora, vamos adicionar essa alteração do
ESLint ao Git. Então, vou
confirmar e dar um nome, transformar nenhum vars não utilizado em aviso e, em seguida, fazer
o upload de tudo para o GitHub. Ótimo. No próximo vídeo, vamos limpar todos
esses arquivos dentro do código-fonte. Depois disso, vamos começar com o desenvolvimento.
Nos vemos lá.
59. 03 Limpeza de arquivos redunant: Olá. No último vídeo, criamos um novo projeto usando o modelo de aplicativo
Create React. Neste vídeo,
vamos apenas fazer uma pequena limpeza, que removerá esses arquivos desnecessários que não
vamos
usar da fonte. Nesse exato momento,
começaremos o desenvolvimento. Vamos embora. Em primeiro lugar, no último vídeo, eu realmente não
abordei nada sobre testes de
configuração e
os pacotes de bibliotecas de teste que temos aqui. Portanto, podemos realmente testar aplicativos
React. Podemos escrever testes programáticos usando algo chamado biblioteca de testes
React. Não vamos fazer
isso aqui na bilheteria. É por isso que simplesmente o removemos porque não será usado. A primeira coisa que
farei é remover “App.test.js”. Vou remover
“Setup.tests.js” de “package.json”.
Vou remover todas essas dependências desse
jeito. Vamos ver, e pronto. Agora removemos a biblioteca de
testes do projeto porque
não vamos abordá-la aqui. Em seguida, temos “logo.svg”. Nós realmente não precisamos disso. Temos "index.css “, podemos realmente mantê-lo. Temos "App.css “, nós realmente não precisamos
dele porque" index.css " contém estilos globais para o corpo, vamos mantê-lo
lá e não tocá-lo. Então temos
“reportWebvitals.js”. Talvez precisemos dele para medir o desempenho se estivermos
realmente interessados, então podemos
mantê-lo, por precaução. "Service-worker.js" é
algo que podemos anexar posteriormente, quando vamos
lidar com aplicativos web progressivos. E, a propósito, se você olhar para
dentro do prestador de serviços, já
podemos ver que temos algo aqui
destacado em vermelho. Novamente, são nossas
adoráveis regras de ESLint. O que podemos fazer sobre isso é simplesmente desativar o ESLint
somente nesses dois arquivos, dentro de "service-worker.js" e dentro de
“serviceWorkerRegistration.js”. Novamente, falaremos
sobre esses arquivos mais tarde. Só queremos ter certeza de
que esses arquivos não produzam nenhum erro ou
aviso por parte do ESLint. Vamos usar o eslint-disable assim
com uma barra em asterix, para desativar o ESLint
somente para esse arquivo. Vou copiar essa
linha e colá-la dentro "serviceWorkerRegistration.js"
na parte superior. Agora não temos nenhum
aviso ou erro de ESLint aqui. Incrível. A próxima
coisa que faremos é renomear
"index.js" e " App.js
" para ter a extensão.jsx apenas para
diferenciar arquivos com marcação
jsx e arquivos
sem marcação jsx, apenas arquivos js comuns. Isso é especificamente importante para "service-worker.js" e "erviceWorkerRegistration.js”. Porque esses arquivos
não são nada sobre o React. Esses são arquivos
apenas sobre front-end. Eles não podem ser usados
especificamente no React. Nós renomeamos "index.js"
para ter a marcação.jsx. Exatamente o mesmo, faremos para "App.js”. Dentro do App.jsx, não
precisamos
importar o React do
React porque, novamente, usamos o React 18. E o React 18
não exige que você
importe o React para o escopo do jsx. Removemos "logo.svg “, então removemos
a referência a um arquivo inexistente. Removemos "app.css “, removemos novamente
a referência a um arquivo existente. Dentro do componente App,
podemos simplesmente manter olá por enquanto, sem
nenhum nome de classe aqui. Muito simples. É muito simples aqui também. "Index.css" é mantido, por
isso que importamos. Vamos ver o que
mais aqui também. O que quer que tenhamos em
público no final, vamos
substituí-lo por nossos próprios ícones, por nossas próprias imagens. Não os excluímos por enquanto, e acho que
é basicamente isso. A única coisa que precisamos fazer executar o npm install para refletir as mudanças que
fizemos em “package.json”. Como removemos essas dependências da
biblioteca de teste aqui, elas são removidas
de “package.json”, mas não são desinstaladas
de “node_modules”. Se eu executar o npm install, ele apenas removerá as dependências inexistentes e “package.json” da pasta
“node_modules”. Você pode ver: “Foram removidos
71 pacotes”. Novamente, tenho seis altas vulnerabilidades. Por favor, não
me assuste com eles. Por enquanto, vamos nos comprometer, git add. Já está em estágio e o
“git commit” será removido ou limpo da pasta
de origem do aplicativo Create React
inicial. configuração. Incrível. Nós nos esforçamos para dominar
tudo e, nessa boa nota, nos
vemos
no próximo vídeo.
60. 04 React Router v6: Ei, neste vídeo, finalmente
prosseguiremos
com a codificação
e, finalmente,
começaremos a construir
algo. Vamos embora. Se você se lembra de Tic-Tac-Toe, tínhamos apenas uma
página em nosso aplicativo. Não tínhamos nenhuma
navegação entre as páginas, e o fato é que, no React, não
há navegação embutida na biblioteca. Isso significa que, se
quisermos fazer alguma navegação
entre as páginas, precisamos fazer isso sozinhos. Bem, há um
pacote para isso,
que gerencia a
navegação para nós. Na realidade, existem
vários pacotes que podem fornecer roteamento dentro do aplicativo. Essa navegação entre páginas é chamada de roteamento entre páginas. Existem
pacotes diferentes que podem fazer isso, eles têm mais ou menos
a mesma interface. O que vamos usar é
o React Router. Se eu abrir a
documentação oficial aqui, posso escolher que sou novo. No entanto, posso concordar que sua documentação mais recente não
é muito clara. Não vi nada que eu precisasse executar para instalar o React Router e esse tutorial
também é muito longo e
abrange tudo, mas e se eu quiser começar rapidamente? Para começar com o React Router, primeiro precisamos instalar esse
pacote e, para fazer isso, precisamos executar npm
install react-router-dom. Fazemos isso, depois disso, ele aparecerá
dentro do pacote json. Agora, vou executar o servidor de
desenvolvimento novamente e vamos dar uma olhada
na documentação. Aqui, se passarmos
pela configuração, ela realmente nos solicitará a inicialização de um novo aplicativo
React com o Vite. Vamos pular essa etapa. Depois disso,
vemos “Adicionar um roteador” e aqui precisamos
criar algo assim. Mas eu pessoalmente acho um pouco confuso seguir
esta documentação, porque eu conheço o React
Router das versões anteriores, então atualmente ele está na versão
6 e todas as versões principais, como 5, 4, 3, ele sempre muda sua
API, sua interface, porque agora é completamente diferente do que
era antes. Para simplificar, vamos para os conceitos principais
à esquerda e aqui vamos para a seção chamada
Renderização, se eu não estiver errado. Aqui, você pode encontrar um exemplo
muito bom do qual fica claro o que
exatamente o React Router faz
e o que vamos fazer? Em vez de seguir toda
essa longa documentação, vamos pegar apenas o que precisamos. Vamos pegar esse
exemplo e
entender o que exatamente o
React Router pode nos dar. Podemos ver uma chamada raiz de criação bem
básica que já temos dentro index.jsx e vemos que
precisamos ter essa árvore de classificação. Em primeiro lugar, precisamos
ter um roteador de navegador. Vamos importar
isso e
provavelmente
faremos tudo isso dentro do App. Na verdade, podemos importar roteador
do navegador e
usá-lo dentro do index.jsx, no entanto, vamos fazer isso dentro do App. Primeiro precisamos obter de algum lugar todos
esses componentes, todos
eles são importados
do react-router-dom e há algum lugar dentro
dessa longa documentação. Você pode realmente
encontrá-los lá. Precisamos de um roteador de navegador e precisamos de rotas,
e precisamos de rotas. Então, vamos importar algo do react-router-dom, então precisamos pegar o roteador
do navegador e precisamos pegar rotas, não o roteador, e
precisamos pegar a rota. Esses três componentes. Agora, o que vou fazer copiar essa marcação e colocá-la dentro do App, sem mais
nem menos. Mas aqui, agora não
temos todos
esses componentes definidos
aqui, tudo bem. Na verdade, o que está acontecendo aqui? Usando essa estrutura em
forma de árvore, podemos definir rotas em
nosso aplicativo React. Pense nas rotas como se fossem páginas, então cada rota é
representada por uma página. A rota é basicamente
apenas um segmento de URL. Se você tiver,
digamos que para equipes de caminho, sempre que o URL for, digamos, equipes de corte, podemos exibir esse
componente de equipes usando a sintaxe. Mas não vamos fazer isso. Por enquanto, só precisamos
mostrar pelo menos alguma coisa. Vamos comentar isso, esses componentes de rotas
e, analisando-os, vamos ver o que podemos fazer para nós mesmos. Vamos apenas
seguir em frente e criar rota no caminho; rota e índice. Um elemento será
alguma coisa. O que precisamos mostrar aqui? Aqui, precisamos renderizar o componente que
representará nossa página. O que eu sugiro é
que, dentro do Source, criemos uma nova
pasta e a chamemos de Pages, e aqui vamos criar componentes que
representem nossas páginas. Vou criar
um novo arquivo aqui, vamos chamá-lo de Home.jsx. A partir daqui, vou criar um componente
doméstico
como esse e depois exportá-lo por
padrão desta forma. A partir de agora, será uma
div simples que diz Página inicial. Então, para o índice de caminho apenas
para rota, vamos renderizar o
componente inicial e, a propósito, você pode ver assim que eu digito home e quando meu cursor
é colocado no final, eu tenho esse IntelliSense
aqui no menu suspenso. Se eu pressionar “Tab”, ele será importado para mim, muito legal, não é? Agora, eu mantenho assim
e, se eu voltar ao meu aplicativo, veja o que eu tenho. Eu tenho uma página inicial aqui e,
se eu acessar qualquer outro URL, tenho uma página vazia. Se eu inspecionar a marcação, abro o corpo, tenho a rota. Mas dentro da rota, eu
não tenho nada. Isso porque aqui, eu não defini nenhuma
rota, nenhuma página. React Router funciona
da forma que combina o segmento de
URL aqui, o nome do caminho com o caminho que você especifica aqui nas renderizações, elemento
correspondente. Agora, vamos tentar
criar outra página. Vamos chamá-lo de Contato e
aqui vamos apenas renderizar. Só para dar um exemplo, vou criar
div e dizer contato. Agora, se eu entrar em contato, vejo a marcação,
o que eu passei como elemento aqui, sem
mais nem menos. Agora sabemos como o
React Router funciona. O resto que você vê
aqui no exemplo, abordaremos isso
nos próximos vídeos, porque isso
é algo sobre layout, então podemos ter um layout que pode ser compartilhado entre
várias páginas. É aí que entra essa rota sem nenhum caminho ou sem
nenhum índice. Além disso,
abordaremos esta coluna aqui, que será
a representação
de uma página dinâmica,
mas, novamente, vamos
abordá-la mais tarde. Esse não é o momento. O que faremos por enquanto, talvez apenas
criaremos
nossas páginas iniciais. O que posso dizer
aqui é que na bilheteria teremos
a página inicial
e, em seguida, teremos
a página favorita. Para referência futura, como já
criamos duas páginas, vamos adicionar outro componente de
página, que
chamaremos de básico de início, e vou copiar
tudo o que tenho dentro. Vou
renomeá-lo para estrelado. Então, dentro do componente do aplicativo, novamente, vou
importar o componente favorito, que representa nossa página. Em vez de contato, vou exibir o caminho com estrela
e, em vez de contato
, o caminho com estrela apenas para verificar
se, se
eu for para favorito, tenho minha página favorita. Ótimo. E
essas páginas vazias , então, se seguirmos por uma rota
indefinida? Não é 404, mas é uma
página que não foi encontrada. React Router tem uma explicação para isso, como lidar com isso. Se formos para a seção de perguntas frequentes aqui, podemos ver como adiciono uma rota 404 sem correspondência
no React Router 6. Você pode simplesmente usar isso. Vamos colocá-lo talvez
no final ou no topo.
Se não me engano, ele
pode ser colocado em qualquer lugar. Em vez de nenhuma correspondência importante por enquanto ou talvez não a
alteremos, vamos apenas
exibir não encontrada. Vamos tentar. Nós acessamos o aplicativo e
sempre que vamos para qualquer rota que
não definimos, recebemos não encontrada. Mas se formos para a página inicial, teremos a página inicial, se formos para estrelar,
teremos estrelado. Incrível. Agora, como
podemos navegar entre essas páginas porque
temos tags âncora,
mas não podemos realmente
usar tags âncora quando
usamos uma
biblioteca de roteamento do lado do cliente, como o React Router. Precisamos usar um
componente específico para isso. Vamos para casa e agora precisamos de algo
chamado componente link,
que importamos novamente do componente de link dom do React Router. Vou apenas exibir um componente de
link assim, é basicamente apenas um invólucro
em torno da tag âncora, mas é específico
do React Router então o React Router pode
entender que você queria fazer a transição
de uma rota para outra rota e, em seguida, vamos chamá-la de
go para a página favorita. Para esse componente de link,
precisamos passar prop called para especificar a rota
que gostaríamos seguir quando
clicarmos nesse link. Como nosso componente favorito é definido em caminho marcado com estrela, quando clicamos em Ir
para a página favorita, vamos para a rota favorita. Agora voltamos para casa, se olharmos a marcação,
você pode ver que, por baixo do
capô, é na verdade uma etiqueta de ancoragem que
leva à rota marcada com estrelas. Se clicarmos nela,
agora estamos na página favorita. Legal, não é? É isso. Bem, esses são, na verdade,
os princípios básicos do React Router. Como você pode ver, seu
objetivo é oferecer essa experiência de navegação
no aplicativo React. Porque, novamente, o React não tem nenhuma
solução embutida para
isso, é por isso que precisamos
usar nossa própria solução ou instalar uma biblioteca que forneça
recursos de roteamento para nós. Acho que é isso para a introdução
sobre o React Router. No próximo vídeo,
começaremos a criar layouts e
continuaremos com nosso aplicativo. No final, eu só
queria adicionar uma nota
sobre o React Router, e por que realmente os
chamamos de rotas, por que não os chamamos de páginas? O fato é que estamos
criando algo chamado
aplicativo de página única. Um
aplicativo de página única é
basicamente um único arquivo
HTML de índice aqui, por
isso é
chamado de aplicativo de página única. Sempre que navegamos entre rotas ou as chamamos de páginas, o que realmente acontece é
que o React Router usa JavaScript para
substituir a marcação HTML e, em seguida, exibir os componentes
correspondentes, chamamos isso de navegação, mas
basicamente o que
ele faz, ele apenas pega o
HTML existente, o remove e insere um novo HTML
e, em seguida, substitui o URL por qualquer coisa que
especifique como rota. Tudo aqui é
gerenciado por JavaScript. Ainda temos a mesma página, não muda que o
HTML não mude aqui,
o esqueleto, o modelo, essa indexação não mude, mas o JavaScript realmente imita essa experiência de navegação,
então, para o usuário final que consome o aplicativo,
parece que estamos
navegando nas páginas. Bem, podemos dizer que de fato somos. Tecnicamente falando, isso
é apenas remover HTML e inserir um novo HTML na página e alterar o
segmento de URL, só isso. Nos aplicativos tradicionais, quando
você clica em uma página diferente, a página é atualizada, e é quando
você tem uma
navegação real,
digamos, de página para página. Aqui, no que
chamamos de navegação do lado do cliente, a navegação do lado do cliente
significa que, na verdade,
navegamos pelas páginas
usando JavaScript. Agora, vamos confirmar as
mudanças que fizemos. Dentro do aplicativo, talvez
eu o mantenha. Vamos guardá-lo para referência
futura. Vamos adicionar jsx, vamos adicionar home, vamos adicionar
tudo ao estágio, instalamos o React Router e, eventualmente, vamos confirmar
tudo
e dizer Edit, React Router dom no aplicativo ou talvez tenha
instalado
o React Router dom. Perfeito.
Nos vemos na próxima.
61. 05 Layouts e navegação entre páginas: Olá de novo. Neste vídeo, falaremos
sobre layouts, como podemos gerenciá-los e quais são os layouts
em primeiro lugar. No último vídeo,
instalamos e digamos, configuramos o roteador de
reação. Essa é a solução de roteamento que
usaremos para nosso aplicativo. Agora, veremos
como podemos realmente aplicar layouts porque temos uma página de índice,
e digamos que elas
compartilhem um layout comum. Nas duas páginas, queremos
ver a navegação. O que podemos realmente fazer ir até um componente doméstico
e colocar o link aqui. Então vamos para o componente estrelado
e colocamos o link aqui, mas isso é muita repetição. Só queremos ter uma
marcação comum que coloquemos em um só lugar e que
seja exibida em todos os lugares. Olhando para este exemplo, se voltarmos
à documentação, se formos para
Conceitos principais, renderização, este é o lugar onde tiramos essa marcação do último vídeo. Podemos ver algo
chamado Layout Routes. Se você ler aqui, ele diz basicamente que esse elemento de
rota aqui que envolve outras rotas é apenas um componente que pode fornecer algum layout
para as rotas subjacentes. Ela não representa a
página em si. Os pagers são
representados apenas por rotas que definem o caminho prop aqui. Para obter o layout, podemos
seguir essa abordagem. Se precisarmos compartilhar o layout entre a página inicial
e a página com estrela, podemos agrupá-las na
rota, como aqui. Então, vamos em frente. Vamos criar um componente de
rota. Vamos agrupar a página inicial e a página com estrela nesse caminho. Podemos especificar
um único elemento sem
nenhum suporte de caminho. Aqui, estará nosso
layout que
gostaríamos de ver para essas páginas. Como vamos gerenciar isso? Dentro das classificações, criaríamos uma nova pasta e a
chamaríamos de componentes. Aqui, vamos
colocar um novo componente, que chamaremos MainPageLayout ou vamos
chamá-lo de MainLayout. Aqui, vou
criar o layout principal. Em seguida, exporte-o daqui,
exporte o padrão, MainLayout. Incrível. Agora,
vamos importar esse layout dos
componentes, MainLayout. Então, em vez do layout da página, vamos usar o layout da página
principal. No entanto, como exatamente isso funciona? Porque se eu abrir
meu layout principal, ele ficará completamente vazio. Não há nada lá dentro. Então, o que será renderizado? Vamos tentar ver. Se voltarmos ao aplicativo, agora, nosso aplicativo está vazio. Bem, o que acontece? O fato é que, se você se lembra, no React, temos algo
chamado adereço infantil. Se definirmos um componente e digamos
algo assim,
MainLayout e por dentro
passarmos algo,
o que MainLayout e por dentro
passarmos algo, quer
que passemos dentro desse componente entre o colchete de
abertura e fechamento,
ele ficará disponível
como o suporte infantil que podemos usar dentro da
marcação JSX dentro desse componente. No entanto, com o roteador React, não parece assim. Não passamos por nenhuma
criança porque passamos como um componente de
fechamento automático. Então, como isso funciona? Se olharmos aqui
dentro do PageLayout, precisamos de algo
chamado outlet. Aqui à direita, está
a seção chamada tomada. O Outlet é usado dentro desses componentes que
representam layouts. Eles
representam basicamente as crianças, pelo
menos, o conceito é
muito parecido com o de crianças. Eu passo por esse conjunto de rotas. Esse elemento tem
o layout principal. Mas, como não temos
acesso a crianças aqui, ainda
precisamos informar
esse componente
MainLayout que queremos renderizar
o que quer que esteja dentro. Para isso, o roteador React tem
esse componente chamado outlet. O Outlet é basicamente
como crianças, mas para todas as rotas que são passadas dentro desse componente de rota. Bem, é confuso. Na verdade, deixe-me mostrar a você. Importamos algo da reação para dom e esse algo vai sair. Em vez de escrever para crianças, tomada é a substituta. Não usamos crianças, usamos apenas tomadas. Simples assim. Aqui em cima de nossa loja, vamos dizer que
isso é marcação compartilhada. Eu o guardo. Eu volto e você
pode ver que o que está sendo renderizado aqui é que esta
é uma marcação compartilhada e, em seguida, esta é uma página com estrela. Basicamente, a saída aqui
representa tudo o que
passamos dentro desse layout , conforme definido pelos componentes da
rota. Agora, se formos para casa, veremos exatamente
a mesma imagem. Temos isso como marcação compartilhada. Agora,
vamos adicionar uma navegação que
será compartilhada entre as páginas. Dentro dos componentes, vou
criar um novo componente, que chamarei de Navs. Por enquanto, novamente, como
sempre, será div, que diz algo e
depois exportará por padrão Navs. Ótimo. Então, dentro de main,
em vez disso,
está a marcação compartilhada, vamos exibir o componente
Navs. Novamente, você pode ver que comecei a digitar, meu cursor está no final. Eu tenho o menu suspenso com a inteligência e
se eu pressionar “Tab”, agora, boom, ela é importada automaticamente. No entanto, tenha cuidado com isso. Esse é um recurso muito importante, eu diria
que ele pode
importar facilmente os outros arquivos, não exatamente o que você espera. Tenha cuidado com isso e
sempre verifique suas entradas. Estamos sob o comando da Marinha aqui. Dentro do Navs, gostaríamos
de exibir a navegação. Vamos pegar
aquele trecho de código que já
temos na página inicial. O componente de link, você lembra que usamos para navegar entre as páginas quando
usamos a biblioteca do lado do cliente
react-router-dom. Vou copiar o
link de importação do react-router-dom. Vou
colocá-lo dentro de Navs. Aqui, precisamos exibir a navegação. Como
vamos fazer isso? Antes de tudo, precisamos definir nossos botões nos quais
vamos clicar e fazer a
transição entre as páginas. Vamos definir
nossa matriz de botões, matriz de elementos,
que serão nossos links. Em seguida, mapearemos esses links para a marcação
JSX exatamente da mesma forma que fizemos com a
história no tic-tac-toe. Aqui fora do Navs, vou criar um componente porque conhecemos um componente,
apenas uma variável chamada links. Será uma matriz de objetos e cada objeto
terá a seguinte forma. Ele terá texto e precisará. Para será algo
que passaremos para o componente do link e o
texto será o texto exibido. O texto vai chegar em casa. Ele irá para a
rota, para a página inicial. Em seguida, vamos adicionar
outro objeto aqui. Vamos chamá-lo de Starred. Isso nos levará
à rota estrelada. Agora, precisamos pegar essa matriz e
marcá-la com a marcação JSX. Então, aqui, dentro do Navs, em vez de div, podemos
exibir elementos do UL, ou talvez dentro do div ,
vamos exibir o UL, vamos continuar assim. Agora, dentro dessa UL, vamos mapear nossos links. Então, vou abrir
colchetes aqui. Eu vou dizer ao Links.map. Agora pegamos o item. Vamos nomear esse objeto
que mapeamos como item. Vamos
mapeá-lo para o elemento li. Dentro desse elemento li,
vamos dizer que ,
por favor, exiba
item.text e, como uma chave, porque você se lembra que
quando mapeamos elementos sempre para a marcação JSX até
o elemento de encapsulamento, sempre para a marcação JSX até
o elemento de encapsulamento,
precisamos passar uma
chave exclusiva
que identificará esse elemento dentro da
marcação JSX que está sendo mapeada. Portanto, em nosso caso, o segmento de URL que usamos aqui é
exclusivo para cada item ou pode ser texto. Mas vamos passar para a chave. item to
identificará nosso elemento. Também precisamos
transformá-lo em um link. Usamos o
componente link para isso, que importamos do
react-router-dom. Então, em vez do texto do item, vamos fazer o texto do item do
link. Para o adereço da fila
dentro do oponente do link, vamos passar item.to. Vai ficar assim. Agora, voltamos ao aplicativo e o que vemos,
vemos a navegação. Se clicarmos em Favoritos, vamos para a página Favoritos. Se clicarmos em Início, vamos para Início. Legal, não é? Parabéns, agora temos o componente de
navegação, que funciona muito bem, assim
como usamos
layouts para gerenciar isso. Agora, vamos limpar a
página inicial e eliminar link aqui e apenas dizer Início. Agora, parece que sim. Incrível, não é? Talvez, vamos continuar
aqui e adicionar um título. Vamos criar um novo
componente aqui e chamá-lo de Título ou,
digamos, AppTitle. Então, a partir daqui, vamos adotar outra abordagem,
porque sempre
estávamos criando uma função e depois a
exportando por padrão. Então, em vez disso, podemos apenas dizer export default e, em seguida, a
função e o que ela diz, vamos ver que
falta o nome de exibição da definição do componente, é claro. Então, o que ele quer que façamos, ele quer que façamos
algo assim. Função AppTitle. Porque ele quer que
exportemos uma função que
realmente tenha nome, não apenas uma
função anônima como essa,
mas com o nome. Isso é bom. Isso tornará o código um pouco
mais declarativo. Às vezes, ajuda a rastrear erros que podem vir
de diferentes funções. No nosso caso, esse não
será o caso. Mesmo assim, vamos explorar mais a sintaxe do
JavaScript. Vamos chamá-lo assim. Então, aqui, em vez de
Navs e outlet, podemos exibir o título h1. Então, o título será o adereço que
receberemos. Novamente, como
começamos a explorar mais a sintaxe de JavaScript, em vez de desestruturar, vamos aplicar a desestruturação
em outro lugar. Então, recebemos o objeto de adereços. Aqui, na próxima linha, vamos aplicar a
desestruturação, em vez de incorporá-la
diretamente nos argumentos. Então, vamos
pegar o título, assim como vamos pegar a legenda. A legenda estará dentro
do parágrafo, do subtítulo, e vamos usar esse
AppTitleComponent dentro do layout
principal, logo abaixo dos navs. AppTitle, novamente,
IntelliSense e tab, e boom, ele é importado. Vamos ver como fica. Não vejo nada ou
perdi alguma coisa? Deixe-me ver. Não, eu não fiz isso. Na verdade, eu fiz. Se eu inspecionar a marcação, posso ver que tenho minha marcação, mas ela está vazia.
Bem, o que acontece lá? Porque, bem, você deve
ter notado, mas eu executei o AppTitle sem que
nenhum adereço fosse passado. No entanto, AppTitle renderiza
título e subtítulo. Como não os ultrapassamos, eles estão vazios. Isso significa que eles são indefinidos. O título está indefinido, o subtítulo é indefinido porque, novamente, não os
passamos. Nesse caso, precisamos
transmiti-los, olá e outra coisa. Boom, agora está aqui, foi exibido,
tudo funciona. Mas aqui está uma alternativa. Digamos que temos
situações em que não
passamos adereços, apenas por algum motivo. Talvez tenhamos esse
componente que tenha sido reutilizado em vários lugares, muitas vezes, seja o que for, e nem
sempre que passamos adereços. Por esse motivo, como
os componentes são apenas funções e sabemos que podemos aplicar argumentos
padrão às funções, podemos fazer exatamente o mesmo
aqui em Componentes. Portanto, a partir do objeto
props, o objeto props é sempre definido, ele está pelo menos vazio. Desse objeto, distraímos seu título, subtítulo que não está definido nesse objeto porque não
passamos adereços. Mas podemos aplicar
valores padrão para eles. Se não passarmos nenhum
título por padrão, será
Bilheteria e Legenda, aplicativo de
pesquisa de filmes ou
talvez, digamos assim, você
está procurando
um filme ou ator? Só uma pergunta,
algo assim. Nossa estrutura final ficará assim. Se olharmos para dentro, você pode ver, bem, que eles estão sendo aplicados. Se eu voltar ao layout
principal, bem, você pode ver que eu
não passo nada, mas ainda tenho
meus valores padrão. Se eu quiser
alterá-lo ou sobrescrevê-los, eu simplesmente os passaria
imediatamente e eles funcionarão. No entanto, como
os definimos aqui dentro do
AppTitle por padrão, não
vamos passar
nada aqui para os adereços. Na verdade, vamos
colocá-lo em cima dos Navs. Então, parece que sim. Incrível. Então eu acho
que é isso para aquele vídeo. Na verdade, fizemos muita coisa e
abordamos muitos conceitos novos. Falamos sobre layouts,
como podemos gerenciar layouts que podem ser
compartilhados em várias páginas. Se olharmos
para dentro, usamos esse componente de saída, usamos esse componente de saída,
que substitui crianças, mas para a definição de rota
que temos aqui. Em seguida, também
abordamos como podemos criar navegação usando o componente de link e exibi-la dentro de uma marcação
compartilhada, bem
como títulos e argumentos
padrão, bem como valores padrão para os
argumentos ou para os adereços. Parece bom até agora. Vamos comprometer tudo e terminar este vídeo
com uma boa nota. Então, vou parar o aplicativo. Vou comprometer
tudo com uma mensagem. Vou chamá-lo “navegação adicionada e
layout compartilhado para páginas iniciais
e iniciais”. Incrível.
Nos vemos na próxima.
62. 06 entradas: Olá novamente. No último vídeo, gerenciamos layouts e navegação
dentro do nosso aplicativo. Parece muito legal. Agora podemos navegar
entre páginas diferentes. Sabemos como criar rotas. Nosso próximo passo aqui será
a caixa de tags que temos
na página inicial na qual
inserimos algo depois clicamos no botão. Em seguida, pegamos o texto
da caixa de texto e o
enviamos para algum back-end, que nos devolve os dados. No entanto, antes de
implementarmos tudo isso, precisamos entender como
podemos gerenciar as entradas no React. Neste vídeo,
vamos fazer exatamente isso. Então, vamos navegar até o componente
inicial e aqui, vamos criar uma
entrada simples do tipo texto. Nada chique. Se formos para Início, agora temos esse
elemento vazio aqui, caixa de texto vazia. Não podemos fazer muito sobre isso. E se eu quiser obter
algum valor disso? Como posso fazer isso? Porque, bem, no
futuro vamos adicionar um botão aqui e quando
clicarmos nesse botão, precisamos de alguma forma encapsular
o valor dessa entrada. Do Tic-Tac-Toe, você sabe
que precisamos usar o estado sempre que temos um
valor que muda durante o período do ciclo de vida do
componente. Sempre que digitamos
algo na entrada, esse é o valor que muda. É por isso que, por esse
motivo, vamos
usar o React, usar state hook. Então, vamos em frente. Do React, assim como antes,
vamos voltar novos. Então, chamamos usestate hook e, internamente, precisamos
passar o valor padrão que será o valor do
nosso estado inicialmente quando
o componente for montado. Como
será um elemento de entrada e o elemento de entrada será sempre uma string e, se não tivermos
nada dentro, insira apenas livros didáticos vazios, ainda
é uma string, mas vazia. É por isso que vamos
passar uma string vazia aqui. A razão para isso
é porque, se
não especificarmos nada para usestate, apenas o
chamamos
assim, por padrão, valor do estado
inicial
será indefinido. Então, como você se lembra,
usestate retorna uma matriz de exatamente
dois elementos, em que o primeiro elemento
é o próprio estado. Então, vamos chamar
esse valor de entrada de estado. A função de atualização de
estado será definido como valor de entrada. Agora, como podemos realmente ouvir essas atualizações de que digitamos algo
dentro da caixa de texto? Se você se lembra, temos eventos disponíveis em
cada elemento HTML. Então, eles começam com
o prefixo on. Portanto, se lidarmos com entradas, precisamos usar o evento
onChange. Então, para esse evento onChange, vou passar por
um manipulador de eventos e vamos ver o que temos
e quando esse evento é acionado. Vou criar
uma função aqui , chamá-la de OnInputChange. Se você se lembrar,
todos os manipuladores de eventos sempre recebem o objeto de evento
como o primeiro argumento. Vou apenas registrar
o objeto de evento no console e
, em seguida,
passarei onInputChange como manipulador de eventos
onChange. Agora, sempre que digito
dentro da entrada, posso ver algo
sendo registrado no console cada vez e, se eu
expandir esse objeto, tenho
aqui a propriedade de destino na qual estamos
interessados. Portanto, o alvo
do evento representa o alvo desse evento. No nosso caso, esse será
o próprio elemento de entrada. Se eu expandi-lo aqui, tenho a propriedade value, que representa o valor que o elemento
de entrada tem por vez. É por isso que podemos continuar e registrar o destino do evento no
console. Vamos primeiro considerar o destino do
evento apenas para ver mais uma vez que,
sempre que digitamos, destino
do evento representa
nosso elemento HTML de entrada. Nesse elemento HTML de entrada, temos essa propriedade de valor, que representa o
valor de entrada por vez. Sempre que eu digito,
você vê que agora podemos ter acesso ao valor que
temos dentro da
caixa de texto. Muito legal. Agora podemos usar o valor de entrada definido, estado dos dados. Nesse estado de dados, podemos passar o
valor alvo do evento para definir o estado. Agora, sempre que digitamos, atualizamos o estado com o valor alvo do
evento. Ótimo. Agora, como
podemos realmente ver esse valor de entrada é o que
escrevemos nos livros didáticos. Como você se lembra, podemos simplesmente colocá-lo aqui, registrar e verificar o
console, pois a atualização de estado
acionará a reentrada do componente e, quando os componentes forem alugados, o JavaScript interno é executado
novamente e, a cada reentrada,
veremos esse log do console. Vamos tentar. Sempre que digito, agora, posso ver que realmente
home.jsx6 na linha 6. Sim, eu tenho esse log do console, o que significa que o componente entra novamente, nosso estado é atualizado
de acordo com a entrada. Com essa abordagem,
temos um problema. O que você vê aqui é chamado de vinculação
de dados unidirecional. Portanto, nas estruturas de bibliotecas, você sempre terá
esse conceito de vinculação de dados
unidirecional ou vinculação
bidirecional de dados. O que isso significa? Portanto, com essa abordagem, introduzimos a vinculação de
dados unidirecional, ouviremos as alterações dentro da caixa de texto e
atualizaremos o estado. No entanto, se atualizarmos o estado, não
atualizaremos o valor da entrada. Vamos tentar ver o
que quero dizer. Então, se quisermos mostrar esse valor de entrada
em algum lugar da página, podemos simplesmente usar a interpolação. Simples assim. Nós
já sabemos o que fazer. Temos o valor de entrada aqui. Vamos ver se funciona. Sempre que eu digito, está sendo interpolado em
J6 e exibido. Muito legal. Como podemos verificar se é uma vinculação de dados
unidirecional? Vou criar
um botão aqui com o botão “Tipo”, atualizar para aleatório. Para desclicar, vou dizer, defina o valor de entrada como
algo como meu nome. Vamos ver o que temos. Então, sempre que
eu digito, meu estado é atualizado, mas se eu clicar em “Atualizar
para atualizações de estado aleatórias”, no entanto, o texto dentro da
entrada não será atualizado. Então, o que acontece aqui exatamente? O problema é que, até
termos uma vinculação de dados unidirecional,
vinculamos as alterações as alterações
que fazemos
nos livros didáticos ao estado, mas não vinculamos
o estado à caixa de texto, à entrada. Para corrigir isso, precisamos
passar um atributo de valor para o elemento de
entrada para que qualquer valor dentro
do estado que tenhamos, ele seja
mapeado e vinculado ao valor da caixa de texto. Então, para o atributo de valor, vou passar o valor de entrada. Vamos ver se eu digito algo aqui e depois clico
em
“Atualizar aleatoriamente”, agora o texto foi
atualizado não só aqui, mas também foi atualizado
dentro do elemento de entrada. Porque agora temos vinculação
bidirecional de dados. Se atualizarmos o estado, ele atualizará a caixa de texto
e, se atualizarmos a caixa de texto,
atualizará o estado. É bidirecional, funciona em duas direções, ao contrário do que tínhamos feito anteriormente. Se avançarmos na mudança e mantivermos apenas valor aqui,
será o mesmo. Será uma vinculação de dados unidirecional. Temos esse erro
aqui que diz que você forneceu uma propriedade de valor
sem um manipulador onChange. Até o React diz que
algo não está certo aqui. Então, como você pode ver, vinculação de dados
unidirecional
pode ser muito complicada. Portanto, você deve sempre se lembrar do
que é melhor para você. Eu diria que,
na maioria dos casos, você pode nem perceber que vinculação
unidirecional de dados pode
potencialmente trazer seus problemas
e, na maioria dos casos, não. No entanto, a vinculação bidirecional de dados é importante e você precisa entender a
diferença entre ela e saber como aproveitá-la. Até agora, neste vídeo, aprendemos como gerenciar o
estado com entradas. Como podemos usá-los para mudanças no
elemento de entrada e no estado da atualização. Também aprendemos o que é vinculação de dados
unidirecional, o que é vinculação bidirecional de dados e qual é a
diferença entre elas, e por que a
vinculação de dados unidirecional pode ser complicada. É sempre melhor usar a vinculação de dados
bidirecional
se você não tiver certeza. Acho que é isso. Agora você sabe tudo o que
precisamos no próximo vídeo. Vamos criar
um botão aqui. Vamos pegar
tudo o que escrevermos dentro da caixa de texto e enviá-lo para a API. Vamos ver como isso se
desenrola. Nos vemos lá.
63. 07 Submissão de formulário: Ei, aí. Como você se lembra,
no último vídeo, falamos sobre entradas, como podemos gerenciar entradas, como podemos vincular o
valor de entrada ao estado e a diferença entre vinculação de
dados
bidirecional e unidirecional. Neste vídeo,
enviaremos dados que gravamos dentro de
uma caixa de texto para uma API e receberemos os resultados
da API para que
possamos exibir algo em nosso aplicativo para o usuário. No último vídeo, fizemos tudo isso
dentro do Home.jsx. Na verdade, podemos mantê-lo, vamos
colocar esse botão aqui,
logo abaixo da entrada, logo abaixo da entrada, para que possamos digitar o texto. Já temos InputValue e temos onInputChange. Talvez possamos chamá-lo de
algo como SearchString, porque será basicamente nossa string de pesquisa
para resultados de pesquisa. Podemos renomear o estado para searchString, searchs-t-r e definir searchs-t-r.
Não precisamos emiti-lo, valor
será searchString e onChange será onSearchString
ou onSearchInputChange , e vamos
atualizar o SearchString. Então, para esse botão OnClick, vamos
removê-lo completamente. Vamos agrupar
esses dois em um formulário
e, em seguida, vamos aproveitar o atributo OnSubmit do
formulário. Na verdade, as formas reagem, elas funcionam de forma um pouco diferente. Em aplicativos de página única,
você trabalha com formulários um pouco
diferentes dos aplicativos tradicionais. Em aplicativos tradicionais,
quando você clica em “Enviar” e tem um formulário, você precisa definir
uma ação aqui que o levará
a alguma outra página. Quando você clica em “Enviar”, ele redireciona o usuário e envia
dados para outra página. Em aplicativos de página única
e aplicativos web modernos, ele não é gerenciado dessa forma. Como isso é gerenciado então? No formulário, colocamos
o método onSubmit, e esse método onSubmit
será a função que chamaremos de onSearch. Novamente, como é um manipulador de eventos para
o evento de envio, temos o objeto de evento. Vamos tentar e, por enquanto, não
fazer nada, o que vai
passar para OnSubmit OnSearch. Novamente, como é formulário, em
vez de digitar botão, para que
possamos
enviar o formulário, precisamos especificar que esse botão será do tipo enviar. Quando clicamos
nele, ele realmente envia o formulário
e, em vez de ser atualizado aleatoriamente, ele será pesquisado.
Algo parecido. Vamos tentar ver
se eu digitar algo aqui e pressionar “Enter”
ou se eu clicar em “Pesquisar”, deixe-me pressionar “Enter”. Você vê que o aplicativo
foi atualizado? Você pode ver que a
página foi atualizada. Agora eu tenho esse ponto de
interrogação no topo. Isso ocorre porque não
tratamos o formulário adequadamente, porque ele acha que o formulário, a ação, precisa ser
tratada por alguma outra página. Ele tenta redirecionar para alguma
outra página para enviar dados. No entanto, assim como uma ferramenta
em aplicativos web modernos, não é
assim que o formulário é tratado. Para que o onSubmit
impeça a atualização da página, precisamos impedir a ação
que o evento de envio realiza. Por isso, chamamos de padrão
a prevenção de eventos. Ao chamar esse método, evitamos o
comportamento padrão desse evento. Se eu atualizar a página, deixe-me remover o ponto de
interrogação na parte superior. Agora, eu digito algo,
clico em “Entrar”. Você vê que nada acontece. No nosso caso, em vez
de nada acontecer, precisamos realmente
enviar dados para a API. O que será a API? Como vamos gerenciar isso? onde vamos começar?
Se formos adivinhar aqui, se olharmos para os recursos, você pode encontrar a API TVMaze aqui. Vamos abrir esse link. A API TVMaze é
uma API pública que pode nos fornecer informações sobre diferentes
filmes e atores. É totalmente gratuito, tem cota ilimitada
e é público. Você pode simplesmente abrir esse URL
e seguir a documentação. Está muito
bem documentado, com bons exemplos e
boas explicações para os endpoints que possui. O que nos interessa é na verdade, o
primeiro parágrafo aqui, que diz “mostrar pesquisa”. Ele tem esse URL, e aqui está um exemplo. Vamos tentar abrir
isso em uma nova guia. Como você pode ver, temos dados aqui. Nós apenas o acessamos e
recebemos os dados de volta. Se você der uma olhada no URL, aqui nós fornecemos o q, parâmetro de string de
consulta, e se eu o alterar
para outra coisa, ele me dará resultados
diferentes com
base na string de pesquisa. Esse parâmetro q é
basicamente a string de pesquisa. Você pode ler sobre isso na descrição do
que esse endpoint faz. Vamos usar esse
endpoint dentro do nosso aplicativo. Vamos voltar e
colocá-lo aqui. Vou apenas
comentar isso. Agora, você pode ter uma pergunta. Como enviamos uma
solicitação para essa API? Bem, podemos
acessá-lo no navegador, mas como podemos fazer
isso dentro do aplicativo? Bem, dentro do navegador, temos uma API da web chamada Fetch. A função Fetch está
disponível globalmente no ambiente
do navegador,
portanto, podemos usá-la
dentro do JavaScript. O que o Fetch faz, ele envia uma
solicitação para o URL fornecido. Podemos pegar esse URL, podemos chamar Fetch. Novamente, é uma função
que envia solicitações e
está disponível globalmente
no JavaScript do navegador. Chamamos essa
função Fetch aqui e
passamos o URL para dentro. Eu clico em “Entrar”
e, como você pode ver, ele nos retorna uma promessa,
um objeto de promessa. Isso significa que começamos a trabalhar
com JavaScript assíncrono. É aqui que as coisas
começam a ficar interessantes. Para obter valor
da promessa, temos que aguardar essa
promessa ou resolvê-la. Por enquanto, vamos
usar a sintaxe.then aqui. Essa função Fetch é resolvida
para o objeto de resposta. A promessa
retornada do Fetch resulta no objeto de resposta, que representa a resposta dessa solicitação. Vamos
chamá-lo assim. Vou chamá-la de resposta, e vamos tentar a resposta
console.log. Esse é o
objeto de resposta que temos. Ela representa o
status da resposta, o URL usado, os cabeçalhos e algumas coisas
diferentes aqui. No entanto, esse objeto de
resposta também tem o método.JSON disponível
em sua resposta ao JSON. Também é um método
que retorna uma promessa. A promessa é revertida
para o corpo de resposta. O que você vê aqui dentro do
navegador é o corpo da resposta. É basicamente o que está sendo
retornado do servidor, a resposta, então a
obtemos no formato JSON. É por isso que chamamos
o método.JSON. Novamente, ele retorna uma promessa, que se resolve para o corpo.
O que vamos fazer? Vamos agrupar
vários densos aqui primeiro. Depois, chamaremos o
método.JSON no objeto de resposta. Em seguida, retornamos essa promessa
de.then callback, o
que significa que, no próximo,
ela será resolvida. Em seguida,
teremos nossa carga útil
ou corpo de resposta. Vamos chamá-lo de body
e console.log body. Agora, essa string nos deu
essa matriz de 10 elementos. Se o expandirmos, você poderá ver que esses
são os dados que temos aqui dentro
da janela do navegador. Legal. Mas agora gerenciamos isso programaticamente
usando a API Fetch. Exatamente o mesmo,
podemos fazer não apenas aqui, mas dentro do nosso código, porque o que
escrevemos aqui será o
JavaScript do navegador do lado do cliente e nós
apenas brincamos com ele aqui diretamente dentro do navegador , mas ainda assim não importa. Isso foi apenas para dar uma visão geral de como
isso vai ser. Mas vamos fazer isso
aqui dentro do nosso código. Dentro do OnSearch,
chamaremos essa API Fetch de
tvmaze.com/search/shows. Agora, em vez de
usar a sintaxe.then, podemos usar async-await para
torná-la mais legível. Para usar await, se você ver eu passar o mouse
sobre ele, ele diz que expressões de
espera só são
permitidas nas funções de sincronização , o
que significa que precisamos
marcar essa função como uma sincronização e agora a mensagem desaparece. Aguardamos Fetch, então obtemos uma resposta. Então temos body by
await Response.json. Aqui, quando eu digito
resposta e pressiono “Dot”, você pode ver que agora eu tenho
o IntelliSense, que me dá o método.JSON. Se eu ligar, você pode
ver a janela aparecer, que significa que ela retorna uma promessa. Agora temos o corpo. Se tentarmos cancelar o corpo do
registro aqui e voltarmos ao nosso
aplicativo, onde está? Aqui. Na verdade,
isso não importa. Se eu digitar algo aqui, posso ver os dados aqui que
vêm da linha 16 do Home.jsx, do registro do nosso console aqui, que significa que acabamos de fazer a
pesquisa programaticamente. Enviamos uma solicitação. Se abrirmos a guia de rede aqui e eu
clicar em “Pesquisar”, você verá que enviamos uma solicitação para o URL que
especificamos no Fetch
e, se
visualizarmos, obteremos os dados. Incrível. Agora, vamos tornar essa solicitação dinâmica porque temos a string de pesquisa aqui, mas enviamos voz o tempo todo. Declaramos
aqui SearchString, para que possamos passá-lo para o Fetch substituindo a
string estática por acentos invertidos. Em vez de meninos, aqui, podemos interpolar
nosso SearchString. Agora, vamos testar o corpo
do log do console. Mais uma vez, eu refresco. Eu digito garotas. Eu
clico em “Pesquisar”. Se eu olhar dentro da guia de rede, posso ver que envio programas de
pesquisa para garotas de consulta. Se eu digitar outra coisa, você pode ver que
será outra coisa. Se eu digitar alguma
bobagem, será sem sentido. Nosso pedido é dinâmico. Quão legal é isso? Agora você sabe como
poderemos buscar dados. Você pode ver que tudo
está conectado agora em uma única peça
dessas poucas linhas. Ótimo. Usamos a API TVMaze. Você pode lê-lo completamente. É muito simples
com bons exemplos, basta
folhear rapidamente a caixa. No próximo vídeo, vamos tornar essa função reutilizável
e tentaremos exibir os resultados que
recebemos aqui da API. Vamos tentar
exibi-lo dentro de nossa marcação JSX. Deixe-me confirmar as
mudanças que fizemos. Vou clicar
no sinal de adição. Vou parar o aplicativo
e dizer: deixe-me ver quais
mudanças eu fiz? Digamos que pesquise filmes ou pesquise
programas com o clique do botão. Digamos que tenha adicionado uma
caixa de texto ou uma pesquisa. Pesquise programas ao
clicar no botão. Algo parecido. Em seguida, faça o upload para o GitHub e até o
próximo. Nos vemos lá.
64. 08 renderização mostram dados da API do TV Maze: Olá de novo. Neste vídeo, finalmente
exibiremos os resultados que
obtemos da API. No último vídeo, descobrimos como podemos consultar dados com base no que digitamos
dentro do elemento de entrada. Desta vez,
vamos tentar
exibir os dados que recebemos da API TVMaze que
usamos para consultar dados. Vamos embora. Se voltarmos ao nosso código, teremos a seguinte
lógica para buscar dados. No entanto, também usaremos a mesma lógica em
outras páginas. Por que não criamos um invólucro
muito simples em torno dessas funções para que seja mais fácil
reutilizá-las em outros arquivos? O que
vou fazer dentro do código-fonte é criar
uma nova pasta, que vou chamar de
algo como API ou talvez como utils ou você pode
chamá-la do que quiser. Basta
separá-lo do resto da lógica
do resto
do arquivo e
será mais fácil encontrá-lo. Aqui, eu vou
criar um arquivo chamado tvmaze.js, e dentro desse arquivo,
o que eu vou fazer? Vou criar uma função
reutilizável que chamaremos de ApiGet. Esse ApiGet receberá apenas
o nome do caminho da URL
, exatamente como você vê
na documentação. Só passaremos esse segmento
de URL para a função, e a função
fará o resto. Em vez de fazer isso, chamaremos apenas ApiGet
e, em seguida, passaremos programas de
pesquisa e cadeias de
caracteres de consulta, algo assim. No entanto, podemos ir ainda mais longe e criar
outro invólucro para isso. Em vez de usar essa
função dessa forma, podemos simplesmente chamar a função search
for shows
e, em seguida, passar
a string de pesquisa, e pronto, e o resto, toda essa lógica aqui, será gerenciada internamente. Muito legal. Vamos seguir
em frente e implementar isso. Antes de tudo, precisamos criar esse ApiGet para
que possamos usá-lo dessa forma. Esse ApiGet será uma função que
retornará como uma promessa, que será o
corpo da resposta, assim como aqui. Eventualmente, vai
ficar assim. Vamos seguir em frente e fazer isso. Passamos a queryString aqui. O primeiro argumento que essa função receberá
será queryString. Essa função
usará buscar essas duas linhas. Vou
copiá-los daqui. Como usamos a palavra-chave
await aqui, pretendemos usar async-await, então eu marco essa
função como async
e, a partir dessa
função, retorna o corpo. No entanto, obtemos esse
URL codificado aqui. Podemos movê-lo para fora
apenas para, de alguma forma ,
declará-lo em algum lugar
no topo para que
saibamos o que é o BASE_URL aqui. Aqui no topo, vou
apenas criar uma variável chamada BASE_URL e
será https://api.tvmaze.com sem barra inicial. Então, vou
interpretá-lo na chamada de busca BASE_URL. Em vez de usar
barras de pesquisa mostram e depois uma string de pesquisa, vou aplicar aquela queryString que
passamos como argumento, que será essa
string com a barra inicial. Em vez de tudo isso, vou
usar apenas queryString. Eventualmente, nosso URL
ficará assim. Ele pegará
BASE_URL e
pegará a queryString que
passamos dos argumentos. Eventualmente, esse
tipo de URL será formado. Agora, vamos em frente. Concordamos em ir mais longe do que o ApiGet e criamos
outra função em cima do ApiGet que
chamamos de SearchForShows, para não passar barras de
pesquisa com barras. Se você quiser gerenciar isso, ele será gerenciado
em um único local, em um único arquivo aqui
dentro de tvmaze.js. A partir daqui, vou
exportar porque
vamos usá-lo mais tarde na função
inicial chamada
export const searchForShows. Novamente, essa função
receberá apenas o queryString, exatamente o que digitarmos
dentro da entrada. Será uma consulta. Vamos chamá-la apenas de consulta. Essa função que chamaremos de ApiGet
e passará pesquisas, shows e consultas será
a consulta que passamos. Chamaremos isso de ApiGet e tudo o que o ApiGet retornar
será retornado do SearchForShows. Estou usando aqui a sintaxe curta
das funções de seta. Essa sintaxe, sem usar
explicitamente o corpo
da função com colchetes
, retorna tudo o que o ApiGet retorna. Isso é o mesmo que
escrever return ApiGet. Para encurtá-lo, nós o usamos assim. Eu o salvo e agora posso usar esse SearchForShows
dentro da minha casa.jsx. Vou importar de, vamos voltar para
o nível acima. Pegamos um labirinto de api/tv e pegamos o SearchForShows. Agora, podemos remover tudo isso e chamar SearchForShows
com o queryString, que será
nosso SearchString. Assim. Se
virmos os resultados, vamos chamá-lo de ApiData
e registrar ApiData, e voltaremos ao aplicativo. O que quer que digitemos aqui, vamos inspecionar a guia Rede. Nós digitamos garotas, pressionamos “Enter”. Você pode ver que a solicitação está
sendo formada corretamente, o URL da
solicitação está correto. Tudo funcionou perfeitamente. Se olharmos dentro do console, podemos ver que na linha 15 do
home.jsx, exatamente onde temos
nosso log do console, é
isso que recebemos. Este é o nosso API Data. Agora, o que podemos fazer? Podemos criar outro estado e, quaisquer dados que
recebemos aqui, podemos colocá-los dentro
do estado porque, novamente, esses dados de API que recebemos
são dados que mudam ao longo do ciclo de vida do componente porque são dados
que pesquisamos. Ela pode estar vazia, não pode ser carregada, algo pode estar carregada com ela. Vou seguir em frente e
aqui vou criar um novo estado, que chamaremos de
showsResult ou vamos chamá-lo apenas de ApiData
e setApiData, e ele será usado no estado aqui. Por padrão,
será uma matriz vazia ou talvez seja
nula por padrão. Aqui, o que vou fazer, essa variável de comprimento 15, vou chamá-la de
resultado ou resposta. Sim, vamos chamá-lo de result e eu vou
chamar setApiData, e setApiData será
o resultado. Qualquer que seja a matriz que
recebermos aqui, nós a colocaremos dentro do
nosso estado ApiData. Então, já sabemos o que
fazer com as matrizes.
Você se lembra disso. Podemos mapear cada elemento para algum JSX Barker
e depois exibir. O que faremos
logo abaixo do formulário. Vamos criar um div aqui. O que faremos,
criaremos uma função aqui. Em vez de embutir
o método de mapa de pontos ou vamos primeiro embutir
esses métodos de mapa de pontos. Há uma coisa a ter
em mente ao mapear. Vamos chamar o mapa ApiData. Temos dados aqui e, por enquanto, vamos
mapeá-los para uma div simples. Vamos inspecionar que
tipo de dados temos aqui. Qual é a forma dos dados? Temos uma variedade de objetos. Se inspecionarmos esse objeto de dados que representa esse
objeto que eu destaquei, ele tem a chave de pontuação e
, em seguida, a chave show. Dentro do show, temos o nome, temos o URL do ID. Por enquanto, vamos
exibir apenas o nome. Precisamos acessar data.show. Se eu interpolar data.show.name. Você sempre deve se lembrar que precisa
passar o suporte da chave. chave precisa ser algo único, pois
lidamos com dados da
API, os dados da API quando vêm de
acenados geralmente têm ID e o ID
representa o item de forma exclusiva. ID é o estojo perfeito
para o suporte de chave. Os dados mostram o ID para
identificar de forma exclusiva o elemento mapeado. Vamos tentar. Nós acessamos o aplicativo
e o que temos aqui? Já temos o
erro que diz: não é
possível ler as propriedades
de nulo, lendo o mapa. Se eu atualizar a página, sempre
verei esse erro. O que acontece? O fato é que nosso
estado inicial aqui é nulo. Isso significa que, quando o
componente
for renderizado, os dados da API de estado serão nulos. Como não
clicamos em nenhum botão, não
obtivemos nenhum resultado.
O estado é nulo. Se tentarmos mapear null, obteremos esse erro
porque, basicamente, nosso código tem a seguinte
aparência, null.map. Bem, isso está errado. É por isso que vemos esse erro. Diz que não é possível ler propriedades
de nulo, lendo o mapa. O que significa que ele
tenta fazer null.map. Como podemos superar isso? Podemos fazer isso de várias maneiras. A maneira mais fácil de lidar
com isso é mudar o estado
inicial de nulo
para um array vazio. Deixe-me voltar aos dados da API. Se a mudarmos para
uma matriz vazia, sempre que não
tivermos nenhum dado, já que a matriz está vazia, não
veremos nada. Porque bem, nada
será mapeado em última análise. Quando pesquisamos
algo como para meninos e quando obtemos nossos
resultados da API, cada elemento da API é mapeado para a div correspondente com
o nome do show. No entanto, o que eu quero mostrar
alternativamente é que, em vez de usar uma
matriz vazia como estado padrão, ainda
podemos usar null, mas podemos lidar com nossa
lógica de forma um pouco diferente. Vamos além
e vamos criar uma função auxiliar que
chamaremos de renderApiData. Em vez de inserir o
método.map aqui diretamente, que chamará como você lembra,
já fizemos isso, renderApiData e gerenciaremos uma lógica de renderização condicionalmente
dentro dessa função. Aqui eu vou
criar RenderApiData. Em vez de usar isso, direi que nosso
estado inicial é nulo, lembre-se. Quando tentamos exibir nulo, obteremos um
erro porque, bem, não
podemos mapear nulos. Podemos simplesmente verificar se os dados da API são nulos ou se nossos dados de API
são falsos, retornamos nulos. Caso contrário, sabemos que
definitivamente será uma
matriz depois de configurada. Ou talvez possamos inverter
a lógica para que ela
seja mais legível e melhor.
Nós podemos dizer. Se tivermos dados de API, se os dados forem verdadeiros
, não serão nulos. É algo, por
exemplo, como uma matriz. Nesse caso, chamamos
o método.map para retornar ApiData, map, data
e, em seguida, a lógica que temos. Caso contrário, por padrão, se essa condição falhar
e nossos dados de API forem falsos
, eles passarão por aqui, passarão por essa condição. Então, por padrão, não
retornamos nada. Lembre-se de que resultados nulos em nada serão renderizados
dentro da marcação JSX. Se voltarmos ao aplicativo, você verá que nada é exibido. Isso porque nossos dados de API
foram inicialmente definidos como nulos. É por isso que renderizamos como nulo. Mas assim que eu
procuro a API, tenho meus dados aqui. Incrível. Sempre que eu mudar a
consulta, ela será atualizada. Olha só isso, como é? Mais uma coisa que eu quero
acrescentar aqui é, na verdade, o tratamento
de dados. Eu sei que já cobrimos
muita coisa e é muita coisa. Mas e quanto aos erros? Se nossa solicitação
que enviamos aqui, se olharmos dentro da rede, se a solicitação que enviamos
aqui
falhasse por algum motivo, geraria um erro. O que acontece nesse caso? Na verdade, podemos emular esse erro na busca por
shows ou nos dados da API. Então, em vez de apenas
fazer uma pesquisa na API, podemos simplesmente gerar um erro até que
algo ruim aconteça. Isso é exatamente o que
acontecerá se essa solicitação falhar por algum motivo,
algo ruim aconteceu. Vamos tentar ver. Temos um código inacessível, que novamente vem do eslint. Eslint, você me salvou muito. Por enquanto, vamos apenas
comentar isso. Vou procurar qualquer coisa,
algo como olá. Se eu clicar, nada acontece. Mas você pode ver aqui
dentro do console que não
detectamos um erro de
promessa,
algo ruim aconteceu. Nesse caso, precisamos sempre
lembrar quando lidamos com JavaScript
assíncrono, quando lidamos com APIs, sempre
precisamos detectar e
lidar com erros, não importa o que aconteça, mesmo que você tenha certeza
sobre essa API, de
quão boa ela é e
possa pensar em qualquer erro. Bem, você precisa
mudar sua mentalidade. Algo acabará por
trazer um erro, então você precisa
ter certeza de como lidar com isso. Nesse caso, dentro dessa busca de
espera por programas, podemos encapsulá-la e tentar capturar o
bloco para detectar quaisquer erros. Vou mover essas
duas linhas para dentro da tentativa. Se algo dentro
do bloco try falhar, ele emitirá o erro
dentro do bloco de captura. Podemos criar outro estado, e qualquer erro que
recebamos aqui, podemos colocá-lo
dentro do estado. Aqui na parte superior,
vou criar ApiDataError e o estado
setApiDataError. Por padrão, também
será nulo. Vou seguir em frente
e, dentro do bloco catch, vou
chamar setApiDataError para qualquer erro
que tenhamos aqui. Agora, se tentarmos
cancelar o erro de log, o estado, por
padrão, é nulo. Mas sempre que temos um erro, podemos ver que temos o outro
objeto dentro do nosso estado. Podemos usá-lo dentro do
RenderApiData e exibir qualquer mensagem de erro
caso haja um erro. Podemos dizer se
temos ApiDataError. Nesse caso,
exiba div, que diz que ocorreu um erro, e podemos interpolar ApiDataError.message,
pois nosso ApiDataError será o objeto de erro. Vamos tentar. Se você se lembra dentro do API Gateway,
algo ruim aconteceu. Dizemos que não importa. Clicamos em Pesquisar e agora
vemos que ocorreu um erro,
algo ruim aconteceu. Legal. No entanto, também precisamos
lembrar que precisamos atualizar esse estado caso
cliquemos uma vez em Pesquisar vermos que esse erro ocorreu. Em seguida, clicamos na próxima
vez em Pesquisar
e, em seguida, a próxima solicitação
será processada. No entanto, nossos dados de API em
nosso estado estão pendentes. Ele ainda tem seu estado anterior, então será exibido. Precisamos ter
certeza de que o limpamos antes de cada solicitação
que enviamos. Chamamos setApiDataError para
saber o estado inicial. Assim, gerenciamos
todo o fluxo de nossa solicitação. Agora podemos remover o novo
erro e unificar a lógica. Vamos ver tudo mais
uma vez em ação. Procuro meninas, tenho meninas, tenho meninos e tenho
tudo o que digito aqui. Tudo funciona conforme o esperado. Caso tenhamos um erro
gerado pela API, ele será tratado aqui. Como podemos testar isso? Na verdade, podemos simplesmente digitar
algumas bobagens
no euro e ver o que a
API nos fornece. Eu datilografei garotas. Eu clico em Pesquisar. Você pode ver dentro da
guia Rede, agora ela está vermelha. Diz 404, o que significa que fizemos
algo errado. Obviamente, esse endpoint
não existe. Nossa API para a API VMAs
retornou algum erro. No nosso caso, ele
retornou um erro. Ele acabou de retornar uma mensagem de status
404. Fetch entendeu
que era um erro, mas não tinha
nenhuma mensagem de erro. Diz que falhou
na busca por padrão. Agora, se tentarmos
alterá-lo novamente. Se procurarmos garotos. Agora, tudo
foi exibido. Quão legal é isso? Eu acho que parece incrível. Lidamos com todas as
situações possíveis que poderiam dar errado. Agora temos uma lógica bastante
robusta, não apenas para criar dados, mas
também para lidar com quaisquer erros, além de exibir
os dados que vêm da API,
algo assim. Acho que, na verdade,
abordamos muita coisa aqui. Falamos sobre estados
diferentes, falamos sobre busca de dados, falamos sobre captura de erros, falamos sobre exibição de dados. Isso é muito. Vamos encerrar tudo. Git add, git commit. Vamos chamá-lo de buscar e exibir dados da API tvmaze. Crie uma
função reutilizável para buscar dados. Para função reutilizável, refiro-me à busca por programas. Incrível. Vamos nos comprometer e nos esforçar para dominar tudo. Eu vou te ver
na próxima.
65. 09 Fix Prettier não funciona: Olá. Este vídeo vai
ser rápido porque acabei de notar um pequeno
problema na configuração do projeto. O problema é esse arquivo
prettierc. Então, digitei incorretamente o nome do arquivo
e, por causa disso, o conflito que
especificamos aqui não funcionou. No entanto, você deve ter notado que,
quando eu estava salvando arquivos, eles estavam fora de formação. Isso ocorre porque temos a extensão Prettier
instalada e, por padrão, quando essa extensão não consegue encontrar a configuração
colocada em seu projeto, ela retornará
à configuração definida em algum lugar internamente
dentro dessa extensão. É por isso que ainda funcionou. No entanto, não
usou esse conflito. Para corrigir isso, deixe-me renomear
esse arquivo para prettierrc. Então, agora ele pode realmente
ser captado. Se eu acessar, digamos, o
componente do aplicativo e salvá-lo, agora você vê que eu realmente tenho aspas
simples, conforme definido
em um conflito mais bonito. No entanto, para corrigir
o pequeno problema, preciso examinar cada
arquivo dentro da fonte. Pode ser entediante e
não temos muitos arquivos, então podemos fazer isso manualmente, mas aqui vai uma dica. Podemos usar uma interface de
linha comum mais bonita e escrever um pequeno script que formará fonte interna de
um arquivo antigo. Se eu acessar a
Documentação do Prettier, clico em Documentos e , na
seção Uso, posso procurar
CLI, posso encontrar esse trecho aqui. Na prática, isso pode ser
mais ou menos assim. Eu posso simplesmente copiar este. Vá para o pacote JSON, defina um novo script aqui, que chamarei de formato, onde escreverei um traço mais bonito,
dash, write dot. O Dot formatará todos os arquivos
no diretório atual, mas eu não quero fazer isso. É por isso que vou alterá-lo
para fonte dot blast streaks,
asterix, dot e, em seguida, colchetes
curvos, JS, JSX. Não entre em pânico, isso
é algo chamado padrão global ou sintaxe global. Ele é usado para combinar
arquivos e o Prettier pode aceitar esse padrão
ou sintaxe como argumento. Portanto, ele procurará
todos os arquivos dentro do código-fonte e em
subpastas antigas e procurará apenas arquivos com extensão dot JS e dot JS6.
Eu vou salvá-lo. Vou fazer o formato de execução do NPM. Vamos ver o que temos. Agora, podemos ver a saída. Então, esses são todos os
arquivos que foram formatados pelo script de formatação por recurso. Este é mais bonito aqui a
que me refiro, ele será
retirado dos módulos do Node porque o instalamos
como uma dependência de desenvolvimento. Então, escrevemos mais bonito aqui
dentro dos scripts do NPM e ele será resolvido como o
mais bonito instalado a partir dos módulos do Node,
tão simples quanto isso. Agora que
tudo foi corrigido, vamos confirmar tudo e dizer que corrigiu o erro ortográfico de
configuração mais bonita, adicionar script de formato
ao pacote JSON. Incrível.
Nos vemos na próxima.
66. 10 botões de rádio: Olá. Neste vídeo, continuaremos com o desenvolvimento
da página inicial
e, desta vez, adicionaremos
botões de rádio em nosso formulário que usamos
para pesquisar os resultados, e poderemos
selecionar se queremos procurar programas ou procurar atores. Vamos embora. Vou
voltar ao componente inicial, dentro do componente inicial, logo
abaixo da entrada do texto do tipo, vou criar
outra entrada aqui, já que
será um botão de rádio,
vou colocá-la
dentro do elemento do rótulo, então será uma entrada do tipo. etiqueta da rádio será shows, o nome
será SearchOption, o valor desse
botão de rádio será shows. Então eu vou
criar outra entrada, outro botão de rádio,
desta vez para atores. Atores, tipo rádio, nome permanece o mesmo porque esses dois botões de rádio
compartilham o mesmo estado, valor serão os atores. Volto à minha marcação e
vejo que as caixas de seleção estão lá, desculpe-me, botões de rádio. Agora, para que possamos incluir de
alguma forma o valor, a seleção de nossas caixas de seleção
na solicitação da API, precisamos ter outro estado
para esses botões de rádio. No topo, vou
criar outro estado, que chamarei de SearchOption,
algo assim, algo assim, defina SearchOption por padrão, ele será exibido. Nosso estado SearchOption pode
ser shows ou atores, mostra string
ou string de ator. Com base nisso, enviaremos a solicitação
relevante para a API TVMaze. Agora, precisamos
associar esse estado
que acabamos de criar aos botões de rádio
que escrevemos anteriormente. É praticamente o
mesmo que com a entrada do tipo texto, vamos fazer uma vinculação
bidirecional de dados , já
temos valor, agora precisamos ouvir o evento de mudança
nessas entradas. A lógica é exatamente a mesma Vou apresentar aqui o manipulador de eventos on
change, que
chamarei de mudança de rádio, e será o mesmo para os dois elementos aqui no
canto superior direito ao lado dele. OnSearchInputChange,
escreverei sobre mudança de rádio, ele também recebe o objeto de
evento e agora, para definir o estado de
searchOption, posso me referir ao atributo de
valor que
passamos para cada botão de rádio
correspondente. Os botões de rádio são
representados por valores para que possamos realmente
acessar event.target, que será resolvido
no elemento HTML de entrada. Eles têm um atributo de valor
e isso nos dará o valor correspondente que
associamos a
cada um dos rádios. SetSearchOption
será event.target.value, basicamente o mesmo que fizemos
com onSearchInputChange. Agora, essa é uma
vinculação de dados unidirecional, como você se lembra, mas ouça as alterações dentro
do rádio, mas não
associamos o estado searchInput
ao elemento de entrada, então já temos o atributo de
valor aqui, mas o estado do botão de rádio é representado não
pelo atributo value, mas pelo atributo check, e nosso botão de rádio mostra marcado quando nossa
SearchOption é igual a shows, para que possamos escrever desse
jeito. Pesquise programas iguais a shows. Essa expressão será
verdadeira quando a busca por
shows for uma sequência de caracteres. Exatamente a mesma
lógica que vamos
aplicar para a contribuição dos atores. Isso será
verificado somente quando a busca por programas for igual a atores. Ótimo. Agora vamos dar uma olhada. Vamos registrar o
SearchOption no console e, desculpe-me, ainda diz que usei a pesquisa
de programas aqui, desculpe, eu pretendia usar o SearchOption, se o estado for igual a shows,
essa entrada será verificada. O mesmo vale para atores. Ótimo. Agora vamos tentar registrar o SearchOption no
console apenas para ter certeza de que
fizemos tudo certo. Por padrão, é mostrado que
esse é o estado inicial. Se eu selecionar atores, agora, são atores, se eu selecionar programas novamente, ainda são shows, o que
significa que tudo
funciona perfeitamente bem. Agora, precisamos de alguma forma inserir esse estado de SearchOption em nossa solicitação e colocar a
lógica correspondente em algum lugar dentro do manipulador de pesquisa on. No momento, vamos
simplificar, mas no próximo vídeo, vamos refatorar um pouco esse componente e
fazer com que pareça muito, muito melhor. Mas qual será a
lógica em primeiro lugar? Se voltarmos à documentação
da API TVMaze, usamos esse ponto final aqui
para procurar os programas. Se olharmos dentro do
índice, há outro link que nos leva à seção de
pesquisa de pessoas aqui, e é quase o
mesmo que nos programas. Você pode ver que, bem, o modelo
é basicamente o mesmo, mas desta vez procuramos
pessoas em vez de programas,
para saber como podemos conseguir
isso em nosso código. Se voltarmos ao TVmaze.js, aqui já temos essa função reutilizável
chamada search for shows. Podemos copiar essa função e
renomeá-la para SearchForPeople
e, em vez de passar
/search/shows para a API get, passaremos
/search/people, e todos os argumentos permanecerão os mesmos porque também
temos uma string de consulta aqui. Incrível. Voltamos ao homejsx, desta vez importamos o
SearchForPeople. A lógica interna do
manipulador de pesquisa será muito simples. Se SearchOption for igual a shows, execute essa lógica
que já temos, caso contrário, execute a mesma lógica, mas
chame searchForPeople. Você pode ver que temos uma
pequena repetição aqui, mas vamos ajustar isso
no próximo vídeo. Por enquanto, não pense
muito sobre isso. Vamos ver como fica. Voltamos ao nosso aplicativo, mostramos os programas selecionados por padrão, procuramos algo e você pode ver que tudo
funciona conforme o esperado. Se selecionarmos atores e
clicarmos em “Pesquisar”, teremos uma
tela em branco, o que aconteceu? Se olharmos dentro da guia de rede, ainda
podemos ver que a
solicitação foi processada com o endpoint correto
/search/people, mas se olharmos dentro do console, temos esse cabeçalho, que diz
que não é possível
ler as propriedades do nome de leitura indefinido. O que aconteceu? Se observarmos o corpo da resposta que
recebemos da API, esse é o objeto que temos,
mas dentro do código, mas dentro do código na verdade
escrevemos que, se
tivermos o estado dos dados da API, renderizaremos
data.show.id ou data.show.name, mas no resultado de
nossos atores, não
temos isso. Não temos data.show,
temos data.person. Basicamente, estamos
acessando os dados errados. console aqui
nos fala sobre isso. Não é possível ler propriedades do nome de leitura
indefinido, porque data.show é indefinido dentro desse objeto de resposta
e, em seguida, tentamos
acessar undefined.name, e é isso que vemos, não podemos ler propriedades do nome de leitura
indefinido. Esse é o nosso problema. A solução para
isso será que em algum lugar aqui,
precisaremos escrever, quando procurarmos
atores ou quando tivermos, digamos, resultados de atores, exiba atores, mas quando tivermos resultados de programas
, exiba programas, e não podemos fazer a
mesma lógica que aqui. Não podemos confiar em nosso estado, precisamos confiar na
forma de dados que temos. Aqui dentro da lógica, podemos simplesmente fazer se, onde está? Temos uma matriz,
vamos perguntar:
se o primeiro elemento dos dados da API
tem a propriedade show, nesse caso, podemos dizer que
estamos trabalhando com os shows, temos os dados mostrados da API. Caso contrário, se
não tivermos shows, se nosso primeiro elemento dentro dessa matriz não
tiver a propriedade show, podemos dizer que estamos
trabalhando com as pessoas aqui, com esse objeto de pessoa. Vamos dizer o contrário, execute ApiData.map e os dados desta vez
não serão mostrados, mas data.person. pessoa de dados, vamos ver, também se
identifica e a pessoa dos dados, digamos, o nome, praticamente
da mesma forma que com os programas. Agora vamos tentar.
Parece um pouco confuso, não se preocupe, vamos consertar tudo isso um pouco mais tarde. Vamos ver se tudo funciona. Eu procuro programas, obtenho resultados da API, eles são renderizados, perfeitos. Eu mudo para atores e procuro algo como Andrew e agora você pode ver que não
temos nenhum somador, console está limpo, obtemos a resposta na guia
da rede e
temos os dados renderizados, então podemos ver que funcionou. Incrível, não é? Ótimo. dizer que alcançamos
o que queríamos por enquanto, vamos confirmar nossas mudanças
e, no próximo vídeo, vamos refatorar levemente esse componente e encapsular lógica
que temos com o elemento do formulário aqui em
um componente separado. Mas, por enquanto, vamos
cometer tudo, e nomear esse commit
como, deixe-me ver, adicionar busca por atores. Ótimo. Vamos para o GitHub e nos
vemos na próxima.
67. 11 Movendo a lógica do formulário de busca para seu próprio componente: Olá de novo. Neste vídeo, continuaremos trabalhando
com nossa lógica que apresentamos
no vídeo anterior. Adicionamos uma opção para selecionar programas ou atores e, com
base nessa seleção, enviamos a
solicitação correspondente para a API TV maze. Você pode ver que, uma vez que
adicionamos essa lógica, nosso componente doméstico ficou um pouco inchado com
muitas lógicas diferentes. Na verdade, podemos
simplificá-lo e é exatamente isso que
vamos fazer agora. Por que não movemos toda essa
lógica relacionada ao elemento do formulário, todos esses estados, por que não a movemos para um componente separado e
colocamos a lógica lá, e então vamos expor apenas o que
precisamos por meio de sondas. Vamos tentar fazer isso.
Dentro da pasta de componentes, vou criar um novo componente, algo
como searchformjsx. A partir daqui, vou
exportar o componente do formulário de pesquisa. Mas agora será
apenas um div vazio com formulário
de pesquisa
padrão para exportação. Então, agora vamos tentar uma coisa
importante e vamos ver o quão aproximadamente queremos que
esse componente
se comporte para que possamos escrever
a lógica de forma correspondente. Vou importar o pesquisa do formulário de pesquisa de
componentes. Em vez de tudo isso, o que vai escrever um formulário
de pesquisa. O que precisamos? Queremos realizar a
pesquisa em algum lugar aqui nesse componente porque esse é
o componente em
que realmente renderizamos os dados. Se quiséssemos gerenciar
tudo dentro do formulário de pesquisa
, não poderíamos
acessar essa lógica
de fora. Vamos gerenciar
a lógica de estado com entradas dentro do componente , mas a pesquisa
realmente acontecerá aqui. A lógica de pesquisa será
escrita dentro do JSX doméstico. Precisamos, de alguma forma, encontrar uma maneira expor uma sonda que
nos permita pesquisar programas
aqui dentro do JSX doméstico. Na verdade, podemos simplesmente
passar essa função de
pesquisa para o formulário de
pesquisa e o formulário de
pesquisa de insights quando
clicamos em enviar, que
chamará a função
definida aqui na página inicial. Vamos
chamá-la de algo como na pesquisa e passaremos nossa função de concerto
que já
temos , mas
modificaremos um pouco a lógica. Em vez de escrever
tudo isso,
teremos apenas uma única linha. Agora, vamos copiar essa marcação com o elemento de formulário que temos e colocá-la dentro de um formulário de
pesquisa como este. Agora, precisamos mover a lógica
que temos no JSX doméstico para seu estado, como na alteração
da entrada de pesquisa e
na mudança de rádio. Vamos mover tudo isso para o formulário
de pesquisa. Aqui, também esses estados, opção
de pesquisa e sequência
de pesquisa. Vamos copiar esses dois. Vamos colocá-los aqui em cima. Precisamos importar
o estado de uso agora. Vou copiar isso também. Agora, a única coisa
que perdemos aqui é o gerenciador de pesquisa. Vamos seguir em frente e
defini-lo aqui. Em vez de ligar para
isso na pesquisa, ligaremos para o envio, o motivo
será o seguinte. Podemos passar isso
para o manipulador de pesquisa aqui diretamente como
uma sonda e depois especificar diretamente como
no manipulador de envio mas exporemos
o objeto do evento, que significa que
teremos que escrever a lógica para evitar
o evento de envio. No entanto, o
componente externo que é o
Home.jsx realmente não
precisa saber disso. Por que eu realmente preciso
evitar alguma lógica padrão,
algum comportamento padrão? Podemos mover parte
dessa lógica da
pesquisa diretamente dentro do componente do formulário de
pesquisa. Aqui, vou criar a função ao enviar e passá-la como atributo no
envio. Novamente, temos o
objeto de evento dentro dessa função. Impedimos a ação de
envio padrão chamando event prevent default
e, logo em seguida, precisamos executar essa lógica. Mas essa lógica
será definida aqui. Podemos esperar o suporte de pesquisa
, que será uma função, e
simplesmente o chamaremos aqui, sem mais nem menos. Vamos tentar. Aqui, em vez de escrever
event prevent default, não
precisamos dele porque
isso já foi feito
dentro do componente do formulário de pesquisa, vou removê-lo. No momento, chamamos de busca própria
sem nenhum argumento, o que significa que não
recebo nada aqui. Apenas uma função
sem argumentos. No entanto, perdemos a opção de acesso à pesquisa e perdemos
o acesso à string de pesquisa. Para corrigir isso, sempre que chamamos a função de pesquisa que
definimos dentro de casa, podemos passar argumentos
aqui porque o
temos aqui
dentro do formulário de pesquisa. Por que não chamamos a sequência
de pesquisa na web e a opção de pesquisa? Mas, para torná-lo mais
fácil de usar, a API que expomos do componente
do formulário de pesquisa para
torná-la fácil de usar aqui, podemos passar que pode ser um objeto,
algo como opções. Consulta, que seja apenas Q
será a string de pesquisa
e a opção de pesquisa, vamos mantê-la como está. Eventualmente,
teremos um objeto chamado options com propriedade Q e propriedade
de opção de pesquisa. Vamos passar esse objeto para a função on search. Aqui recebemos
o objeto de opções e podemos fazer a desestruturação
diretamente aqui. Vamos desestruturar a
propriedade Q e a propriedade da
opção de pesquisa. Pegamos Q, pegamos a opção de pesquisa
em vez da string de pesquisa. Agora vamos usar Q. Vamos tentar ver. Se eu atualizar a
página, nada acontece porque eu não executei
o servidor de desenvolvimento. Deixe-me fazer isso muito rapidamente. Vamos esperar um segundo. Está aqui. Deixe-me
refrescar. Vamos ver. Nossa funcionalidade não
deve realmente ser alterada porque estamos apenas
fazendo um fator menor aqui. Esperamos que tudo se comporte exatamente da
mesma forma que antes. Meninas, temos garotas, funciona perfeitamente, atores. Digamos que, Garry, temos Garry. Você pode ver que a funcionalidade permanece
a mesma, mas agora nossa lógica dentro de um JSX doméstico foi
drasticamente simplificada. Basicamente, não temos quase nada aqui, exceto a lógica relacionada
à pesquisa em si. A lógica que
cuida da forma de todas as entradas foi encapsulada
dentro do formulário de pesquisa. Agora, separamos as preocupações. Faz sentido. Eu acho que sim. É isso por enquanto. Na verdade, espere, não é isso. Ainda precisamos fazer algo a
respeito, porque você
pode ver que ainda temos
uma pequena repetição aqui. Na verdade, podemos
continuar assim e não pensar
muito sobre isso. Não há nada de errado com isso, mas
podemos simplificar. Digamos que primeiro crie
uma variável chamada resultado. Assim, moveremos
os dados da API do conjunto para
cá e faremos algo assim. Ou talvez possamos até
simplificar alinhando a lógica
com operadores ternários, mostrados na opção de pesquisa. Aguarde a
busca por programas, caso contrário, aguarde a busca por programas,
caso contrário, aguarde as pessoas. Mas acho que essa
declaração serve. Incrível. Agora é totalmente isso. Vamos comprometer tudo o
que acabamos de fazer. Como podemos nomear isso? Podemos nomear isso de forma muito simples. Nós apenas o chamamos de lógica do formulário de pesquisa
fatorado ou, digamos ,
oscilado,
e componente do formulário de pesquisa. Perfeito. Te
vejo na próxima.
68. 12 Mostrando cartas para shows e atores: Oi. Neste vídeo, continuaremos com
o desenvolvimento e continuaremos
com a exibição dos dados da API TV maze. Neste momento, nossa lógica para
exibir dados é muito básica. Simplesmente mapeamos o estado dos dados
da API e, em seguida, exibimos o
acrônimo ou o nome do programa. Vamos tornar isso real desta vez. Então, em vez de escrever isso, podemos, novamente, oscilar toda essa lógica
em um componente separado, especificamente para atores, e em outros componentes,
especificamente para shows. Vamos fazer isso. Dentro da pasta de
componentes, vou criar mais
duas pastas aqui, uma para atores e outra para shows. Nessas pastas, colocaremos componentes
específicos relacionados apenas a programas ou relacionados a atores. Dentro da pasta shows, vou
criar um novo componente, que
chamarei de ShowGridJSX. Agora, será
o ShowGrid padrão de exportação
div
e, para referência futura, vou copiar
essa lógica e colocá-la dentro do ActorsGrid também. Mas vou renomeá-lo
para ActorsGrid desta vez. Agora vamos voltar para casa. Agora, em vez de fazer isso, em vez de mapear
elementos aqui diretamente, podemos exibir
ShowGrid ou ActorGrid. Quando tivermos shows, exibiremos o ShowGrid. Você pode ver o intellisense
novamente. No menu suspenso, pressiono “Tab” e
verifiquei se ele foi
importado corretamente. Bem, foi, então eu posso continuar. O mesmo que farei com os atores, em vez de mapear
elementos aqui, vou exibir o ActorsGrid. O intellisense,
boom, importado. Eu verifiquei a entrada. Parece ótimo. Muito
mais simples agora, não é? Para que possamos exibir
dados dentro desses componentes, precisamos passar
dados para que eles
possam , de alguma forma,
manipulá-los internamente. Para o ShowGrid, vamos
passar shows prop, e serão dados da API. Para a grade de atores
, serão os atores, novamente, dados da API. Por enquanto, terminamos
com o componente doméstico. Toda a lógica será colocada
no componente de
grade correspondente. Vamos começar com os shows primeiro. Vamos ao ShowGrid, aqui, recebemos o adereço do programa que passamos aqui do homejsx. Ótimo. Agora, dentro do Mostrar grade, vamos mapear os dados agora. Vamos escrever
showsgrid.map. Aqui temos nosso objeto de dados. Por enquanto, vamos nos lembrar
rapidamente:
o que temos? Temos data show.name,
se eu não estiver errado, e para a chave, vou passar dados, mostrar ID. Vamos verificar isso rapidamente. Vamos voltar ao aplicativo. Eu digito algo e
recebo um erro, que diz que não é possível tratar
propriedades de indefinido. Acho que entendo agora. O problema é que
lidamos com o caso quando
temos estágio igual a nulo. Mas nós realmente não
resolvemos o caso quando o palco é
uma matriz vazia. Porque você viu que eu
digitei algo sem sentido agora, mas se eu digitar algo
sensato e realmente
tivermos resultados da
API, teremos uma matriz. Mas se eu digitar
algo sem sentido, será uma matriz vazia. Se olharmos dentro
da guia de rede, você pode ver na
API em sua pré-visualização que
temos uma matriz vazia e
não lidamos com isso aqui. Mas na lógica que escrevemos, verifique o primeiro
elemento dentro da matriz. Mas como o primeiro
elemento não existe, ele é indefinido, temos undefined.show, basicamente. Precisamos consertar isso. Precisamos considerar o caso
quando temos uma matriz vazia. Aqui, vamos adicionar
outra condição if, se apidata.length for igual a zero. Você pode ver o que eu fiz aqui. Na verdade, adicionei esse ponto de
interrogação aqui. Isso é chamado de
encadeamento opcional porque, se os dados
da API forem nulos e eu
digitar null.length, receberei um erro. Para evitar esse
erro e
garantir a duração do acesso ao JavaScript somente quando os dados da API forem verdadeiros, podemos adicionar esse ponto de
interrogação aqui. Se os dados da API forem falsos, são nulos, não
gerará um
erro dizendo que é possível ler o
comprimento da propriedade de nulo. Mas quando for verdade, ele prosseguirá e
usará a propriedade length. Se apidata.length for igual a zero, se nossa matriz estiver vazia, não
exibiremos nenhum resultado. Vamos tentar ver
se eu digitar sem sentido, obtemos uma matriz vazia da API
e, desta vez,
não temos textos de resultados. Parece bom para mim. Vamos digitar algo
que faça sentido. Temos garotas, a
lógica que mostra
todos os programas mais antigos está
escrita dentro do ShowGrid. Parece perfeitamente bom. Agora, vamos criar
o componente de cartão para o show. O componente do cartão
será nosso estilo show-card, onde vemos todos os dados sobre
o programa em vez de apenas
mostrá-los em uma div simples. Dentro da pasta shows,
vou criar ShowCardJSX. Isso vai ser um show card. Novamente, div simples
e, por padrão,
exportamos o ShowCard. Agora vamos usar esse show-card aqui
dentro do ShowGrid. Em vez de mapear cada elemento, cada objeto show para
aquela div simples, vamos mapear cada elemento para o componente show card. Em vez de fazer isso, vou mapear cada
elemento para o ShowCard. Novamente, insira Alto, e eu precisarei passar
adereços para o componente ShowCard. No entanto, está tudo
vermelho porque, novamente, preciso passar o suporte da chave. Não importa
se o elemento é seu próprio componente personalizado ou se
é apenas um elemento HTML, você sempre precisa passar a chave. A chave será a ID do show de dados. Agora, quais dados queremos
exibir dentro do ShowCard? Vamos começar com
algo simples. Então, primeiro vamos
receber o nome prop, e provavelmente
vamos receber a imagem ou vamos começar
com o nome primeiro. Dentro do div,
vamos exibir isso dentro da tag h1. Vamos interpolar o nome. Agora precisamos passar
esse nome para cá. Ao mapear o componente
show card, passarei name, equals data, show.name,
algo assim. Vamos tentar ver. Na verdade, você pode ver que agora tudo
é grande e ousado. Esta é a nossa tag h1. Em seguida, passaremos a imagem se inspecionarmos
nossos dados de API. Vamos tentar ver. Temos a imagem do show. Uma imagem é um objeto com teclas
médias e originais. Vamos tentar ver se esses
dados mudam de alguma forma. Imagem, ainda temos algumas, mas posso
dizer que a imagem aqui pode ser nula
porque nem todos os programas
que recebemos dessa API têm imagens. Eles podem não ter nenhum dado. Nesse caso, a imagem
será nula. Como poderemos
exibir algo? Para essas situações,
o que eu sugiro fazer. Caso não recebamos
nenhuma imagem da API, mostraríamos a
imagem do espaço reservado para o usuário, algo como imagem não encontrada. Para isso, podemos voltar para o convidado que
você compartilhou com você. Aqui você pode encontrar esse
espaço reservado para shows, atores sem imagem de capa. Você pode clicar nessa imagem, clicar com o botão direito nela, salvar a imagem como e vamos
colocá-la em nosso projeto. Vou colocá-lo dentro pasta
pública e
vou
chamá-lo como image.png não encontrado. Ótimo. Se eu olhar para o público, agora ela apareceu aqui e
podemos realmente nos referir a essa imagem PNG dentro do
nosso código-fonte. Vamos ver rapidamente
como fica. A fonte da imagem não será
uma imagem vinculada porque nosso
arquivo é colocado em público e é exibido
pela rota do aplicativo. Nós o salvamos, voltamos
ao aplicativo e sempre que
procuramos programas, temos isso, perfeito. Essa é a imagem que temos. Agora, dentro da grade show, vamos passar image prop, mas vamos especificar se data.show.image é
verdadeiro. Nesse caso,
pegue este image.medium, data.show.medium, caso contrário
, mostre não encontrado. Como o chamamos? Não foi encontrado image.png. Ótimo. Agora, dentro do cartão de exibição, podemos pegar esse suporte de imagem e exibir
em algum lugar aqui em cima. Vamos encapsular a
imagem em uma div. Então, a fonte será
a imagem que
distribuímos e divulgamos será
o nome do programa. Vamos ver rapidamente
o que temos. Temos algo errado aqui. Vamos ver, não
temos nenhuma fonte. Por que isso? Tem que ser
data.show.image.medium. Agora você pode ver que
funcionou muito bem. Vamos tentar procurar atores, e você pode ver agora que temos
todas essas imagens de capa. Bom. Vamos prosseguir e
preencher os dados do aplicativo. O que mais precisamos mostrar? Gostaríamos de mostrar talvez apenas um resumo e o
interior de cada cartão, mas também teremos um botão para começar esse show
no futuro. Quando clicamos nesse
botão, ele inicia e, quando
clicamos no cartão, nos
leva
à página de exibição. Que criaremos
no futuro. Dentro do cartão de exibição,
precisaremos de um documento de identidade. Também precisaremos de um resumo. Vamos ver como podemos
exibir tudo aqui. Vamos
criar um div aqui. Um div
provavelmente será um link por enquanto que importamos
do [inaudível]. Dentro do link,
diremos leia mais. O link
nos levará, por enquanto, à rota. Não vamos fazer
nada sobre isso por enquanto. Então, temos um botão
aqui do tipo botão, que será estrelado por enquanto,
no futuro, o
substituirá pelo ícone. Sobre o resumo. O resumo que
vamos exibir em algum lugar aqui e não o
resumo, pois isso simplesmente não exibirá o
suporte que
recebemos, vamos
transformá-lo de alguma forma. A razão por trás disso é que, se analisarmos
a resposta da API, teremos a sequência de resumo. Mas, como você pode ver,
é uma string HTML. Isso significa que podemos simplesmente
pegar esse HTML e usar. O problema é que
é bem longo. Queremos que seja breve. Não queremos exibir
centenas de palavras aqui. Eu sugiro transformar essa sequência de resumo em
algo muito curto. Vamos retirar todas as tags
HTML daqui e vamos pegar apenas,
digamos, as primeiras 10 palavras, provavelmente. Como podemos fazer isso? Suponha que recebamos
essa string aqui. Vamos escrever a lógica dentro do console
do navegador aqui. Temos essa corda aqui. Nessa string,
primeiro vamos
transformá-la em uma matriz
chamando o método.split
e vamos dividi-la por espaços vazios. Agora temos algo assim. Então, vamos pegar
apenas os primeiros 10 elementos
dessa matriz, .split depois disso, vamos cortar do
índice zero para o índice 10. Acabamos com uma
matriz de 10 elementos. Em seguida, vamos transformar essa matriz novamente em string. Vamos unir todos os elementos com uma string vazia no meio. Parece que sim. Mas ainda temos tags
HTML aqui, então precisamos substituí-las. Vou mudar o método.replace disponível em todas as strings. Aqui, vou passar algo
chamado expressão regular. Vou combinar todos os caracteres
desnecessários e depois substituí-los
por uma string vazia. Basicamente, isso
apenas os eliminará. Não pense
nisso para combinar. A expressão regular que vou escrever apenas
substituirá todas as tags HTML dentro da
nossa string atual. Ficará assim. Só não preste muita
atenção nisso. Nosso resultado final
ficará assim. Pegamos essa sequência de caracteres HTML, a encurtamos e
removemos todas as tags HTML. Eu posso simplesmente copiar essa lógica. Eles acabaram de escrever aqui, e eu farei algo
como um resumo retirado. Se eu não estiver errado,
no resumo do programa também
pode não estar presente, é por isso
que vamos verificar valores falsos aqui. Se tivermos um resumo
, chamaremos o método split
e toda essa lógica para transformar nosso HTML
em uma string simples,
caso contrário, não contaremos
nenhuma descrição. Em seguida, vamos
exibir o resumo retirado. ID por enquanto não está sendo usado, mas vamos
mantê-lo assim. Salvamos o arquivo, vamos para show grid novamente
e passamos o ID, que será
data.show.id e, por nome, já o temos. No final, vamos
passar um resumo. Será bem simples,
apenas data.show.summary. Eu sei que parece
muito, mas confie em mim, essa é apenas uma forma normal de
trabalhar com dados da API. De alguma forma, você precisa pensar como deseja que ele exiba os dados. Isso é apenas uma coisa
normal aqui. Eu a guardo, volto aqui, e se eu procurar
meninos dessa vez, onde estão meus meninos? Eles estão aqui. Agora eu tenho a sequência de resumo
que transformamos com link
Ler, bem como
o botão Star Me. Bem, parece ótimo, não é? Agora, na verdade, passamos
muito tempo em shows aqui. Vamos resumir rapidamente
os atores que temos. Dentro da grade de atores, podemos simplesmente copiar essa
lógica daqui. Não precisamos do log do console. Vou apenas copiar a
lógica da grade de exibição colocá-la dentro da grade de atores. Receberei rapidamente o adereço do
ator que passar aqui. Atores. Dados pop. Eu faço isso dentro do show grid. Eu preciso fazer isso
dentro da grade de atores. Eu recebo atores aqui. Eu mapeio atores e
os mapeio para o cartão de atores. ActorCard.jsx. Vou copiar essa lógica muito
rapidamente do cartão de exibição, colocá-la dentro do cartão do ator. Vou renomear o
cartão de apresentação para cartão de ator
e, desta vez, quais
dados receberei? Em primeiro lugar, os atores
também têm nomes. Eles também têm imagens e também identidades,
ou talvez não. Não precisamos de identificação porque
teremos uma
página separada para cada programa, mas não teremos uma página
separada para cada ator. Precisaremos de um nome, precisaremos de uma imagem, provavelmente precisaremos de
algo como sexo, país, talvez
aniversário e dia da morte. Então, aqui dentro da grade de atores, vou usar esse cartão de
ator aqui. Foi importado automaticamente em vez
de passar por todos esses adereços. Deixe-me removê-lo. Para a chave, vou
passar o ponto de dados, deixe-me realmente ver. O que temos aqui?
Mostrar cartão não está definido. O resumo não está definido. Vá lá. Deixe-me procurar atores. Deixe-me ver a solicitação de rede. Aqui eu tenho uma pessoa. Isso é pessoa, então dados, pessoa. Pessoalmente, tenho aniversário, país
nulo,
dia da morte nulo, sexo nulo, mulheres. Você pode ver
que já tem muitos nulos. Bem, isso não é ruim. Vamos passar o nome. Será apenas
data person.name. Então será um país. Se eu não estiver bêbado, o país
pode ser na verdade um objeto. É um objeto com nome aqui. Vou apenas passar dados,
pessoa, país.nome. No entanto, o país pode ser nulo, então precisamos
verificar isso. Se os dados, a pessoa o
país
forem verdadeiros, anote o nome. Caso contrário, por favor, dê nulo. Então, fazemos aniversário. Como você viu, o aniversário não
pode ser nulo, mas vamos lidar com esse cartão
interno de ator. Vamos passar
dados, pessoa, aniversário. Então também temos o dia da morte, que é praticamente
o mesmo que aniversário. Então também temos gênero. O gênero será
dado, pessoa, gênero. Além disso, acho que esquecemos a imagem. Imagem, acho que será praticamente a
mesma que com os shows. Vou apenas copiá-lo. Vou perguntar se existem dados, pessoas e imagens. Por favor, indique dados, pessoa, imagem, mídia,
caso contrário, imagem PNG não encontrada. Ótimo. Agora, qual será a
marcação da grade de atores? Deixe-me ver. A imagem
permanecerá a mesma sem nome. Dentro de H1, ainda exibiremos
o nome, mas ao lado do nome também
exibiremos gênero entre parênteses,
se houver algum. Podemos incorporar nossa lógica aqui. Você lembra que podemos
embutir a renderização condicional diretamente dentro do JSX.
Se o gênero estiver presente, exiba a string,
que será
entre parênteses
e dentro dos parênteses, interpolaremos o gênero, e esse gênero pode ser nulo. Quando usamos o operador and para
renderizar condicionalmente essa lógica, queremos sempre
garantir que o gênero seja um valor booleano. É por isso que vamos transformá-lo em um
booleano como esse para verificá-lo, ou podemos aplicar a negação dupla, que também o transformará
em um valor booleano. Ao lado do nome,
vamos exibir o país dentro da
tag do parágrafo, eu acho. Vamos perguntar
se o país é conhecido e, em
seguida, exibiremos uma sequência que
diz que vem do país. Caso contrário, não
contaremos a nenhum país, a ninguém. Então temos aniversário
e dia da morte. Vamos fazer a
mesma lógica aqui. Se tivermos aniversário,
um valor booleano. Por favor, exiba a tag p
com nascido no aniversário. Provavelmente o mesmo
para o dia da morte ou para o dia da morte, em vez de não mostrar nada
quando acontece agora, ainda
podemos dizer que
essa pessoa está viva. É por isso que vamos
criar a tag p aqui e
vamos perguntar se
temos o dia da morte, por favor. Display morreu neste dia da morte. Caso contrário, exiba ao vivo. Nós realmente não precisamos
desse div na parte inferior. Nossa marcação final
é assim. Não precisamos do
componente de link na parte superior. Bem, isso foi muito e
eu já estou cansado escrever toda aquela
lógica bem chata de exibir dados. Mas ainda temos que
passar por isso. Vamos procurar shows. Temos tudo
sendo exibido. Agora, mudamos para atores. Vamos procurar Harry desta vez, não Gary, mas Harry. Aqui temos a imagem. Você pode ver se
a imagem não existe, ela mostra a imagem não encontrada. Então temos o nome, o gênero entre parênteses. Então não temos nenhum país, ninguém vivo ou não vivo, quando a pessoa nasceu. Todos os dados que tivermos
da API serão exibidos dessa
maneira. Eu acho que é isso. Vamos comprometer tudo
e seguir em frente. Eu vou cometer tudo. Eu sei que você viu este aviso que temos
por causa dessa identidade. Isso é bom. Vamos
mantê-lo lá por enquanto. Vamos lidar
com isso mais tarde. Vamos comprometer tudo
e divulgar os programas
exibidos e os dados dos atores. Vamos pressionar tudo para
dominar e fazer uma pausa. Eu vou te ver
na próxima.
69. 13 Páginas com conteúdo dinâmico: Olá. No último
vídeo, criamos cartões para shows e atores. Desta vez,
falaremos sobre páginas dinâmicas. Como você se lembra em
cartões para shows, temos aquele link para ler mais. Se voltarmos à marcação, esse é o componente de link que usamos do
React Router dom. Por enquanto, ele vai para
a página inicial até a raiz. Basicamente, ele não faz nada
se clicarmos nele. Agora, o que queremos fazer em vez disso, ao clicarmos em
“Leia mais”, devemos ser direcionados para
a página específica do programa. Em primeiro lugar,
precisamos decidir
exatamente como nossa página do programa
será representada. Nesse caso, e na
maioria das vezes, as páginas são representadas
por IDs. Temos ShowID. Pode ser nosso
identificador exclusivo para a página,
portanto, sempre que
clicarmos em uma página no URL, alguma forma
veremos showID. Podemos considerar
duas opções aqui. Primeira opção, nosso URL será
parecido com uma barra
e, em seguida, o ID do show será fornecido como parte
da string de consulta. Algo parecido com isso. Segunda opção que
podemos considerar, em vez de fornecer Id como
parte da string de consulta, podemos realmente transformar
showId em segmento de URL. Eventualmente, a
página de exibição terá um URL, algo como
slash show, slash showId, e
esse ID será alterado com base no
programa em que clicamos. A questão aqui é como isso pode ser feito
com o React Router. Se voltarmos ao componente do
aplicativo aqui, como você se lembra, comentei a marcação
que retirei da documentação para
referência futura. Aqui temos essas equipes de
rota e dentro delas temos
algo com dois pontos, temos o ID da equipe de dois pontos. Tudo o que você vê aqui
é algo chamado parâmetro de URL
dinâmico
ou segmento de URL dinâmico, porque é algo
que muda. Todos os nossos dados
que temos em
nosso aplicativo são dinâmicos, porque o que quer que
digitemos na entrada
, eles serão dinâmicos. Não podemos realmente prever quais dados devemos
esperar da API. Precisamos
pensar de alguma forma em como podemos escrever o esqueleto para
os dados dinâmicos. O que eu sugiro fazer
é considerar a segunda opção
que acabei de mostrar, e nosso URL será parecido com
slash show, slash showId. Esse parâmetro dinâmico de
URL showID é o que você vê aqui
neste exemplo com dois pontos. Damos a ele algum nome,
digamos TeamID. Especificamos que esse parâmetro
nomeado será algo dinâmico que
podemos extrair do URL. No nosso caso, o que
podemos fazer aqui criar outra rota
e criá-la fora do layout principal
porque, para a página de exibição, não
usaremos principalmente a rota
que criamos anteriormente. Essa rota terá path slash show,
slash, colon showId. Esse segmento dinâmico de URL aqui, eu dei o nome de ShowID. Eu terei o parâmetro de URL, que será dinâmico, e terá o nome ShowId. Para essa rota, eu
gostaria de exibir a página de exibição. Vamos seguir em frente e criar um. Em páginas, vou criar outro componente chamado show, outro arquivo chamado show, e a marcação por enquanto será muito simples: mostrar
página dentro do aplicativo. Vou importar esse componente de exibição da página
e vamos tentar. Se eu navegar até a barra, mostrar, cortar alguma coisa, você
verá que eu tenho a página de exibição. Na verdade, funciona. React Router conseguiu combinar esse caminho e
me renderizar o componente show. Se eu for apenas mostrar,
eu encontrei, não encontrei, porque apenas mostrar sem segmento de URL
dinâmico não
corresponderá a essa definição de rota. É por isso que ele
volta para, não encontrado. Mas assim que eu for
mostrar alguma coisa, terei a página de exibição. Ótimo. Agora, a questão é: como podemos, de alguma forma,
recuperar esse showID do URL aqui e usá-lo
dentro do nosso componente show. Nossa estratégia
será a seguinte. Sempre que navegamos até a página de
exibição e temos showID no segmento de URL
dentro de nosso componente, podemos pegar esse segmento de URL, podemos pegar esse showID
e usá-lo dentro do componente para consultar a
API TVMaze e obter dados de exibição. Essa é uma
abordagem muito comum quando você lida com páginas dinâmicas. Você terá uma
parte dinâmica dentro do URL
e, sempre que
navegar até essa página, você pega essa
parte dinâmica do URL e a
usa dentro do componente
para consultar dados. No nosso caso, isso
será showID. Agora, como podemos extrair esse
showID do URL? Se voltarmos à documentação
do React Router, à
esquerda temos o menu. Podemos rolar para baixo até
a seção de ganchos e aqui estaremos interessados no gancho de parâmetros de
uso. Você pode ler essa descrição
rápida aqui para que use params hook
retorne um objeto, pares de
valores-chave dos parâmetros dinâmicos
do URL atual que
corresponderam ao caminho da rota. Vamos tentar isso.
Você pode ver que ele foi importado do
React Router dom. Eu farei exatamente o mesmo. Vou copiar
isso muito rapidamente. Eu não preciso de rota,
então eu só preciso usar parâmetros e dentro de Show, vou
chamar use params. Vou criar uma nova
variável chamada params. Por enquanto, vou simplesmente cancelar parâmetros de
registro e ver
o que eu tenho. Eu vou para o navegador para cancelar aqui, e aqui você pode ver
que eu tenho um objeto em que showId é igual a tudo o que
eu forneço na URL. Essa chave aqui corresponderá nome
do parâmetro que demos a esse segmento de URL
dentro da definição da rota. Se colocarmos aqui algo
como, sei lá, muito aleatório, eu
atualizo a página, você pode ver
agora as principais mudanças. Eu especificamente dei a ele algo
significativo, como showId, para que mais tarde possamos acessar esse showID dinâmico
usando o gancho use params. Como vai
ser um objeto, podemos usar essa estruturação. A partir desse objeto de parâmetros, vou pegar ShowID. Vamos tentar interpolar
isso dentro do nosso JSX aqui. Mostrar página para showID. Vamos tentar e percebi
que meu aplicativo não está salvo, deixe-me salvá-lo. Você pode ver a página de exibição para mostrar
tudo o que eu coloquei no URL. Se foi exibido com Id1, eu tenho para, Show 1. Assim,
agora criamos uma página dinâmica que
representará nosso programa. Há mais uma coisa nisso. Não vamos
alterar o URL dentro da caixa de pesquisa
do navegador
manualmente o tempo todo, não é? Precisamos modificar o link
que temos dentro do cartão de exibição. Na verdade, isso nos
leva a essa página dinâmica. Vamos tentar fazer isso. Dentro do show, sabemos
que, para atributos, para adereços, podemos fornecer
valores dinâmicos usando JavaScript. Em vez de apenas passar
uma raiz de string estática, podemos abrir colchetes. Podemos dizer, por favor, vá para a barra, mostre o ID da barra e pronto. Vamos tentar ver isso. Se procurarmos olá, e sempre que eu passar
o mouse sobre o link no canto inferior
esquerdo, você poderá ver a barra do URL
mostrar, cortar cinco e algo. Sempre será
diferente para cada show. Se eu clicar nele e
navegar até a página, deixe-me voltar e clicar em
outra coisa . Você verá que
agora é diferente. Assim,
podemos criar páginas
dinâmicas dentro do nosso
aplicativo com o React Router dom, e podemos pegar parâmetros
dinâmicos do URL
usando o gancho use params
e, em seguida, você os usa dentro
do componente para buscar dados. Vamos fazer isso
no próximo vídeo. Por enquanto, vamos comprometer
tudo o que fizemos aqui. Vamos dar uma visão geral. aplicativo Insight, criamos uma
nova multidão dinâmica
, baseada no
parâmetro showID. Chamamos esse
parâmetro de showID. Dentro do componente Show que criamos e esse
componente representa nossa página, pegamos o parâmetro
showId, usando o gancho use params. Dentro do cartão curto,
modificamos
o link para realmente
nos redirecionar para a página do programa. Incrível. Vou
nomear tudo como página de exibição dinâmica criada, e acho que tudo
ficará bem, envie tudo para o GitHub e
nos vemos na próxima.
70. 14 Introdução ao gancho useEffect: Olá. No último vídeo criamos uma página de exibição dinâmica. Agora é a hora de
buscarmos alguns
dados dinâmicos nessa página. Neste vídeo, vamos
falar sobre as formas como isso pode ser alcançado. Para
entendermos como funciona, precisamos conhecer outro gancho do React
chamado useEffect. Anteriormente, você
lembra que
conversei com alguém sobre o ciclo de vida dos
componentes. O ciclo de vida do componente é o
período de tempo desde a montagem do componente até ser desmontado da página. Vamos examinar mais de perto o ciclo
de vida dos componentes. Podemos diferenciar
três pontos
de tempo diferentes quando o componente é montado. A segunda é quando
o componente já está montado e é renderizado novamente toda vez que o estado interno muda. Uma nova renderização e o terceiro
ponto no tempo serão desmontados ou apenas quando
o componente for desmontado. Esses três pontos no tempo representam o ciclo de vida do
componente. Para nossa estratégia de busca de dados, estamos interessados
apenas no momento
em que o
componente é montado. Porque nossa lógica
será a seguinte. Assim que abrimos a página
dinâmica para exibição, pegamos o ID de exibição do URL
e, em seguida, usamos esse ID de
exibição para buscar dados apenas uma vez quando
o componente é montado. Não queremos
executar novamente essa lógica de
busca de dados toda vez que lógica de
busca de dados toda vez componente
for renderizado novamente. Isso é importante para entender que precisamos executar a
lógica apenas uma vez. Agora vamos tentar ver como o UseEffect Hook pode nos
ajudar a conseguir isso. Provavelmente, deixe-me navegar até
o formulário de pesquisa. Neste componente,
vamos
brincar com esse UseEffect Hook e entender como ele funciona
e como pode nos ajudar. Vou colocar
esses três pontos sobre o ciclo de vida do componente aqui. Então, no topo do React, vou importar useEffect. Agora, vamos tentar
usar esse gancho. Dentro do componente, vou chamar esse gancho, e esse gancho recebe
dois argumentos. O primeiro argumento
é a função, o retorno de chamada que executará a lógica que
queremos e o segundo, argumento, é algo chamado de
matriz de dependências. Falaremos
sobre a matriz de dependências um pouco mais tarde. Por enquanto, vamos
passar uma matriz vazia. Agora, nosso primeiro caso de uso
será quando o componente for montado. Queremos executar a lógica apenas uma vez quando o componente é montado. A propósito, esse
retorno de chamada é chamado de efeito
do useEffect. Vamos nos referir a esse
retorno de chamada como o efeito. Meu efeito será que
vou apenas executar o log
do console e dizer montagens de
componentes. Nada complicado. Agora vamos voltar ao nosso aplicativo,
abrir o console e, dentro do console,
vemos montagens de componentes, impressas duas vezes. Ele é impresso
duas vezes porque temos o modo estrito do React. Se você se lembra do desenvolvimento, intencionalmente, isso
equivale a um componente duas vezes para detectar
possíveis erros. Não queremos esse comportamento
quando trabalhamos com useEffect. Por enquanto, vou apenas
remover o modo estrito do React. Vamos voltar ao nosso aplicativo. Quando eu atualizo a página
e o componente é montado, o
componente do formulário de pesquisa é montado, vejo meu registro do console aqui. Se eu tentar atualizar
um desses estados, se eu digitar algo na entrada, componente será renderizado novamente. Mas você verá que as montagens de
componentes nunca mais
serão executadas. Deixe-me tentar. Eu digito
algo na entrada, esse componente é renderizado novamente. No entanto, as montagens de componentes nunca mais
funcionarão. Para tornar a observação mais fácil
, aqui, vou adicionar o log do console
e dizer que o componente renderiza novamente. O que temos aqui?
Suportes de componentes. Vemos a renderização do componente novamente. Isso é bom porque é a primeira vez que
o componente é montado. Então, na verdade, vemos a mensagem que
usamos dentro de useEffect. Agora, se eu atualizar esse estado, você só verá o componente
renderizado novamente. Nunca vemos montagens de componentes. Assim, podemos
executar a lógica apenas uma vez quando o
componente é montado. Agora, vamos observar o
terceiro caso de uso aqui. Quando o componente é desmontado. Em useEffect dentro desse efeito, dentro do callback,
você pode passar algo chamado função
de limpeza. É basicamente
a função que retornada do retorno de chamada. Função de retorno. Esta função aqui será executada quando o componente for desmontado. Vamos tentar ver. Dentro da função de limpeza, vou escrever componentes
desmontados. Vamos ver. Primeiro, temos exatamente o
mesmo comportamento de antes. Mas assim que eles mudarem
a página, a navegação, se eu for para a página inicial, esse formulário de pesquisa de componentes será desmontado da página. Vamos ver o que acontece. Vou começar e você
vê componentes desmontados. A lógica definida dentro da função de
limpeza será executada logo antes de o componente desmontado da página. Dessa forma, podemos nos conectar
ao ponto desmontado no tempo. Até agora, calculamos
dois momentos em o componente é montado e quando o componente é desmontado. Com o segundo caso de uso, quando o componente
é renderizado novamente
, fica um pouco
complicado com useEffect. Digamos que eu gostaria de
executar alguma lógica, sempre que a opção de pesquisa mudar. UseEffect é capaz de executar alguma lógica quando
algo muda. Esse segundo argumento, a matriz de dependências, serve
exatamente a esse propósito. Ele define e instrui o useEffect a executar essa lógica a partir do callback
quando algo muda. Dentro da matriz de dependências, listamos os valores que
gostaríamos de ouvir
e, quando esse valor muda, instruímos useEffect, execute novamente a lógica. Vamos experimentar e ver. Vou comentar sobre
a função de limpeza Em vez de montagens de componentes, contarei algo como mudanças nas opções de
pesquisa. Como matriz de dependências, como um dos valores dentro
da matriz de dependências, passarei a
opção de pesquisa. Vamos ver. Eu atualizo a página, nada é impresso porque
atualmente estou na página inicial. Assim que eu vou para a página inicial, vemos uma nova renderização de componentes
e mudanças nas opções de pesquisa. Por que vemos mudanças nas
opções de pesquisa quando
especificamos algo dentro
da taxa de dependência? O fato é que o
useEffect sempre é executado pelo menos uma vez,
não importa o que aconteça. UseEffect é executado pelo menos
uma vez, não importa o que aconteça. Agora, se eu tentar digitar
algo dentro da entrada, veremos apenas a renderização do componente novamente, nunca
veremos alterações nas
opções de pesquisa. Mas assim que eu atualizar o estado das opções de pesquisa
chamando set search option, o useEffect será executado novamente. Vamos ver. Vemos mudanças nas opções de
pesquisa. Nós o alteramos novamente e,
toda vez que o valor é alterado, o efeito é executado novamente. simples quanto isso. Aqui, você pode listar
quantas dependências quiser. Se um deles mudar, o efeito será
repetido toda vez. Basicamente, ouvimos mudanças de
valor e, se essa mudança de
valor ocorrer,
o efeito será repetido. Usando esse método, podemos nos conectar à
lógica de renderização do componente e executar nossa
própria lógica aqui usando,
novamente, o gancho useEffect. No entanto, vamos
chamá-lo de caso de uso 2.5, quando queremos executar a lógica
antes da próxima renderização. Pode parecer sofisticado, e até certo ponto é, mas vamos ver como funciona. Nosso 2.5 será lógico antes das
próximas três renderizações. A função de limpeza aqui, eu disse
anteriormente, se você quiser executar alguma lógica antes da quantidade do
componente, você pode retornar
essa função
a partir do efeito e tudo o que você colocar dentro será executado antes que o
componente seja desmontado. No entanto, isso só funciona quando a matriz de dependências está vazia. Se tivermos dependências
dentro da matriz de dependências, a função de limpeza
será executada para cada efeito. Quando o efeito atual terminar, a lógica será executada para
esse efeito antes que o próximo efeito seja executado. Em vez de quantidades de componentes, digamos que a opção de pesquisa mude, e aqui dentro do
mesmo log do console, também
vamos
colocar a opção de pesquisa. Poderemos ver
o valor do estado. Vamos tentar. Eu atualizo a página. Vejo mudanças nas opções de pesquisa. Atualmente, mostra. Assim que eles
mudarem a opção, vamos ver o que acontece. Vemos a
renderização do componente como de costume, vemos mudanças nas opções de pesquisa. Digamos que seja a opção de pesquisa,
digamos, antes da próxima opção de
pesquisa ser alterada
ou, digamos, antes da
próxima execução do useEffect. Vamos tentar novamente. Vemos mudanças nas opções de
pesquisa, shows. Agora mudamos a opção, e o que eu vejo antes da próxima execução de
UseEffect, vemos shows. Essa função de limpeza
é executada para cada execução de efeito. Nossa atual corrida aqui nesse sentido é
para atores estatais. Como nosso
estado atual é de atores, é quando ocorre o
último efeito. Da próxima vez que o efeito for executado, a função de limpeza
será executada para nosso efeito atual para atores. Se eu mudar para shows novamente, veremos antes da próxima execução do
UseEffect com atores e, em seguida, veremos mudanças nas opções de
pesquisa com shows. Vamos tentar. Vemos antes da
próxima execução de useEffect, na verdade, a partir de agora nossa execução anterior de useEffect
e nossa nova execução de useEffect. Bem, parece complicado. Na verdade, à primeira vista, é. No entanto, isso realmente
faz sentido. Há muitos
casos de uso em que você
deseja usar cada uma dessas opções. Ao usar o useEffect, podemos executar
alguma lógica durante o ciclo de vida
competente sob diferentes condições
e circunstâncias. Podemos usar a
matriz de dependências para instruir useEffect quando
quisermos executar essa lógica. No momento, analisamos useEffect e
registramos o valor do estado das opções de pesquisa sempre que
uma opção de pesquisa muda. Você pode ter uma pergunta: por que usamos useEffect
aqui se podemos simplesmente colocar o log do console diretamente
aqui sem useEffect, assim como fizemos com a renderização de
componentes novamente. Bem, o fato é que, com useEffect novamente, você
tem a matriz de dependências. Essa nova renderização
do componente de log do console será executada em todas as
renderizações competentes, não importa o que aconteça. O componente é renderizado, você sempre verá
esse log do console. No entanto, com o useEffect, você escuta somente
valores que mudam, e esses valores são especificados dentro da matriz de dependências. Se você especificar uma matriz de
dependências vazia, esses
useEffect serão executados apenas uma vez quando o
componente for montado. Essa lógica, a função
de limpeza aqui será executada quando o
componente for desmontado. Mesmo se você tiver a dependência, quando o componente
for desmontado, você verá que a
função de limpeza também será executada. Vamos observar isso.
Mudamos de ator e temos nossa execução antes da
próxima execução do UseEffect. Quando o componente
for desmontado, você verá antes da
próxima execução do UseEffect. Basicamente, a função
de limpeza, como
eu disse, limpa
a execução
atual do UseEffect. Usando essa abordagem, podemos buscar dados apenas uma vez quando o
componente é montado. Vamos especificar uma matriz de dependências
vazia para instruir o useEffect a ser executado apenas uma vez quando o
componente for montado. Dentro do efeito, vamos buscar a
lógica da API. simples quanto isso. Agora que conhecemos um pouco mais sobre o ciclo de
vida competente, agora sabemos que
podemos usar o useEffect para manipular
a lógica competente durante o ciclo de vida do componente, podemos buscar dados e
finalmente exibir algo. No próximo vídeo,
faremos exatamente isso. Por enquanto, vamos recuperar o modo
estrito de reação e falaremos
sobre isso mais uma vez. Por enquanto, é isso. Eu vou te
ver na próxima.
71. 15 dados da API do labirinto da TV com o useEffect: Olá de novo. No último vídeo, falamos sobre o
UseEffect Hook, como ele pode nos ajudar a manipular a lógica dentro do componente
durante o ciclo de vida do componente. Vamos tentar aplicar useEffect em nossa página de exibição dinâmica para
buscar alguns dados. Vamos embora. Eu vou para
páginas, Show.jsx. Aqui, como você se lembra, pegamos o showID do URL. Vamos procurar shows. Digamos, meninos. Vamos ler mais. Nós temos esse URL. O que quer que tenhamos no URL, nosso parâmetro dinâmico, nós o capturamos usando
o gancho useParams. Agora, vamos importar o
useEffect do pacote React, e agora dentro, o que
fará o useEffect. Como queremos
buscar dados apenas uma vez, queremos executar a lógica apenas uma vez
quando o componente é montado. Por esse motivo, especificamos uma matriz vazia de dependências. Dentro desse useEffect,
buscaremos Data. Vamos ver como será a aparência do
endpoint. Isso nos dará informações sobre o
show. Se acessarmos a API TVMaze e procurarmos a seção de programas aqui, teremos esse endpoint/shows/id, e você poderá ver este exemplo. Vamos abri-lo e ver. Ao fornecer o ID do programa, poderemos obter
todos os dados necessários. Vamos criar
outra função reutilizável dentro do tvmaze.js, onde
consultamos esse endpoint. Vamos explorar outra
função a partir daqui que
chamaremos de getShowById. Como argumento,
vamos especificar showID
e, internamente,
chamaremos ApiGet e chamaremos esse
URL de ponto final. Como o ID é algo dinâmico que fornecemos
por meio do argumento, usaremos
acentos invertidos para
podermos aplicar a interpolação de
strings. Nossa função
ficará assim. Agora, dentro do show jsx, podemos importar getShowById
da API TVMaze. Então, dentro de useEffect, poderemos chamar getShowId
e passar showId para dentro. Gostaríamos de
usar uma
sintaxe de espera de sincronização porque ela é
mais fácil de usar, mas você não pode tornar o
retorno de chamada de useEffect assíncrono. Se eu fizer isso, você
verá este aviso aqui, que vem desta regra de regras de ganchos da
ESLint. Diz que os retornos de chamada de efeito são síncronos para evitar condições de
corrida, coloque a função assíncrona e o site. Você pode ver esse exemplo aqui. Bem, vamos
fazer exatamente isso. Vamos criar
uma função assíncrona dentro de useEffect e depois
chamar essa função interna. Vamos tentar isso. No nosso caso, será parecido com FetchData. Não marcamos o
retorno de chamada como assíncrono, que é chamado de fetchData. Dentro de fetchData,
chamaremos um peso de ser exibido por ID e forneceremos showID que extraímos do URL. Agora, assim que eu usar
showId dentro de useEffect, você notará que agora eu tenho este aviso
aqui que diz: gancho do
React useEffect tem uma dependência
ausente, showId. Se você tem algo definido
dentro do componente e usa esse algo,
esse valor dentro de
useEffect, idealmente, ele deve ser especificado como a dependência
desse useEffect. A razão para isso
é porque digamos nosso showId aqui também possa
ser dinâmico, por exemplo,
pode ser nosso estado, e queremos executar
esse useEffect sempre que esse valor mudar. Se não fornecermos
nenhuma dependência aqui, mantenha nossa matriz de
dependências vazia, a lógica será executada apenas uma vez
quando o componente for montado. Mas e se esse showID mudar,
digamos, de 1 a 2? Nesse caso, faz sentido
atualizarmos os dados para pegar o último programa
com ID igual a dois. Mas se mantivermos a matriz
de dependências vazia, o efeito
nunca mais será executado. Para que possamos corrigir isso,
tudo o que usamos
dentro de useEffect, todos os valores aqui que podem ser potencialmente
dinâmicos ou mudar, precisamos especificar isso. Essa é nossa dependência
desse retorno de chamada useEffect. É por isso que vou listar
showID como parte do useEffect. Agora, obtemos nossos dados aqui. Vamos testar os dados de registro do console. Nós voltamos aqui. Agora, o que vemos, vemos dois registros do console. Novamente, a razão para isso é o StrictMode que temos. StrictMode é problemático e foi introduzido
na versão 18 do React, mas agora você pode ver que temos
esse problema no desenvolvimento de
que o componente é
renderizado novamente duas vezes. Como buscamos dados
dentro de useEffect, isso significa que
buscamos dados duas vezes. Isso não é realmente o que queremos. Nesse caso, a equipe do React recomenda que, a
partir do React 18, se você quiser buscar Data, use
outra coisa em vez de useEffect. Vamos falar sobre
isso um pouco mais tarde,
no entanto, isso é
muito controverso. Antes do React,18
na versão 17 e anteriores, a maneira mais básica e
padrão de fetchData era exatamente
isso, usando useEffect. Bem, com o React 18, nada muda muito, exceto que agora temos o
React StrictMode. Por enquanto, sugiro que
removamos o React StrictMode
e o ativaremos mais tarde, quando veremos
uma alternativa ao uso do
useEffect Hook para fetchData. Por enquanto, dentro do índice jsx, vou remover o
React StrictMode. Nosso useEffect não será executado duas vezes no desenvolvimento.
Agora, vamos salvá-lo. Eu atualizei a
página e veja, eu tenho dados aqui. Se eu abrir a guia Rede, eu atualizo a página. Aqui, posso encontrar a chamada para a API
TVMaze com showID que
recebemos do URL. Se eu pré-visualizar, esses são
os dados que temos. Agora, vamos criar um estado e colocar esses
dados dentro do estado. Vamos chamá-lo apenas de showData e definir show data. Essa será a chamada useState. Por padrão, os dados serão nulos. Em seguida, vamos criar
outro estado para detectar qualquer erro caso
a solicitação falhe. Vou criar ShowError,
setShowError. Por padrão, as chamadas são nulas. Vou encapsular uma maneira de getShowId, getShowById no bloco try catch. Dentro do bloco catch,
chamarei set showError como null. Então, quando recebo dados, chamo setShowData e defino esses dados como
parte do estado. Agora, aqui
podemos usar a renderização condicional para exibir quaisquer dados
que coletamos e poderemos
usar o estado ShowData. Podemos escrever a lógica de renderização
condicional diretamente dentro do componente, não apenas dentro da marcação JSX, não apenas usando, digamos, uma função auxiliar na
qual definimos lógica, mas também
podemos escrevê-la diretamente
dentro do componente. Aqui, vou perguntar, se tivermos showError dessa função,
do nosso componente, retorne
div, que
diz que temos um erro, que será showError.message, porque showError
será o objeto de erro. Aqui eu o defino como nulo, desculpe, tem
que ser o outro
objeto que capturamos aqui. Agora, caso tenhamos um erro, retornamos a marcação JSX com erro. Se tivermos showData, neste caso, obtemos os dados do show. Por enquanto, vamos cancelar. Vamos ver. O que nós temos? Temos um nome, então
seja o nome ShowData. Por padrão, se nenhuma dessas
duas condições for mantida, podemos dizer que os dados estão sendo carregados. Eu posso ver que não
usei a pesquisa ShowError. Aqui, eu realmente não o
usei. Vamos ver. Tenho que mostrar dados, garotos. Quando eu atualizo, você pode
ver isso piscando aqui, e esse piscar é
que esses dados estão carregando. Os dados são carregados tão
rápido que
nem percebemos que os dados
estão carregando a mensagem. Mas se essa chamada de API demorasse, digamos, 10 segundos, veríamos que os dados estão sendo carregados. Usando essa abordagem, você pode buscar dados
quando o componente é montado. No próximo vídeo, apresentaremos
um novo termo para nós, chamado React Hooks
personalizados. Por exemplo, aqui, costumávamos usar UseState e usamos useEffect
e useParams. O que quer que você importe diretamente
do React, esses ganchos são chamados de React Hooks
integrados. Mas você pode ver em
react-route-dom que importamos algo
chamado useParams. Também é um React Hook, mas não faz parte
da biblioteca React. É algo personalizado que foi criado pelo react-router-dom. No próximo vídeo, falaremos sobre isso e criaremos
nosso próprio gancho personalizado. Mas antes de terminarmos esse vídeo, vamos confirmar tudo o
que fizemos. Em primeiro lugar,
desativamos o StrictMode,
portanto, no desenvolvimento, nosso useEffect
não será executado duas vezes. Em seguida, criamos uma função
getShowById que busca dados e dentro do componente show,
usando o
gancho useEffect, o fetchData. Git add dot commit everything. Vamos contar fetchData dentro do componente show ou buscar mostrar dados dentro do
componente show, sem mais nem menos. Próximo vídeo,
ganchos personalizados. Te vejo lá.
72. 16 ganchos de reação personalizados: Ei, aí. No último vídeo, buscamos dados dentro do componente
show com a ajuda de useEffect. última vez, mencionei que,
neste vídeo,
falaremos sobre a diferença entre ganchos de reação
integrados
e ganchos personalizados que podemos
importar de outras bibliotecas. O fato é que esses ganchos
personalizados são, na verdade apenas mais lógicos do que ganchos de reação
integrados
que você já viu, como useEffect ou useState. Qual é a diferença então? Esses ganchos useParams,
por exemplo, são apenas ganchos com lógica
extra, então
não precisamos escrever essa
lógica dentro do componente. A questão está aqui por que precisamos de ganchos personalizados? Você pode ver que,
no último vídeo, usamos três ganchos
diferentes, na verdade dois ganchos,
mas os usamos três vezes dentro do
nosso componente,
useState, useState e
depois useEffect aqui. Agora, digamos que eu queira reutilizar essa lógica dentro de
outros componentes. Qual é a minha opção então? Uma abordagem muito ingênua é
simplesmente copiar esse trecho de código e usá-lo em algum lugar
dentro de outros componentes. Mas você pode ver que é
muita repetição. Se não falarmos especificamente sobre
reagir, se pudermos ver o
exemplo de programação para reutilizar a lógica de
alguma forma, usamos funções ou se
quisermos apenas extrair algo
do local, também
usaríamos
uma função para não colorir o espaço onde
essa lógica está presente. Exatamente o mesmo
se aplica aos ganchos. Se você quiser
reutilizar a lógica dos ganchos, ou se quiser apenas extrair a lógica
do componente, você pode colocá-la dentro de
um reator personalizado. Essa é a
razão pela qual os usamos. Eles são usados para reutilizar
a lógica dos ganchos e segunda opção é quando
você deseja extrair a
lógica do componente
para que não ocupe muito espaço
dentro desse componente. Em nosso caso, essa lógica não
será reutilizada
em nenhum lugar do aplicativo porque temos apenas um
local onde buscamos show
específico dentro
do componente show. Mas vamos imaginar que tivéssemos outro lugar onde queríamos
buscar esses dados do programa. Em vez de copiar
e colar a lógica, poderíamos
colocá-la em um gancho personalizado dentro de todos os componentes em que precisamos
buscar esse programa. Deixe-me mostrar o que quero dizer. No topo do arquivo, vou criar um gancho
personalizado de função que
chamarei de algo como useShowById. Você pode dar o
nome que quiser. Mas todos os ganchos de reação têm convenção de que devem
começar com o prefixo de uso. Se você quiser nomear
seu gancho personalizado, certifique-se de que ele comece
com use, useShowById .
Será apenas
uma função simples e vou apenas copiar minha lógica para fetchData do componente para
o gancho useShowById. Você pode ver
algumas coisas aqui. Em primeiro lugar, dentro do gancho, não
temos acesso
à variável showID. Mas, como é uma função, podemos recebê-la como
argumento. Vamos fazer isso. Você pode ver que dentro do componente
show, agora, não
temos nenhum acesso
a showError ou ShowData. Exatamente a mesma abordagem. Se nosso useShowById
for apenas uma função, poderemos retornar
algum valor dela. Vamos dizer que
retorna um objeto com duas chaves, ShowData
e ShowError. Agora podemos usar esse gancho
useShowById dentro
do componente show. Simplesmente chamamos esse gancho
interno, passamos showId e esse gancho
nos retorna um objeto com duas chaves, showData
e ShowError. Vamos desestruturá-los. Agora, veja nosso resultado final. Temos apenas uma única linha e a lógica está
escrita em outro lugar. Se eu esconder isso, você pode ver agora nosso componente está muito mais
limpo do que era antes, e nossa lógica de buscar dados para buscar o show está
em outro lugar. Agora, se eu quisesse reutilizar essa
lógica em outros componentes, simplesmente
chamaria useShowById,
pass, showId como argumento
e, em seguida, receberia meu
ShowData e meu ShowError, por exemplo, vamos
copiar esta linha. Se eu quisesse buscar show
dentro do componente do aplicativo, eu usaria esse gancho
no passado, qualquer programa que eu quisesse, como argumento e
terei acesso a ShowData
e ShowError. A lógica com ganchos personalizados, a ideia com ganchos
personalizados é a
mesma das funções
na programação, mas com ganchos personalizados, você escreve lógica sobre ganchos
embutidos ou outros ganchos de reação. simples quanto isso.
Agora é isso. Mas você lembra que no último vídeo, quando
introduzimos
o gancho useEffect, tivemos esse problema com modo estrito de
reação
no desenvolvimento. O modo estrito de
reação renderiza
o componente duas vezes. É por isso que nosso useEffect
sempre é executado pelo menos duas vezes. Isso foi problemático. A solução que a
reação recomenda é usar outra coisa
em vez de useEffect. No próximo vídeo, falaremos sobre isso. Vamos falar
sobre a alternativa
ao useEffect para buscar dados. Finalmente, poderemos
recuperar nosso modo estrito do React e não teremos
problemas em buscar dados apenas uma vez quando
o componente for montado. Por enquanto, vamos nos comprometer com
tudo e terminar este vídeo com
uma boa nota, como sempre. Minha mensagem de confirmação será muito simples:
extraia a lógica de agrupamento de dados em um gancho personalizado useShowById. Incrível.
Nos vemos na próxima.
73. 17 Dados obtendo com bibliotecas: Olá de novo. No último vídeo, falamos sobre a
diferença entre React
integrados
e ganchos React personalizados. Basicamente,
ganchos React personalizados são os ganchos que
escrevemos com nossa própria lógica em
cima dos ganchos React integrados. A razão por trás
disso é que
queremos extrair alguma lógica, ou se queremos tornar a lógica dos
ganchos reutilizável. Nesse caso,
usamos ganchos personalizados. Também buscamos dados
da API TVMaze apenas uma vez
quando o componente é montado. Fazemos isso com a ajuda
do gancho useEffect. Mas se você se lembrar, desabilitamos o React
StrictMode porque ele força o componente a ser renderizado novamente duas vezes no desenvolvimento,
o que significa que useEffect sempre
será executado pelo menos duas vezes
em vez de apenas uma vez. Isso é problemático para nossa situação específica
e, para evitar isso, a equipe do React recomenda
buscar dados com outra coisa. Eles não recomendam
usar o gancho useEffect para buscar dados quando você tem o
React StrictMode ativado. Eles falam sobre outra coisa. O que é isso? Bem, no front-end, existe o conceito
de algo chamado bibliotecas de busca de dados. Dois exemplos aqui
podem ser React Query e usar SWR; ambos são muito populares e são muito
semelhantes entre si. Mas o que eles realmente fazem, por exemplo, na página de uso de SWR, podemos ver aquele exemplo muito
simples com
o qual chamamos de gancho use SWR, digamos, o caminho
que queremos buscar
e, em seguida, a função
que busca dados. Em seguida, o gancho nos dá um erro de
dados que podemos
usar em nosso aplicativo. Agora, se compararmos isso com
o que escrevemos aqui, você pode encontrar uma nota muito
semelhante, no entanto, nosso gancho aqui é
voltado especificamente buscar programas da
API TVMaze e buscá-los por ID. Portanto, essa é a lógica específica
que está fortemente acoplada à API
TVMaze para buscar o
programa especificamente por ID. Se tivéssemos, digamos, muitas lógicas de
busca diferentes dentro de nosso aplicativo em centenas de
componentes, nesse caso, teríamos que
criar algo
mais abstrato para tornar nossa lógica de
busca mais
reutilizável e não fortemente acoplada a uma implementação
específica. As bibliotecas de busca de dados fazem exatamente isso; elas nos fornecem o gancho abstrato que podemos usar para buscar
dados dentro do componente. Portanto, é mais fácil reutilizar essa lógica em todo
o aplicativo que escrevemos, que criamos. Por exemplo, no React Query,
vamos encontrar o Quick Start. Você pode ver que a lógica
é muito semelhante; temos algo chamado
chave de consulta e função de consulta, vamos falar
sobre isso em um segundo, mas a lógica é a seguinte. Temos um
gancho abstrato para buscar dados, para esse gancho abstrato, fornecemos nossa lógica
para buscar dados, e esse gancho personalizado nos
dá um erro de dados e está carregando
variáveis que
podemos usar dentro do componente. Eles existem para tornar a
busca de dados mais otimizada, mais reutilizável e mais fácil de usar
para os desenvolvedores. Vamos tentar instalar
uma dessas bibliotecas. No nosso caso, vamos usar
a consulta React, só porque
eu decidi assim. Se você quiser, pode experimentar o UseSWR, a sintaxe é
muito semelhante. Dentro da
documentação, vou para a página de instalação. A partir daqui, vou apenas copiar o
tanstack/react-query instalado pelo NPM. Vou adicionar essa
dependência ao meu projeto. Ele aparecerá dentro do
pacote Jason aqui no topo. Ótimo. Agora vou para o Quick Start e
seguir o exemplo. Primeiro, precisamos
criar um cliente, depois precisamos usar
algo chamado provedor
de clientes de crédito e
passar esse cliente para lá. Então, dentro dos componentes, podemos usar o gancho useQuery. Vamos ver como isso pode nos ajudar. Vou copiar
essas entradas daqui, vou para o componente do aplicativo aqui, no topo, vou importar
apenas o vou importar cliente de consulta e o provedor
crítico do cliente, assim mesmo
, depois criarei um
novo cliente de crédito fora
do componente, depois usarei o provedor do
cliente de crédito, digamos, em algum lugar aqui
e o fecharei no final. Eventualmente, meu aplicativo
agora tem essa aparência. Ótimo. Agora posso ir para a página de exibição e, em vez de usar o gancho use show by ID, usaremos o gancho
useQuery aqui. Vamos comentar
o que temos aqui, vamos chamar useQuery, que também pode ser importado
de tanstack/react-query. Vamos fazer isso. Só precisaremos useQuery e, dentro
do componente, chamaremos
useQuery assim. Agora precisamos
passar as opções aqui. Opções é apenas um objeto com chaves diferentes
que fornecemos. A chave de consulta e a função de consulta são opções
obrigatórias que
precisamos passar. A chave de consulta
identificará exclusivamente nossa lógica de consulta, nosso fator, como GetStodos,
em todo o aplicativo. função de consulta é a
lógica para buscar dados. Vamos ver como podemos usar isso. Primeiro, precisamos passar a chave de consulta, e você pode ver
agora que é uma matriz. No nosso caso, podemos chamá-lo de
algo como show may e, seguida, nosso programa é identificado
por ID, conforme você se lembra. Vamos aprovar
show e showID. Então precisamos passar pelo buscador. No entanto, você pode ver que
agora , no exemplo em que é
passada, apenas a função de consulta é getsToDOS. Mas no nosso caso,
precisamos de alguma forma obter acesso ao showId
dentro do nosso buscador. Nosso buscador é essa
função que
criamos anteriormente
chamada getShowById. Se olharmos a documentação interna, ela está escondida em algum lugar, eu vou te dizer onde. Está aqui na seção
Query Keys. Se formos aqui e
rolarmos
até o final pudermos ver
toda essa seção aqui, se sua
função de consulta depende
da variável incluída
em sua chave de consulta. Vamos apenas seguir
esses exemplos aqui. Vou apenas
copiá-lo e colocá-lo assim. chave de consulta será mostrada
em vez de todoID, vamos colocar showId
em vez de fetchTodoById, vamos chamar getShowById. Vamos passar o ShowID. UseQuery nos retorna o resultado. Se tentarmos usar o IntelliSense
a partir desse objeto de resultado, você verá que temos
muitas coisas aqui, mas estamos interessados especificamente
nos dados e no somador. Vamos tentar fazer isso. Do objeto resultante, vou pegar os dados e
pegar o erro. Vou renomeá-los. Podemos usar dados
em vez de showData, mas vamos renomeá-los, vou colocar dois pontos ao lado chave
desestruturada e
vou chamá-la de ShowData. Dessa forma. A chave de dados que eu desestruturei será
renomeada para ShowData. Do objeto resultante, eu ainda desestruturei os dados, mas só queria ter
outro nome, ShowData. O mesmo acontece com o erro
, será ShowError. Agora, posso realmente voltar ao meu aplicativo
e ver como ele funciona. Mas eu preciso iniciar
o aplicativo novamente, npm run start, eu volto aqui. Vamos nos refrescar. Você pode ver, bem,
nada mudou, no entanto, agora, usamos
o gancho useQuery. É uma lógica
de gancho personalizada que está escrita em algum lugar dentro da biblioteca
tanstack/react-query. Nós apenas o usamos para buscar dados. Você pode ver
que esse gancho nos fornece essa interface abstrata para
que
possamos encapsular essa função em um gancho como useQuery e buscar dados apenas
uma vez dentro do componente. Essa chave de consulta aqui é um pouco parecida com aquela
matriz de dependências dentro de useEffect. Se algo dentro da chave de
consulta mudar, os dados aqui serão obtidos da mesma forma que com
useEffect, muito semelhante. Na verdade, a equipe do React
nos aconselha a usar algo
assim para buscar dados. Na verdade, essa é uma recomendação muito
boa. Você não queria lidar com toda essa lógica repetitiva todas as
vezes em seu aplicativo. Essas bibliotecas têm
muitas opções, são
otimizadas para busca, têm essas chaves de cache
e podem fazer muito
mais do que simplesmente buscar dados em montagens
pontuais de componentes. Em aplicativos React modernos, biblioteca de busca de
dados é
uma ótima opção. Vamos usar useQuery
para nosso exemplo específico. Agora podemos remover a lógica que escrevemos
anteriormente e, na verdade agora podemos incluir
React.StrictMode novamente, porque agora nossa
lógica de consulta não será executada duas vezes. Vamos ver isso. Se
eu atualizar a página, aqui, tenho apenas
uma chamada para a API, o que significa que nossa
lógica que escrevemos aqui não será buscada duas vezes e ainda teremos
acesso ao React StrictMode. Com essa abordagem, matamos
dois coelhos com uma cajadada só. Espero que não tenha sido
muito complicado ou sofisticado
entender como a
busca de dados funciona no React. Começamos com o
mínimo com useEffect, porque useEffect pode
ser usado para manipular dados e manipular
a lógica para o ciclo de vida de um componente Usamos useEffect para buscar dados apenas uma vez quando
o componente é montado, mas tivemos que desativar React StrictMode,
caso contrário, precisamos
escrever alguma lógica para , de
alguma forma, superar dupla renderização dentro
do modo de desenvolvimento. Para superar isso, usamos
uma biblioteca de busca de dados. Em nosso exemplo,
instalamos o React Query. React Query nos fornece aquele gancho abstrato useQuery que podemos usar para buscar dados
dentro do componente. Espero que faça sentido. Essas
bibliotecas de busca são uma ótima opção quando você trabalha com aplicativos React
modernos. Vamos confirmar as mudanças
que fizemos. O que fizemos foi
basicamente instalar o React Query, depois substituímos
nosso gancho personalizado fetchShowById pelo gancho useQuery. Também
retornamos o React StrictMode para o aplicativo porque
não tivemos mais problemas com a busca de
dados dentro do
useEffect. Agora, vamos adicionar
tudo ao estágio,
vamos confirmar e, digamos, a consulta de reação
instalada,
substituída, useShowById pelo
gancho useQuery. Incrível. Até a próxima.
74. 18 atribuição: Oi, lá. No último vídeo, falamos sobre bibliotecas de
busca de dados. Falamos sobre a consulta
React e
integramos a
consulta React em nosso aplicativo. Usamos o gancho de
consulta use dentro do componente show para
buscar dados por show ID. No entanto, se
voltarmos ao Home jsx, seu componente doméstico, você poderá ver que também buscamos dados aqui. É um pouco
diferente de apenas fazer uma solicitação GET simples quando
o componente é montado. Como temos
basicamente filtros, digitamos algo dentro da caixa de pesquisa
, podemos escolher diferentes botões de rádio
e clicar
no botão Pesquisar somente após o envio da solicitação. No entanto, as
bibliotecas de consulta
e busca de dados do React também podem lidar com
esses cenários. Tenho uma tarefa para você. Você pode integrar o gancho de consulta
Use na página inicial para que possamos
substituir esses estados de uso aqui por um único gancho de consulta
Use. Vá em frente, tente integrar o gancho de consulta
Use dentro
do componente inicial. Aqui está um conselho
que posso lhe dar. Você pode acessar a
documentação do React Query especificamente para ver os itens e conceitos
que você pode procurar. Deixe-me ver as consultas
desativadas e pausadas
e, na parte inferior, elas têm esse exemplo com consultas preguiçosas. Você pode usar este exemplo
aqui para integrar, use query inside home component. A lógica será muito
semelhante a esse exemplo, mas você precisa ajustar essa
lógica ao nosso caso de uso. Vá em frente, tente fazer isso e depois
compararemos o resultado no próximo vídeo.
Te vejo lá.
75. 19 Usando o React Query para pesquisar dados na página inicial: Olá. Como foi sua tarefa? Você conseguiu
alcançar o que queríamos? Você conseguiu integrar o gancho useQuery
nos componentes domésticos? Vamos tentar ver. Assim como eu disse,
você pode consultar esse exemplo para
implementar a lógica
com o gancho useQuery. O que eu vou
fazer simplesmente copiar esses dois aqui e colocá-los em cima. Também precisamos importar e
usar Query de react-query. Vamos colocar a entrada no topo. Então, não precisamos usar
React.useState porque importamos useState
diretamente da biblioteca e agora precisamos ajustar
isso ao nosso caso de uso. Em primeiro lugar, o que é
essa chave habilitada aqui? O fato é que
há situações em que
queremos buscar dados
condicionalmente,
porque essa lógica, por padrão, é executada quando o
componente é montado. Os dados são obtidos quando
o componente é montado. No entanto, isso
nem sempre é verdade. E se tivermos uma opção, e quando essa alternância for verdadeira, ou quando aplicarmos o filtro somente então
quisermos buscar a lógica. Nesse caso, podemos usar a opção
habilitada aqui para permitir react-query entenda
que queremos executar
ou não
essa lógica. No nosso caso, temos filtros. Nossos filtros são
a sequência de caracteres de consulta, tudo o que digitamos
dentro da caixa de pesquisa. Depois, também temos
a opção de pesquisa, que é o valor para ler
seu botão que selecionamos, sejam programas ou atores. Esses são os filtros que temos. Como gerenciamos toda
a lógica relacionada
à inserção desses filtros para selecionar e ler seus botões, gerenciamos tudo isso
dentro do SearchForm. Em seguida, passamos os dados de volta para casa usando a função
OnSearch aqui. Precisamos
pensar de alguma forma em como podemos passar essas informações do filtro
para o gancho useQuery. Podemos usar, digamos, estados
auxiliares para filtros
e, em seguida, podemos passar esse
filtro como parte da QueryKey. Se o filtro for
nulo ou estiver vazio, não
selecionamos nada, simplesmente desativamos a consulta, porque quando
entramos na página, não queremos buscar
dados porque, bem, não
temos filtros. Não inserimos nada. No nosso caso, filtre por padrão, em vez de uma string vazia, ela será nula e a
passamos para a opção habilitada. Somente se o filtro for verdadeiro,
poderemos consultar os dados. Nesse caso, o
gancho será ativado. Em seguida, também passamos o filtro
como parte da QueryKey. Isso significa que se o filtro mudar, se esse valor mudar de alguma forma, no nosso caso,
será um objeto. Se esse objeto for alterado, ReactQuery entenderá isso e a QueryKey mudará, e o gancho UseQuery
revalidará a consulta. Ele executará novamente a consulta
com a nova QueryKey. Basicamente, o QueryFunction que fornecemos aqui será executado. Novamente, ele atualizará os dados e preencherá novamente a
variável de dados que temos aqui. Chega de falar, vamos finalmente fazer alguma coisa. Em primeiro lugar, precisamos
definir esse filtro aqui. Faremos isso dentro da função Onsearch
que temos aqui. Não precisamos de todos
esses blocos para tentar pegar. Eu só vou
comentar isso. Dentro do Onsearch, vou apenas
chamar setFilter e
definir setFilter para qualquer string de consulta que
tenhamos e qualquer
SearchOption que tenhamos. Então, como eu disse, passamos o filtro como parte da
QueryKey em vez de todos. Vamos chamá-lo de
algo como pesquisa, isso realmente não importa. Dentro de QueryFunction,
precisamos de alguma forma colocar lógica
que temos aqui
com base na SearchOption. Dentro dessa QueryFunction, perguntaremos se
filter.searchOption é
isso que definimos
e, quando eu
escrever a lógica dentro desse
filtro QueryFunction, ela não será nula. Porque, como você se lembra, a consulta será
desativada quando
o filtro for nulo em nosso caso. Isso significa que é
seguro escrever aqui filter.searchOption sem
se preocupar com o fato de o filtro ser potencialmente nulo e isso nos gerará um erro. Algo como não é possível ler as propriedades searchOption de null. Se o filtro SearchOption
= mostrar, nesse caso, pesquise ForShowsFilter.q,
caso contrário, SearchForPeopleFilter.q. É
isso mesmo. Agora
podemos remover a lógica que tínhamos
anteriormente na pesquisa. Podemos remover esses dois ganchos
useState aqui, dados que desestruturamos
do gancho useQuery, vamos
chamá-los de ApiData, um erro que
desestruturamos, vamos
chamá-lo de ApiDataError. É isso. Eu removo esse comentário indesejado e
vamos ver o que temos. Vamos inspecionar o console. Vamos inspecionar a guia Rede. Vou digitar
algo como olá. Clique em “Pesquisar” e
você verá que funcionou. Bem, o mesmo comportamento
que tínhamos anteriormente. Se eu mudar para atores
e digitar garotos. Por exemplo, aqui
temos a solicitação, se eu voltar para
shows e depois fizer novamente, algo como meninas, você verá que os dados são buscados. Porque, novamente, o filtro muda sempre que pressionamos
o botão Pesquisar. Sempre que clicamos
no botão Pesquisar, atualizamos o estado do filtro. estado dos filtros é atualizado, QueryKey fica, digamos,
invalidado, ele muda. Isso significa que o ReactQuery
buscará novamente os dados com
o filtro mais recente, com a última QueryKey que
passarmos. Simples assim. Você provavelmente já percebeu
esse comportamento estranho, quando você pode ver várias
solicitações sendo processadas. O fato é que o ReactQuery
tem algo chamado busca novamente de
dados ao refocar. Esse é um dos recursos
dessas bibliotecas de busca de dados. Sempre que você tentar
reorientar a janela, ela atualizará os dados. Você pode ver se eu clico
dentro do trabalho de rede
e, em seguida, clico em algum lugar dentro da página novamente, ela sempre envia a solicitação. Esse comportamento, na maioria
das vezes, pode ser desejado, mas no nosso caso, esse comportamento é
definitivamente indesejado. Podemos desativar isso. Dentro das opções, vou
passar RefetchOnWindowFocus
e, se você passar o mouse, poderá ler a descrição do que
exatamente essa opção faz, o que a
manterá como falsa. Vamos ver. Vamos
procurar alguma coisa. Se eu tentar reorientar a janela novamente, nada acontecerá. Algo parecido. Agora, temos o useQuery também dentro do componente
inicial, parabéns. Eu realmente espero que você tenha
acertado essa tarefa. Pode ser muito desafiador, e definitivamente foi porque é algo novo, uma nova
biblioteca, uma nova lógica. Mas você pode ver
que, quando se acostuma, não há nada realmente
complexo no final. Vamos confirmar as mudanças
que fizemos. Vai ser bem simples. Vamos apenas
dizer que edite ou
use o Query na página inicial
para buscar dados de pesquisa. Incrível. Enviando
tudo para o GitHub e até o próximo.
76. 20 Mostrando informações na página Mostrar: Olá, novamente, no último vídeo adicionamos o gancho de consulta de uso à página inicial e agora temos o ciclo completo de busca de dados em
nossos componentes. Mas, como criamos a página de exibição, precisamos exibir
os dados de exibição nessa página. Isso é exatamente o que
vamos fazer neste vídeo, vamos preencher os dados na página
do programa dentro do componente
show, vamos lá. Quais dados precisamos exibir? Se dermos uma olhada na resposta
da API, é isso
que recebemos em nossos dados. Precisamos decidir o que exatamente queremos
exibir na página , então vamos
criar alguns componentes e eu já tenho uma
ideia, então vamos em frente. Em primeiro lugar,
na pasta show, vou criar um novo arquivo chamado
ShowMainData.jsx. Isso vai ser um componente. Mas agora ele retornará um simples padrão de exportação
div para
mostrar os dados principais. Em seguida, também criarei, deixe-me ver outro componente
que chamarei de detalhes, detalhes do
jsx e provavelmente adicionaremos outra
coisa. Por enquanto, isso é suficiente
, voltamos à página de exibição. Aqui temos esses dados do
show, showData.name. Em vez disso,
vamos usar o componente show main data que
importamos dos componentes, mostra showMainData onde
agora o mantemos assim. Depois disso, vamos
exibir os detalhes. Aqui, podemos ver os detalhes na tag h2 e
,
em seguida, exibir os detalhes Também
precisamos
importá-los de shows details. Tudo bem, deixe-me
salvá-lo, deixe-me
voltar para a página do programa
e aqui tenho olá, olá, exatamente o que
temos dentro de nossos
componentes por enquanto. O que vamos exibir
dentro do ShowMainData? Acho que precisaremos do nome do programa, algo como grade,
resumo e imposto, deixe-me ver. Temos um nome aqui, temos gêneros, temos média ou não média, média de
classificação, então
vamos exibir tudo
isso dentro de ShowMainData,
vamos passar para lá. Antes de tudo, também precisamos de uma
imagem e, se você se lembrar temos essa mídia original e
ela pode ser nula. vamos lidar com casos
nulos dentro Desta vez, vamos lidar com casos
nulos dentro
do componente
, então vamos passar showData.image e depois
passaremos o nome que será showData.name e depois
passaremos a classificação. A classificação será
apenas deixe-me encontrá-la,
apenas a média de classificação, passaremos o objeto e manipularemos. Média
dentro do componente, classificação
ShowData, então
precisaremos de um resumo, pois
lembramos que exibimos versão
muito curta do
resumo dentro cartão de
exibição. Desta vez,
exibiremos o resumo completo
na página de
exibição. Vamos passar um resumo
que está localizado aqui. Esta é a
string HTML, conforme você se lembra resumo de
ShowData e, em seguida,
passaremos os gêneros. Deixe-me encontrar gêneros aqui. Esta é apenas uma
variedade de gêneros
deste programa, gêneros ShowData. Incrível. Agora vamos entrar ShowMainData e
pegar todas essas instruções. Vamos pegar imagens, vamos pegar nome,
classificação, resumo e gêneros. Agora, o que vamos
escrever dentro dessa div, antes de tudo, precisaremos exibir
a imagem. A fonte será
Image.medium, como você se lembra, mas desta vez vamos exibir
a imagem original em vez da pré-visualização em tamanho médio. No entanto, precisamos lidar com os casos de uso nulos
conforme você se lembra , então vamos perguntar se a imagem é verdadeira,
as imagens estão definidas? Em seguida, use a imagem original, caso contrário,
use a imagem não encontrada. Se eu voltar para o cartão de exibição ou para a grade de exibição, tenho uma lógica bem
semelhante aqui, vou apenas reutilizar a
imagem não encontrada em png e colocá-la
aqui e, se você lembrar que imagem não encontrada em png e colocá-la ela colocada dentro
da pasta pública, ela será exibida sob a raiz. Ao lado da imagem,
talvez também vamos adicionar alt aqui, que será mostrado nome, então
exibiremos as informações, então vamos separar esse
bloco com um div. Aqui, vamos
colocar algo como
nome como título e, em
seguida,
exibiremos aqui a classificação para que
possamos colocar classificação como média,
esse objeto, mas a
classificação também pode ser nula ou, se eu não estiver
errado, a média da classificação pode ser nula ou não definida ou
pode ser zero. Não tenho
certeza disso, mas a média de
classificação dessa estrutura
sempre será a mesma. Nesse caso, podemos fazer
algo se a média da classificação for algo verdadeiro ou
digamos que não seja zero, podemos usar o operador or. O que quero dizer é que suponha que tenhamos uma classificação média zero. Vamos criar essa média aqui, é zero, então
vamos exibir a média
ou olá e você pode ver olá
sendo impresso , o que significa que a média não foi aprovada porque é falsa
e zero é considerado um valor falso.
Nesse caso, exiba olá. Vamos aplicar
exatamente a mesma lógica aqui, então, se a média
for zero ou se for falsa nesse caso,
exiba N/A, faz sentido? Em seguida, vamos exibir o resumo, mas
aqui está o problema. Vamos tentar fazer isso, vamos ver o que teremos. Vamos voltar ao nosso aplicativo e temos uma imagem bem
grande aqui. Tudo bem, vamos
aumentar e rolar para baixo. Aqui você pode ver que obtemos a string
HTML como está. Na verdade, a string HTML
a considera como uma string, não como HTML. Se olharmos dentro dos dados
, é apenas uma string e o React não sabe
que isso é HTML. Para tratarmos o
HTML como se fosse HTML, precisamos usar o seguinte. Antes de tudo, vamos
transformar esse div em um componente de fechamento automático
e, para esse div, podemos passar algo chamado
DangerouslySet innerHTML. Este é um suporte especial do React, deve ser um objeto
e
esse objeto tem propriedade HTML e
passamos um resumo para dentro. Com essa construção, React entende
que queremos
tratar o HTML na verdade como HTML. Vamos tentar ver. Agora você pode ver que não temos nenhuma tag HTML aqui
e, se inspecionarmos a marcação, qualquer HTML que
recebemos será realmente
tratado como HTML. Por que isso é definido como
DangerouslySetInnerHTML? O problema é que quando você deseja,
digamos, exibir HTML ou
injetar HTML na página, ela pode conter
JavaScript malicioso. Portanto, para evitar isso, React avisa que, se
você quiser ter certeza de que deseja inserir HTML na página, a decisão é totalmente sua e a
precaução é que você precisa usar
dangerouslySetInnerHTML porque é perigoso. Ao lado do resumo,
vamos mostrar os gêneros. Podemos dizer os gêneros e por que eu
tenho um ponto de interrogação aqui. Os gêneros serão,
deixe-me ver, então temos que é uma matriz, o que significa que podemos mapear cada elemento para a marcação jsx. Vamos usar o
método.map, vamos lá. Vamos criar
outra div aqui e os gêneros serão gêneros. mapa. Aqui teremos gênero e talvez
exibiremos uma tag span e, por dentro, podemos exibir o
gênero. Quando usarmos o.map para mapear a
marcação jsx, precisamos passar
a chave exclusiva para
o elemento do mapa. Deixe-me ver que os gêneros são
bastante únicos, eu diria, então podemos passar o gênero
em si como a chave única. Vamos tentar ver. Eu amplio, temos
gêneros, comédia, família. Eu acho que esse programa
tem apenas um gênero. Tem comédia e família. Como não temos espaço, parece que essa é uma única
string, mas não é. Não preste atenção,
pois, por enquanto, isso não tem estilo. Por enquanto, lidamos apenas com a
lógica dentro de nosso aplicativo. final, lidaremos com o
estilo. Agora deixe-me ver, então usamos todos os
problemas que queríamos. Por enquanto, acho que é isso. Vamos mais longe e
lidar com os detalhes. Quais detalhes internos
vamos mostrar? Deixe-me ver que tipo de
dados temos aqui? Provavelmente exibiremos algo como o
status do programa, se ele ainda está em exibição, ele
terminou ou talvez tenha
acabado de ser lançado e quando exatamente esse programa estreou, e talvez a rede, onde exatamente o
programa foi publicado. Em qual região, em qual canal de TV,
algo assim. Para detalhar o componente, vou passar primeiro
o status e isso será apenas
showData.status, então provavelmente quando
o programa estreou, então será apenas
ShowData.premiered e depois network. A rede é apenas um
objeto, ShowData.network. Legal. Eu o guardo. Desta vez, vou para o componente
Details aqui, passo status premiered network e
vou pegar status premiered network ou talvez vamos usar
outra sintaxe desta vez apenas para fazer novamente,
digamos, uso casual do JavaScript. Em vez de desestruturar adereços diretamente dentro dos argumentos da
função, faremos isso em uma linha separada só
porque queremos que seja assim, nada de especial nisso. Aqui, em vez de “olá”,
vou apenas dizer, talvez adicione uma tag de parágrafo
e diga “status é status”. Então, dentro de outro
parágrafo, direi “estreou nesta data” e depois
exibiremos a rede. No entanto, essa rede também pode ser nula
porque nem todos os programas contêm essas informações, então precisamos lidar com esse caso. Precisamos presumir
que, na verdade, essa é uma boa prática quando você
trabalha com algo desconhecido É muito bom supor
que algo pode ser nulo ou indefinido ou pode
nem mesmo ser passado. Vamos perguntar à rede, se ela é confiável, se existe? Nesse caso, exibiremos uma sequência
de caracteres, algo como estreada
nesta data em um
canal ou país específico. Provavelmente vamos escolher apenas o nome, estreou nesta
data em network.name. Usei crases
para especificar que
queremos usar a
interpolação de string dentro
da string e, em seguida,
interpolo o nome da rede dentro da string do nome da
rede. Caso contrário, exiba nulo, não exiba nada
ou podemos
ter certeza de que usamos o valor
booleano aqui. Podemos transformar a rede em um valor booleano e em vez de usar o operador
ternário, podemos usar a extremidade lógica. Nesse caso, nenhum nome
de rede será exibido somente quando a
rede for verdadeira. Agora, vamos
ver o que temos e
temos o status encerrado e
estreado nesta data na CBC. Incrível. Agora, parece que exibimos quase
tudo o que queríamos. No entanto, podemos dar mais
um passo
e exibir mais dados, como informações sobre temporadas e informações sobre o elenco. O que precisamos nesse caso? Se analisarmos
os dados da API que
recebemos, não temos nenhuma informação
sobre elencos ou shows. Mas se voltarmos
à API do TV Maze, aqui temos esta seção, deixe-me ver, sobre incorporação. incorporação nos permite carregar
mais dados sobre o programa, e aqui está um exemplo.
Deixe-me abri-lo. O URL tem essa aparência. Incorporamos episódios, incorporamos elenco e, se
rolarmos para baixo, veremos esta
seção embutida de
sublinhados com episódios e elenco. Isso é exatamente o que
vamos fazer, mas precisamos modificar nossa
função para pesquisar e mostrar. Vamos copiar essa parte
incorporada e usar a
função getShowById para obter dados. Aqui no URL, podemos adicionar incorporação, episódios e elenco. Mas em vez de episódios, vamos incorporar temporadas. Também podemos obter informações sobre
as temporadas. Em vez de episódios, vamos especificar temporadas. Nós o salvamos,
voltamos ao programa
e agora ele foi revalidado
porque você lembra que, e agora ele foi revalidado
porque você lembra que ao alternar o foco entre a
janela e outra coisa, os dados serão atualizados porque
usamos o gancho useQuery e podemos evitar seu comportamento usando
RefetchOnWindowFocus. Se você não quiser esse comportamento,
na verdade, provavelmente
não precisamos desse comportamento, vou desativá-lo da mesma forma que fizemos na página inicial. Vamos ver o que
temos nesse caso. Você pode ver que agora temos esta seção
embutida de sublinhados, aqui temos informações sobre o elenco e
as temporadas. Na verdade, vamos copiar esse URL, abri-lo aqui e inspecionar a forma
dos dados das temporadas e do elenco. Antes de tudo, precisamos criar componentes
correspondentes
para as temporadas e o elenco. Na pasta Shows, vou
criar cast.jsx e
vou criar seasons.jsx. Vou copiar rapidamente a marcação,
então, por enquanto, será div, adereços, vamos
desestruturá-los em linha e vou chamá-la de Cast. O mesmo que farei com as temporadas. Agora vamos usar esses
componentes dentro da mostra aqui. Então, na próxima div, teremos algo como div novamente, outra tag de título
que dirá Seasons. Aqui vamos
exibir o componente Seasons. Foi importado automaticamente. Se eu olhar para o topo, ele foi importado das temporadas de shows de
componentes. Vou copiar isso. Em vez de temporadas,
agora vou
exibir o elenco e depois importar o elenco
novamente.
Como importar? Eu pressiono “Tab”, boom, importado na parte superior. Ótimo. Quais dados eu vou passar? Para o componente Seasons, vou passar o adereço Seasons, e Seasons será
sublinhado nas temporadas incorporadas. Isso é o que
recebemos da API, então vou passar a mostrar
dados sublinhados incorporados. Certifique-se de não
escrever incorretamente, .seasons,
e exatamente o mesmo que farei com o elenco, mas em vez de passar as temporadas, passarei o adereço do elenco, ShowData
embedded.cast. Agora, dentro de Seasons, vou desestruturar o suporte de
temporada que passamos. Vamos ver o que
vou mostrar aqui. Em primeiro lugar, queremos saber quantas temporadas
temos no total. Se eu voltar ao aplicativo, terei esse problema: padrão inesperado de objeto
vazio. Vamos corrigir isso rapidamente.
Se formos para o Cast, vou simplesmente remover isso. Então, dentro de Seasons,
o que vou mostrar. Em primeiro lugar, dentro da tag p, vou exibir
as temporadas no total. Vamos verificar se temos
isso, temporadas no total. Aqui vamos
adicionar seasons.length. Se analisarmos nossos dados, as temporadas são apenas uma matriz. Portanto, cada temporada é
um item da matriz, o que
significa que o número de elementos é igual ao
número de temporadas. Bem, parece que
é lógico, então vamos
usar seasons.length. Ao lado das temporadas no
total exibiremos episódios no total e
diremos, deixe-me ver. Como temos as temporadas como uma matriz e dentro de
cada elemento,
temos a ordem dos episódios
e, basicamente, quantos episódios temos em
uma única temporada? Precisamos
calcular de alguma forma o número total de episódios em toda
a lista de temporadas. Podemos usar algo
array.reduce para calcular isso. Então, vamos
contar seasons.reduce. A redução de
temporadas será por padrão agora, então vamos reduzir
toda a nossa matriz de temporadas em um número. Comprimiremos essa matriz de
temporadas em um número. Basicamente, analisaremos cada elemento da matriz e
resumiremos a ordem dos episódios. Aqui esta será nossa soma e o segundo elemento aqui será o elemento
atual da matriz
que será repetido. Esta vai ser a temporada. Então, vamos
dizer, por favor, devolva-nos um pedido adicional de temporada/episódio. Vamos tentar ver se
não temos nenhum pedido. Temos temporadas no total uma, episódios no total 13. Ótimo, funcionou. Agora, ao lado do
parágrafo,
exibiremos os dados de cada temporada, basicamente, essas informações, o que
significa que precisamos mapear cada elemento da temporada
com a marcação jsx. Vamos usar o método
do mapa de pontos. Vamos dizer
seasons.map, season. Vamos
mapeá-lo para um div ou agora diga olá ou chave, vamos passar a temporada. deixe-me ver os dados. A temporada tem um ID que é
representado de forma exclusiva para que possamos
usá-lo com segurança como chave. Vamos dizer,
por favor, exiba
temporada, temporada.número, então o
número da temporada. Ótimo. Em seguida, vamos
exibir a tag p. Vamos contar aos episódios quantos episódios
esta temporada tem. Provavelmente, na ordem dos episódios da temporada,
podemos usá-la, por que não? Em seguida, mostraremos
quando esta temporada foi ao ar, e podemos usar a data de estreia e a
data de término. Ótimo. Então, deixe-me
separá-lo em um div separado, então
eu direi ao aired. O que vou fazer dizer Season.PremiereDate,
SeasonEndDate. Provavelmente isso, sim. Vamos tentar ver. Temos temporadas no total, episódios no total, então
temos a primeira temporada que tem 13 episódios e foi ao ar desta data
até esta data. Parece bom para mim. Se precisarmos adicionar algo mais,
faremos isso mais tarde, por enquanto isso bastará. Vamos trabalhar no
componente do elenco desta vez. Para o componente fundido
, passamos o suporte fundido. Então, aqui dentro do componente fundido ,
vou pegar o suporte fundido e vamos pensar em quais dados
vamos exibir aqui. Vamos inspecionar a API. O elenco
também é apenas uma matriz e cada matriz
tem essa pessoa, personagem, eu e voz Keith. Vamos ver o que
vamos fazer. Provavelmente vamos mapear cada elemento da matriz para algumas informações e
exibi-las aqui. Vamos fazer isso. Então, vamos
simplesmente fazer cast.map. Vamos chamá-lo de item e
vamos mapeá-lo para um div por enquanto. A chave será, deixe-me ver, item person.id, provavelmente isso. Eu acho que isso
será bem único. Dentro da div, primeiro lugar,
vamos exibir, deixe-me ver, provavelmente uma imagem
real. Vamos
tentar fazer isso. Vamos colocar essa imagem
em um div por enquanto. A imagem será
item.person.image, mas você lembra
que a imagem pode ser nula, então precisamos lidar com isso. Se item.person.image existir, nesse caso, use
item.person.image.medium. Caso contrário, use novamente, vamos pegar, vamos usar a imagem
não encontrada png. Ótimo, vamos salvá-lo. Então, ao lado
da imagem que vamos exibir, deixe-me ver, temos item.person.name e depois vamos exibir o personagem dentro
desse programa nesse programa. O personagem
será o nome do personagem, então essa pessoa jogou
item.character.name. E você sabe o que?
É muito repetitivo digitar item ponto
alguma coisa toda vez,
então, a partir desse item vamos desestruturar a
pessoa e o personagem. Em vez de escrever
item dot toda vez, vamos
escrever person.character. Então character.name. Deixe-me ver como podemos
usar outra coisa. Nós temos esse eu
e essa voz aqui. A voz provavelmente se
refere a se essa foi apenas a narração e se o papel não foi desempenhado diretamente
no programa. Foi apenas uma narração dessa pessoa, então talvez
possamos usá-la. Também podemos desestruturar a
voz a partir
daqui porque é a chave do nosso item e vamos perguntar se essa pessoa
cuida da narração. Vamos apenas
exibir algo como outro tubo porque
isso é o que usamos aqui e
vamos dizer voice over, caso contrário, uma string
vazia ou podemos usar novamente o operador and e queremos ter certeza de que isso será um booleano, mas acho que esse
valor aqui
sempre será um booleano, então não
precisamos transformar essa variável, esse valor em um valor booleano aplicando dupla negação ou usando o construtor booleano. Isso será suficiente, eu acho. Agora vamos tentar ver
nosso resultado final. Temos a seguinte página de apresentação. Deixe-me torná-lo menor. No momento, sei que
não tem estilo, mas vamos
cuidar disso, não se preocupe. Temos tudo o que
queremos sobre o programa. Incorporamos o resumo, exibimos a classificação média do
programa, exibimos gêneros, exibimos detalhes
quando foi ao ar, talvez quando foi encerrado, exibimos informações
sobre as temporadas e exibimos
informações sobre o elenco. Qual foi a pessoa
que interpretou esse papel e
essa pessoa era um personagem
de dublagem ou era qualquer
personagem da série. Acho que é isso. Na verdade, foi muito. Trabalhamos com dados de API, criamos
componentes correspondentes para exibir dados. Onde agora vamos
comprometer tudo. Vamos dar uma visão geral rápida do
que temos aqui. Modificamos a
função get show by id para buscar dados,
incorporamos temporadas, incorporamos elenco e usamos
as informações que obtemos da API e exibimos essas informações
na página do programa. Criamos
componentes correspondentes, passamos os adereços correspondentes e depois manipulamos tudo dentro de cada
componente correspondente, algo assim. Vou adicionar
tudo ao palco e minha mensagem
de confirmação
exibirá dados detalhados do show na página do programa. Legal. Mais uma coisa que eu gostaria de salientar aqui é que,
como você se lembra, desabilitamos esse
comportamento RefetchOnWindowFocus da consulta use who. Agora, quando revalidarmos, desculpe-me, deixe-me
iniciar o aplicativo novamente. Onde está nossa página do programa? Opa, eu o fechei acidentalmente. O que quero dizer é que, quando
reorientamos a janela agora, os
dados não são atualizados
o tempo todo , mas o que acontece se
nosso ID de show não existir? Vamos tentar ver. Vamos
tentar algo sem sentido. Vamos ver o que temos? Vemos que os dados estão sendo carregados e
podemos ver esse comportamento de repetição. Na verdade, você pode ver que a solicitação foi
enviada três vezes
e, se, no momento em que a terceira solicitação for atingida,
ainda tivermos um erro nossa solicitação, então use
query exibirá um erro. Você pode ver que a
biblioteca de busca de dados é algo mais do que simples Busque meus dados quando
o componente for montado. Essa busca de dados pressupõe que as solicitações
podem falhar e, se falhar, a
repetirá automaticamente
algumas vezes com algo
chamado recuo exponencial. Por exemplo, se nossa
solicitação falhar
pela primeira vez, a solicitação será
repetida após um segundo;
se falhar, a
próxima tentativa
ocorrerá após dois segundos e próxima tentativa ocorrerá
após três segundos. Use query cuida disso. Muito legal. É isso. Nos vemos na próxima.
77. 21 Adicionando o botão voltar na página Mostrar: Olá de novo. No último vídeo, criamos componentes nos
quais exibimos dados sobre um programa específico
na página do programa. Foi bem longo. Agora precisamos pensar um pouco
mais sobre a experiência do usuário. O que quero dizer com isso? Suponha que estejamos
na página inicial, procuraremos um programa específico clicaremos em Leia mais. Acabamos na página do programa. Agora, não temos nenhum botão extra
para navegação aqui, o que significa que o usuário
precisa clicar em Voltar para a página anterior
e, se
voltarmos para essa página, veremos que todos os
nossos dados sumiram, precisamos iniciar a
pesquisa novamente. O que podemos fazer
nessa situação. Antes de tudo, precisamos
adicionar na página do programa um botão que levará o
usuário de volta à página inicial. Isso será um pouco mais conveniente para o usuário. Mesmo assim, isso não resolve
o problema de os dados quando o usuário retorna a essa página e bilheteria Nós não lidamos com
isso, mas, idealmente, precisamos
lembrar de alguma forma a última pesquisa que fizemos para que, quando o usuário
volte para aquela página, ela ainda está lá. Não vamos abordar
isso na bilheteria, vamos apresentar
uma alternativa. E se procurarmos o programa e, quando
clicarmos em Leia mais, ele levará o usuário para a nova guia? Ele abre esta
página de exibição na nova guia. Vamos seguir em frente e fazer isso. Se voltarmos ao componente show
card que temos, usamos esse componente de link aqui. Usamos o componente de link
porque usamos biblioteca de roteamento
do lado do cliente react-router
e, para que possamos lidar com
a navegação adequadamente
por meio de links, usamos esse componente de
link especial importado do roteador React dom. Mas se quisermos abrir
algo em uma nova guia, isso não está relacionado
ao roteamento do site do cliente. Nesse caso, podemos usar uma tag âncora simples em vez de usar o componente de link
do roteador React dom. Então, podemos simplesmente removê-lo
e, em vez de usar o clink, exibiremos
a tag âncora. etiqueta de ancoragem tem uma propriedade de
calha. Agora podemos fornecer outro
atributo da tag âncora chamado target e especificamos o
sublinhado em branco. Assim que eu especifico
em branco como o destino, recebo este erro do link
ES vindo do
React JS x target blank, que, por favor, use a
relação não referenciada. Eu só vou
copiar não especificado. Essa é apenas uma medida de segurança muito
pequena. Eu o guardo. Agora, vamos tentar. Se eu clicar em Leia mais, ele abre minha página de exibição em
uma nova guia. Muito legal. No entanto, novamente, como concordamos em tornar
a experiência do usuário
um pouco mais conveniente, adicionaremos o botão Voltar ao Início em algum lugar
na parte superior. Vamos para o componente da página de exibição. Aqui na parte superior, logo
acima de mostrar os dados principais. Podemos acrescentar duas coisas aqui. Podemos adicionar um componente de link que nos
leve de volta para casa, algo assim,
voltar para casa, e essa é uma solução totalmente
boa. Na verdade, vamos
usar esse. Mas eu só quero que você veja
a alternativa para isso. Porque o roteador React
é uma biblioteca de roteamento. Tem algo a oferecer. Vamos dar
uma olhada nisso. Mesmo assim, podemos usar
o componente de link. Em vez de usar o clink por enquanto, adicionaremos um botão e diremos
: “Volte para casa”. Nesse botão do tipo botão, vamos ativar o manipulador de
clique, Voltar e esse, ao voltar, faremos algo por nós. Se voltarmos à documentação do
react-router, ela terá algo
chamado use navigate. Usar o gancho de navegação, olhando este exemplo, nos
permite
navegar programaticamente entre as páginas, ainda usando o roteador React dom. Em vez de usar
o componente de link, digamos que de forma mais declarativa, usamos a função que fará a navegação basicamente programaticamente e de forma
mais imperativa. Olhando esse exemplo, posso pegar e usar a navegação
a partir do roteador React dom. Na verdade, eu já importei, então vou fazer assim. Desculpe-me, não use
parâmetros, use navegar. Então vou ligar para
usar navegue aqui. Esse uso de navegação
nos retorna uma função que
precisamos chamar para navegar
até uma página específica. Navegue até, vou
chamá-lo assim. Quando clicamos em, voltamos para a página inicial, ligamos para navegar
até e, em seguida,
especificamos, voltamos para a página inicial. Vamos voltar ao aplicativo. Além disso, temos
esse botão aqui. Novamente, esse botão não vincula o componente, é um botão. Se clicarmos,
voltaremos para casa. Caso você precise
navegar
programaticamente ou redirecionar o
usuário para uma página, você pode usar o gancho de navegação de
uso. Mas, no nosso caso, não
precisamos realmente
transformar o botão em um
link programaticamente. Podemos usar diretamente
o componente de link porque ele realmente
faz mais sentido. É por isso que
não vamos usar, usar a navegação, que ficará com
o componente de link. simples quanto isso. Agora, vamos tentar ver. Se olharmos para dentro da marcação. Agora, na verdade, é
a etiqueta âncora. Legal. Se clicarmos nele, ainda
voltaremos para casa. Mas isso exige
que usemos menos código. Na verdade, é melhor
porque agora faz a marcação adequada, a marcação HTML
adequada para navegar entre as páginas,
pois é uma tag âncora. Legal. Agora, aumentamos um pouco
a experiência do usuário. Agora parece muito, muito melhor. É isso por enquanto. Vamos
confirmar as mudanças. Adicionamos voltar à página inicial e abrimos a
página de exibição em uma nova guia. Vou contar dentro da
minha mensagem de confirmação botão
Abrir ou Ler mais
leva o usuário a uma nova guia agora, adicionado o
link Voltar à página inicial na página de exibição. É isso. Empurre
tudo para se levantar. Eu vou te ver
na próxima.
78. 22 Introdução ao useReducer como alternativa ao useState: Ei, no último vídeo,
falamos um pouco sobre a
experiência do usuário. Agora, quando clicamos em Leia mais, ele abre a página de exibição
dentro de uma nova guia, assim
como adicionamos o
botão
“Voltar para a página inicial” . Tudo isso é ótimo. No entanto, não temos
a funcionalidade do botão “Star Me”. Sempre que
clicamos nesse botão, queremos marcar o show como estrela. Posteriormente, quando navegarmos
até a página com favoritos, podemos ver nossa
lista de favoritos aqui. Como podemos conseguir isso. Antes de podermos fazer isso, precisamos analisar a
alternativa de usar o estado. Vamos voltar ao nosso componente. Digamos que, provavelmente, para a página inicial. Aqui vamos
jogar com o novo gancho. Como você já sabe, se quisermos ter algum valor que mude ao longo
do ciclo de vida do componente, precisamos usar o gancho
useState. Basicamente, é apenas
um valor que muda. Ele nos fornece a variável de
estado e a função que podemos
usar para atualizar esse estado. Essa é a nossa maneira de gerenciar o estado
local de um componente. Existe uma alternativa para
usar o estado chamada UseReducer. É uma alternativa, significa que
não substitui useState, assim como useState
não substitui useReducer. Você pode usar o que
quiser e o
que achar mais apropriado. Se tivermos useState e tivermos, digamos, definir a
função de filtro que podemos chamar para liderar o estado
com useReducer, temos algo
chamado ações. Na verdade, iniciamos
uma ação e, em seguida essa ação é tratada
por uma função, e essa função decide como atualizar o estado
com base em uma ação. Vamos dar uma
olhada no exemplo de um contador. O gancho do qual eu estava
falando é UseReducer. Vamos definir o que
é um redutor em um segundo. Aqui em cima, vou
chamar UseReducer. Esse useReducer como
primeiro argumento recebe algo
chamado redutor. Além disso, vou
criar a função redutora. Agora será uma função vazia e eu a passarei para
useReducer. Como segundo argumento, preciso passar pelo estado inicial. Assim como no caso de useState, nosso estado por padrão será zero porque vamos
implementar counter. Quando clicamos em um botão, queremos
incrementar ou diminuir. UseReducer, assim como useState, nos
retorna uma matriz de
exatamente dois elementos. Vamos desestruturar
esses dois elementos. O primeiro elemento, novamente
, será o estado, assim como com o useState. Digamos que contador. O segundo elemento será
algo chamado despacho. Agora, o que eu preciso fazer para atualizar o estado de alguma forma? O conceito de redutor,
portanto, esse gancho UseReducer é baseado no
conceito de redutores. Deixe-me abrir a pintura e
explicar uma coisa. Basta visualizar a ideia do
UseReducer. Com o UseReducer,
abordamos ações que são tratadas por uma única função
chamada redutor. Temos várias ações
acontecendo em nosso estado. Por exemplo, no caso de
contador, temos incremento. Deixe-me torná-lo um pouco maior
e então teremos um decréscimo. Digamos que temos outra
ação chamada algo como reset counter, reset. Então, todas essas ações são enviadas por essa função de
despacho para a lógica interna do React. Então, temos uma única
função chamada redutor, que manipula todas
essas ações recebidas. Sempre que uma ação está
sendo despachada, ela está sendo tratada pela função
redutora e qualquer coisa que a função redutora retorne
será o novo estado. Todo esse fluxo substitui o gancho useState e é baseado
no conceito de redutor. Agora, o que é o redutor? Assim como mencionei
anteriormente, redutor é apenas uma função que, de alguma forma, manipula
essas ações. Mas quais são essas
ações? Esse é o ponto. Precisamos definir
ações nós mesmos. Uma ação, nesse caso, é apenas um objeto que
transmite alguns dados. Por exemplo, podemos definir
uma ação para incrementar dados. Normalmente, quando
falamos de redutores, quando falamos sobre todo
esse conceito, uma ação sempre
será um objeto. Com o tipo, digamos, incremento e alguma carga
adicional. Pode ser qualquer coisa. Pode ser um novo valor, seja o que for. Esse objeto pode assumir qualquer forma. Mas geralmente ele tem
esse tipo, chave e carga útil apenas para
torná-lo mais consistente. Precisamos definir essas
ações nós mesmos. Em seguida, eles são manuseados
dentro do redutor. Eu vou para cá. Dentro da marcação JSX,
vou dizer que o contador será um contra-ataque,
interpelará o estado. Em seguida, adicionarei
dois botões aqui. Um será incremento, o segundo será decréscimo e o terceiro será redefinido. Cada função terá esse onClick e vamos nomear esses manipuladores
como onIncrement, depois onDecrement e onReset. Agora precisamos criar
essas funções. Vamos fazer isso aqui em cima. Temos onIncrement, depois temos onDecrement e temos onReset. Algo precisa acontecer. Precisamos enviar
ações para , de
alguma forma, atualizar o estado. Podemos ligar para o despacho. Aqui precisamos aprovar uma ação. Por exemplo, quando ocorrem
incrementos, enviamos uma ação. Novamente, uma ação
é apenas um objeto. Vamos pegar esse, na verdade. Não precisamos de nenhuma
carga útil aqui por enquanto. Vamos apenas
enviar uma ação e ela será um objeto
do tipo INCREMENT. Quando diminuímos,
queremos enviar uma
ação DECREMENTO. Se tivermos uma reinicialização, podemos enviar uma
ação do tipo RESET. Novamente, esses são os objetos que nós mesmos definimos para nós. Será mais fácil para
nós entendê-los. Sempre que esse despacho
estiver sendo chamado essa ação será tratada
pela função redutora. Essa função redutora
deve retornar um novo estado. Por enquanto, vamos retornar zero. Essa função redutora
recebe dois argumentos. Em primeiro lugar, ele
recebe currentState. Assim como no caso da função de atualização de estado com useState quando
passamos o retorno de chamada. Temos acesso ao currentState
como primeiro argumento. A mesma ideia está aqui
dentro do redutor. Temos currentState, vamos
chamá-lo de CurrentCounter. segundo argumento é a
ação que enviamos. Vou registrar
currentCunter e action. Vamos voltar aqui. Nós temos algo assim. Vamos inspecionar o console. Sempre que clico em Incrementar, vejo duas coisas sendo consoladas. Vejo que currentCounter
é igual a zero. Esse é o nosso
estado atual. Nós temos ação. Ação é exatamente o que
passamos quando chamamos a função de
despacho, essa será essa ação aqui. Com base no que passamos, com base no que
despachamos, podemos escrever nossa lógica
dentro de uma única função. Normalmente, quando você
trabalha com redutores, trabalha com o estojo do interruptor. Vamos
mudar action.type. Caso tenhamos o tipo INCREMENT. Nesse caso, do redutor, retornamos currentCounter mais 1. Nós incrementamos o contador. Novamente, tudo o que está
sendo retornado
do redutor será
definido como o novo estado. Caso tenhamos um decréscimo, dizemos currentCounter menos 1. Caso chamemos RESET,
retorne 0. Caso nenhuma dessas
corresponda por padrão, retornaremos 0. Vamos salvá-lo e vamos ver. Se eu clicar em Incrementar, o
contador será incrementado. Se eu clicar em Redefinir, ele será redefinido para zero. Se eu diminuo, está
sendo diminuído. Como você pode ver, usando essa função redutora
e usando as ações que nós mesmos definimos e depois as manipulamos dentro
da função de registro. Podemos alcançar essa lógica para gerenciar o estado
com base em ações. E, novamente, essa é uma alternativa ao uso
do gancho useState. Use o redutor da mesma forma
que o estado manipula o estado, mas com o conceito de redutores
e ações de despacho, qual deles usar. Depende do caso de uso e, na verdade, do que
você preferir. mais comum é usar useState, mas digamos que se sua
lógica para atualizar o estado inclua muitas ações, digamos,
diferentes, como Incrementar,
Diminuir, redefinir, definir um ações, digamos,
diferentes, como Incrementar,
Diminuir, redefinir, definir valor
específico,
digamos, Incrementar em 10, você
possa ter sua lógica
para atualizar o estado com base em ações específicas, você
pode usar o gancho UseReducer. Por que estou dizendo tudo
isso é porque, para implementar
nossa lógica,
Start Shows, usaremos o gancho
redutor de usuário porque
teremos algumas ações, como
Start Show e OnStart Show. Anteriormente, mencionei
que para essa ação você pode
passar qualquer dado aqui. Vamos ver o que quero dizer com isso. Assim como eu disse, temos um único lugar onde lidamos com a lógica e tudo o que for retornado da função
redutora será definido como o novo estado. Por que não definimos
outra ação aqui chamada SET_VALUE,
algo assim. Então, criarei outro botão aqui e
direi a Set para, digamos, 500. Em seguida, clique em Definir como valor. Vou criar essa
função aqui e despachar o tipo SET_VALUE para que ela possa ser tratada
pelo redutor. Vou passar o valor, ou digamos,
newCounterValue 500. Agora, como temos acesso ao objeto de ação
dentro do redutor e sabemos que o objeto de
ação é
exatamente o que despachamos,
podemos dizer que retorna
action.newCounterValue. Tudo o que passarmos como
newCounterValue será retornado da função redutora e será o novo estado. Vamos tentar ver
Incrementar,
Diminuir, Definir para 500, é 500,
algo assim. Quaisquer dados que você passar aqui estão disponíveis dentro da função
redutora. Basicamente, é isso. nada mais a
acrescentar sobre redutores Talvez nada mais a
acrescentar sobre redutores seja que você
provavelmente já ouviu falar sobre redux, uma biblioteca para gerenciar o
estado global em aplicativos React. Redux é baseado
no conceito de redutor. Em um redux, você
envia ações como essa e, em seguida, manipula todas elas dentro
de redutores. Legal. Vamos nos livrar
de tudo isso. Espero que tenha ficado claro por que o useReducer pode ser útil como uma alternativa
ao useState. Na verdade, talvez
eu acrescente que todas essas ações no incremento, no decréscimo, podem ser facilmente substituídas
pelo gancho useState. Em vez de lidar com toda a
lógica dentro do redutor, você pode simplesmente fazer algo
como setCounter, digamos CurrentCounter mais 1. O mesmo que você pode fazer
internamente em decréscimo. Desculpe-me, será
assim, currentCounter menos 1. Basicamente, você escreveria a mesma lógica que você
faz dentro do redutor. Quando você usa, useState
hook e, se estiver reiniciando, bastaria saber o
setCounter e talvez seja
mais fácil. Depende. É por isso que é
chamado de alternativa. Depende de você o que
atenda às suas necessidades. Agora que
conhecemos o UseReducer, podemos realmente
usá-lo para implementar nossa lógica para iniciar shows. Legal. Nos vemos na próxima.
79. 23 Starred mostra p1: Ei, aí. No último
vídeo, falamos sobre o UseReducer como uma alternativa
ao gancho useState. Ele pode ser usado para gerenciar o estado quando temos várias ações definidas e
gostaríamos de atualizar o estado com base em algumas ações. Vamos usar o
UseReducer para implementar nossa lógica de estudo de
programas. Vamos embora. Em primeiro lugar, como
vamos gerenciar
a lógica por trás
dos programas estrelados? Sempre que
clicarmos no botão
“Iniciar”, adicionaremos
show ID à matriz, que será nosso estado. O estado dos shows iniciais será apenas uma matriz de IDs de programas. Se clicarmos em um show, o
ID será adicionado à matriz. Se clicarmos nele duas vezes, ele será
removido dessa matriz. Então, sempre que vamos
para a página inicial, pegamos essa matriz de
shows estrelados e a
usamos para consultar dados
da API TV maze. Bem simples. A questão é: onde vamos
escrever essa lógica? Temos um componente doméstico. No entanto, em todo o componente, que é exibido
, mostre a grade ou grade
real com base nos
dados que temos. Vamos escrever a lógica
dentro do show grid por enquanto
e, mais tarde,
vamos extrair essa lógica para um arquivo diferente. Será mais fácil
acessá-lo dentro de outros componentes, por exemplo, o
componente inicial, porque nossa lógica será compartilhada entre vários
arquivos eventualmente. Vamos começar de forma simples. Dentro da grade de exibição, vou importar o
UseReducer do react. Então eu vou ligar para
você com, por enquanto,
digamos, um
redutor de programas estrelados que vamos
criar em um segundo. Nosso estado inicial será
uma matriz vazia. UseReducer retorna como uma
matriz de dois elementos em que
o
primeiro elemento será o próprio estado,
então starred é exibido
e, em seguida, a função de despacho,
digamos, dispatch start. Agora precisamos criar um redutor de shows
estrelado, uma função que
manipulará a lógica para atualizar o estado, bem como
precisamos definir ações. Basicamente, teremos
apenas duas ações aqui. Para começar um show e cancelar um
show. Vamos defini-los. Sempre que clicarmos em me marcar como estrela, enviaremos uma ação do tipo start-me ou,
digamos, start-me, e os dados
passados serão mostrados como ID. A segunda ação
será unstar. Novamente, vamos passar o
show ID para o redutor. Dentro do redutor, o primeiro argumento é
nosso estado atual. Vamos chamá-lo de início atual. O
segundo argumento será um objeto, a ação que está
sendo enviada. Então, aqui, usando
novamente o caso do switch, escreveremos a
lógica para lidar com as ações que estão
sendo despachadas. Escrevemos a lógica com
base no tipo de ação. Nós trocamos o tipo de ação. Caso tenhamos uma
estrela, nesse caso, retorne currentStarred.concat a
ação showId. Seja qual for o ID de exibição que
passarmos pela ação, adicione esse valor à
nossa matriz atual com estrelas. A segunda ação será
a estrela com a qual
vamos encarar. Nesse caso, precisamos remover esse ID de exibição de nossa matriz de estado
atual. Podemos usar o método de filtro de
pontos, que está disponível na matriz. Para elementos, então, antes de tudo, o método de filtro espera um
retorno de chamada no qual escrevemos a lógica para filtrar
elementos dentro da matriz. Esse método de filtro de pontos, assim como o mapa escuro, recebe exatamente
os mesmos argumentos. primeiro elemento é valor, o elemento atual
que
percorremos do que o índice desse elemento e
a referência à própria matriz, precisamos apenas do valor
que será mostrado o ID. O que quer que esse
filtro de pontos retorne, ele pode ser verdadeiro ou falso. Se esse retorno de chamada retornar
verdadeiro para esse elemento
, esse elemento
permanecerá dentro dessa matriz Se o retorno de chamada retornar false para o elemento
que percorremos, ele não será incluído
na matriz final. Só vamos
dizer se mostrar ID
não é igual a ação mostrar ID. Com essa lógica,
podemos filtrar todos os elementos que não
atendem a essa condição. Por padrão, se passarmos
algo desconhecido nesse caso, retorne o mesmo estado estrelado pelo
padrão. Vamos aqui e criar uma função que manipulará a lógica quando clicarmos
no botão “Star Me”. Vamos dizer a
const on star, eu clico. Dentro dessa função,
vamos escrever a lógica. Em primeiro lugar, ao me estrelar ,
clique será uma função que receberá show
ID como argumento. Este será o ID de exibição, o ID de exibição correspondente
com o botão Star Me. Ele se referirá a mostrar
o ID no qual basicamente clicamos. Então, aqui dentro,
precisaremos
determinar se o
programa já foi estrelado. Se o show não estiver marcado com estrelas, enviaremos
a ação inicial, caso contrário, enviaremos a ação Desmarcar estrela. Podemos criar uma variável chamada starred e
simplesmente perguntaremos
se a matriz starred shows inclui
show ID em que clicamos. Se esse programa for estrelado, nós vamos enviar estrelado. A ação
será do tipo OnStar, e mostrar ID, precisamos
passar o ID do show aqui, será o que chamarmos de
OnStar me click width. Caso contrário, chamaremos dispatch starred do tipo star Agora, precisamos de alguma forma
usar esse OnStarmeClick. Bem, podemos usar essa
função dentro do ShowCard. Podemos, digamos, passar um argumento, passar um
adereço chamado onStarClick e podemos passar o diretório
onStarmeClick aqui, assim, ou
digamos que onStartMeClick
será onStarmeClick. Dentro do ShowCard, vamos
pegar a sonda OnStarmeClick pela qual passamos agora. Você pode ver que esse onStarmeClick está sendo
chamado com o argumento showID, o que significa que sempre que
chamamos onStarmeClick, precisamos passar showID. Neste botão aqui, OnStarMe, vamos dizer
ao OnClick, ligue para OnStartMeClick e passe o ID do programa. Legal. Agora, já temos o fluxo
completo, vamos tentar cancelar log StarredShows para ver o que exatamente
temos em nosso estado. Até agora, inicialmente é uma matriz vazia,
é isso que definimos. Se eu clicar em StarMe, agora
vejo que esse ShowID foi adicionado a esse
estado. Muito legal. Vamos tentar adicionar outro. Agora podemos ver que
temos três elementos. Se eu clicar no
mesmo programa duas vezes, ele será
removido da taxa estadual. Nossa lógica básica de estrelar e
não estrelar programas funciona muito bem. No entanto, como esse
gancho está dentro do componente
ShowGrid, sempre que navegamos até Iniciar e, em seguida, vamos voltar
para Início ,
nosso estado voltará ao inicial novamente, porque esse estado é local
para aquele componente, quando o componente é desmontado, o estado desaparece. Precisamos pensar em como podemos
realmente manter esses dados. Podemos fazer isso, digamos, salvando StarredShows
no armazenamento do navegador para que mais tarde
possamos recuperá-lo. Isso vai ser
um pouco avançado porque a primeira coisa que me
vem à mente quando precisamos compartilhar o estado
entre várias páginas,
entre vários componentes,
podemos elevar esse estado,
digamos, em algum lugar
para talvez um aplicativo. Se tivermos nosso
estado administrado aqui, esse estado então pode ser
passado como um suporte para,
digamos, componentes infantis
para estrelar e para casa. Mas neste caso, elevamos tudo
até o topo, para
que todos, nosso componente raiz, saibam
algo sobre esse estado. Isso não é ruim, e essa
é uma maneira bastante padrão de gerenciar o estado de compartilhamento entre
componentes no React. Mas vamos apresentar
uma alternativa para isso. Por que vamos
fazer isso dessa maneira e não elevar o componente de
estado para aplicativo? Porque mesmo se compartilharmos o estado
entre as páginas dentro do aplicativo, quando
atualizarmos a página, esse estado desaparecerá. Mas não queremos fazer isso. Em vez disso, queremos manter o estado de
alguma forma,
então, sempre que atualizamos a página, nossos StarredShows ainda estão lá. Mesmo se fecharmos o navegador
ou talvez fecharmos essa guia, nossos StarredShows não
desaparecerão. O que vamos
fazer nesse caso é usar algo
chamado armazenamento de navegadores. Podemos usar especificamente o
armazenamento local ou o armazenamento de sessão. É como
um pequeno banco de dados que fica dentro do navegador e você pode usá-lo para armazenar dados
temporários
dentro do navegador. É um banco
de dados do tipo valor chave, o que significa que, sob chave específica, você pode salvar um valor específico e, ao atualizar a página,
ou, digamos, fechar o navegador e
voltar para aquela página, para aquele URL específico, para aquele site específico, esse armazenamento é persistente. Os valores ainda estão lá, a menos que sejam limpos
pelo
próprio aplicativo ou manualmente
por você, pelo usuário. Vamos armazenar nossa
página inicial no armazenamento local. Vamos pensar em
como podemos fazer isso. Precisamos pensar em
como podemos
gravar o estado que
temos dentro do nosso aplicativo
no armazenamento local. Precisamos sincronizá-lo, porque sempre que
alteramos esse estado, também queremos salvá-lo
no armazenamento local, salvá-lo no banco de dados
e, quando atualizarmos a página, gostaríamos de
recuperar os dados desse armazenamento e
usá-los em nosso aplicativo. Com isso, podemos
escrever, digamos, lógica
adicional em
cima do UseReducer. Para isso, podemos criar
um gancho personalizado em cima do
UseReducer com lógica
extra que persiste no estado dentro do armazenamento
local. Isso é um pouco avançado, mas não há nada, digamos, de confuso nisso. Vamos seguir em frente e
tentar fazer isso. Já temos o gancho
useReducer e queremos escrever
a lógica que faz tudo exatamente da
mesma forma que useReducer, mas também sincroniza o
estado com o armazenamento local. Podemos criar um
gancho personalizado chamado algo como UsePersistedReducer, talvez. Vamos fazer
esse gancho personalizado na parte superior, vamos chamá-lo de
UsePersistedReducer. Queremos manter a API
do gancho embutido, o que significa que queremos usar
exatamente os mesmos argumentos, queremos retornar exatamente
os mesmos elementos, para que tudo seja
praticamente o mesmo. Vamos seguir em frente e
tentar fazer isso. Dentro de usePersistedReducer, vamos usar useReducer. Como esse gancho será,
digamos, reutilizável, não queremos,
digamos, unir digamos, reutilizável, não queremos, fortemente a lógica a
StarredShows aqui,
ele será algo, digamos, abstrato e reutilizável para
lidar com vários casos de uso. Vamos apenas nomear
esse patch como dispatch
e, em vez de StarredShows, vamos
chamá-lo de state. Então, dentro desse UseReducer, precisamos passar o
redutor, pois vamos reter
a API de
usePersistedReducer. Na verdade, vamos
usá-lo como useReducer, usePersistedReducer,
vamos passar,
digamos , um redutor, depois queremos passar
a chave inicial e também queremos passar
a chave de armazenamento local sob a qual os valores
serão salvos aqui. Agora, como precisamos passar
três argumentos, precisamos recebê-los dentro de
usePersistedReducer, então recebemos reducer, receberemos initialState e receberemos localStorageKey. Passamos para UseReducer. No redutor, passamos initialState e passamos
algo chamado initializer. O que é isso? Quando atualizamos a página, queríamos recuperar
dados do armazenamento local e usá-los como nosso estado inicial. Queremos executar essa lógica apenas uma vez quando
o componente é montado, para que possamos usar a função
inicializadora. É o terceiro argumento
que é executado apenas uma vez para inicializar initialState. Esse inicializador recebe
um argumento, initialState. Basicamente, tudo o que
passarmos aqui estará disponível como argumento
dentro do inicializador. Isso é feito neste
caso se o inicializador for criado como uma
função separada em algum lugar externo. Nesse caso,
não vamos fazer isso, vamos apenas embutir
o inicializador diretamente aqui, que o chamará
de inicial. Esse argumento inicial
será basicamente apenas o estado inicial
que passamos aqui. Agora, a lógica
será a seguinte. Primeiro, precisamos
verificar se já
temos dados dentro do armazenamento local. armazenamento local está disponível
no objeto da janela, digamos, uma variável
global que significa que podemos simplesmente iniciar armazenamento
local e, em seguida,
aumentar, ele simplesmente funciona. Aqui, vamos
perguntar a PersistedValue. Se o armazenamento local obtiver Item
sob uma chave específica, precisamos primeiro
entender se esse valor existe dentro da base da
camada ou não. Talvez vamos brincar
um pouco
com o LocalStorage para que você tenha uma ideia. LocalStorage, podemos setItem
sob uma visão específica da chave. Digamos que abaixo da chave baixa
eu possa dizer valor alto. Eu executo essa lógica e
volto para localStorage. Aqui, caso eu o atualize, você pode ver que, na tecla
baixa, agora tenho um valor alto. Posso armazenar o máximo de valores aqui, posso reescrevê-los. Agora, como esse valor é
armazenado no armazenamento do navegador, posso simplesmente chamar getItem
e especificar
a chave sob a qual eu
queria obter meu valor. Eu especifico getItem low, recebi meu valor alto. O problema com o
LocalStorage é que ele só pode funcionar com strings. Em nosso caso, o
estado
com o qual trabalhamos será
uma matriz, o que significa que quando escrevermos em
localStorage, converteremos nossa matriz em uma string e, quando
recuperarmos tudo
do armazenamento local,
precisamos convertê-la de
string em uma matriz novamente. Como podemos fazer isso. Em primeiro lugar, no LocalStorage obtemos Item em
LocalStorageKey. Nosso valor
persistente será nulo ou uma string. Nulo caso
esse valor não exista dentro do armazenamento local,
caso contrário, sempre será uma
string porque localStorage novamente funciona
apenas com strings. Aqui, tudo o que retornarmos
do inicializador
será definido como o estado
inicial final. Tudo o que especificamos aqui vem como argumento para o
inicializador e , em seguida, o inicializador decide qual será o initialState
final. Se não tivéssemos
esse inicializador, podemos simplesmente passar
initialState e ele funcionará. Mas se trabalhamos com o
inicializador e trabalhamos com o inicializador porque
trabalhamos com o localStorage, adicionamos toda essa
lógica em cima dele. Aqui, perguntaremos se o valor
persistente é verdadeiro.
Nesse caso, aplique o método JSON.parse. O que é JSON.parse? Temos uma matriz de,
digamos, elementos 1, 2. Nós o convertemos
em uma string usando o método chamado
JSON.stringify. Agora nossa matriz se transformou em uma string e, quando
recuperamos do localStorage, esse valor persistente
será essa string. Agora precisamos
converter essa string volta em objeto, de volta em matriz. Podemos usar JSON.parse em
vez de JSON.stringify para desserializar nosso valor de localStorage e podemos ver que temos um
inesperado, não branco. Como isso já é um
objeto, ele tem que ser uma string, então digamos que passamos
uma string que é essa matriz e ainda
temos esse problema; não
é um JSON válido. O que está acontecendo? Provavelmente quer que eu
use isso. Vamos ver. Agora, eu passo a
string válida e você pode ver que ela analisou a string de
volta para a matriz. Agora, essa estrutura de dados tem o tipo de matriz,
não apenas uma string. Espero que faça sentido. Aqui analisamos persistedValue,
caso contrário, se
persistedValue for nulo, se o valor não existir,
use o valor inicial, que será
o initialState. Agora, finalmente terminamos com a
lógica de inicializar o estado de
quando a página está sendo atualizada ou quando
voltamos à página. Legal. Agora, precisamos
também sincronizar as atualizações de estado dentro do
gancho UsePersistedReducer em que trabalhamos. Podemos usar o UserEffect
porque você lembra UserEffect
nos permite conectar-se ciclo de vida do
componente e executar a lógica quando
algo muda. Vou importar UserEffect
e, a partir daqui, chamarei UserEffect e passarei a matriz de dependências na
qual vou especificar. Se nosso estado mudar
, assim como se nossa chave; localStorageKey mudar,
nesse caso,
execute esse retorno de chamada. Novamente, se os estados
mudarem ou se localStorageKey mudar, chamamos essa função. Essa função sincronizará o estado com localStorage, então vamos informar
LocalStorage.set. A chave do item será localStorageKey
e o valor será state. No entanto, precisamos transformá-la em uma string antes de podermos
gravar em localStorage. Vamos chamar o estado
JSON.stringify. No final desse gancho,
queremos que ele retorne uma matriz de
exatamente dois elementos para que nosso redutor
usePersisted de gancho redutor
usePersisted se pareça com o gancho
useReducer original. Nós vamos contar [inaudível]. Declare e devolva esses
pacotes e pronto. Este
será nosso último gancho. É basicamente apenas uma lógica
extra em cima do useReducer
integrado
que sincroniza o estado com o localStorage. Assim como eu disse,
é um pouco avançado,
no entanto, se você der uma olhada na verdade não há nada
complicado aqui. Agora, em vez de usar useReducer, aqui dentro do ShowGrid
chamaremos usePersistedReducer
e, como chave
do terceiro argumento,
diremos StarredShows. Agora vamos tentar ver. Se voltarmos ao aplicativo, vamos
abrir o armazenamento local do aplicativo. Vamos limpar isso por enquanto, vamos procurar shows. Você pode ver que, assim que o
componente é montado na página, esse
gancho usePersistedReducer é executado, o estado é inicializado, pois
nosso estado muda e o useEffect é executado pelo
menos uma vez. Ele já começou
a sincronizar o estado com o
localStorage aqui. Em key start shows, colocamos nossa
matriz vazia, nosso initialState. Se eu tentar fazer
algo bombar, mostrar é editar aqui. Está sincronizado. Se eu clicar em “Me marcar como estrela” em outra
coisa, ela
sempre será sincronizada com LocalStorage, o que
significa que funcionou. Incrível. Por enquanto, acho que isso
vai ser bom porque, bem, acho que é o suficiente por enquanto. No próximo vídeo,
falaremos sobre como
podemos prosseguir com essa lógica, para que
possamos, de alguma forma mostrar se esse programa é estrelado ou não. De alguma forma, diga visualmente ao usuário que esse programa
já começou e , em seguida, provavelmente buscaremos todos esses dados dentro
da página marcada como favorita. Por enquanto, vamos comprometer isso; o que já temos, para não perdermos as mudanças. Aqui vou dizer adicionei lógica inicial para estrelar
shows com UseReducer. Foi criado UsePersistedReducer para sincronizar o estado com o LocalStorage. No próximo vídeo,
vamos continuar com isso. Nos vemos lá.
80. 24 Starred mostra p2: Olá. No último vídeo, começamos a trabalhar na funcionalidade com estrelas. Criamos um redutor persistente de
uso de gancho personalizado, que sincronizou nosso estado
StarredShows com o armazenamento local para que,
sempre que o
atualizarmos, possamos reinicializar o
estado a partir do armazenamento local. Eu não mostrei isso
no vídeo anterior, mas se tentarmos cancelar log StarredShows se
eu atualizar a página, vou voltar para casa. Se eu atualizar a página e
quando o componente for montado, nosso estado inicial será
recuperado do armazenamento local, o que quer que tenhamos aqui. Se limparmos tudo,
se removermos tudo
do armazenamento local, atualizarmos a página
e procurarmos shows, nosso estado padrão
é uma matriz vazia. Legal. Agora precisamos pensar em como podemos
realmente, digamos, reutilizar esse gancho em
várias páginas, inicial e no início. Mas primeiro, vamos dizer
ao usuário se esse
programa foi iniciado ou não. Vamos
voltar para o ShowGrid aqui e para o ShowCard, podemos passar outro
adereço chamado isStarred. Isso é Starred será
bem simples, vamos apenas perguntar
se StarredShows. Indique que incluímos
esse ID de demonstração de dados. Portanto, isStarred será um
booleano que indicará se esse show já está presente dentro da matriz
starredShows. Então, dentro do ShowCard,
vamos
pegar IsStarred como adereço. Por enquanto, vamos
perguntar se esse programa
já foi estrelado,
por favor, exiba-me no
Star me, por favor, ou apenas Unstar me ou Star me. Vamos tentar ver. Sempre que eu clico aqui, ele
se transforma em Unstar me star. Se clicarmos em “Olá amanhã”
, ainda será Unstarme. Agora, se eu atualizar a página, procuro olá novamente.
Se eu rolar, você verá que os
valores estão sendo persistidos. Mesmo que eu feche meu navegador, feche esta guia e volte para aquela página novamente para ver
os programas específicos, eles ainda mostrarão
Unstar me porque
novamente sincronizamos o
estado com o armazenamento local. Legal. Agora vamos
prosseguir e extrair lógica
que escrevemos aqui do ShowGrid em
um arquivo separado, para que posteriormente possamos reutilizar a mesma lógica dentro
da página inicial. Vamos embora. Provavelmente
dentro do código-fonte ou talvez vamos criar uma nova pasta chamada library, abreviadamente lib. Aqui vamos criar um
arquivo chamado UseStarredShows. Dentro desse arquivo, vou
colocar toda essa lógica relacionada aos ganchos que
escrevemos anteriormente. Isso será
usePersistedReducer, isso será
StarredShowsReducer, essa será essa chamada
usePersistedReducer e a importação de
useReducer e useEffect. Então, se quiséssemos, digamos, usar exatamente o mesmo gancho
dentro de outro componente, digamos, dentro das páginas marcadas com estrela, simplesmente
copiaríamos assim. Precisamos chamar
UsePersistedReducer novamente, precisamos passar
StarredShowsReducer novamente, especificar a mesma chave, mas podemos dar um passo adiante, podemos criar outro gancho
personalizado em cima disso
e, digamos, ocultar
a lógica lá. Dentro de useStarredShows,
criaremos um novo gancho chamado useStarredShows e
esse gancho
chamaremos usePersistedReducer
e, em vez de apenas valores de destruição aqui, retornaremos qualquer valor que
usePersistedReducer aqui retorne. Aqui provavelmente não vamos passar nada
porque queremos, digamos, ocultar a lógica
logo por trás desse gancho,
então, dentro de nosso componente, podemos simplesmente chamar useStarredShows e
realmente salvá-lo, depois exportá-lo de
useStarredShows e importá-lo da biblioteca UseStarredShows e o gancho será useStarredShows. Chamamos isso e simplesmente obtemos StarredShows e simplesmente
recebemos DispatchStarred. Você pode ver agora que parece muito,
muito mais limpo do que antes. Agora também é reutilizável, o que significa que dentro
do componente favorito podemos fazer exatamente o mesmo, basta chamar useStarredShows
e descartar os mesmos dados. Vamos fazer isso. Dentro de
starred, vou importar useStarredShows e aqui provavelmente não
precisaremos de dispatchStarred, não
precisaremos da função de
despacho, então não vamos
desestruturá-la,
vamos pegar apenas o primeiro
elemento, o StarredShows. Agora, aqui podemos escrever a
lógica para creditar os dados, vamos fazer isso
no próximo vídeo. Por enquanto,
provavelmente vamos acessar a página com estrela, estrelada, StarredShows.length,
que exibirá o número de programas que
estrelamos até agora. Vamos tentar ver
se funcionou. Se formos para a página inicial, podemos ver que temos
dois programas com estrela, isso é o que vemos
em nosso estado que persiste no armazenamento
local. Se tentarmos limpar o armazenamento
local e atualizarmos a página, a
estrela será zero porque
removemos tudo, o estado foi reinicializado,
algo assim. Por enquanto, vamos comprometer
tudo o que fizemos aqui. Extraímos a lógica do gancho em um arquivo separado e
criamos outro gancho personalizado em cima do nosso
usePersistedReducer para StarredShows especificamente e o
chamamos de useStarredShows. Em seguida, usamos esse gancho
personalizado interno, com
estrela, para exibir, por enquanto, o número total
de programas que
adicionamos e usamos esse
gancho dentro de ShowGrid, useStarredShows, bem como
o usuário visualmente notificado,
exibindo textos com estrela
me ou não com estrela com base no ID do show, esteja ele dentro
da matriz de estados ou não. Na verdade, pareceu muito. No entanto, não
foi muito, não é? Então eu adiciono tudo
ao estágio e
digo que criei useStarredShows, gancho
personalizado colocou
toda a lógica do gancho, colocou tudo ou, digamos colocou a
lógica de gancho useStarredShows em um arquivo separado. Diga ao usuário se o
programa está marcado ou não. Diga ao usuário se o programa está
marcado ou não. É isso. Vamos para o GitHub e nos
vemos na próxima. No próximo vídeo, vamos
buscar todos esses programas quais temos acesso
dentro do componente inicial. Agora, vamos
buscá-los na
API de criação de TV e exibi-los
finalmente. Te vejo.
81. 25 Starred mostra p3: Olá. Neste vídeo, finalmente
terminaremos a página
do programa estrelado. No vídeo anterior, criamos um
gancho personalizado chamado user starred shows, que
é um gancho sobre o redutor persistente de uso, que
também é um gancho personalizado sobre
o redutor de uso , mas com lógica extra que sincroniza o estado
com o armazenamento local. Neste vídeo, pegamos os programas
com estrelas que temos dentro do
componente marcado com estrela e os buscamos na API TVMaze. Em primeiro lugar, temos
uma série de IDs de shows. Se examinarmos a documentação do TVMaze,
não temos nenhum endpoint. Experimente e procure onde possamos assistir vários shows ao mesmo tempo. Então, em nosso caso, enviaremos várias
solicitações para a API. Vamos para o componente estrelado. Aqui, por padrão, usaríamos o efeito de uso para capturar dados
da API somente quando o
componente é montado, mas agora, como usamos a biblioteca de busca de
dados, use query, podemos
usá-la para capturar dados. Deixe-me copiar isso
do componente inicial, eu vou aqui, dentro starred eu importo use query
da biblioteca de consultas React. Agora, nossa chave de consulta será marcada com estrela e passaremos a matriz de programas
com estrela que
temos como chave de consulta. Então, dentro da função de consulta, precisamos obter todos os nossos programas. Como podemos fazer isso? A primeira e ingênua
abordagem é que
podemos realmente usar o for-loop
simples, depois percorremos cada
programa que temos dentro da matriz de shows com estrela, pegamos cada ID de show
e, em seguida, enviamos a solicitação. No entanto, você pode ver que todas essas solicitações que podemos enviar, digamos que temos dois IDs de exibição dentro do estado e
enviaremos duas solicitações. Quando pudermos
passar por cima de cada elemento ,
ele enviará a primeira solicitação, somente quando terminar , enviará
a segunda solicitação. Isso não é eficiente porque as solicitações que
enviaremos para shows não
dependem umas das outras. Queremos que isso aconteça
o mais rápido possível. É por isso que precisamos enviar várias solicitações ao
mesmo tempo. Para alcançar esse comportamento, vamos usar promise.all. Deixe-me mostrar o que quero dizer. Dentro da função de consulta, vamos escrever
a seguinte lógica. Antes de fazer isso, vamos remover a opção ativada e
continuaremos atualizando o Window Focus. Aqui, a lógica
será a seguinte. Que seja apenas uma função
e uma função de sincronização. Aqui vamos primeiro
mapear nosso, onde está? API TVMaze. Esta função Get Show by ID. Vamos mapear
essa função que retorna a promessa em uma matriz. Já parece complicado, mas deixe-me mostrar o que quero dizer. O que faremos aqui. Vamos dizer, digamos, promessas de solicitação de
API. Faremos starredshows.map. Vamos mapear o
show ID para a API para que seja exibido por ID dessa forma. Vamos
especificar o ID do show aqui. Com essa abordagem,
acabaremos
com uma série de promessas. Porque mapeamos cada ID do programa para ser exibido por ID, o que
retorna uma promessa. Eventualmente, acabamos
com uma série de promessas. Para lidar com uma série de
promessas e
garantir que essas solicitações
sejam tratadas, digamos que em paralelo ao
mesmo tempo, podemos usar o método
promise.all. Vamos contar
await promise.all. Na verdade, podemos, você sabe o que, mover toda essa lógica daqui para uma função reutilizável
dentro do TVMaze.gs. vamos
contar os shows por Desta vez, vamos
contar os shows por
IDs e
receberemos os IDs dos programas aqui. Em vez de apenas
fazer a API Get Here, vamos transformar
essa função em uma função de sincronização e
colocaremos a lógica que escrevemos
aqui dentro de get show by IDs. Vamos mapear cada ID de
show para uma promessa, depois dentro de promise.all, e já vemos
que essa promessa não está definida vindo do
ES lint, na verdade. Bem, isso é interessante. Suponho que seja porque
dentro do ES lint RC precisamos
instruir o ES lint a
entender que
usamos a sintaxe mais recente
do
JavaScript , a moderna, então
vamos dizer que o
ES6 será verdadeiro. ES6 significa ECMAScript
versão 6 e superior. Agora, acho que não temos
nenhum erro, isso é verdade. Para promise.all,
vamos aprovar promessas de solicitação de
API ou vamos chamá-las de promessas
para simplificar as coisas. O que o promise.all faz é resolver uma série de
promessas em paralelo, e elas são resolvidas uma só vez e tratadas em paralelo. baixo do capô,
parece promessa 1, promessa 2, promessa 3 de
prometer. Tudo de novo, uma série de promessas. Promise.all resolve
todos eles de uma vez. Em seguida, prometa.all resultados.all para
uma matriz de valores resolvidos. Se tivermos uma série de
promessas, digamos que promessa 1, promessa 2, promise.all
resolva todas elas de uma vez. Promise.all retorna uma
matriz de valores resolvidos. Se a promessa 1 for resolvida
para, digamos, valor 1, receberíamos uma matriz com, digamos, o valor resolvido 1. Eles prometeram
resolver outra coisa, nós receberíamos resolução, valor
resolvido 2. Se a promessa não resolver em nada,
talvez para nula, para um valor indefinido
seria indefinido ou nulo. Mas o pedido foi mantido. Qualquer ordem
presente aqui na mesma ordem,
as promessas são resolvidas ao usar promise.all. Um ponto aqui, promise.all
também retorna uma promessa, então precisamos evitá-la. Isso é importante. Agora, podemos chamá-lo de resultado. Aqui fazemos promessas
e retornamos o resultado. Como no nosso caso, cada promessa
resolverá mostrar dados, eventualmente
receberemos uma série de promessas
resolvidas,
o que significa que receberemos uma série de programas. Vamos
registrá-lo no console apenas para ver com o que
exatamente trabalhamos. Dentro da inicialização J6, vamos
chamar isso de get show by IDs. Talvez, você sabe o que? Dentro do get show by
ID, incorporamos dados. Mas dentro da página inicial, não
precisamos dela. Em vez de chamar get show by ID aqui,
vamos apenas
chamar o ApiGet sem
a parte incorporada. Algo parecido com isso. Agora, dentro da página com estrela, vamos especificar:
ligue para obter shows por IDs. função de consulta interna e a
passagem interna com estrela mostram
o que temos. Agora teremos um erro estrelado
e marcado com estrela. Não
nos confunda com nomeação. Provavelmente vamos chamá-lo de
programa estrelado, IDs de programas estrelados. Aqui, serão
apenas StarredShows e StarredShows à prova de erros. Agora vamos aplicar renderização condicional
simples aqui, assim como
fizemos anteriormente na página de
exibição com if
e if you turn. Vamos perguntar se
StarredShows é realmente verdadeiro. Nesse caso, retorne ShowGrid porque usamos show grid para exibir todos
os programas que temos, então o que usará o ShowGrid, mas primeiro
precisamos importá-lo. Importe ShowGrid. Ele já é preenchido automaticamente para
mim a partir dos componentes,
mostra ShowGrid. Se começarmos os shows, retornaremos
o ShowGrid e o ShowGrid espera que
passemos os shows aqui. Vamos tentar fazer isso, os programas são iguais aos StarredShows
escolhidos e, por padrão, fim de semana e exibem olá. Vamos primeiro tentar
ver o que temos. Nosso aplicativo não está funcionando porque não
iniciamos o servidor div ok, agora temos nossos programas vamos tentar adicionar
algo estrelado para mim. Agora vamos para a
página inicial e pronto, temos uma tela em branco e,
se olharmos dentro do console, vemos que não é possível ler as propriedades
do ID de leitura indefinido. O que acontece se olharmos para
dentro do ShowGrid? Onde está? Recebemos shows,
que deveriam ser uma matriz e,
dentro dessa matriz, cada elemento tem a chave.show
property.show mas examinaremos
nosso resultado e é isso que o console
faz login, é mostrado por IDs aqui. Você pode ver que temos uma matriz de elementos e cada
elemento da matriz não tem o. mostrar propriedade. Precisamos
consertá-lo de alguma forma. Precisamos ajustar essa forma de dados
à forma de dados que se espera que seja usada
dentro do componente. A questão é: onde
exatamente precisamos fazer isso? Essa é uma boa pergunta. Bem, se quisermos tornar
essa função, digamos, reutilizável
possível em nosso caso, em nosso aplicativo, isso
não é verdade, mas ainda assim, uma boa prática fazer as alterações necessárias
somente onde elas são necessárias e se quisermos
torná-las reutilizáveis, não queremos,
digamos, modificar de
alguma forma a forma
dos dados aqui. Vamos fazer essa lógica
dentro da função de consulta. Aqui em GetShowsByIds, não
preciso
mais registrar o resultado no
console ou, na verdade,
vamos mantê-lo por enquanto
e, mais tarde, nos
livraremos disso. Mas dentro da função de consulta aqui, faremos o seguinte. Quando getShowsByIds
a promessa for resolvida, usaremos a sintaxe do
ponto com essa agora porque ela se encaixará
melhor Vamos ver essa sintaxe
que temos aqui. Em vez de usar async await, podemos remover async daqui Assim, quando essa
solicitação getShowsByIds terminar quando a promessa for resolvida com esse resultado,
o
que
faremos, mapearemos cada
elemento da matriz e aninharemos quaisquer dados que tenhamos
aqui
sob a chave show , sob
a propriedade show ,
para que correspondamos à estrutura
esperada ser usado pelo ShowGrid porque
precisamos de uma matriz de elementos em que cada elemento tenha
a propriedade show dentro. O que faremos,
contaremos o resultado. mapa, obteremos os dados de exibição
aqui e, a partir desse retorno de chamada, que retornará
showData para torná-lo mais simples.
Em vez de usar a
sintaxe mais longa com return, diremos para retornar showData
com colchetes. Agora, se tentarmos cancelar o
log StarredShows aqui, ainda
teremos esse problema. Deixe-me ver. Temos ShowData. Isso ocorre porque
mapeamos que você pode ver cada elemento da matriz
tem a chave ShowData, mas esperamos que ela
seja apenas mostrada. Aqui, em vez de mostrar dados, podemos usar mostrar e mostrar. Agora vamos tentar ver se
atualizamos e explodimos, tudo funciona magicamente agora. Se analisarmos o resultado, temos esses dados
que recebemos do getShowsByIds e
depois mapeamos os dados. Na verdade, aninhamos
esses dados sob a chave show dentro de cada elemento da matriz,
algo assim. Agora podemos finalmente remover
esse resultado daqui e simplesmente retornar
promise.allpromise. Aqui não precisamos mudar nada, essa
é a nossa lógica aqui. Agora precisamos lidar com
o caso quando
não temos nenhum programa estrelado. Digamos que eu
limpe o armazenamento local, atualize a página, nada seja exibido,
mas, idealmente, queremos dizer ao usuário que, ei, não temos
nenhum StarredShows. Já escrevemos
essa condição if, que funcionará tanto se
tivermos shows quanto se
não tivermos shows, porque uma matriz vazia também é um valor verdadeiro, então
podemos apenas dizer se starredShows.length é
maior que zero se tivermos pelo
menos um show e usamos o
encadeamento opcional aqui porque nosso estado inicial
será indefinido pela consulta de uso. Bem, a solicitação
não acontece imediatamente, então esse StarredShows pode ser indefinido e não
gerar nenhum erro, por exemplo, deixe-me remover isso, eu o atualizo, vou para console e vejo que não consigo ler
propriedades de undefined, porque inicialmente, esse
estado é indefinido novamente, a solicitação não
acontece imediatamente. Podemos usar o
encadeamento opcional aqui ou podemos perguntar se starredShows é verdadeiro e, usando
o operador add, esse starredShows, nesse momento será
definido, podemos
digitar com segurança starredShows.length,
mas para simplificar isso, usamos o encadeamento opcional. Se o comprimento de StarredShows
for maior que zero, exibimos showGrid e
adicionamos outra condição na parte superior. Se o comprimento de StarredShows for
igual a zero. Nesse caso, exibimos div algo
como se nenhum programa tivesse sido marcado com estrela. Em seguida,
adicionaremos outra condição caso tenhamos algum erro. Se tivermos iniciado shows adder, informaremos que
ocorreu um erro e
diremos StarredShowsError.message. Por padrão, se nenhuma
dessas condições for
mantida nesse caso, estamos dizendo que os programas estão parados
ou que apenas os programas estão carregando. Este é o nosso mercado final, por enquanto, vamos tentar ver. Se eu atualizar rapidamente, você verá um
piscar de olhos porque, inicialmente, esse estado é indefinido, o que significa que por um curto período de tempo, essas condições não corresponderão e veremos os programas sendo
carregados. Se a solicitação demorar mais do que o esperado, veremos que os programas estão carregando e veremos que nenhum programa foi marcado
como estrela. Se formos para casa, procuramos programas em que estrelamos
alguns programas aqui, este, depois procuramos outra coisa, como, ei cara, ei, voltamos a estrelar você pode ver agora
que temos esses programas aqui. Mesmo se atualizarmos a página, os programas ainda estão
lá. Muito legal. Agora temos o ciclo
completo e completo dessa funcionalidade
estrelada. Parabéns. Por enquanto, é isso mesmo, vamos adicionar todas
as mudanças ao palco. Primeiro, instruímos ao
ES link que estamos usando JavaScript moderno para que não
haja nenhum
erro ao escrevermos construtor de
promessa como este. Adicionamos outra
função aqui
para buscar todos os programas, conhecendo os IDs dos programas. Usamos o
método promise.all para lidar com todas as solicitações ao mesmo tempo, porque essas solicitações não
dependem umas das outras, elas precisam ser
tratadas em paralelo e resolvidas de uma só vez É exatamente
isso que
promise.all faz. Em seguida, dentro do componente estrelado, usamos o
gancho de consulta use para buscar dados.
Já sabemos o que ele faz e por que os usamos. Em seguida, aplicamos a
renderização condicional para exibir dados. É isso. Ótimo. Vamos confirmar tudo e
digamos que buscado, estrelado mostra dados e exibição. ShowGrid para eles. Legal. Eu envio tudo para o
GitHub e, com essa boa nota, nos vemos na próxima.
82. 26 atribuição: Olá novamente, tenho outra pequena tarefa
para você lembrar que para implementar, o
Start mostra que os dados
persistem dentro do navegador. Quando atualizamos a página, nosso estado ainda está lá. Usamos armazenamento local, armazenamento dentro do navegador
que pode persistir dados. Não seria bom
se também pudéssemos persistir o que digitamos
dentro da caixa de pesquisa, dentro do componente inicial. Então, se eu atualizar a página, tudo o que está dentro da
caixa de texto ainda estará lá. A ideia aqui é
praticamente a mesma. Então, se para começar, criamos nosso próprio gancho que sincroniza o estado chamado redutor persistido de
fusível. podemos criar um
arco muito semelhante, chamado Desta vez, podemos criar um
arco muito semelhante, chamado de estado persistente de
Hughes no
topo do estado dos EUA, e então usar esse estado para implementar essa data
na caixa de pesquisa. Esta é a tarefa para você. Vá em frente e tente isso. E desta vez, em vez
do armazenamento local, talvez
você possa usar o armazenamento de
sessão. A diferença entre armazenamento
local e armazenamento de
sessão é que o armazenamento
local persiste os dados, mesmo que você feche a guia
e feche o navegador, armazenamento da
sessão só persiste os dados até você
fechar a torneira, fechar a guia e
voltar para a página. Novamente, o armazenamento da sessão
estará vazio, ou seja, pode ser mais adequado para a caixa de texto,
porque não é algo que gostaríamos de
salvar quando
fechamos a guia ou
fechamos o navegador. Portanto, a API não é a mesma, o
que significa que, em vez
do armazenamento local, você gravará o armazenamento da
sessão e o resto permanecerá o mesmo, obterá o item e o item do site. Então, vá em frente e tente criar
esse estado de uso persistente e, em seguida,
implemente para manter o estado
da caixa de pesquisa. Boa sorte com esse. Nos vemos na próxima.
83. 27 Implementando o uso de gancho personalizado usePersistedState: Olá de novo, como foi
sua tarefa? Você conseguiu
alcançar o que queríamos? Você conseguiu manter os dados dentro do
armazenamento da sessão? Vamos ver. Se voltarmos ao formulário de pesquisa, aqui temos aquela chamada de estado de uso para ter o estado da string de pesquisa. Agora, se quisermos persistir no armazenamento local
ou no armazenamento da sessão, precisamos escrever uma lógica extra. Podemos extrair toda essa lógica
em algum lugar dentro de outro arquivo
e, aqui,
dentro do formulário de pesquisa simplesmente
chamaríamos use persisted ou talvez
use search string, que nos retorna novamente uma
matriz de dois elementos, string e
string de pesquisa, para que
não alteremos a API
do use state hook. Será praticamente o mesmo. Vamos seguir em frente e
implementar tudo isso. Na pasta da biblioteca que tenho aqui, onde está localizado o uso start
chose, vou criar um
novo arquivo chamado use search, STR, search string. Aqui vou exportar
const, usar a string de pesquisa. Nosso gancho não
aceitará nenhuma discussão, vamos lidar com
tudo interno, então o estado inicial será
definido pelo gancho interno. Não queremos nos
preocupar com isso sempre que
usamos esse gancho. Então eu o guardo por enquanto. Então, a partir daqui,
vou importar da biblioteca e usar a string de pesquisa. A aparência final será essa. Praticamente o mesmo que tínhamos anteriormente, mas com toda a
lógica, agora vamos entrar. Em caso de uso, o início
mostra semanalmente auxiliado aquele gancho personalizado chamado redutor persistido de
uso. Podemos fazer exatamente o mesmo com estado de
uso, mas em vez
do redutor de uso, vamos usar o estado de uso. Vou
comentar isso para referência. Use novamente um fatorável, necessário para sincronizar esse
estado com o armazenamento da sessão. Vou precisar do seu estado
e aqui vou criar um estado persistente de uso. Usar
estado persistente receberá o estado
inicial como argumento. Aqui, vou chamar o estado de
uso e passar o estado
inicial aqui. Mas, diferentemente do use reducer, use state pode receber o estado inicial
como argumento ou a função inicializadora, que será executada apenas uma vez
para inicializar o estado. No caso do redutor de uso, era o terceiro argumento no caso de alguns estados, ainda
é
o mesmo argumento, mas basta passar
o retorno de chamada para lá. Aqui dentro, a lógica será praticamente a mesma
que fizemos com o armazenamento local. Em primeiro lugar, nos referimos
ao armazenamento da sessão, obtenha a chave de armazenamento local do item. Precisamos obter essa chave de armazenamento
local aqui. No nosso caso, será a chave de armazenamento
da sessão. Vamos tirá-lo do
uso de argumentos estatais persistentes. Ao lado do estado inicial, podemos passar a chave de armazenamento da sessão. Então, novamente, temos um
valor persistente; se o valor existir, nós o desoralizamos
da string,
caso contrário, usamos o
valor inicial que passamos, que será o argumento
inicial do estado. Incrível. Aqui recebemos a função de atualização de estado
e estado. Então, exatamente a mesma
lógica com efeito de uso. Vamos
partir daqui e dizemos
que, sempre que o estado mudar ou
sempre que a chave de
armazenamento da sessão mudar, chame o item do conjunto
de pontos de armazenamento da
sessão, a chave de armazenamento da sessão
JSON, stringify, state. Então, a partir do estágio persistido de uso, novamente para manter exatamente a mesma
API do use state hook, retornaremos uma matriz de dois elementos em que o primeiro
elemento é o estado e o segundo é a função de atualização de
estado. Agora, podemos remover esses comentários aqui e
dentro de usar a string de pesquisa. Podemos chamar use
persistent state, dentro de passarmos o estado inicial, será uma string vazia
e a chave de armazenamento da sessão será uma string de pesquisa. Incrível. Agora, qualquer que seja esse
uso, o estado persistente retorna
e ele retorna uma matriz de dois elementos em que o primeiro
elemento é o estado, segundo é a função de atualização de estado, exatamente a mesma
API do use state hook. Em vez de escrever isso e, em seguida escrever state return
e set state, podemos simplesmente retornar
o que a
função de uso persistente retorna. Retorne, use o estado persistente. Agora, é isso. Agora podemos usar esse
gancho que criamos dentro do formulário de pesquisa e
ele funcionará magicamente. Vamos tentar ver. Se eu atualizar a página,
você poderá ver que, dentro do armazenamento da
sessão, tenho uma string de pesquisa de chave, tudo o que especificamos aqui como a
chave de armazenamento da sessão, para que o estado seja inicializado com o valor que passamos aqui por
padrão como uma string vazia. Agora, o que quer que digitemos
dentro da caixa de pesquisa, ele será desviado
como valor dentro da chave de armazenamento da sessão na string de
pesquisa, porque
usamos o efeito para
sincronizar o estado. Se eu atualizar, você poderá
ver que tudo o que temos dentro do armazenamento da sessão agora
está sendo exibido como estado inicial dentro da
caixa de texto, se eu atualizar. Isso é muito conveniente,
por exemplo, se eu acidentalmente
atualizar a página, espero que faça sentido. Não é muito complexo como você pode ver, e eu realmente espero que você tenha implementado
praticamente a mesma lógica. Por enquanto, vamos
confirmar tudo e dizer que esse foi o uso do gancho de caracteres
de pesquisa, a mensagem de
confirmação
será persistida na terceira forma, valor da caixa de
texto no armazenamento
da sessão. Toda a lógica em uso,
busca, cadeia de caracteres, gancho. Eu envio tudo para o GitHub. Nos vemos na próxima.
84. 28 Introdução aos componentes estilo: Olá. No último vídeo, eu diria que terminamos toda
a nossa lógica dentro do aplicativo. Agora é a hora de
falarmos sobre estilos. Como vamos
estilizar o aplicativo. Neste vídeo,
falaremos sobre a abordagem
que vamos adotar e aqui está um
spoiler para você, a abordagem será sobre componentes
estilizados. Neste vídeo, veremos
como os componentes estilizados funcionam. Por que exatamente
os escolhemos e, no final, compararemos os componentes
estilizados a forma tradicional de vender aplicativos apenas com estilos CSS
comuns. Vamos embora. O que são componentes
estilizados? Essa é apenas uma biblioteca
para estilizar ou reagir aplicativos com uma
abordagem chamada CSS-IN-JS. CSS em JavaScript é uma
abordagem que nos permite
escrever marcação CSS com
a ajuda do JavaScript. momento, estou
no site oficial dos componentes de estilo, documentação
oficial. O que faremos
agora neste vídeo, analisaremos o
básico para entender exatamente
como
poderemos usar essa biblioteca. Se eu rolar um pouco para baixo, passarei pelo processo
de instalação simples. Voltarei à
minha inscrição. Vou abrir uma nova instância de
terminal aqui e executar componentes com
estilo npm install. Depois de instalado, vou simplesmente fechar a instância. Eu fiz isso apenas
para não interromper o aplicativo em si. Agora, temos componentes estilizados que aparecem no pacote Jason. Dependências dentro da
documentação, podemos ver seu primeiro componente estilizado. Precisamos importar estilos
de componentes estilizados
e, em seguida, usar
algo assim. Vamos para o componente inicial
e podemos aplicar com componentes
estilizados
aqui na página inicial. Na parte superior, vou importar
estilos de componentes estilizados. Em seguida, farei styled.button e, no final deixarei
marcações vazias para ele. Agora, o que é isso? Ao chamar style, elemento
style.HTML
que você tem
nessa lista muito longa,
você pode criar, digamos, o elemento
subjacente que você deseja estilizar, por exemplo, botão estilizado. A partir desse elemento,
os componentes estilizados
criarão um componente e esse
componente terá estilos. Se voltarmos à documentação
e rolarmos um pouco para baixo, aqui encontraremos
este exemplo básico, style.button back-ticks e, em seguida marcação
CSS. Como você pode ver, marcação
CSS é escrita
dentro de back-ticks. A propósito, o
destaque da sintaxe que você pode ver aqui vem da extensão
VS Code, que é chamada de componentes no
estilo VS Code. Se você quiser que sua sintaxe
seja destacada e preenchida automaticamente, instale
essa extensão. Somos capazes de escrever CSS
aqui dentro de back-ticks. componente estilizado
usará o elemento de botão e basicamente
apenas
pegará elemento de botão HTML nativo e
aplicará esse
elemento de botão HTML nativo e
aplicará esses estilos que
escrevemos aqui em cima
dele e, no final, produzirá o componente de
botão que podemos usar
dentro de nossa marcação. Vamos tentar. Dentro da marcação, vou usar esse componente de estilo de botão que foi criado
e dizer olá aqui. Eu o guardo. Eu volto para o meu
aplicativo e o que temos aqui? Se olharmos para dentro da marcação, temos esse
lindo botão estilizado aqui com esse nome de classe
exclusivo. Todos os estilos foram mesclados e vamos detalhar o que temos aqui. Em primeiro lugar, esse componente de
botão renderiza elemento de botão
HTML
exatamente o que
especificamos aqui como o
elemento base para aplicar estilos, que significa que esse componente de
botão aqui basicamente renderiza o elemento de botão HTML
nativo, o
que significa que todos os adereços que
esse styled.something tem, podemos passar diretamente
para esse componente. Se o elemento do botão tiver um
atributo chamado tipo, podemos passar o tipo aqui. Se eu salvá-lo, você
verá que ele será refletido. Eu tenho o botão de digitação agora, exatamente o mesmo que você
fará com qualquer
atributo HTML normal,
digamos, nativo no elemento do
botão, se você quiser que ele passe
algo como um clique, ou se você quisesse passar
algo como atributos de dados, algum atributo personalizado ,
você faria isso e funcionaria. Legal. Agora, temos esse nome de classe
exclusivo aqui. O que é isso e por que
parece tão estranho? O fato é que esses blocos que você escreve aqui
especificamente para esse elemento têm como escopo
apenas esse elemento, o que significa que esses
estilos são exclusivos. Esse nome de classe é
exclusivo e foi gerado
automaticamente
por componentes estilizados. Componentes estilizados
garantem a exclusividade das classes que você
escreve para esse elemento. Se eu criar outro
componente estilizado, que parece exatamente o mesmo, mas tem um
nome diferente, não importa. Pode ser, digamos, qualquer coisa, e então eu uso esse componente de
qualquer coisa ao lado desse componente de botão, eles têm exatamente
os mesmos estilos. Eles parecem visualmente iguais. Mas se você comparar os
nomes das classes, eles são diferentes. O que os componentes estilizados fizeram
, gerou um
nome de classe exclusivo com base nesses estilos. Novamente, os componentes estilizados
criam estilos
exclusivos com escopo local , especificamente
para o elemento. Faz sentido? Eu acho que sim. Também temos aqui um
estilo dinâmico disponível para nós. Se voltarmos
à documentação, se rolarmos para baixo, aqui, podemos encontrar outro exemplo, exemplo estendido com interpolação de
strings aqui. Vamos copiar essa interpolação de
string. Vamos voltar ao nosso botão, e aqui,
vou usar essa interpolação de
strings. Também preciso importar CSS chamado export de componentes
estilizados. Agora, se voltarmos ao aplicativo, nada será alterado. Mas o que exatamente essa interpolação de
strings faz? Em primeiro lugar, podemos
usar a interpolação de strings aqui porque escrevemos CSS
aqui dentro de crases. Dentro dos backticks, podemos
interpolar o JavaScript usando os colchetes
$ e curly. Aqui passamos uma função
que retorna esse CSS, digamos, outra marcação
CSS aqui. O que está acontecendo? Aqui usamos algo
chamado argumento de adereços. Esse argumento
será um objeto que tem a propriedade da chave primária,
mas nada muda. Esses adereços aqui se referem
aos adereços que realmente
passamos
para o componente. Se eu passar o primário aqui, será um suporte personalizado para esse componente de botão
, o que significa que ele estará disponível aqui
sob esse objeto props. Se eu voltar ao aplicativo, você verá como
esses estilos mudaram. Se eu examinar a marcação, esses são os estilos que foram aplicados quando passamos
o suporte principal. Eles sobrescrevem nossos estilos básicos. Para deixar isso mais claro, vamos criar outro
botão chamado também hello, mas sem passar
o atributo primário,
sem passar o adereço primário. Você pode ver agora que
eles são diferentes. Eles têm a mesma classe
base aqui, gerada de
forma exclusiva, mas a
segunda classe é única. Dessa forma, podemos aplicar estilos
dinâmicos usando componentes
estilizados. Você pode basicamente
passar qualquer adereço aqui. Pode ser qualquer coisa que não seja primária. Digamos que seja como tamanho
da fonte e você possa especificar quantos
pixels deseja, por exemplo, 20. Então, dentro da
interpolação de strings, usando essa função, você pode retornar CSS com
base nos adereços que você
passa para o componente. Por exemplo,
digamos que quiséssemos especificar o tamanho da fonte
dinamicamente para cada botão, chamaríamos novamente outra
interpolação de string dentro desse componente de estilo e aqui simplesmente passaríamos. No tamanho, se
passarmos o tamanho da fonte, inclua CSS, que tem a propriedade de tamanho da fonte
com propriedades de
interpolação contraditória . Os
pixels de tamanho da fonte que passamos. Basicamente, interpolamos
JavaScript em marcação CSS. Agora, se voltarmos aqui e
inspecionarmos o elemento, temos o tamanho da fonte
aqui, 20 pixels. Acabei de notar que também temos esse atributo de tamanho de fonte anexado
ao elemento do botão. Isso pode não ser necessário e talvez nem
seja desejado. Acho que quando passamos
algo aleatório para iniciar componentes e queremos disponibilizá-lo apenas como um argumento como parte
desse objeto props aqui, queremos prefixá-lo com
$ para permitir que os componentes estilizados
entendam que,
por favor, não
digamos, interpolam. Não transmita esse tamanho de fonte como o atributo real
do elemento subjacente. Torne-o disponível somente dentro dessa interpolação de strings
quando aplicarmos estilos. Agora, nos referiríamos ao tamanho da fonte
dos
adereços aqui, ao tamanho da fonte dos adereços com o
prefixo $, se eu não estiver errado. Sim, agora você
pode ver que ainda temos os estilos e ainda funciona. Dessa forma, podemos
aplicar estilos dinâmicos. Se voltarmos à
documentação aqui, podemos encontrar outro exemplo
de componentes estilizados. Criamos outro
componente estilizado chamado container. Vamos seguir em frente e
fazer isso no topo. Vou criar
esse estilo de tempo, o div, o componente no final que
teremos será o contêiner. Agora podemos colocar nossos botões
no componente do contêiner. Se inspecionarmos, novamente, você verá um
nome de classe exclusivo que
identifica especificamente esse componente que tem os estilos correspondentes. Eu diria que esta é uma boa
introdução para componentes de estilo. Você pode ver que
é muito fácil estilizar o aplicativo
usando essa abordagem porque tudo
aqui é um componente. Pode ser, digamos, confuso diferenciar
entre componentes regulares e componentes
instalados, mas
essas são as desvantagens. Você precisa encontrar a média
dourada onde
deseja ter seus estilos ou onde deseja ter
seus componentes regulares. Mas os componentes de estilo são uma
solução muito popular. Eu diria. Além disso, uma coisa que ele
também fornece é algo chamado tema global ou configuração
global. Se voltarmos aos documentos de
componentes estilizados
e, no
canto superior direito, pesquisarmos o tema, podemos encontrar a referência do
provedor de tema, e a referência do provedor de tema é algo que
vamos tentar agora. Vamos importar o provedor de temas componentes
estilizados
aqui na parte superior. Em seguida, seguindo esse exemplo, passaremos o tema prop para o componente do provedor de tema. O tema que precisamos
passar aqui deve ser um objeto. Vamos defini-lo
em algum lugar no topo. Vamos chamá-lo de tema. Será apenas um
objeto e esse objeto, o que você especificar aqui, ficará disponível dentro da interpolação de
strings dentro de
cada componente estilizado. O que significa que aqui, você pode definir qualquer configuração global
que
gostaria de usar em componentes
estilizados. Pode ser em cores, pode ser,
digamos, tamanhos de fonte, pode
ser uma família de fontes,
nas bilheterias. Quando vamos
estilizar o aplicativo, usaremos
cores e família de fontes, por exemplo, aqui
podemos especificar cores. Digamos que o principal será apenas vermelho. Em seguida, passamos o objeto do tema
pelo provedor do tema aqui. Agora, dentro da interpolação, onde quer que você queira usar esse conflito global de temas
que você tem aqui, basta escrever que a cor será
novamente reaberta a interpolação. Passamos uma função que deve
retornar uma marcação CSS de string. Serão, digamos, adereços. Props.theme e o props.theme se
referirão a esse objeto aqui. Props.theme.colors.main. Agora, se voltarmos
ao aplicativo e vermos, cor ficará vermelha. Agora, em vez de escrever vermelho em todos os componentes
estilizados, você apenas se referiria a
props.theme.colors.main. Então, em vez de mudar essa
cor em todos os lugares, você terá um único lugar onde essa cor é definida. Por exemplo, agora decidi
mudar minha cor principal
de vermelho para azul. Eu apenas digitaria azul aqui
e isso se refletirá em todos os componentes aos
quais prompts.theme colors main é referido. Vamos adotar essa
abordagem para criar, digamos, alguma configuração global
nas bilheterias. Agora, essa foi uma introdução
aos componentes estilizados. Agora vamos comparar o que
exatamente isso nos dá, quais são
exatamente as desvantagens e qual é a
diferença entre, digamos, usar componentes de
células e uma forma tradicional de usar CSS. Vou abrir o Paint. À esquerda, teremos
algo chamado
CSS estático e, no canto direito, teremos algo
chamado CSS em tempo de execução. Os componentes estilizados
fazem parte do CSS em tempo de execução, mas vamos começar
com a primeira estática. O que é CSS estático? Da maneira tradicional, quando escrevemos CSS, nós
os escrevemos dentro de arquivos CSS
e, em seguida, os arquivos CSS são
importados para o aplicativo. Por exemplo, se dermos uma
olhada no GitHub, eles usam CSS estático para
estilizar seu site. O que quero dizer com isso é que,
se olharmos dentro da marcação
deles, dentro da hashtag ,
eles carregam arquivos CSS, e se abrirmos
um
desses estilos, um dos CSS, talvez
vamos abrir outro. Existe um global. Tem esses nomes de classe,
como borda de cor inversa, talvez algo como BG grey. Eles importam arquivos CSS estáticos que foram definidos
no momento da criação
e, em seguida, usam os nomes das
classes que vêm desses arquivos CSS
dentro da marcação. Vamos abrir a etiqueta corporal. Aqui você vê nomes de classes regulares, compreensíveis e
abrangentes. Mas se olharmos para dentro
dos componentes estilizados, é um pouco diferente. Nomes de classes estáticas, independentemente do que esteja definido
no momento da construção. Se quisermos aplicar nomes de classes
dinâmicas ou se
quisermos aplicar estilos dinâmicos com nomes de classes CSS estáticos,
abordagem com CSS estático. Digamos que temos um botão
aqui que pode ser primário, criaríamos, digamos, com uma classe de botão de
pontos CSS normal, depois criaríamos uma classe primária de
pontos
e, quando vamos
estilizar esse botão, vamos apenas
alternar os nomes das classes. Por padrão, digamos que fosse um elemento de botão que você
teria aqui, como ponto, digamos classe de botão aqui, e quando você
clica em algo, esse botão tem um nome de
classe adicional chamado primário. Dessa forma, você pode usar nomes de classe
estáticos estilos CSS
estáticos para criar nomes de classes
dinâmicas
especificamente para elementos. Com componentes estilizados ou com CSS em
tempo de execução, é diferente. O CSS é, digamos,
construído com precisão. O que quero dizer com isso. Se
olharmos dentro do nosso aplicativo aqui, na hashtag, não temos
nenhum arquivo CSS conectado. A questão é de onde exatamente
esses estilos vêm? Eles estão vindo de. Deixe-me ver. Se abrirmos o chapéu. Aqui temos a etiqueta de estilo. O problema é o
CSS em tempo de execução,
o que ele faz, os componentes com estilo de biblioteca injetam estilos dinamicamente na página
usando a tag de estilo. Se abrirmos componentes estilizados , marcações e
documentação oficial, eles os terão, deixe-me ver,
eles têm exatamente
a mesma tag de estilo
aqui em que eles têm exatamente
a mesma tag de estilo esses
estilos são injetados. Isso está vazio, não
sei por quê. Vamos ver isso,
isso é uma confusão global. Esses não são estilos dinâmicos. Todos esses estilos que
você vê aqui
são injetados na etiqueta de estilo. Está vazio aqui. Deixe-me tentar com o código-fonte da página. Aqui não está vazio. Todos esses estilos aqui são injetados aqui dentro
da tecnologia de estilo. O fato é que esses
arquivos são injetados no Defly. Eles não foram definidos
no momento da construção. O que significa que quando eu
acesso esta página, primeiro, a tag de estilo estava vazia. Mas quando eu realmente
vou para aquela página, os componentes estilizados, as partes, qualquer JavaScript que estavam
aqui dentro de crases. Em seguida, leva algum
tempo para processar isso, analisar o que escrevemos aqui, então ele cria essa marcação
CSS e depois injeta essa marcação CSS
aqui dentro da tag de estilo. Dessa forma, os estilos são injetados em tempo de execução, durante as interações
do usuário. O problema com essa abordagem é que, quando você
alterna entre as páginas, ela injeta apenas os
estilos necessários para exibir o conteúdo nessa
página específica. Isso significa que ele carrega estilos
necessários apenas para o conteúdo atual. Ele nunca injetará
estilos que
não sejam exigidos por
essa página específica. Ao contrário dos aplicativos
tradicionais aqui, você importa esse arquivo CSS
grande, ele tem muitos nomes de classes
diferentes, mas eles podem não
ser usados na página. Os componentes estilizados, em primeiro lugar,
injetam estilos
dinamicamente em tempo de execução e, se digamos que algo
seja dinâmico, por exemplo, alteramos a sonda aqui, esses estilos também serão injetados
dinamicamente adicionados às tags de estilo para
que fiquem disponíveis
na página. Com aplicativos tradicionais,
isso não está certo. Tudo precisa ser predefinido antecipadamente e
carregado por meio de arquivos CSS. O problema com essa solução
CSS NGS, especificamente com JavaScript
em tempo de execução, é que ela leva tempo. Leva tempo para analisar esse JavaScript para
traduzi-lo em CSS e injetá-lo na página. É computação, leva tempo. Isso significa que se você
tiver uma árvore de elementos muito grande,
digamos, na página que é um componente
estilizado, ela pode se tornar um gargalo em algum momento,
porque
o JavaScript leva tempo para processá-la. Se você tiver milhões de centenas de componentes
na página
, pode levar um segundo, alguns segundos, enquanto os estilos serão
injetados na página. Mas na maioria dos aplicativos, esse não é o caso. Mas você realmente deve
considerar essa opção se trabalha em aplicativos maiores e é
você quem
toma decisões. Mas, novamente, na maioria das vezes, não
estou aqui para te assustar. Na maioria das vezes, isso
é totalmente normal e os usuários finais nem
perceberão a diferença. Para bilheteria, vamos
usar componentes estilizados. Vamos
experimentar essa opção. As vantagens dos componentes
estilizados são que eles facilmente
nos permitem definir primeiro a
configuração global com JavaScript. Criamos o objeto do tema e ele fornece tudo por meio da interpolação dentro
dos componentes estilizados. A segunda vantagem é
que podemos
aplicar facilmente nomes de classes dinâmicas usando,
novamente, a mesma
interpolação de strings
e, terceiro, tudo
é JavaScript. Você não precisa criar arquivos
CSS de forma alguma. Tudo está escrito
aqui diretamente. A desvantagem é que, em primeiro lugar porque
se trata de JavaScript, leva tempo de computação. Novamente, em aplicativos muito grandes, isso pode ser um gargalo. Em aplicativos menores, isso
nem será visível. Segunda desvantagem, pode ser confuso porque
agora tudo é um componente e
é fácil
confundir componentes
regulares
e componentes estilizados. Acho que é isso. Por enquanto,
vamos remover todas as mudanças que
fizemos dentro do GS6 doméstico. Vou manter
a instalação de componentes
estilizados e
, no próximo vídeo, finalmente
estilizaremos o aplicativo inteiro
usando componentes estilizados. vejo lá.
85. 29 Estilando o aplicativo p1: Oi, lá. Neste vídeo, continuaremos falando sobre estilos. Neste vídeo, vamos
estilizar nosso aplicativo, não inteiramente, mas vamos
fazer a parte principal. Vamos embora. No vídeo anterior, eu já instalei
styled-components, acabei de executar npm install
styled-components, posso executar esse
comando novamente para garantir que o pacote
esteja definitivamente instalado. Logo depois disso, vou iniciar o servidor de
desenvolvimento local e vamos ver
exatamente onde
vamos começar a estilizar
nosso aplicativo. Os estilos que vou
usar neste vídeo serão compartilhados com você por meio do convidado ao qual você
já tem acesso. Vamos começar por aqui. Em primeiro lugar, vamos conectar
a fonte do Google, especificamente o Roboto,
ao nosso aplicativo e talvez alterar o título. Porque agora
é apenas um aplicativo React. Vou simplesmente ir aqui, StylingPart1.md e
copiar o índice HTML
que tenho aqui. Em seguida, vou
navegar até index.HTML. Aqui, em vez do título, conectarei essa fonte, carregarei essa folha de
estilo e alterarei o
título para Box Office. Agora, ele aparecerá
em Box Office. Meu aplicativo aparece na
bilheteria e eu tenho essa fonte Roboto conectada aqui. Incrível. Agora,
do vídeo anterior, você lembra que eu falei sobre o tema de componentes
estilizados, usamos o provedor de temas. Vamos seguir em frente e
criar esse tema. Se eu voltar para o convidado, tenho esse objeto aqui. Esse objeto aqui será nossa configuração global de tema. Apenas algumas cores mais a fonte global que
vamos usar, o Roboto que acabamos de
conectar dentro do índice HTML. Vou pegar
esse objeto de tema, vou até,
deixe-me ver, o aplicativo JS6. Aqui, vou adicionar
esse objeto de tema e agora preciso usar o provedor de
tema e passar esse objeto de tema para os componentes
subjacentes. Em primeiro lugar, vamos nos
livrar dessa marcação aqui, não
precisamos mais dela, ela foi comentada. Então, a partir dos componentes estilizados, vou importar o provedor de
temas. Aqui abaixo, consulte
o provedor do cliente, ou ainda por cima. Realmente não importa, vou chamar o provedor de
temas, vou encapsular o roteador do
meu navegador no provedor de temas e,
como objeto de
tema, vou passar o objeto de tema que temos aqui e o
copiamos do convidado. Agora, você pode ver que realmente
foi essa nova edição, digamos que com esse
novo objeto de tema, nosso aplicativo j6 ficou
um pouco poluído. O que podemos fazer nesse caso é talvez
oscilar parcialmente ou extrair lógica que escrevemos
até agora aqui em um arquivo separado. Por exemplo, podemos de
alguma forma extrair esse provedor de tema e
o objeto do tema em um arquivo separado e gerenciar
tudo a partir daí. O que quero dizer com isso é
que, dentro da pasta de origem, podemos criar um novo arquivo
chamado theme.jsx. Agora, aqui podemos mover
o objeto do tema, e aqui podemos criar
nosso próprio componente, que talvez seja
chamado de tema global. Vamos tentar criar
esse, const, GlobalTheme. Vamos usar este GlobalTheme dentro do appjsx em vez
do provedor de temas. Não precisaremos
importar o provedor
de temas de componentes estilizados, gerenciar o
objeto do tema aqui dentro e, em
seguida, usar o provedor de tema para
passar o objeto de equipe, podemos extrair toda essa
lógica dentro do tema jsx, gerenciar tudo a partir daqui. Para isso, podemos criar apenas um componente
chamado tema global e não podemos agrupar o roteador
do navegador no componente de tema global,
assim mesmo. Que vamos importar do considerado jsx. Deixe-me fazer isso. Vou apenas importar
do tema global. Esse GlobalTheme
precisa ser exportado para, vou chamar export
const, GlobalTheme. Agora parece muito mais limpo. Este GlobalTheme deve entregar todos os seus filhos que
são passados para dentro. Isso significa que dentro do componente
GlobalTheme, vou desestruturar
o adereço infantil
e, a partir desse componente, vou
devolver o provedor de tema, que é importado de componentes
estilizados, e crianças mais velhas entrarão. Para o adereço do tema, passarei o objeto do
tema aqui. Agora, criamos o tema, gerenciamos a lógica
no tema jsx, no entanto, também
precisamos aplicar
alguns estilos globais. No momento, temos alguns estilos globais definidos
aqui dentro
do índice CSS, mas
para nossa solução de estilo, usamos componentes estilizados. Na verdade, podemos usar componentes
estilizados para
criar um tema global,
o que, digamos, não é, de alguma forma o
escopo de algum componente
específico. Portanto, alguns estilos são definidos por componentes
estilizados que
estão disponíveis globalmente. Em vez de usar CSS de índice, podemos realmente
excluir esse arquivo. Dentro do índice jsx, agora
podemos remover a
referência a um índice CSS
existente. Agora, precisamos de alguma forma
criar estilos globais. No componente estilizado, temos uma coisa chamada
criar estilo global. Podemos procurar isso na
documentação. Deixe-me ver. Crie um estilo global, referência
APA, crie um estilo global, somente na web. É apenas uma função
que você chama. Novamente, você
escreve estilos globais, CSS
global e depois o usa
apenas como um componente. Basicamente, o mesmo que o uso regular de componentes de
estilo, mas desta vez não
será direcionado a componentes
específicos. Os estilos serão aplicados globalmente. Vamos chamar de criar estilos
globais aqui, mas temos aquele
convidado interno que é compartilhado conosco. Então, podemos simplesmente
partir daqui, vamos copiar e colar. Eu apenas chamo de criar um
estilo global que foi importado de componentes
estilizados e, em seguida,
especifico alguns estilos globais, especificamente aqui
para o orçamento. Aqui, o que eu faço, eu uso a
interpolação de strings para interpolar esse objeto de tema e pegar família de fontes que
está definida aqui. Você se lembra que, como
usamos backtest aqui, podemos usar interpolação de
strings, devemos passar uma
função que retorne algum CSS que será interpolado
diretamente aqui. No
vídeo anterior, usei adereços, logo em seguida fiz props.theme. Mas como o primeiro argumento é um objeto que
contém a chave do tema, podemos desestruturar a chave do tema diretamente
nos argumentos. Isso é totalmente opcional. Isso é apenas para, digamos, simplificar e encurtar
essa sintaxe. Vou apenas
desestruturar o tema a partir daqui e usar a família de fontes do tema. Novamente, o
objeto do tema se refere a isso, o objeto que definimos aqui e depois o passamos
para o provedor do tema. É por isso que está disponível dentro de nossa definição de
componentes estilizados. Em seguida, usamos
esses estilos globais dentro de nossa marcação, como um componente
irregular. Agora, tudo isso
se torna disponível magicamente. Se acessarmos nosso aplicativo novamente e procurarmos a etiqueta corporal, deixe-me encontrá-la, você poderá ver que os
estilos foram aplicados. Temos a família de fontes,
Roboto sans-serif, assim como definimos
no tema e no resto do CSS que
colocamos aqui. Ótimo. Agora, qual
será nosso próximo passo? Acho que vamos
começar com a navegação primeiro porque temos uma pequena
coisa que precisamos discutir. O que quero dizer com essa pequena coisa, quando navegamos entre as páginas, queremos indicar qual
página está ativa no momento. Por exemplo, se eu estiver
na página inicial, gostaria de mostrar
ao usuário que esse link está ativo. Se eu navegar até o início,
quero indicar que o link inicial está
ativo no momento. Como posso fazer isso? Se voltarmos aos componentes, nav.sjsx aqui temos
essa marcação simples, apenas
mapeamos nossa
matriz de links para o elemento LI com o componente de link que é importado do
react-router-dom. Como podemos verificar de alguma forma se
esse link que renderizamos
aqui está ativo. Mas esse roteador React tem um componente
específico
e, se consultarmos a documentação
e se você procurar NavLink nos componentes, podemos ler na
descrição que um NavLink é um tipo especial de link que sabe se está ativo ou
não. Se lermos mais, ele diz que, por padrão, uma classe
ativa é adicionada a um componente NavLink quando
está ativo; portanto, em vez de usar link, podemos usar um componente chamado NavLink e, quando
ele
estiver ativo , a classe ativa será anexada a
esse link por padrão. Vamos tentar ver. Substituí o link pelo navlink
do React-Router-DOM, volto ao meu aplicativo e inspeciono a marcação. Eu vejo a tag [inaudível] aqui, e você pode ver que
agora estou na página inicial e vejo que plus active
foi adicionado a esse link. Se eu navegar para casa, agora o plus active está
sendo anexado à casa. Assim, o roteador
React
nos deu a capacidade de estilizar nosso link ativo apenas
substituindo link por navlink. simples quanto isso. Você pode ler mais sobre como esse NavLink pode ser
personalizável, talvez com base em algumas
condições, mas no nosso caso, ele deseja ser alterado de alguma forma, a interface, por exemplo, se
olharmos a documentação, podemos usar essa tag de estilo, que pode ser uma
função que recebe essa chave ativa
do primeiro argumento. Não vamos mais
longe com isso, vamos voltar
para nosso convidado aqui e eu já preparei
os estilos para nós. Deixe-me explicar
o que temos aqui. Em primeiro lugar,
vamos copiar esse componente com estilo de lista de navegação e colocá-lo
em algum lugar na parte inferior. Antes de tudo, precisamos
importar o estilo. Na parte superior, chamaremos o estilo de
importação de componentes
estilizados. Aqui, criamos um elemento UL
simples, este com estilos. Agora vamos
substituir a UL, por romancista, e tudo dentro da marcação
interna será estilizado. Novamente, criamos estilos, pontilhamos um elemento de lista ordenada
com estilos e , em seguida, também especificamos que cada elemento LI interno
terá uma margem de 10 pixels. Vamos experimentar e ver. Voltamos ao aplicativo, você pode ver que o
layout foi alterado. Se olharmos para a
classe L, assim como antes, temos uma classe gerada de forma exclusiva especificamente para esse elemento da lista
Nav, especificamente para
esse elemento UL, podemos ver os estilos. Se inspecionarmos o elemento LI, ele também tem estilos. Ótimo, funcionou. Mas agora, o que dizer dos links? Porque não tocamos em
nenhum componente do NavLink. Se voltarmos aqui para o convidado, também
temos o link estilizado aqui. Deixe-me copiá-lo e eu
explicarei o que temos. Os componentes estilizados são,
digamos, versáteis o suficiente para
nos permitir não estilizar elementos HTML básicos, digamos nativos. Isso também nos permite estilizar
outros componentes. Aqui estou chamando styled
como uma função e passo o componente NavLink
interno como argumento. Dessa forma, estendemos componente
NavLink com esses
estilos que temos aqui. Dessa forma, no final, esse estilo de link será
apenas um componente NavLink, mas com essa folha de estilo CSS, tão simples quanto isso. Agora, em vez de
usar o NavLink aqui, posso usar com segurança o
estilo Link ou talvez possamos até chamá-lo de
estilo NavLink, se você quiser, vamos mantê-lo no estilo de link. O que fazemos lá dentro apenas especificar novamente a cor
do objeto do tema e
aqui temos o e comercial,
e então temos.active, o que
significa quando esse elemento, então esse e comercial
se refere a si mesmo, que significa que o
e comercial aqui se refere ao próprio componente NavLink, e então quando esse componente,
quando esse elemento, quando esse NavLink tem
a classe ativa, especificamos que ela terá
colorido essa e depois a outra marcação para obter
o efeito que desejamos. Vamos tentar ver.
O que nós temos? Voltamos aqui e você vê que agora temos essa
linda navegação. Quando navegamos, agora é indicada a página que está ativa
no momento. Ótimo, vamos seguir em frente. Se voltarmos para o convidado aqui, teremos mais um momento
aqui chamado Rádio personalizada. Para esses botões de rádio
que temos aqui, digamos que vamos
criar botões de rádio personalizados. Quando se trata de entradas de estilo como caixas de seleção
ou rádios personalizados, é um pouco complicado, mas nada realmente complicado. Se formos para o
componente do formulário de pesquisa que temos aqui, veremos que temos dois rótulos. Dentro de cada etiqueta,
temos uma entrada do tipo rádio. Se precisarmos criar um elemento de rádio personalizado que
queiramos ter um estilo completo, precisamos adotar uma abordagem um pouco diferente dessa para torná-lo, digamos, reutilizável. O que quero dizer com isso é
que sugiro que
criemos um componente que
chamaremos de rádio personalizado. Em componentes,
vou criar um novo arquivo chamado
Custom radio.jsx, então aqui vou
criar um rádio personalizado. Aqui, por enquanto, será apenas um rótulo. Vou colocá-lo de lado e vamos ver o que temos. Temos rótulo, e
dentro temos texto
e, em seguida, temos entrada. Então, podemos simplesmente copiar essa marcação aqui e colocá-la em um rádio personalizado. Agora, o que queremos fazer e qual interface queremos
oferecer a esse elemento de
rádio personalizado? Vamos avaliar exatamente como
gostaríamos de usá-lo. Então, agora, criamos um rótulo e, em vez disso,
passamos a entrada para dentro. partir de agora, será um componente chamado rádio personalizado. Vamos
chamar rádio personalizado,
e para esse
rádio personalizado, idealmente, gostaríamos de
passar todos os adereços, todos os atributos
que passamos para o elemento de entrada do tipo rádio. Então, vou
copiar tudo isso,
talvez sem rádio tipo, porque esse componente
já é sobre rádio. Vamos passar o nome e a verificação de
valor inalterados. Mas e quanto ao rótulo? Quais são nossas opções? primeira opção é que
talvez possamos passar esse
rótulo quando crianças, por exemplo, assim. Isso pode ser uma opção,
mas, em vez disso, eu pessoalmente prefiro passá-la
como um atributo. Então, vamos dizer que
defina mais um atributo, mais
um adereço, que
chamaremos rótulo e vamos
passar os shows aqui. Em vez de usar crianças, será um
componente de fechamento automático com mais
um suporte adicional
chamado rótulo. Agora, como podemos lidar com tudo isso dentro
de um rádio personalizado? Em primeiro lugar,
vamos especificar adereços aqui e, a partir dos adereços, vamos desestruturar. Primeiro, vamos
pegar esse atributo de rótulo, adereços rotulados que
vamos passar, depois dentro da marcação, vamos
interpolar esse rótulo, e agora nosso objetivo é
pegar todos esses adereços,
o resto dos adereços que passamos, não importa quais sejam esses adereços, sabemos que todos eles serão de alguma forma redirecionados para
o elemento de entrada aqui. Então, a questão é:
como podemos fazer isso? Não vamos desestruturar todos os adereços um por um, é? Não
queremos fazer isso. Sabemos que pegamos o rótulo e o resto definitivamente
vai para o elemento de entrada. No React, como o objeto props ainda é
apenas um objeto JavaScript, as mesmas regras se aplicam. Podemos usar essa estruturação, podemos usar o operador de propagação, podemos usar o operador resto. Então, todas essas regras se aplicam. O que eu sugiro é que podemos realmente usar o operador de
propagação. Podemos chamar três pontos aqui
e especificar adereços de entrada. Usando essa sintaxe aqui, talvez eu possa
embuti-la diretamente aqui. Então, pegamos apenas o
suporte do rótulo aqui
e, o que quer que passemos, o resto dos adereços
estará disponível no objeto de adereços de entrada. Agora podemos pegar esse
objeto de adereços
de entrada e espalhar todos esses adereços que
passamos usando o
operador spread desse jeito. Em primeiro lugar, usamos o operador
rest para, digamos, acumular todos os adereços que
passamos para o rádio personalizado, todos eles ficarão
disponíveis em adereços de entrada, objeto
e, em seguida, espalhamos todos os adereços,
todas as teclas dentro dos adereços de entrada, como adereços, como atributos
do elemento de entrada. Agora, a partir do rádio personalizado, vamos exportar por
padrão o rádio personalizado, e agora precisamos de alguma forma
estilizar tudo isso. Então, se voltarmos
para o convidado aqui, temos um rádio estilizado. Vamos copiar tudo isso e
depois colocá-lo na parte inferior. Agora, primeiro precisamos
importar componentes estilizados a partir de componentes
estilizados. Aqui, criamos uma etiqueta de ponto estilizada e chamo o
componente de retorno de rádio estilizado. Em vez de rótulo, podemos usar
apenas um rádio estilizado e agora tudo
funcionará magicamente. Então, toda essa
marcação CSS é apenas para criar um botão de rádio personalizado completamente estilizado
com o tema que temos e as cores que
definimos dentro desse tema. Agora, vamos salvá-lo. Além disso, precisamos adicionar uma marcação
adicional aqui, apenas um
elemento de extensão vazio. Simples assim. Ele será usado dentro da
marcação, será estilizado. Agora, vamos voltar e
dentro do formulário de pesquisa, vamos usar esse rádio personalizado. Agora, em vez de usar um
rótulo e assim, vamos importar primeiro
um rádio personalizado. Importe componentes
de
ROM de rádio personalizados do rádio personalizado,
assim mesmo, e o rádio personalizado é
exportado por padrão, então eu não preciso usar exportação
nomeada, importação de nome. Isso está errado. Agora, vou usar um rádio
personalizado, passarei
o suporte rotulado e o resto dos adereços serão redirecionados,
digamos, para o elemento
de entrada subjacente. Então, a mesma coisa que
farei com os atores. Eu não preciso mais desse
rótulo aqui. Vou copiar essa etiqueta de rádio
personalizada para atores e os adereços
serão o resto. Mais uma coisa que
notei aqui, especificamos que essa entrada
será do tipo rádio. No entanto, não
especificamos em nenhum lugar que nossa entrada subjacente
também tenha o tipo rádio. Primeiro, digamos todos esses adereços que passamos para rádio
personalizado redirecionam para o elemento de entrada
subjacente, mas o que quer que
passemos, podemos substituí-los pelos adereços que
definimos aqui, digamos, incluindo-os
depois de fazermos a propagação. Portanto, nossa entrada
será do tipo rádio. Quando especificamos adereços
após fazermos esse spread, tudo o que especificarmos
será substituído por isso. Por exemplo, se aqui
para um rádio personalizado, eu vou passar o tipo, digamos texto, isso será substituído por tudo o que eu especificar
após esse spread. Mas se eu especificar aqui
dentro de um rádio personalizado, digitar rádio antes da propagação, o spread substituirá,
digamos, os adereços padrão
que eu passo aqui. Mas se for definido posteriormente, será sobrescrito. Exatamente as
mesmas regras que você aplicaria se espalham dentro de um objeto simples. Então você espalha algo aqui,
digamos, adereços de entrada, e então você especifica isso. O tipo será rádio. Basicamente, tudo o que temos na linha 12 é traduzido
aproximadamente. O que você vê dentro dessas linhas três a seis,
aproximadamente o mesmo. Nós especificamos o tipo de rádio, não precisamos
especificar o tipo de texto aqui. Agora podemos salvar tudo. Podemos voltar ao nosso aplicativo e vemos que agora
temos elementos estilizados, mas esquecemos de excluir o rótulo aqui e agora
você pode ver que funciona. Se eu especificar, procure meninos, agora, na verdade,
procura atores. Então eu mudei para
os programas e funciona. Então está tudo bem aqui, e acho que será isso
especificamente para este vídeo. Nós abordamos, digamos, as coisas essenciais para
o estilo. Acho que conseguimos fazer muita coisa. Por enquanto, vamos
nos limitar a isso
e comprometer tudo. Vamos dar uma
visão geral rápida do que fizemos. Em primeiro lugar, dentro do index.HTML, adicionamos esse link
à fonte Roberta, definimos o título como Box
office, dentro do app.jsx, usamos o componente de
tema global que criamos
dentro do jsx. Então, criamos esse componente global
que é apenas um invólucro sobre o provedor de temas e
estilos globais a partir de componentes estilizados. A lógica é gerenciada
dentro do tema jsx. Criamos esse objeto de
tema global que usamos nossos
componentes estilizados em todo o aplicativo. Então, dentro do navs.jsx, usamos o
componente nav link porque esse não é um componente que
nos fornece o link ativo. Assim, o link ativo
recebe a classe ativa
e, em seguida, usamos essa classe
ativa dentro da nossa marcação CSS para
estilizar o link ativo. Em seguida, criamos e usamos o componente de rádio
personalizado, que é um botão de rádio personalizado
que criamos novamente, com a ajuda de componentes de
estilo. Também conhecemos esse novo pequeno truque aqui quando precisamos redirecionar, digamos, ou passar os adereços para o elemento
subjacente usando os operadores
rest e spread. Portanto, podemos realmente
espalhar um objeto em um elemento e, quaisquer que sejam os
valores-chave que ele tenha, todos
eles serão
considerados como adereços, como atributos do elemento. Isso soou muito. Vamos confirmar
tudo e,
digamos , instalar componentes estilizados, então diremos que isso
criou um feixe global com o SC. Vamos simplificar com componentes
estilizados. Criou um rádio personalizado. Usou o link de navegação do
roteador React para estilizar o link ativo. Parece incrível. Vamos enviar tudo para o
GitHub e, no próximo vídeo, continuaremos
com os estilos. Te vejo lá.
86. 30 Estilando o aplicativo p2: Olá novamente. No último vídeo, começamos a estilizar o aplicativo usando componentes
estilizados. Neste vídeo, continuaremos. Se voltarmos ao
convidado compartilhado com você, você poderá encontrar stylingpart2.empty. Esse é o arquivo ao qual
podemos nos referir. Temos muitas marcações CSS, e escrever tudo
isso vai ser muito longo e entediante. Para evitar isso,
vamos
usar apenas a folha de estilo existente, que você e eu não
precisemos escrever tudo
isso sozinhos. Vamos um por um. O que temos dentro de
StylingPart2.md. Primeiro, temos o
AppTittle.jsx e temos componente no estilo
Titlewrapper aqui. Vamos copiá-lo. Vamos voltar ao nosso aplicativo. Vamos para onde está? Qual era o arquivo? AppTittle.jsx? Vamos para AppTittle.jsx
e, aqui na parte inferior, usaremos esse
titlewrapper e importaremos componentes estilizados
a partir de componentes
estilizados. Agora, em vez do
div aqui, vamos usar o Titlewrapper, e todo esse
texto h1 e p interno será estilizado de acordo com nossos
estilos dentro do styled div aqui. Vamos salvá-lo. Vamos
voltar ao aplicativo e ver. Agora, boom, temos esse título
bem centrado. Incrível. Vamos continuar. Em seguida, temos o
formulário de pesquisa na lista. Vamos copiar tudo isso e navegar
para pesquisar. No último vídeo aqui, já
criamos esse componente
CustomRadio. Agora vamos adicionar estilos
adicionais, para que todo o nosso formulário tenha uma boa aparência. Vou colocar todos esses componentes estilizados na parte inferior. No entanto, só para mencionar, você pode colocar esses
componentes estilizados em qualquer lugar. Você pode criar
searchform.style.jsx e colocar todos os componentes estilizados lá e
importá-los dentro do formulário de pesquisa. Isso ocorre caso
você não queira
poluir o próprio arquivo do formulário de pesquisa. Por causa dos componentes estilizados, CSS, ele ocupa muito espaço. Caso você não queira
escrever tudo isso aqui, você pode escrevê-lo em um arquivo separado e
importá-lo aqui no site. No nosso caso, escreveremos
tudo na parte inferior. Primeiro, precisamos importar o estilo, pressiono a inteligência para
abrir o menu suspenso. Aqui, importo componentes estilizados a partir de componentes
estilizados, como sempre. Agora, vamos usar esses componentes. Primeiro, temos um elemento
de entrada estilizado. Temos essa entrada do tipo texto,
então, em vez de usar entrada, vamos usar o componente de entrada de
pesquisa, componente de
estilo
que criamos. Em seguida, temos essa div no estilo
RadiosWrapper. Esta será uma div
adicional aqui, estilizada ou como eu a chamei? Era RadiosWrapper. Será apenas um div
que envolverá
nossos dois rádios personalizados desse
jeito. No final, também temos o invólucro do botão de
pesquisa, que será outro invólucro
div
adicional para esse elemento de botão. Podemos usar o wrapper do
botão de pesquisa e colocaremos o
botão do tipo enviar dentro. Isso é o que escrevemos dentro dos
estilos. Vamos salvá-lo. Vamos voltar ao formulário
e agora basta dar uma olhada nisso. Parece muito bom até agora. Vamos tentar procurar meninos. Você pode ver que nosso cartão ainda não
está estilizado. Vamos corrigir
isso no momento. Mas o formulário parece ótimo. A propósito, não temos nenhum espaço reservado aqui
dentro desta caixa de pesquisa. Talvez vamos adicioná-lo. Vou passar o prompt de
espaço reservado para
pesquisar o componente de entrada, que na verdade não é
como um componente. Ainda é o elemento de entrada. O espaço reservado será
procurar por algo. Vamos tentar ver. Agora, parece melhor. Ótimo. Vamos mais longe. Além disso, temos um conjunto de arquivos que são
prefixados com common. Esses são
componentes estilizados que serão compartilhados entre vários
arquivos dentro do nosso aplicativo. Eles serão importados para
vários outros componentes. É por isso que eles são
prefixados com comum. Isso significa que dentro dos componentes, provavelmente
criaremos
uma pasta chamada common e colocaremos esses componentes
estilizados lá. Primeiro, temos flexgrid.jsx. Vamos copiar isso. Vamos criar um novo arquivo
aqui chamado flex grid. Dentro desse arquivo, apenas
exportamos o componente flexgrid. Nada especial. Então temos o cartão de pesquisa. Este será um conjunto de componentes que usaremos
para estilizar o cartão de pesquisa. Tanto para shows quanto para atores, copiamos essa marcação. Vamos colocá-lo aqui. A partir
daqui, exportamos duas coisas pesquisar o invólucro da imagem e
depois pesquisar os componentes do cartão. Usaremos esses dois
para estilizar os cartões de pesquisa. Agora vamos mais longe. Aqui temos StarIcon jsx. Vamos criar
este, StarIcon, jsx. Isso vai ser interessante. Este é apenas um div estilizado. No entanto, aqui vamos
usar um adereço chamado ativo. Vamos passar um suporte
ativo para mudar a cor desse StarIcon. Vamos abordar
isso em um
momento em que voltarmos
a esse componente, quando vamos usá-lo. Agora temos mais uma coisa
aqui chamada centro de texto. Nada de especial aqui. Apenas um div que
centralizará o texto em seu interior. A próxima coisa que temos é
chamada Pages Show.jsx. Vamos copiar tudo isso. Vamos para Pages Show.jsx. Assim como antes,
vamos usar todos os
nossos componentes de estilo. Na parte inferior, vamos
importar componentes estilizados a partir de componentes
estilizados. Vamos ver como podemos
usar esses componentes. Embalagem de volta para casa. É denominado div
e, por dentro, estiliza
a tag âncora. Aqui temos o link
que nos leva à página inicial. Vamos embrulhar isso no
componente de embalagem doméstica. Eventualmente, parece
algo assim. Em seguida, temos show page wrapper, que será o invólucro
de toda a marcação aqui. Eu só vou
usá-lo assim. Booms. Mostra o invólucro da página e a tag de fechamento
mostra o invólucro da página. Então, também temos o InfoBlock, InfoBlock é esse div reutilizável para nossas
informações adicionais para o programa. Aqui estarão os detalhes do
InfoBlock, temporadas do
InfoBlock
e o elenco do InfoBlock. Aqui também temos isso. Ocorreu um erro,
os dados estão sendo carregados. Em vez de apenas usar div, podemos reutilizar esse componente com
estilo de centro de texto que
criamos dentro da pasta
atual. Vou importar
de componentes, do centro de texto
comum, e vou importar o centro de texto
e, em vez de usar
esses divs aqui, aplicarei o centro de texto. Incrível. Agora vamos tentar ver se eu clico em algum
dos programas em ler mais. É assim
que nossa página está agora. No entanto, ainda temos dados principais do programa
sem estilo, ainda
temos
detalhes, temporadas e elenco sem estilo. Se voltarmos a ser convidados aqui, teremos elenco de programas, detalhes dos
programas,
temporadas e cartão de exibição. Vamos estilizar
tudo isso agora. Vamos começar com o elenco. Vou copiar
tudo isso e
colocá-lo no elenco dos programas. No. Na parte inferior, o estilo será importado dos componentes
estilizados e lista de
moldes será o
invólucro do molde. Dentro, temos coisas que serão denominadas como uma
lista de nomes de classes. Na verdade, podemos usar esses nomes de classe em
nossa marcação e eles serão estilizados porque é isso que
especificamos para o div, os estilos. Dentro da lista de elenco,
temos esta div, que será do nome da
classe item cast. Então temos o invólucro de foto, que será nosso
invólucro de imagem, na verdade, eu o chamo assim, e então temos ator, que será esse nome de
classe ator. Incrível. Agora, se voltarmos aqui, não temos nenhum elenco disponível
para este programa. Vamos tentar outra coisa. Temos uma
imagem muito grande. Saiba o que está aqui. Vamos lidar
com isso em um momento, mas você pode ver que agora, nosso elenco está estilizado. Parece muito legal. Agora, vamos mais longe. Vamos ver o
componente de detalhes aqui. Os detalhes serão mostrados
neste DetailsWrapper. Nada realmente especial aqui
dentro do componente de detalhes, em vez de div, podemos
simplesmente aplicar detailsWrapper. Vamos voltar e ver os detalhes. Nada realmente especial, apenas uma margem
adicional aqui. Vamos voltar aos divs. Agora, temos temporadas aqui. Vamos copiar tudo isso. Vamos às temporadas. Na parte inferior,
vou importar
novamente o estilo de componentes
estilizados. Temos o SeasonsWrapper. Isso é denominado div,
SeasonsWrapper. Vamos usá-lo assim. Então, lá dentro, o que temos? Por que não foi usado? Porque eu esqueci o S.
Também temos a SeasonList aqui. Vamos usar isso para aquela div
quando mapeamos a marcação. Aqui dentro, também
estilizamos itens sazonais. Em seguida, passamos na classe esquerda, depois na classe direita. Nosso item da temporada será
essa div que mapeamos. O sobrenome será o item da temporada, conforme definido no componente
do arquivo. Item de temporada. Então saímos
da aula e da aula de redação. Mas aqui, temos a marcação a
seguir, o que significa que queremos
exibir temporadas e episódios. Vamos ver no lado esquerdo e o resto no lado direito. Podemos encerrar temporadas
e episódios em div. Direto no div, podemos dar o nome da classe left. Então, para o div, daremos o
nome da classe à direita. de estreia e a
data de término desta temporada talvez
possamos colocá-las dentro da etiqueta forte para torná-la ousada. Vamos tentar ver o que
temos no final. Agora, temos isso, vamos ver. lado esquerdo e o lado direito são
exatamente como definimos aqui. Não vemos nada de ousado aqui, mas agora vemos
porque o temos. Vamos inspecionar a marcação. Ótimo. Nossas datas agora estão negrito porque estão
dentro da etiqueta forte. Perfeito. Agora, vamos
seguir em frente. Também temos o ShowCard aqui. Isso vai ser
interessante finalmente. Dentro do ShowCard na parte inferior, vou colocar
esta seção de ação
e a seção StarBtn. Deixe-me importar o estilo dos componentes
estilizados, como de costume. A primeira coisa que eu gostaria
de fazer aqui é a seguinte. Se voltarmos ao nosso aplicativo e olharmos o
resumo que retiramos aqui, como você se lembra,
receberemos HTML bruto. Substituímos todas as
tags HTML, caracteres HTML. Mas parece que está
sendo cortado sem motivo. No final,
podemos adicionar apenas três pontos para torná-lo mais fácil de usar,
digamos. Podemos aplicar um modelo de
string como
este e, no final, podemos adicionar três pontos. Mas para torná-lo,
digamos menos detalhado, podemos simplesmente
concatená-lo usando o operador plus e ele nos dará exatamente
o mesmo resultado, mas acho que parece muito
melhor. É mais adequado neste caso. Se olharmos, agora, vemos três pontos no
final, o que é incrível. Agora, vamos usar os
componentes estilizados que temos aqui. Em primeiro lugar,
não temos nenhum componente, digamos, estilizado que envolva nosso marcador,
que forneça,
digamos, estilos para o cartão, apenas para algo específico, como seção de
ação e StarBtn. Mas criamos esse arquivo de componente de
estilo comum chamado
SearchCard.jsx e, por dentro, temos o cartão de pesquisa e o invólucro de imagem de
pesquisa. Vamos usar esses dois
dentro do ShowCard e
usaremos esses dois cartões internos de
ator mais tarde. Vou importar do SearchCard
comum interno. Vou especificar que eu importe SearchCard e importe o
SearchImageWrapper. Agora, o SearchCard
será a div de embalagem. Então, o div que quebra a imagem será, na verdade,
SearchImageWrapper. Esta ActionSection aqui será a div que define
nossa seção de ações Leia mais nos botões StartMe. Então, também temos StarBtn aqui, que é um
elemento de botão estilizado, que é isso. Agora, vamos tentar usá-lo. Vamos ver como nossos
cartões estão agora. Você pode ver que eles não parecem ruins. Tudo parece válido, mas não temos, digamos, nenhum ícone aqui. O ícone que criamos
anteriormente é esse StarIcon. Este é apenas um
div estilizado com esse atributo
CSS específico, digamos, clip-path. Vamos tentar usá-lo e ver como vai ficar. Em vez de usar os textos IsStarred
Unstar me e Star me. Eu vou comentar isso. Lá dentro, passarei o componente
StarIcon, mas também preciso
importá-lo do StarIcon comum. Ótimo. Agora, vamos ver. Agora, temos a estrela aqui, que é obtida com a propriedade CSS do caminho do
clipe. Mas você pode ver
se eu clicar nele, se eu tentar começar o
show, nada acontece. Precisamos torná-lo ativo de
alguma forma. Precisamos informar aos usuários
que esse show está começando. Anteriormente, usávamos renderização
condicional, Star me e Unstar me. Mas agora, como temos componentes
estilizados, podemos aplicar estilos dinâmicos
com muita facilidade usando interpolação de cadeias de
caracteres
dentro de componentes estilizados. Acabei de passar essa
função e especifico. Se tivermos props.active passado para o componente
do ícone de estrela, aplique essa cor amarela. Caso contrário,
aplique essa cor branca acinzentada. O que precisamos fazer
aqui é simplesmente passar o suporte ativo aqui para o componente do ícone em
estrela, que será isStarred. Quando isStarred for true, prop
ativo será verdadeiro, o que significa que ele
será usado dentro do componente de estilo para
escolher a cor amarela. Quando for falso,
será a cor cinza aqui. Vamos experimentar e ver. Eu salvo tudo. Agora, você pode ver que na verdade é amarelo porque esse
programa agora é estrelado. Se eu clicar nele, os
estilos serão alterados. Eu clico novamente, boom, o show é estrelado. Muito incrível. Legal. Nós
terminamos com o ShowCard aqui. Agora, vamos passar para o nosso convidado. Aqui, também temos
nosso último componente aqui dentro dos convidados ShowMainData. Na verdade, vamos copiar
tudo daqui. Onde está? Ele simplesmente voou para longe. Vamos voltar ao ShowMainData. Na parte inferior, temos muitos
componentes aqui, na verdade. Vamos para o
topo e vamos ver. Primeiro, temos o MainDataWrapper. Essa será a div
que envolverá tudo,
então, abrindo o colchete,
fechando o colchete. Boom, nós temos isso. Depois, temos o image-wrap
e, por dentro, temos estilo de texto da
imagem, o que significa que precisamos modificar um pouco
a marcação aqui. Vamos adicionar um invólucro div
adicional para a tag de imagem e className para o div será image-wrap. Legal. Agora, essa div aqui
que envolve o resto da marcação será essa
seção de dados que temos aqui. Vamos usá-lo. Ótimo. Agora, também temos o título e
também temos o resumo e os gêneros. Nosso título será o invólucro
para h1 div e span. É um pouco abstrato demais, mas o título será
apenas a tag h1 aqui, aquela div e talvez o
ícone de início que não
usamos aqui anteriormente. Deixe-me encapsular h1 e div aqui. Temos o Headline, que agora tem o título, que tem
a div com classificação, mas dentro da div
também podemos adicionar, digamos, StarIcon. Deixe-me realmente usar rating.average
aqui e, de acordo com nossos estilos, temos o elemento
span dentro do mergulho, então podemos realmente
envolvê-lo em um espaço. Então, aqui podemos usar o
StarIcon que vamos
importar do StarIcon comum. Vamos apenas chamar o componente
StarIcon e deixar claro que ele estará sempre ativo. Sempre teremos
a cor amarela. Eventualmente,
a marcação ficará assim. Vamos experimentar e ver o resultado. No final, temos essa estrela
amarela aqui que sempre estará
amarela ao lado da classificação. Legal. Não parece ruim. Aqui também temos
resumo e gêneros. O resumo será exatamente esse div
estilizado e os gêneros
também serão denominados div; vamos usá-lo, ou aquele div de
embrulho ou talvez não. Os gêneros serão apenas a div
que descarta o método.map. Vamos tentar ver, e agora basta ver em nossa
página como ela é linda. É totalmente responsivo. Você pode tentar
redimensionar a janela, acessá-la no seu celular. Ficará ótimo
em todos os dispositivos. Volte para a página inicial, temos esta página estilizada. Temos quase
tudo estilizado, mas perdemos algumas coisas. Por exemplo, você pode
ver que essa lista de cartas, digamos,
não tem nenhum estilo. Queremos ter uma rede. Vamos ver quais coisas não
estilizamos aqui. Não definimos o estilo show grid, então voltamos ao ShowGrid. Aqui, para esse div, vamos usar
esse
componente de estilo reutilizável que
criamos chamado FlexGrid. Vou usar
esse FlexGrid dentro do ShowGrid e deixar eu fechar todos esses componentes porque
temos muitos arquivos abertos. Eu volto para o ShowGrid. Aqui eu uso o FlexGrid e o
importo de /common/FlexGrid. Incrível. Eu
volto para a página e você vê que tudo
parece bem. É totalmente responsivo
e tem uma boa aparência. Agora, e quanto aos atores? Deixe-me procurar atores. Você pode ver que os atores
não têm estilo porque nos esquecemos
completamente deles. Vamos corrigir isso. Nós
vamos aos atores aqui. Para o ActorCard, vamos
importar esse componente comum do
SearchCard do SearchCard comum que
será o SearchCard e embrulhar tudo
em um SearchCard se examinarmos o arquivo
SearchCard. Também temos o
SearchImageWrapper aqui,
então, para o div que envolve a tag da
imagem, usaremos SearchImageWrapper, que também é importado do SearchCard comum. Vamos ver, talvez precisemos
mudar alguma coisa
daqui de acordo com os estilos, mas não acho que não
precisemos fazer isso. também precisamos usar o FlexGrid Na verdade, também precisamos usar o FlexGrid para criar uma
grade com nossos cartões. Vamos ao ActorsGrid
e, como antes, vamos usar o FlexGrid que foi importado
do FlexGrid comum. Agora, veja isso. Parece incrível. Os atores são estilizados, os shows são estilizados, tudo
parece incrível. Temos esse
StarIcon, mas se formos para a página com estrela, também veremos que tudo parece bem porque dentro do
componente Starred dentro da página Starred, usamos o componente
ShowGrid reutilizável. Vamos ver o resto. O que temos aqui? Dentro de outras páginas, usamos
também apenas algumas coisas. Por exemplo, dentro do Starred, usamos aqueles divs vazios
sem nenhum estilo. Podemos substituí-los pelo componente sensorial de
texto que está localizado dentro de uma pasta comum. Isso está na página favorita. Em vez de apenas mostrar
div, nenhum programa foi estrelado. Vamos usar o
TextCenter e esse TextCenter precisa ser importado de
components/common/TextCenter'. Simples assim. Em vez desse div,
vamos usar o TextCenter, ele mostra nosso TextCenter de carregamento. Em todo lugar está o TextCenter. O mesmo que provavelmente
faremos. Deixe-me ver. Dentro do JSX doméstico, em vez de mostrar esse div
e div sem resultados, vamos apenas mostrar TextCenter IntelliSense importado
do TextCenter comum, sem resultados TextCenter, e acho que é isso. Deixe-me ver. Se eu for para casa e digitar algo
completamente sem sentido
, definitivamente não
teremos resultados. Teremos esta mensagem
aqui, sem resultados. Se formos para Favoritos
e
limparmos o armazenamento aqui
e atualizarmos a página, veremos a mensagem
Nenhum programa foi marcado com estrela. Finalmente, nosso aplicativo
agora está totalmente estilizado. Temos tudo e
cuidamos de todas as
páginas do aplicativo. Ótimo. Agora vamos comprometer
tudo aqui. Isso permitiria? Foi uma
longa jornada neste vídeo. A mensagem de confirmação será estilizada, todo
o aplicativo
usará componentes estilizados. Incrível. No próximo vídeo, adicionaremos algumas coisas
de estilo
menor, digamos , ao aplicativo. Para torná-lo ainda
mais interativo, isso vai ser
interessante. Nos vemos lá.
87. 31 Estilando o aplicativo p3: Olá, parabéns por
estilizar todo o aplicativo. Agora temos tudo pronto. No entanto, podemos
melhorar algumas partes, para que fique um pouco
melhor, na minha opinião. Em primeiro lugar, a primeira coisa gostaria de mencionar é que, sempre que procuramos cartas, elas simplesmente aparecem em nós. Não seria bom fornecer alguma animação quando
esses itens aparecessem, por exemplo, animação fade-in. No registro do NPM, você pode encontrar esse pacote
chamado react fade in, que é apenas um componente
que você importa. Você o especifica da mesma forma
que usamos componentes estilizados. Muito parecido
com isso e, em seguida, fornece animação para
seus elementos infantis. Eles desaparecem e
desaparecem com o atraso. Este pacote é
muito simples de usar, no entanto, ainda é um pacote. Quero dizer que, para um caso de uso tão
simples, talvez não
precisemos de nenhum pacote. Você pode simplesmente
instalá-lo e não pensar em escrever nenhum CSS, mas menos pacotes você tem, melhor porque ele tem menos
dependências em seu aplicativo. Primeiro, eu queria
usar esse pacote, mas depois decidi que
podemos realmente escrever apenas uma marcação CSS muito pequena que obterá um efeito
muito semelhante. Se voltarmos à essência aqui,
estilizando a parte de três pontos do arquivo MD, aqui você pode descobrir que, digamos, uma grade de bandeiras aprimorada
que já temos dentro da grade flexível
comum jsx com esta
animação e quadros-chave. Deixe-me copiar tudo isso
e substituí-lo. Agora, sempre que
um componente de grade flexível for montado, ele terá essa animação
de desvanecimento, conforme definido por esses quadros-chave. Isso apenas aumentará a
capacidade de zero para um e obteremos um efeito
muito semelhante ao react fading, mas sem demora. Vamos tentar ver. Agora, sempre que
procuro atores ou programas, assim como sempre que uso
o componente de grade flexível em algum lugar, você verá esse desvanecimento na
animação em jogo, seja para shows ,
seja para atores, seja na página inicial. Efeito muito semelhante, mas
sem qualquer dependência. Você também deve considerar
que, no futuro, quando for
instalar algo do npm, primeiro faça uma pergunta a si mesmo. Você realmente precisa dessa dependência ou
pode fazer isso sozinho? Isso é muito importante
quando você vai
trabalhar em projetos reais. Ótimo. Agora, a próxima coisa que eu
gostaria de acrescentar é que, sempre que começamos
um show, agora, nossa estrela que temos
aqui fica amarela. Isso não é ruim, mas podemos torná-lo mais fácil de usar e fornecer, digamos
,
uma animação quando começamos com um botão, quando
iniciamos
o programa, a estrela, na verdade, digamos que de
alguma forma esteja sendo animada. Se voltarmos a isso aqui, também
podemos encontrar isso
na terceira parte do MD, que mostra a placa JSX com componente
aprimorado no
estilo StarBtn. Vamos aos shows, mostre o cartão. Aqui temos aquele StarBTN,
se compararmos. Aqui definimos outra classe chamada Animate e
temos algo novo aqui. Vamos copiá-lo e
inspecionar o que temos. Em primeiro lugar, definimos
essa classe animada, que também tem
animação conforme definida por esses quadros-chave, mas também
temos aqui essa
interpolação e
temos o ícone de estrela
aqui, o que ela faz. Você sabe que dentro
da marcação CSS, dentro do componente estilizado,
podemos especificar, semelhante ao SAS, o aninhamento de elementos. Aqui, eu interpolei ícone
Iniciar e isso
significa que tudo o que eu interpolou aqui
realmente se resolverá para componentes de estilo
existentes
como equipamento de referência. Dentro dessa classe animada, sempre que esse elemento
StarBtn tem classe animada, dentro desse elemento StarBtn, deslocamos nosso ícone. Sempre que houver StarBtn, terá uma classe ativa, terá uma classe animada,
por favor, estilize o componente de
ícone de estrela, que é usado dentro dele. Dessa forma, podemos resolver
iniciar especificamente o estilo do ícone. Esse elemento, sempre que
StarBtn tem alguma classe. Vamos tentar ver. Gostaríamos de animar o
nome da classe do componente
StarBtn sempre que o
programa estiver sendo iniciado. O que só vai especificar
, por favor, quando o show começar, anexe a classe animate. Vamos tentar ver. Vamos voltar ao
nosso aplicativo e você acabou de ver aquela animação. Sempre que clico no programa, agora ele está aumentando e diminuindo de tamanho. Funciona. Parece bom até agora, mas se formos para a página inicial
e eu atualizar a página você ainda verá a mesma animação e
eu não fiz nada. Isso ocorre porque quando
o componente é montado, essa classe animada está
sendo adicionada porque nosso show já começou
e vemos a animação. Isso não é ruim, mas esse não é exatamente o comportamento
que queremos alcançar. Só queremos executar a animação quando
o componente foi
realmente iniciado, não quando o componente
está sendo montado. Para alcançar o resultado que
queremos, vamos
introduzir um novo gancho chamado use ref. O que é isso? Em primeiro lugar, vamos
importá-lo do React. Esse é um dos ganchos
integrados que você precisará durante sua
futura carreira de desenvolvedor. O que é esse gancho? Use ref é apenas um gancho
que você chama assim e esse gancho retorna
uma referência. Uma referência que
você especifica
ou, digamos, associa
essa referência a algum elemento. Vamos tentar ver. Por exemplo, queremos dar uma referência a
esse StarBtn. Vamos chamar essa referência de
StarBtn ref, sem mais nem menos. Agora, para
associarmos essa referência, acabamos de chamar o gancho, obtivemos nossa variável de referência starBtn, mas ela ainda não está
associada a nenhum desses elementos. Para fazer isso,
precisamos passar para starBtn, um prop, na verdade um atributo
chamado ref e para essa ref, especificamos, starBtn ref. Você pode simplesmente passar ref para seus
componentes personalizados, digamos. Se eu tiver isso, deixe-me ver, por exemplo, o título do
aplicativo que eu uso
dentro do layout principal Não
posso simplesmente passar ref e
depois especificar outra coisa. A referência está sendo passada somente para elementos HTML nativos
subjacentes. Se você quiser passar
a referência para seus componentes personalizados, ela deve ser tratada adequadamente, e falaremos
sobre isso no futuro. Mas, por enquanto,
vamos
nos limitar aos elementos nativos, já que StarBtn é basicamente
apenas um elemento HTML nativo, porque, no fundo, ainda
é apenas um botão. É um componente criado pela biblioteca de componentes
estilizados e trata as referências adequadamente. Basicamente, o que quer que
passemos aqui, seremos redirecionados para o elemento nativo
HTML do botão
subjacente. Passamos ref como starBtnRef. Agora, o que podemos fazer com isso? Por que faríamos isso? Vamos tentar refatorar manipulador onClick aqui
que passamos para starBtn. Em vez de passar uma função
que chama onStarmeClick, vamos criar uma função chamada handleStarClick que
vamos criar aqui. HandleStarClick inside,
que chamará OnStarmeClick
e passará o ID para dentro. Mas também, vamos registrar o
StarBtnRef no console e
ver o que temos. Se abrirmos um console, sempre que eu clicar aqui, veremos o objeto com apenas uma propriedade
chamada atual. Sempre que você cria uma
referência como essa, você sempre tem um
objeto, não importa o que aconteça, com a chave atual. Você pode ver que a propriedade
atual aponta para o elemento do botão, para o elemento HTML chamado botão, não chamado de botão 2, apenas o elemento do botão
subjacente. Na verdade, isso é equivalente a escrever document.getElementById,
por exemplo. Quando você pega algum
elemento por ID, isso é o equivalente. No React, sempre que
você precisar acessar o elemento subjacente
diretamente com a API DOM, em vez de usar
document.getElementById, document.getElementByClassName,
por outra coisa, você usaria referências
e, em seguida, usaria starbtnRef.current e, em
seguida, obteria seu elemento. Eu o salvo, StarBtnRef.current. Novamente, clico no botão, você verá que agora eu
tenho esse elemento, o que significa que posso
usar o que eu quiser aqui e brincar com
ele usando a API DOM. Mas é importante
associar elementos
e passar a referência. Porque se eu não fizer isso, minha referência ficará vazia. Deixe-me tentar ver. Eu atualizo a página. Eu clico, agora meu starBtnRef.current me
dá indefinido porque agora minha
referência está vazia. Não estava
associado a nada. Sempre que você usar ref, não
esqueça de passar
o atributo ref. Como agora temos
StarBtnRef.current apontando para o elemento
DOM subjacente, podemos usar a API DOM para
manipular nossa lista de nomes de classe. Aqui, vou
criar uma variável chamada,
digamos, starBtnElement. Será starBtnRef.current. Em primeiro lugar, nossa
corrente, como você acabou de ver, pode ser indefinida, então vamos
fazer uma verificação segura aqui. Se starBtnRef.element for falso, saia dessa função. Caso contrário,
continuamos e dizemos que, se o programa for estrelado, nesse caso,
faça o seguinte. Acabei de notar que se chama
início em vez de estrela. Deixe-me renomeá-lo
para StarBtnElement. starbtnElement.classList.remove (animado).
Caso contrário, chamamos
star.btnElement.classList.add (animate). Em primeiro lugar, a lógica
não se encaixa aqui. Em primeiro lugar, vamos
ver se isso funciona e depois
vamos discutir isso. Sempre que clico, você
pode ver que meu programa está sendo estrelado e eu
vejo a animação somente quando clico aqui. Mas se eu voltar a estrelar, ainda
tenho aquela animação. Isso ocorre porque eu uso
esse className aqui. Deixe-me removê-lo. Agora vamos tentar ver. Nenhuma animação é executada no momento. Deixe-me voltar para a página inicial. Mas quando estou tentando
estrelar o programa, você pode ver que a
animação está lá. Por que usamos essa lógica aqui? Quando essa função for executada, isStarred ainda estará
no estado anterior. Basta lê-lo, pois o
código está escrito aqui. Nosso programa está atualmente estrelado. Quando clicamos nele, não
queremos
rodar nenhuma animação. Quando nosso programa está atualmente
estrelado e quando o
desestrelamos, removemos a classe animate. Não queríamos rodar
nenhuma animação aqui. Mas se nosso programa
atualmente não é estrelado, essa outra condição dispara. Nesse caso, adicionamos a classe animate para
fornecer a animação. Dessa forma, usando a API DOM, usando o arco useRef, podemos manipular nomes de
classes diretamente,
digamos, usando imperativamente
a API DOM em vez de usar a interface className
que o React nos fornece. Assim, podemos
adicionar animação e conhecemos o novo
gancho chamado UseRef. Novamente, para resumir rapidamente, useRef pode ser usado
como referência para elementos HTML nativos
subjacentes, caso você queira obter acesso
à interface DOM desse
elemento, algo assim. Vamos adicionar tudo ao
palco e nos comprometer. Primeiro, na verdade, não
usamos o pacote React Fade-In. Usamos nosso CSS simples para obter um efeito de
fade-in muito semelhante. Então, em vez de usar apenas className para fornecer animação para o elemento estrela, usamos o gancho useRef para obter acesso ao elemento DOM
subjacente. Em seguida, usamos essa API DOM, propriedade classList do elemento
DOM para adicionar e remover a classe animate de forma imperativa para adicionar ou remover a animação, que é definida dentro de
nosso componente estilizado. Agora, podemos confirmar isso e dizer, adicionar animação ao FlexGrid. Digamos que adicionou
animação fade-in ao FlexGrid. Adicionou animação StarBtn
ou, digamos, adicionou
animação em escala ao StarBtn. Incrível. É isso por enquanto. Eu vou te ver
na próxima.
88. 32 implantação para o Github Pages: Olá. Neste vídeo, finalmente implantaremos o Box Office,
então, no final, teremos um URL disponível
publicamente que podemos compartilhar com nossos amigos. No projeto anterior, no Tic Tac Toe, usamos um serviço
chamado Search.SH, desta vez vamos
tentar algo novo. A hospedagem que
vamos usar será o GitHub Pages. Por que GitHub Pages e não Search? Em primeiro lugar, eles
são muito parecidos, ambos são usados para
hospedar arquivos estáticos, mas
queremos explorar , experimentar coisas novas, queremos ver alternativas. No final, você poderá
comparar o que você mais gosta, GitHub Pages ou o Search, ou talvez até
algo mais. Vamos embora. Em primeiro lugar,
vamos navegar até a documentação do
Create React App. Se clicarmos em “Começar”, à
esquerda, podemos procurar
a seção de implantações. Dentro da seção de implantação podemos procurar o GitHub Pages. O que
vamos fazer é seguir esse simples tutorial
passo-a-passo. A primeira coisa que ele nos
pede é abrir package.json e adicionar o campo da página inicial para
o seu projeto. Vamos fazer isso. Vou apenas copiar a página inicial, abrir package.json,
em qualquer lugar do package.json
vamos adicionar a página inicial. Mas aqui precisamos
mudar algumas coisas. Em primeiro lugar, meu
nome de usuário.github.io. Meu nome de usuário deve ser
substituído pelo seu nome de usuário no GitHub. Vou pegar o meu. Meu aplicativo precisa ser
substituído pelo nome do seu repositório no GitHub. No meu caso,
será box-office-app. Eventualmente, o URL para
mim ficará assim. Muito parecido, deve
ser para você também. Eu salvo package.json, volto ao tutorial. Vamos ver a etapa número 2. Em seguida, precisamos instalar um
pacote chamado gh-pages
e, em seguida, adicionar um
script de implantação ao package.json. Vamos primeiro instalar
a dependência. Vou apenas copiar o comando. Vou parar meu aplicativo e, em seguida, executar o comando
de instalação. Durante a instalação, vamos ver o que precisamos para empacotar. json. Precisamos adicionar mais dois scripts, implantar e pré-implantar. Vamos copiá-los. Vamos voltar para package.json. Até agora, já temos
a dependência instalada. Vamos navegar até os scripts
e, no final, adicionar
pré-implantação e implantação. Não precisamos de nenhuma vantagem
que tenha sido copiada, salvamos e aqui o que vemos. Temos o script de implantação definido e, em seguida,
temos a pré-implantação. Digamos que o Npm seja inteligente
o suficiente para entender que pré-implantação deve ser executada
antes do script de implantação. Portanto, sempre que executarmos o script de implantação, o
predeploy será executado. Predeploy construirá o
aplicativo, a compilação do aplicativo será produzida na pasta build
e, em seguida, especificamos que implante a pasta
build aqui, para que a compilação que
você vê na linha 35 se refira a essa pasta de construção
dentro da raiz do nosso projeto. Então, se avançarmos
no tutorial, se você estiver implantando em uma página de usuário do
GitHub, observe que esse não é o nosso caso. terceira etapa é apenas
executar npm run deploy. Vamos tentar fazer isso. Agora podemos fazer npm run deploy. Vamos ver a saída. Primeiro, vemos o npm run build, vem do script de
pré-implantação, depois temos o gh-pages
menos o comando build, e agora diz publicado, mas não temos nenhum URL, onde precisamos ir? A página inicial que
especificamos em package.json é na verdade, a URL que precisamos visitar
para acessar nosso aplicativo. Vamos copiar esse URL. Vamos abri-lo em uma nova guia. Mas assim que navegarmos aqui, veremos
que não foi encontrado, é 404. Então, o que acontece? Vamos investigar. Se voltarmos ao
nosso repositório, aqui está uma coisa que eu
não mencionei anteriormente, é que o GitHub Pages
está disponível
gratuitamente apenas para
repositórios públicos. No meu caso, o
repositório é privado. Ele está marcado aqui no
canto superior esquerdo, Privado,
então, para usar o
GitHub Pages gratuitamente, preciso ter certeza de que
esse repositório é público. Vamos para Configurações
e, nas Configurações,
mudaremos a visibilidade
do
nosso repositório de privado para público. Vamos para a página de configurações, rolamos até o final
e, aqui, em Danger Zone, alteramos a visibilidade do repositório transformamos em público. Sim, eu quero tornar isso público. Sim, tenho certeza. Ele também pode solicitar sua senha, tudo bem. Agora meu repositório se tornou público. No entanto, se tentarmos
acessar o URL novamente, ele ainda será o
mesmo, não encontrado. Precisamos instruir a hospedagem, precisamos instruir o GitHub Pages de que
queremos publicar nosso aplicativo agora. Em primeiro lugar, como isso funciona? Se formos para a página principal
do repositório aqui, veremos duas
ramificações agora disponíveis. Anteriormente, era apenas um. No momento, se clicarmos
nessas duas ramificações,
veremos a ramificação gh-pages aqui. Se clicarmos nessa ramificação, você verá todos os arquivos que temos dentro
da pasta build. Basicamente, o
comando deploy aqui, o que ele fez, usou
aquela pasta build, criou uma nova ramificação
em nosso repositório e carregou todos os arquivos
da pasta build para a ramificação
gh-pages no GitHub. A forma como a hospedagem do GitHub
Pages funciona é que ela usa uma
de suas ramificações em seu repositório e todos os
arquivos que estão localizados aqui são hospedados nos servidores
do GitHub. Dessa forma, podemos
hospedar arquivos que estão localizados dentro do
nosso repositório. Para configurar corretamente o
GitHub Pages para direcionar a
hospedagem para essa ramificação específica do
gh-pages para esses arquivos, precisamos novamente acessar a página Configurações
do nosso repositório. À esquerda, procuramos a seção
Páginas, a página Páginas, e aqui especificamos que, ok, fonte para nossa implantação
será implantada a partir de uma ramificação. Por padrão,
isso é o que você
deve ter por enquanto
e, para a ramificação, você
especifica que hospede nossos arquivos
a partir da ramificação gh-pages. Clicamos em “Salvar” e logo após a
implantação ser acionada. Agora, levará
alguns minutos, um minuto ou dois para implantar
todos os seus arquivos
do gh-branch em seu
repositório para a hospedagem. Se formos para Ações aqui, aquela guia Ações em
seu repositório, aqui você verá agora
esse único fluxo de trabalho sendo executado. Se você clicar nele, verá o progresso
da sua implantação. Quando terminar, você
verá uma marca verde aqui, que significa que seu aplicativo será publicado aqui, sob esse URL. Vamos esperar até que esteja pronto e eu entrarei em contato com você. Agora parece que nosso
aplicativo foi implantado. Você pode ver que tudo está verde. Agora eu também tenho esse
URL que apareceu aqui. Se eu clicar nele, é
isso que eu vejo. Em primeiro lugar, meu
aplicativo,
como estava anteriormente,
está disponível na mesma URL que
você especificou na página inicial, chave
da página inicial dentro de package.json. Mas se o
acessarmos, veremos Não encontrado. Por que isso? O fato é que ele realmente foi implantado, mas por algum
motivo diz que não foi encontrado, e definitivamente
vem de nosso aplicativo, porque se inspecionarmos a marcação, isso se assemelha ao nosso aplicativo, o que temos dentro do
index.html, nosso esqueleto. Dentro do público,
temos esse esqueleto. É nosso. Temos
a mesma cabeça, temos tudo o mesmo. Mas o que aconteceu? O fato é que, se voltarmos ao tutorial
na documentação do Create
React App, ele terá essa nota chamada Notes,
sobre roteamento do lado do cliente. O problema é que
a hospedagem do GitHub
não está realmente configurada para lidar com aplicativos
do lado do cliente, para não lidar com aplicativos de página única que usam roteamento do lado do cliente. Na verdade, você pode ler
mais informações aqui dentro da
documentação oficial. Vamos usar
algo chamado HashRouter, do React Router. Essa é uma das
soluções fornecidas aqui. Vamos fazer isso. Voltamos ao aplicativo,
abrimos o código, App.jsx. Aqui usamos o BrowserRouter, que é importado do
React Router dom. Em vez disso, podemos
usar algo chamado HashRouter, e pronto. O resto estará no
React Router dom. Não precisaremos de etapas
extras para isso. Para entender o que ele
faz, vamos primeiro executar o servidor de desenvolvimento local
novamente, npm run start. Isso é o que temos agora. Em primeiro lugar, nosso aplicativo agora,
apesar de ser servido localmente, está disponível sob o prefixo
/box-office-app, qualquer prefixo que
especificamos na página inicial
do pacote JASON. Criar um aplicativo React é inteligente o suficiente para entender que podemos implantar sob o prefixo
do aplicativo de bilheteria. É por isso que é mantido aqui. Mas quando você serve
aplicativos sob prefixo, você precisa considerar
isso como sua URL base. O que quero dizer com isso, se procurarmos,
mostra, por exemplo, que
aqui, se passarmos o mouse em ler mais, vamos para a página
/show/show ID. Quando pudermos
hospedar no GitHub, nosso URL ficará
assim :
/box-office-app/show/show ID. Mas não
teremos esse prefixo, assim como temos
aqui no host local. Será problemático
porque, caso contrário, nossa página não será encontrada. O
que quero dizer com isso é que vamos primeiro implantar o aplicativo e
você mesmo o verá, e depois corrigiremos
isso com uma adição muito pequena
ao nosso código existente. Acabei de executar o script
de implantação novamente. Novamente, ele cria meu aplicativo e publica
novamente no
GitHub Pages. Se voltarmos ao repositório na
guia Ações, veremos novamente
outro fluxo de trabalho em execução. Nós apenas esperamos até que ele seja implantado e depois
vamos fazer o check-out. Está implantado agora. Vamos voltar ao aplicativo. Se voltarmos ao nosso aplicativo, ainda
veremos não encontrado. Mas se eu atualizar, agora temos o aplicativo. Parece perfeitamente bom. No entanto, se você olhar o URL, agora temos esse hash aqui. Ele será usado para lidar
adequadamente com roteamento
do lado do cliente quando
implantarmos no GitHub Pages. Mas ainda temos
mais um problema que
acabei de mencionar anteriormente
sobre o link, sobre esse botão Leia mais. Se eu clicar nesse botão, você verá que navegamos
até /show/show ID. Não temos o prefixo do aplicativo de
bilheteria
e, por
isso, temos 404. Para resolver o problema, precisamos primeiro
entender por que isso acontece. Vamos ler
mais e marcar. Serão componentes,
shows, cartões de exibição. Aqui, usamos uma tag
âncora simples que aponta para /show/show ID. Tudo bem e funcionará. Funcionará se
nosso aplicativo for servido sob a rota, não
sob o prefixo. Precisamos consertar isso de alguma forma. Uma solução ingênua é inserir manualmente qualquer
prefixo que você tenha aqui. Vai funcionar, mas essa não
é uma boa solução. Precisamos, de alguma forma resolver
automaticamente
qualquer prefixo que tenhamos aqui. React Router cuida disso. No passado, substituímos o
componente de link que usamos do React Router por
essa verificação de âncora porque realmente não
precisávamos desse componente de link. No entanto, agora vamos
recuperá-lo novamente. Vou importar o link
do React Router dom. Então, em vez da tag âncora, vou usar um link
novamente, mais uma vez. Em vez de href, vou especificar to e vou manter o alvo em branco e
os atributos de relacionamento. Dessa forma, ainda
teremos o mesmo link
de antes, mas desta vez o componente de
link do React Router dom
cuidará do prefixo. Ele será automaticamente
resolvido para o URL correto. Agora, vamos tentar executar
o script de implantação novamente, reimplantar o aplicativo e ver o resultado final. Te vejo assim
que for implantado. Eu esperei mais um minuto. Aqui está minha terceira implantação que acabou de ser publicada há
um minuto. Vou voltar ao meu aplicativo. Eu vou me refrescar. Eu procuro programas e agora,
se eu clicar em Leia mais, agora minha URL foi
resolvida corretamente porque agora era gerenciada
pela biblioteca React Router. Assim,
conseguimos implantar nosso aplicativo. Parabéns. Agora, vamos voltar ao nosso código e
confirmar tudo. Em primeiro lugar, instalamos biblioteca
gh pages
para implantar no GitHub Pages, o campo da página inicial
no pacote JSON especifica exatamente onde o
aplicativo será implantado. Novamente, implantamos a pasta
build que é produzida pelo comando npm
run build. Agora, também substituímos o roteador
do navegador pelo roteador de
hash porque o GitHub Pages
não lida adequadamente com hash porque o GitHub Pages o
roteamento do lado do cliente. Uma maneira de corrigir esse problema
é usar o roteador de hash conforme sugerido na documentação do aplicativo Create
React. Em seguida, também mudamos uma tag âncora simples
para o componente de link do React Router dom porque
precisamos resolver o prefixo depois que nosso aplicativo for
implantado no GitHub Pages. Vamos adicionar tudo ao estágio e vamos nos comprometer
e dizer implantar,
implantar o aplicativo
no GitHub Pages, usar o HashRouter, usar o link em vez da tag âncora nativa. Legal. Eu
coloco tudo para masterizar, volto ao meu
repositório para garantir que
tudo seja implantado. Minha última mudança,
10 segundos atrás. Eu tenho uma segunda filial
chamada gh pages. Sempre que você executa o npm run deploy, ele atualiza o GitHub Pages e atualiza os arquivos hospedados em sua URL que você pode usar
para compartilhar com seus amigos. Mais uma coisa simples que
eu acrescentaria aqui é que podemos realmente usar esse URL para onde nosso
aplicativo está. Vamos
visitá-lo mais uma vez. Sim, está realmente aqui. Podemos adicionar esse URL à nossa seção
Sobre na página do
repositório. Eu clico no sinal
de Configurações aqui. No site, adiciono o link e
clico em Salvar alterações. Agora, boom, aparece aqui. Isso é apenas para você
acessar facilmente seu aplicativo
no futuro. É isso por enquanto, nos
vemos na próxima.
89. 33 PWA (Progressive Web App): Olá de novo. No último vídeo, finalmente
implantamos a
bilheteria em um ambiente vivo. Desta vez, vamos
falar sobre trabalhadores de serviços. Como você se lembra,
no primeiro vídeo em que
criamos esse projeto, temos o prestador de
serviços, o registro do prestador de serviços,
assim como o
ponto
de registro do prestador de serviços no registro, e eu disse que falaremos
sobre isso mais tarde. Agora, essa é a hora. Esse prestador de serviços é necessário
para criar nosso aplicativo, para fazer bilheteria em um aplicativo web
progressivo. O que é um aplicativo web progressivo? Um aplicativo web progressivo é qualquer outro aplicativo
da web, qualquer outro site que
segue uma lista de itens
específicos e,
quando o
aplicativo DevUp do site preenche
essa lista de opções, esse site
se torna um aplicativo web progressivo. Isso significa que o aplicativo
fica disponível off-line. O aplicativo pode
ser instalado como aplicativo móvel real, esteja você no desktop
ou no dispositivo móvel. A questão aqui é:
quais são essas opções que tornam um site um aplicativo web
progressivo? No navegador Chrome, se você acessar as ferramentas de
desenvolvedor do Chrome, se expandir esta
seção à direita, poderá ir para a seção
farol. Lighthouse é uma
ferramenta embutida no navegador Chrome. Ele nos permite avaliar o desempenho
do site
medindo sua velocidade
, tempo de espera e algumas métricas
diferentes. Aqui, nas categorias, temos essa verificação progressiva de aplicativos da web. Vamos chegar lá e
clicar em Analisar carregamento de página e ver o
que vai acontecer. Levará apenas alguns
segundos até que ele audite o site e agora sabemos
que temos quase
tudo verde perfeito, mas não estamos realmente
interessados em nenhum deles. Se estiver, você pode facilmente
ir uma a uma, expandir seções diferentes e ler o que pode ser melhorado,
o que pode ser alterado. Talvez você não precise mudar nada, mas na parte inferior, você terá a seção PWA, um aplicativo web
progressivo. Uma lista de coisas que você
vê aqui é basicamente
o que o site precisa
seguir para se tornar um aplicativo
web progressivo. Em primeiro lugar, não
temos algumas coisas aqui. Nosso aplicativo
não é instalável,
portanto, para torná-lo instalável, precisamos apresentar
um service worker. O que é um prestador de serviços? Assistente de serviços, na verdade é mais fácil quando eu
vou visualizá-lo. Temos o site aqui. Nosso site aqui à esquerda. Então, à direita,
temos solicitações de saída. Simples assim. Talvez vamos inspecionar
isso nós mesmos, então vamos até a guia de rede e,
quando atualizamos a página, vemos uma lista de solicitações, então
este é nosso navegador que faz uma solicitação ao
servidor de páginas do GitHub para obter o índice HTML, para obter arquivos CSS JavaScript
do servidor de hospedagem. Um prestador de serviços
é apenas um script. Ele está dentro do navegador, em algum lugar dentro do navegador, fora do nosso agente de
serviços de aplicativos e, o que
faz, simplesmente intercepta
todas essas solicitações, solicitações de
saída e
faz algo com elas. No nosso caso, o service
worker será apenas um proxy que interceptará todas essas solicitações de saída
e as colocará no armazenamento em
cache dentro do navegador. Assim próxima vez que esses
arquivos forem acessados, em vez de
deixá-los passar, service worker
usará o armazenamento em cache recuperará todas
essas solicitações, todos os arquivos que
foram recuperados anteriormente
a partir do armazenamento em cache, e disponibilize-os em nossa página da web. Dessa forma,
nosso aplicativo pode ficar disponível off-line, que significa que qualquer solicitação
enviada, o
service worker a interceptará. Ele verificará o cache e se essas solicitações estiverem
presentes no cache, elas serão atendidas a partir do
cache pelo service worker. Para resumir rapidamente,
um service worker é apenas um script
em algum lugar dentro do navegador. É apenas um proxy
que intercepta solicitações de
saída do
navegador. Algo parecido. Se voltarmos ao
nosso aplicativo, veremos que temos o arquivo JS do service
worker aqui. Esse é o script em si, o próprio service worker, que será executado
dentro do navegador, fora do nosso aplicativo. Esse arquivo que você vê aqui
ficará em algum lugar
dentro do navegador. Mas a questão é: como podemos lidar com isso? Como podemos realmente fazer
algo com isso. Antes de podermos responder a
essa pergunta, temos uma caixa de trabalho aqui. O que são essas e, se
olharmos dentro do pacote Json, temos muitas dependências da
caixa de trabalho. Essas são basicamente
apenas bibliotecas que nos permitem, de alguma forma, escrever
facilmente alguma lógica
dentro do script do service worker. Você pode ver que esse script
foi gerado automaticamente
criando o aplicativo React e a
lógica escrita aqui simplesmente intercepta
todas as solicitações e as coloca no armazenamento em
cache. Nós realmente não precisamos
pensar muito nisso. Não vamos escrever nossa própria lógica para o
service worker aqui, vamos usar a lógica
existente
e será
suficiente armazenar
tudo em cache, e será
suficiente armazenar
tudo em cache e a caixa de palavras é apenas um conjunto de funções que
importamos e usamos
para conseguir isso. Como esse arquivo foi
gerado pelo aplicativo Create React, não
vamos modificá-lo, não
estamos interessados nele. Novamente, isso será suficiente. Agora também temos o registro de
prestador de serviços. Para que o navegador entenda que queremos de alguma forma usar
esse JS do service worker, precisamos registrá-lo dentro do navegador porque, se
quisermos
colocá-lo como parte de
nosso aplicativo, nada acontecerá, então precisamos alguma forma
registrar
esse service worker nosso aplicativo e esse registro do service worker
tem duas funções aqui. A primeira função
é chamada register, que foi
exportada daqui e segunda função é
chamada de unregister. Novamente, toda essa lógica é gerada automaticamente ao
criar o aplicativo React e será novamente
suficiente para nosso caso de uso. A função de registro
registrará o
JS do service worker quando nosso aplicativo executado e a
função de cancelamento de registro
cancelará o registro do
service worker
existente em nosso aplicativo. Se olharmos dentro do índice jsx, aqui inserimos tudo como prestador de serviços a
partir do registro do prestador
de serviços. Isso significa que objeto de
importação do registro do
service worker, temos duas funções, registrar e cancelar o registro
e, o tempo todo,
era realmente cancelar o registro para nós porque não estávamos
interessados no service worker. Para registrar
um prestador de serviços, precisamos chamar a função de
registro. No entanto, se você
for usar o registro, ele funcionará em ambos os ambientes quando você
for desenvolver localmente e quando for
implantado
ao vivo , digamos, na hospedagem de
páginas do GitHub. Mas como ele usará cache e a estratégia de cache
aqui é agressiva, isso significa que ele armazenará
tudo em cache , então o que
eu sugiro façamos é primeiro verificar se estamos atualmente no desenvolvimento
local, não queremos chamar essa função de
ponto e registro. Mas se estivermos dentro de um ambiente
ao vivo,
então, por favor, sim, chamamos
a função de registro. Como podemos verificar
isso e como podemos finalmente ver como isso funciona? Dentro do aplicativo, temos acesso a algo
chamado process.env. Esse é apenas um conjunto de variáveis de ambiente às
quais temos acesso. ambiente são
variáveis definidas
globalmente pelo ambiente
em que nosso código é executado. Vamos tentar o console
log process.env, e se eu digitar dot,
tenho intellisense aqui, tenho node ENV. Se eu passar o mouse, você pode
realmente ver que ele tem três valores potencialmente
diferentes:
desenvolvimento, produção e teste. Mas no nosso caso, ainda
vamos cancelar o registro para ver. Digamos que o ENV atual seja atual
e, por enquanto,
ainda cancelaremos o registro. Vou executar o servidor de
desenvolvimento local e também vou
corrigir esse problema não definido vindo do ESLint porque
o protesto é
algo executado no lado do node JS, não no JavaScript executado
dentro do navegador,
então precisamos deixar o ESLint entender que
também executamos dentro do ambiente
node.JS, não apenas dentro do
navegador. Node true, esse node
true, vamos deixar o ESLint entender que estamos dentro do
ambiente JS do node agora. Isso não fará nada , exceto que apenas
removerá esse erro. É isso. Eu executo meu aplicativo localmente. Se eu for ao console, vejo que o ENV atual
é igual ao desenvolvimento. O que vou executar o comando build aqui para
criar uma compilação de produção esse nó variável
ENV será definido no momento
da construção, então, quando usamos o servidor de desenvolvimento
local, isso é compilação de desenvolvimento. O aplicativo foi criado, mas logo abaixo do capô,
não vemos isso. É por isso que vemos o node ENV definido para desenvolvimento, porque esse é nosso desenvolvimento construído e, novamente, essa variável é definida
durante o tempo de construção. Quando
executarmos o comando build, nosso aplicativo terá o
node ENV definido para produção e podemos
realmente usar essa variável para registrar ou cancelar
o registro do service worker. Vamos tentar fazer
isso. adicionar uma condição simples aqui. Se process.env.node
ENV for igual a produção,
nesse caso, ligue para registro de
prestador de serviços e registre-se. Legal. Agora, vamos tentar
reimplantar o aplicativo. Depois de implantado, veremos como
tudo mudou. vejo lá em um
segundo. Olá de novo. Agora nosso aplicativo está implantado. Meu primeiro
fluxo de trabalho de implantação aqui. Agora voltamos ao
nosso aplicativo
e, se o atualizarmos, agora algo foi alterado. Em primeiro lugar, temos
esse ícone de instalação aqui
na barra de pesquisa, mas vamos
tocá-lo em um segundo. Estamos interessados na guia
Aplicativo aqui. Se formos para a seção Service
Worker aqui, agora temos service-worker.js. Este service-worker.js
foi novamente registrado por função de registro
que é importada do arquivo
ServiceWorkerRegistration. Essa é a função de
registro, acesse
"service-worker.js”, que está disponível no
box-office-apps/service-worker.js. É o registro, aquele
service worker dentro do navegador quando nosso
aplicativo foi acessado e agora esse service
worker está em execução, o que significa que agora o service
worker está ativo e intercepta todas as
solicitações
enviadas e as armazena em cache
dentro do navegador. Você pode ver que, se
eu atualizá-lo novamente, meus arquivos, por exemplo, aquele índice HTML, serão fornecidos pelo ServiceWorker, assim como o resto
dos arquivos aqui. Deixe-me “Esvaziar o cache e recarregar com
força”. Faça isso de novo. Na verdade, nada mudou,
mas ainda assim o aplicativo está sendo servido
pelo ServiceWorker. Se eu não estiver errado, está em algum lugar dentro do armazenamento em
cache aqui. Você pode vê-lo
na seção de cache
na guia Aplicativo. Em Armazenamento em cache, agora você
vê onde a caixa pré-armazena os arquivos que estão sendo
armazenados dentro do cache. Assim, podemos
administrar o Farol. Comande novamente e veja
o que temos até
agora para uma lista de verificação progressiva de
aplicativos web. Vamos embora. Estamos auditando meu aplicativo. apenas alguns segundos, vamos até o final e agora vemos que o aplicativo web
progressivo
agora pode ser instalado e
não está realmente otimizado. Bem, na verdade está otimizado, mas só temos um ponto aqui. Manifest não
tem um ícone mascarável, mas vamos corrigir isso
no próximo vídeo, quando vamos
personalizar o ícone, o nome do nosso aplicativo e o resto de
algumas coisas. Por enquanto, podemos ver que nosso
aplicativo é instalável. Nesse ícone que vemos aqui
no canto superior
da barra de pesquisa, podemos clicar nele
e instalar nosso aplicativo como se
fosse um aplicativo nativo. Se você estivesse em um dispositivo móvel, você também teria o
pop-up ao acessar seu aplicativo
para um dispositivo móvel. Você verá o
pop-up de que, Ei, você pode realmente instalar este
site como um aplicativo. Se você clicar em
“Instalar”,
o site será adicionado à sua tela inicial como se fosse um aplicativo
nativo. Agora, se eu voltar para o meu desktop, aqui, tenho esse aplicativo chamado
Create React App Sample. No momento, ele tem esse nome estranho porque é
o que está especificado arquivo de manifesto que vamos personalizar
no próximo vídeo. Mas o fato é que agora isso é um aplicativo,
é instalável. Se eu clicar nele, você pode ver que agora ele
não abre dentro de um navegador. Ele se abre dentro de sua própria janela como se fosse um aplicativo
real nativo. Funcionará muito bem
, como funcionava
anteriormente. Muito legal. Você pode ver que ele realmente abriu aquela nova guia dentro do navegador. Esse é o problema dos aplicativos web
progressivos. Idealmente, você não deve abrir
nada dentro de novas guias, mas deve usar a guia
atual e usar apenas,
digamos, uma página para navegação
sem usar novas guias. Mesmo assim, agora temos o aplicativo que
é executado como um aplicativo nativo. Tudo isso foi conseguido
usando o ServiceWorker, que nos deu a lista de verificação
verde para aplicativos web progressivos. Resumindo, um aplicativo web
progressivo é apenas um aplicativo da web, que segue uma
lista específica de itens. Por exemplo, ele deve
ter um service worker, o aplicativo deve
usar algum cache para que possa estar disponível offline. Então, ele também deve ser
servido a partir de HTTPS e algumas outras coisas que você
pode encontrar dentro do Lighthouse. Vamos tentar ver novamente. O que mais temos aqui? Várias guias estão sendo abertas. Deixe-me atualizá-lo.
O que você quer? Analise o carregamento da página. Vamos
ver rapidamente a lista novamente. Dentro da lista, temos, deixe-me ver, a cor do tema, tela inicial personalizada
configurada, o ícone de toque, aquela tag específica da janela de
visualização e aquele manifesto que
cuidaremos em breve, prestador
de serviços. Todas essas
coisas tornam um site, aplicativo web
progressivo,
tão simples quanto isso. Mais uma vez, o
service worker que foi registrado como proxy dentro do navegador para
interceptar a solicitação é o cerne de tudo isso. Somente porque, como prestadores de serviços, conseguimos obter essa seção
instalável aqui. Nosso aplicativo agora se tornou instalável e também está disponível offline. Acho que ficou bem claro o que exatamente é um aplicativo web
progressivo, o que é service worker e como tudo funciona
aproximadamente. Por fim, vamos voltar ao nosso aplicativo e confirmar
as alterações que fizemos. Primeiro, editamos o Eslintrc, para que possamos usar
o process.env sem nenhum aviso ou
erro, e verificamos. Se estivermos na fase de construção, use
ServiceWorkerRegistration.register. Isso registrará esse arquivo
service-worker.js
dentro do contexto do navegador. Legal. Vamos fazer
essas mudanças. Habilite o prestador de serviços
no ambiente de produção. Eu atualizo meu repositório do GitHub e pronto por enquanto. No próximo vídeo, vamos lidar com o problema
que
vimos no Lighthouse, então ele ficará 100%
verde. Te vejo lá.
90. 34 Corrigindo URL base para resolver imagens corretamente no Github Pages: Olá. No último vídeo, criamos aquele ótimo aplicativo web
progressivo chamado Box Office. Mas aqui está um problema que
eu realmente esqueci e
é novamente sobre o
URL base dentro do nosso aplicativo. Se você percebeu quando procura programas
específicos e quando
eles não têm uma imagem, tentamos exibir essa imagem
não encontrada em PNG. No entanto, todos os nossos
arquivos são exibidos sob o prefixo do aplicativo Box Office
na hospedagem do GitHub Pages. Mas essa imagem não carregada porque
você pode ver que ela é sempre 404 porque ela não existe no caminho que
tentamos carregar. Não especificamos o prefixo. Como podemos realmente consertar isso? Se voltarmos ao nosso aplicativo e procurarmos uma imagem não encontrada, especificaremos exatamente assim. Apenas um caminho estático específico. Mas, como temos o prefixo, precisamos
entendê-lo de alguma forma. Uma maneira de corrigir
isso é, em vez de usar
a imagem dentro da pasta pública, podemos colocá-la dentro da pasta de origem e
usá-la como se fosse,
digamos, um módulo. Em seguida, ele será processado pela configuração
subjacente do Webpack e o caminho base será resolvido
automaticamente. A mesma
coisa que fizemos com tag
âncora e o componente de
link. Bem, pelo menos a
ideia é a mesma. Vou apenas mover a imagem não
encontrada para algum lugar,
digamos, para a pasta da biblioteca, imagem
não encontrada PNG. Agora, em vez de referenciar PNG de imagem
não encontrada em todos os lugares, vou apenas importar imagem não
encontrada da biblioteca, imagem
não encontrada PNG. Talvez eu a nomeie como fonte de imagem não
encontrada e vou especificá-la assim. Em seguida, copiarei essa importação e farei a mesma importação em todos os lugares. Aqui, isso é o que eu também
acabei de fazer no elenco interno. Aqui, deixe-me ver
o caminho correto. Voltamos para uma pasta, segunda pasta, biblioteca, imagem PNG
não encontrada. Especificamos a fonte da imagem não
encontrada, o mesmo que faremos
dentro da grade de exibição. Importe a fonte
de imagem não encontrada de. Voltamos novamente, voltamos à biblioteca, imagem
não encontrada PNG, fonte
não encontrada e o mesmo. Por fim, faremos isso
dentro do ShowMainData. Fonte de imagem não encontrada na biblioteca, imagem PNG
não encontrada. Agora, vamos tentar
reimplantar o aplicativo e ver exatamente como isso se
refletirá
em nosso código final. Nos vemos em um minuto
assim que esse código for implantado. Agora, o aplicativo foi implantado
com sucesso. Vamos voltar ao nosso aplicativo. Agora, vamos atualizar a página. Nossa última pesquisa foi “Olá”. Nós o procuramos novamente. Desta vez, também vemos que
não foi encontrado. Por que isso? O problema é que
nossa imagem agora, nossa imagem anterior,
é veiculada pelo Service Worker. Não foi atualizado. Ele é servido a partir do cache, o que significa que precisamos limpar o cache para ver as atualizações. Vou clicar com o botão direito do mouse
no botão Atualizar
no canto superior esquerdo e clicar em “Esvaziar cache” e
“Hard Reload”. Como alternativa, posso ir
até a guia Aplicativo, acessar Armazenamento e clicar em “Limpar dados
do site”. Isso limpará todo
o cache dentro do navegador especificamente
para este site. Deixe-me clicar em
“Limpar dados do site”. Então eu apenas refresco. Então eu procuro por “Olá”. Desta vez, nosso aplicativo
foi resolvido com sucesso. Você pode ver que, em vez
do URL real, vemos essa
imagem de dados de base 64. O que é isso? Novamente, como nossa imagem foi trazida até nós pelo aplicativo
Create React, a
configuração subjacente do Webpack cuidou disso. Dentro da documentação do
aplicativo Create React, foi mencionado em algum lugar
que, se a imagem tiver um tamanho menor do que o limite
específico, em vez de, digamos, processar o arquivo e servir o arquivo dentro
da pasta pública. A imagem é convertida para formato
base 64 e, em seguida
,
digamos que, em linha, essa sequência longa
represente nossa imagem, não como um arquivo, mas como uma string. Muito legal. Agora tudo
parece bom até agora. No próximo vídeo, conforme prometido, daremos um toque final ao
aplicativo. Vamos usar
ícones personalizados, nomes personalizados, para que nosso aplicativo seja
perfeito. Nos vemos lá.
91. 35 toque final: Olá. Neste vídeo, finalmente
daremos um toque final em
nosso aplicativo. Vamos criar ícones, vamos mudar os títulos para que o aplicativo seja
finalmente perfeito. Vamos embora. Mas antes de fazermos isso, vamos realmente
confirmar as mudanças que fizemos no vídeo anterior. No vídeo anterior,
como você se lembra, resolvemos nosso problema com a imagem. Vamos adicionar tudo rapidamente ao palco e, em seguida, confirmar
tudo dizendo que imagem não encontrada foi
movida
do público ou simplesmente mover a imagem
não encontrada para a
fonte e
importá-la em vez de vê-la
da pasta pública. Muito longo, mas vale a pena. Então eu
pressiono tudo para dominar e finalmente vamos
voltar aos nossos ícones. Em primeiro lugar, precisamos
escolher um ícone que usaremos
dentro da guia aqui. Se voltarmos para o convidado
que temos para a bilheteria, aqui temos esse ícone de dinheiro
que preparei para nós. Podemos simplesmente baixar
esse ícone aqui. Vou colocá-lo
na pasta Downloads. Em seguida, precisamos gerar
um conjunto de ícones que
vamos colocar
na pasta pública. No momento, temos esses ícones básicos de reação
que agora podemos substituir, mas primeiro precisamos
gerar esse conjunto de ícones. Normalmente, o que você faria é primeiro decidir sobre um ícone
que deseja usar. Pode ser seu, por exemplo. Não é obrigatório
usar esse específico. Se você tiver o seu,
fique à vontade para usá-lo. Nós vamos para Resources.md. Aqui na parte inferior, podemos encontrar esse gerador de favicon
que deixei para nós. Nós vamos para essa página. Clicamos aqui, carregamos
a imagem que
queremos que seja usada para o conjunto de
ícones. Nós baixamos. Dentro da pasta Downloads, agora temos esse favicon_io. Está em arquivo. Agora eu vou
extrair tudo para uma pasta. Esse é o conjunto de ícones
que eu eventualmente tenho. Não vamos
usar tudo isso. Vamos reutilizar
aqueles que
já estão presentes
na pasta pública. Eu só vou abrir
essa pasta pública aqui. Em vez do logo192 do React, vou usar
apenas o que tenho aqui. Eu copio isso. Eu mudo o nome. Eu excluo o anterior. Eu renomeio este. Então, o mesmo
farei com este logotipo. Eu o excluo. Eu movo
aquele aqui do mesmo tamanho. Eu lhe dou o mesmo nome. O Favicon será
completamente substituído. É isso. Tudo está pronto agora. Se formos para manifest.json, aqui fazemos referência a
todos esses ícones. Esses ícones serão usados quando seu aplicativo estiver sendo
instalado na tela inicial. O que quer que você especifique aqui, esse arquivo de manifesto instruirá Progressive Web App a
usar essas informações. Por exemplo, se aqui
especificarmos o aplicativo React
como um nome curto, isso é o que os usuários
verão quando adicionarem seu aplicativo
na tela inicial. Não temos um nome
longo para nosso aplicativo. Vamos
usar Box Office nome
abreviado e Box
Office para nome normal. Os ícones permanecem aqui, mas se voltarmos ao nosso aplicativo
e nos lembrarmos nossa corrida anterior para o Lighthouse, tivemos esse problema
com o ícone mascarável. Vamos ver mais uma vez
o que exatamente tínhamos lá. Novamente, eu executo o Lighthouse outdate. Demora
alguns segundos aqui. Vamos até o final e vemos que nosso aplicativo
pode ser instalado. Está tudo bem,
mas não temos um ícone mascarável. Nós vamos aqui. Você leu sobre ícones
mascaráveis aqui. Esse é um novo formato. Basicamente, precisamos apenas adicionar outro ícone ao
manifest.json e especificar que ele terá a
finalidade de ícone mascarável. Podemos usar esse
editor Maskable.app para converter um
ícone existente em um ícone mascarável. Talvez vamos fazer isso rapidamente. No canto direito, clico no botão Carregar, especifico nosso ícone. Agora, parece assim, mas eu queria ter, digamos, um fundo branco, para que nosso ícone mascarável
ficasse assim. Legal. Este será
nosso ícone mascarável. Isso resolverá nosso problema com esta lista de verificação
no Lighthouse. Clicamos em Exportar. Digamos que será o tamanho máximo. Nós baixamos. Mostrar na pasta. Este será um
ícone mascarável que vamos
colocar na pasta pública. Eu o movo para cá e agora precisamos especificar
esse ícone mascarável. Este está dentro do meu manifest.json e diga
que maskable_icon.png, os nomes devem corresponder, será do tipo, deixe-me ver. Onde está? Onde estão essas informações
sobre ícones mascaráveis? Aqui. Ele terá um
propósito mascarável. Voltamos aqui, especificamos um propósito mascarável. Nós economizamos. É isso. Agora nosso aplicativo ficará
incrivelmente bom em qualquer lugar, com nossos próprios títulos, com nossos próprios ícones. Vamos implantar tudo novamente. Espere, desculpe-me. Eu segui o
caminho errado. Eu queria implantar
tudo no início. Npm run deploy. Agora, vamos esperar
alguns minutos e nos vemos assim que o
aplicativo for implantado. O aplicativo foi implantado
com sucesso. Vamos voltar ao aplicativo
e ver o resultado final. Antes de fazer isso, antes de atualizarmos
a página,
vamos limpar o armazenamento
novamente para
limpar todos os caches,
tudo o que salvamos
dentro do navegador,
esvaziar o cache e atualizar. Agora, você pode ver que temos nosso ícone personalizado
aqui, títulos personalizados. Tudo agora é usado conforme
especificamos dentro do arquivo de manifesto. Na verdade, você pode clicar na guia
do aplicativo aqui no Manifesto e ver informações
diferentes
sobre sua inscrição. Agora, vamos ver como ficará quando
for adicionado
à tela inicial. Em um dos vídeos anteriores, quando adicionamos um dos funcionários
do serviço, quando o registramos, adicionamos nosso aplicativo
à tela inicial. No entanto, você pode ver
que não foi atualizado aqui. Na verdade, vamos executá-lo e primeiro, vamos desinstalá-lo
e instalá-lo novamente. O que eu vou fazer é clicar em
três pontos aqui. Clique em Desinstalar Create
React App Sample. Verifique a marca. Também
limpe os dados do Chrome. Agora desapareceu. Voltarei ao meu aplicativo
dentro do navegador e o
instalarei mais uma vez. Instale o Box Office. Instalar. Agora, boom. Eu volto para minha tela
inicial novamente, no meu caso é desktop. Agora eu tenho meu aplicativo Box
Office, que se parece com qualquer
outro aplicativo no meu computador. Se eu clicar nele, ainda
teremos tudo igual. Eu diria que é isso. Agora vocês criam esse aplicativo incrível
que funciona offline, que é instalável,
que funciona com os diferentes dados
dinâmicos das APIs. Você aprendeu muitos conceitos. Eu diria que você
aumentou significativamente seu
conhecimento sobre React com este, mas agora é isso. Mas antes de terminarmos este, vamos realmente confirmar todos os
nossos ícones que adicionamos. Vou adicionar
tudo ao palco. Eu vou cometer tudo. Digamos que adicionou ícones personalizados
e atualizou o manifest.json. Vamos enviar tudo para
a ramificação master para que
as alterações sejam refletidas no
repositório do GitHub. É isso. Parabéns por isso. No próximo vídeo,
vamos resumir
exatamente o que aprendemos com a
bilheteria. Te vejo lá.
92. 36 resumo: Ei, sim. Neste vídeo, vamos resumir
tudo o que
aprendemos até agora no Box Office. Agora temos esse incrível aplicativo web
progressivo, que funciona offline, que é instalável,
que funciona com API, e parece
muito legal, não é? Talvez vejamos
nosso histórico de confirmações e examinemos isso rapidamente. Em primeiro lugar, como uma ferramenta,
digamos, como um padrão
para criar bilheteria,
usamos o Create React App, que usa a configuração subjacente do
web pack, que consumimos usando
o pacote react-scripts. Agora você sabe o que
são react-scripts. Agora você sabe o que é o
Create React App, o que significa que você sabe como trabalhar com o Create React Boilerplate. Também usamos
Prettier e ESLint, mas isso não é algo novo. Você já conhece essas
ferramentas. Vamos ver. Aprendemos sobre o React
Router porque, como você sabe, por padrão e pelo react, não
temos nenhuma solução
embutida para roteamento dentro de
nosso aplicativo. O React tem tudo a ver com renderização, mas não se trata
de uma navegação tão simples assim. É por isso que usamos uma biblioteca chamada React Router para obter navegação dentro de nosso
aplicativo. Vamos ver. Depois do React Router, adicionamos funções diferentes
para trabalhar com dados dinâmicos, para trabalhar com API. Usamos uma API de navegador embutida chamada “Fetch”. Para buscar
dados da API, chamada “Fetch”. Para buscar
dados da API,
criamos muitas funções
reutilizáveis que
usamos em nosso aplicativo, e elas parecem muito simples. Lidamos com todos os possíveis adicionadores dentro dos componentes, caso
algo dê errado, lidamos com os erros
adequadamente usando blocos
try-catch
dentro de nossos componentes. Também soubemos que, se
quisermos buscar dados quando
o componente é montado, quando fazemos algumas
interações na página, em vez de usar
“useEffect”, podemos usar uma biblioteca de busca de dados. No nosso caso,
conhecemos a biblioteca React Query, que nos ajuda a consultar
dados quando o componente montado ou quando realizamos
pesquisas na página. Agora você sabe sobre bibliotecas de
busca de dados. Bibliotecas de busca de dados são uma ótima opção em aplicativos React modernos. Há uma
maneira recomendada de trabalhar com dados porque, à medida que seu
aplicativo cresce, você terá mais
e mais requisitos. As bibliotecas de busca de dados nos ajudarão a gerenciar tudo isso com facilidade. Agora que também
mencionei “useEffect”, agora
você sabe o que
“useEffect” faz, “useEffect” nos permite executar alguma função de efeito colateral Quando algo dentro do
componente muda, temos uma matriz de dependências
dentro de useEffect. Deixe-me encontrá-lo aqui no código. Temos uma série de
dependências aqui, e quando algo
dentro da taxa muda,
se o valor muda, executamos
essa função de efeito colateral. Sem falar que também
criamos nossos próprios ganchos personalizados em
cima de “useState”, “useReducer”
e “useEffect”. Esses ganchos personalizados são justos, como qualquer outro gancho, mas com lógica extra. Agora você sabe que,
caso precise
criar uma lógica reutilizável
para ganchos integrados, basta criar um gancho
personalizado e colocar toda a lógica dentro. Eventualmente, ele se torna reutilizável. Também trabalhamos com
armazenamento de navegadores, trabalhamos com armazenamento de sessão, trabalharemos com armazenamento local. Você sabe que agora
você pode manter os dados dentro do navegador. Obviamente, isso não
substitui um banco de dados. Mas se você precisar
reter
informações de alguma forma , como a
entrada de pesquisa ou as preferências do usuário, poderá usar esse
armazenamento perfeitamente. Vamos ver o que mais
temos aqui? Vamos voltar ao histórico de
confirmações. Aqui também criamos
essas páginas dinâmicas. Isso também faz parte do
React Router, mas agora você conhece o conceito
de páginas dinâmicas. Você cria um modelo
ou um esqueleto
e, em seguida, pega o
parâmetro dinâmico do URL, no nosso caso, era show ID,
então, se eu procuro algum programa,
vou para mostrar a página
dentro do URL,
temos o ID de exibição
que pegamos dentro do componente e, em seguida, usamos
esse ID de exibição para buscar dados. Dessa forma, podemos
obter páginas dinâmicas. Agora você conhece esse conceito. Vamos ver o que também
temos aqui? Novamente, “UseQuery”
sobre dados de consulta, lógica inicial
diferente
com ganchos personalizados, isso é o que discutimos, também
instalamos componentes
estilizados. Uma solução de tempo de execução de CSS e JS
para componentes de estilo. Agora você pode decidir o que
é melhor para você. Use componentes estilizados
ou algo muito semelhante ou use a
forma tradicional com arquivos CSS. Porque agora você
conhece as desvantagens, agora sabe quais são as
vantagens e é você quem decidirá
o que vai usar. Pessoalmente, prefiro a forma
tradicional de estilizar aplicativos e não sou muito
fã de CSS e JS. Além disso, adicionamos essa animação de
desvanecimento como um substituto para o pacote que mencionei, React-fade-in. Eu mencionei isso apenas uma vez, mas não coloquei
muita ênfase nisso. Precisamos de menos dependências
em nossos aplicativos. Menos dependências, melhor, porque você precisa
gerenciar menos coisas. Acho que faz sentido, e você
seguirá essa regra
no futuro, porque
será para seu próprio bem. Também conhecemos aplicativos web
progressivos. O que é o Progressive Web App? É apenas um
aplicativo da web que segue lista
específica de
itens. Por exemplo, você precisa ter um arquivo de service worker, ele
precisa ser servido por HTTPS, precisa ter
esse arquivo de manifesto
e, quando o aplicativo,
o site, atende a todos
esses requisitos, ele se torna um aplicativo Web
progressivo. É como um site intitulado e o título é
Progressive Web App. O aplicativo ficou disponível off-line por causa do
service worker. Agora você sabe que o
service worker é um script executado em algum lugar
dentro do navegador, fora dos contextos de nossos
aplicativos, e ele encaminha
todas as solicitações, todas as solicitações enviadas e faz algo com elas. Em nosso caso, usamos o
service worker para armazenar em cache toda a solicitação de saída. O aplicativo
funcionará offline depois instalado em algum lugar
na tela inicial. No final, adicionamos nossos próprios
ícones personalizados usando o [inaudível]
que eu gerei e compartilhei com você, mas isso realmente não
importa, você pode usar qualquer
gerador, mas agora você pode ver
o fluxo completo,
como o aplicativo
está sendo construído do zero
até a implantação, estilo e fazendo algumas
modificações no futuro. Algo parecido. Parabéns, você fez um trabalho muito bom. Por enquanto, é isso. Te vejo na próxima.
93. O que é base de firebase?: Ei, bem-vindo à nova seção aqui. Vamos falar sobre a solução de volta para o nosso projeto final. Sempre que criamos um aplicativo de página única para nos comunicarmos com o banco de dados, nós normalmente criaríamos nosso próprio servidor AP I ou usaríamos um existente. modernas, Aplicaçõesmodernas,
pequenas ou médias não necessariamente para trás e de ossos nus por conta
própria a maior parte do tempo que fazem, mas depende do tipo de aplicação. Não seria bom se tivéssemos algum tipo de camada de obstrução nos fundos? E então não precisamos configurá-lo nós mesmos e nos concentrar mais no aplicativo? Bem, base de fogo pode ajudar-nos a conseguir isso. Ele é acenado como solução de serviço que nos dá a camada de abstração em torno de trás e e ele faz. Ainda mais Firebase é Emma Bile e Web Platform, que é construído sobre o Google Cloud Platform. Isso significa que ele pode ser usado junto com qualquer serviço de nuvem do Google. A partir de agora, não
precisamos nos preocupar em criar nosso próprio arquivo de manutenção de banco de dados AP I hospedando tudo já está lá e esperando por nós. Então, em nosso código, em vez de enviar um pedido para um A P I para recuperar dados. Nós apenas usar uma biblioteca que tem funções já muito bem para nós. Como obter este documento por I t. E esta função irá interagir com o banco de dados. Ele tem realmente tempo cantar apoio e consultas mais rápidas. E também está bem documentado, o que é realmente importante para entender. O Bachir. Que base de fogo está no próximo vídeo, mas vai passar por serviços de base de fogo
e vamos tentar avaliá-los. Vejo você lá.
94. Visão geral do Firebase: Ei, vamos explorar rapidamente a Base de Fogo e seus serviços. Para este vídeo, eu abri fogo baseado Dashboard fora do nosso projeto final Aqui. Podemos monitorar e gerenciar todos os serviços que usamos dentro de um projeto firebase. Poderíamos gerenciar vários APS. Pode haver vários APs de volta, e que irá compartilhar o mesmo banco de dados. Ou se tivéssemos aplicativos Android, IOS e Web, poderíamos gerenciar todos eles a partir de um único painel à esquerda. Dentro da barra lateral. Em desenvolvimento, você pode ver uma lista fora dos serviços principais do Firebase. Vamos um por um. Uma sindicação. Com o serviço, somos capazes de fazer login e autenticar usuários em todos os nossos aplicativos. Isso é muito legal porque, digamos que se olharmos com o Google no site e mais tarde, olhamos para o aplicativo android com a mesma conta, os dados serão os mesmos. Existem muitos sinais e métodos diferentes disponíveis para nós, e a coisa é que todos eles são configuráveis. Foram apenas alguns cliques. Este serviço está completo. Ele tem construído em um sistema de e-mail que lida com todas as verificações de e-mail e recesso. Precisamos que você apenas personalize o modelo fora do e-mail. Além
disso, suporta a verificação SMS, o que também é muito legal. Depois vai a base de dados. Firebase tem a base de dados pediu agora loja fogo e banco de dados de tempo riel. Ambos são baseados em Jason nenhum banco de dados sequela com suporte para atualizações em tempo real. Qual é a diferença e qual usar? Depende de muitos fatores, mas aqui estão três diferenças-chave. Primeiro, modelo de
preços Loja Fire é cobrado por operação. Leia, escreva, exclua ou atualize. Isso não é bom para gravações de dados de alta freqüência Banco de dados em tempo real tem mais adequado para isso ,
pois é cobrado para armazenamento e largura de banda, que é o caso de uso perfeito para algo como um aplicativo filho. Segundas consultas. Fire Story nos dá consultas mais avançadas e compostas em comparação com banco de dados em tempo
real Assim base de dados em tempo real tem realmente pobre construtor de consultas, mas é bom o suficiente para gerenciar não estruturas de banco de dados complicadas. Terceira estrutura ambos são Jason baseado Fire Store tem documentos, coleções e sub coleções, que tornam o banco de dados mais robusto. base de dados em tempo real é apenas um grande objeto Jason. É por isso que tem peculiaridade muito apoio e na maioria das vezes precisamos de normalizar um k um dados
duplicados para o nosso projeto. Vamos usar banco de dados em tempo real porque teremos um monte de Faried e operações de gravação. E nós não exigimos consultas complexas. Se não fosse um aplicativo de bate-papo, Eu teria pico loja Fire como ele tem consultas mais sofisticadas e estrutura de base de dados . Além disso, não
estamos limitados a usar em Lee um banco de dados. Podemos combinar tanto armazenamento de fogo e base de dados em tempo real em um único aplicativo. Então temos armazenamento. Nada muito especial. Por aqui. Aqui bolha Porter, imagens
do usuário e arquivos de áudio Firebase hospedagem aqui. Vamos implantar nosso site. Ele só suporta arquivos estáticos. Então, se tivermos um aplicativo de renderização do lado do servidor, esta hospedagem não funcionará. As funções de nuvem em nosso aplicativo também foram capazes de escrever personalizado de volta e informar fora do servidor últimas funções de nuvem que podem ser chamadas de dentro do casaco. Vamos implantar apenas um que enviará notificações aos usuários. Vamos falar mais sobre servidor última quando vamos entrar na máquina tópico. Lauren, obter ferramenta incrível que fornece utilitários de aprendizado de máquina, como reconhecimento de imagem e os outros. Mas, infelizmente, ele só está disponível para IOS e Android APS na parte inferior. Temos outros serviços. Todos eles são complementares e usados para monitorar e analisar aplicativos implantados. Podemos gerenciar o desempenho fora do nosso site, quão rápido ele baixa e algumas outras métricas. Podemos até integrar o Firebase Analytics, que é basicamente o Google Analytics, mas embrulhado como um serviço firebase e, no fundo restringimos serviços para envolver os usuários em nosso projeto. Usaremos apenas mensagens na nuvem firebase que nos permitirá enviar
notificações em tempo real para os usuários se o navegador tiver suporte para ele. E é basicamente isso. Esta foi visão geral de alto nível fora da lareira. Mas e a segurança? É seguro o suficiente? Vamos descobrir que na próxima mídia vê-lo lá.
95. Segurança de Firebase: Ei, vamos ver se a Firebase está segura. Já que não temos nenhum código do lado do servidor, vamos acessar o banco de dados do lado do cliente. Como vamos expor dados confidenciais? Sim e não. Na lareira bancos de dados são acessados via Euro Público. Isto faz parte do conflito. Digamos que temos alguns dados dentro do banco de dados. Temos público o seu el No. Um também. E se a Pessoa Aleatória tentar acessar o Ural e não protegemos o banco de dados, essa pessoa pode obter todos os dados, quer sejam públicos ou não, para evitar acesso não autorizado, suas regras de segurança. Essas regras definem como os dados podem ser acessados e por quem. Isso significa que o nível de segurança depende de como as boas regras de segurança são escritas. É uma boa prática olhar para baixo o banco de dados por padrão e, em seguida, ele apenas regras. À medida que escrevemos regras de segurança de código aplicam-se a Lee aos seus clientes. I Se escrevermos backend personalizado com funções de nuvem, essas regras não se aplicarão quando o aplicativo crescer. Algumas pessoas acham difícil escrever rituais de busca. Por esse motivo, eles usam funções de nuvem e executam servidores na validação. O mesmo se aplica ao armazenamento em nuvem. Temos público que estão doentes e regras por padrão. armazenamento só pode ser acessado por usuários conectados. Para a maioria dos casos, funciona bem. Mas isso não significa que se carregarmos uma imagem que queremos compartilhar, essa imagem será bloqueada. Todos os ficheiros enviados podem ter a Europa pública. Tudo bem, é
isso por segurança. Espero que tenha sido abrangente e conciso. Agora, que tal preços? Firebase é livre? Vou descobrir isso no próximo vídeo. Vejo você lá.
96. Preço do Firebase: Vamos ver se precisamos pagar algo para usar a base de fogo. Quanto a fora, existem duas plantas disponíveis. Faísca e Blaze plano desencadeado é completamente gratuito e vem com algumas limitações. O plano da polícia é modelo de pagamento conforme você vai. Ambos têm muito generais freakier E mesmo se você está inscrito para Blaze plano a menos que o seu APP tem um monte de usuários ativos, você não vai pagar nada para nós para ter certeza de que não vai ser cobrado plano faísca está bem. No entanto, com as atualizações recentes da sua base de fogo e do Google Cloud para usar as funções da nuvem , precisamos ter o plano Blaze ativado para o nosso projeto. Mas não se preocupe, mas vamos entrar nisso quando começarmos com as funções da nuvem. Até então, plano
acionado é a nossa escolha Para obter mais detalhes, navegue até a página de preços para Avala tudo você mesmo. Tudo bem, acho que é tudo o que eu queria cobrir para a base de fogo na produção. No próximo vídeo, vamos finalista começou a construir nosso projeto. Vejo você lá
97. Visão geral do projeto: Bem-vindos à nova seção. Você fez uma pausa? Porque neste momento vou mostrar-vos como será o nosso projecto final quando entrarmos no website pela primeira vez . Mas veremos o sinal na página. Daqui. Podemos continuar com Facebook ou Google. Vamos escolher o Google. Então eu vou escolher por segunda conta e, em seguida, eu estou dentro do aplicativo. Então, à esquerda, eu posso ver esse quadro criar novos fundos de sala de bate-papo e listar as salas de bate-papo disponíveis à
direita . Se eu clicar em qualquer uma das salas de chat, eu vou ver suas mensagens e algumas outras coisas que vamos cobrir apenas em um segundo. Vamos primeiro começar com o painel, então se eu clicar nele a partir daqui, eu posso gerenciar minha conta. Então, no topo, eu posso ver que agora eu estou conectado ao Google, e eu também posso associar minha conta ao Facebook. Então, se eu clicar em um link para o Facebook, ele irá me solicitar minhas credenciais de phrasebook, se necessário. E agora estou ligado ao livro de frases. Isso significa que na próxima vez que eu vou olhar com o Facebook para comprar aplicativo, eu vou ser vinculado a esta conta. Eu vou acabar com a mesma conta, então eu tenho um apelido e eu posso editar a partir daqui. Então, se eu clicar no botão editar, eu serei capaz de alterá-lo. Então vamos alterá-lo um pouco, e se eu clicar seguro, ele será atualizado. Além disso, eu posso editar o meu ómetro se eu clicar em Selecionar Novo Avatar, e se eu escolher esta imagem, Eu vou ser capaz de adicioná-lo um pouco em desenvolver estado. E então eu vou clicar em un upload e meu Al Atar será atualizado. E daqui, também
posso sair. Em seguida, temos criar novo botão de sala de bate-papo. Então vamos especificar no nome da Europa, vamos dizer whoa e descrição vai ser Whoa! Se eu clicar
nele, ele aparecerá aqui, e a sala de bate-papo estará completamente vazia por enquanto. Então vamos selecionar a primeira sala de bate-papo porque ela já está preenchida com algumas mensagens. Então, o que temos aqui? Então, em cada mensagem, se a tivermos nela, podemos ver esse botão. Ele irá mostrar-lhe quantos gosta desta mensagem em particular metade. Então, se eu clicar nele, vou remover o dedo do pé como se eu clicar novamente como será adicionado a esta mensagem. E também podemos ver se este usuário está online ou offline. Então, se a tivermos neste círculo, podemos ver que esse usuário estava off-line neste dia específico, neste momento específico. E esta é a minha conta. É por isso que estou online. Além disso, você
teria aqui se clicarmos no apelido de usuário Global Sea Motile janela com o seu de um carro . É nome completo Membro desde esta data. Então, quando este usuário se juntou ao aplicativo e também podemos controlar a permissão de administrador fora deste usuário se estamos atualmente um administrador fora deste grupo, vamos dar uma olhada na permissão de administrador apenas em um momento. Então, o que mais temos? Então todas as mensagens são divididas em datas. Eles são agrupados por datas. Então você pode ver hoje eu enviar esta mensagem é ontem havia essas mensagens e assim um também nós temos paginação fora. Mensagem é que significa que não baixamos todas as nossas mensagens do banco de dados. Quando vemos o bate-papo um carregamento apenas, digamos 15 mensagens. E então, quando clicamos em carregar mais, veremos mais mensagens sendo carregadas para a nossa aplicação. Tudo bem, então nós somos capazes de enviar mensagens de texto normais para o nosso Chade. Então também podemos enviar arquivos. Então, se eu clicar no botão de anexo, eu vou ver este mortal. Então eu clico no upload. Posso selecionar arquivos normais também. Assim coça. Então eu vou selecionar este arquivo, esta imagem, que eu vou abri-lo. Vai aparecer aqui que eu vou clicar, enviar para o chat. E como você pode ver, se eu enviar um arquivo normal, Eu perdoo Carregá-lo apenas clicando sobre este seu fora. Se for uma imagem, ela será exibida aqui. E se eu clicar nele, eu vou ver a visualização. E também, eu vou ter esta vista inferior original. E se eu clicar nele, o original será aberto com o novo toque. Além disso, somos capazes de enviar arquivos de áudio. Então, se eu clicar neste botão aqui, o registro será iniciado e eu posso ver isso eu posso. Aqui, significa
que atualmente está gravado no meu microfone. Então, se eu clicar neste botão mais uma vez, ele salvará minha mensagem de ódio. Isso foi gravá-lo agora mesmo. E eu poderei reproduzi-lo se for suportado pelo navegador. Tudo bem, o que temos mais? Então, no topo, podemos ver o nome do quarto, podemos ver a mensagem de transmissão. E este botão azul aqui, eles estão relacionados, mas vamos dar uma olhada em um momento. Nisso, podemos clicar nas informações da sala para ver a descrição desta sala de bate-papo. E também, se nós somos um administrador fora deste grupo, nós somos capazes de ver este Aiken. Então, se clicarmos nele, podemos adicioná-lo. Informações do quarto, como nome e descrição. Então, se eu clicar no botão editar novamente, Eu posso para qualquer nome que eu quiser. E então eu sou capaz de salvá-lo, e ele será atualizado com sucesso. Tudo bem, agora, sobre mensagens transmitidas. O que são esses? Deixe-me mostrar como admitir permissão pode ser controlada. Então, deixe-me realmente olhar para esses aplicativos do meu telefone, e eu vou remover a permissão de administrador. Então agora eu estou dentro do aplicativo, e você pode ver que o status foi alterado. E agora posso ver o verde escuro. Tudo bem, então eu vou remover a permissão de administrador para esta conta que você pode ver agora. Então, o que vou fazer? Vou clicar no meu perfil e vou clicar na sala de Admitir permissão, mas a partir do meu telefone. Então, agora, eu removi a permissão de administração. E agora só posso ter este botão de notificação e informações do quarto. Tudo bem, agora, vou dar permissão para mim mesmo, e você pode ver agora que está atualizado e tudo está em tempo real. Então, o que está acontecendo aqui? Então, primeiro de tudo este botão de notificação,
Então, isso significa que eu quero assinar ou cancelar a assinatura de notificações que eu vou receber de admite fora desta sala de bate-papo. Por isso, neste momento, estou inscrito. E se eu mudar de idéia, eu vou estar na assinatura, e eu não vou receber nenhuma mensagem em tudo. Então, o que são essas notificações? Estas são notificações em tempo real que estão sendo exibidas pelo navegador no dispositivo. Portanto, são essas permissões ou notificações que se eu clicar nesta parte inferior, eu posso ver notificações aqui e agora elas são permitidas. Então, o que vai acontecer? Deixe-me enviar uma notificação do meu telefone para todos os usuários dentro desta sala de bate-papo. Então agora, do meu telefone, vou clicar na mensagem de transmissão aqui. Vou especificar o título e a mensagem, e depois vou publicar a mensagem. Então vamos ver o que vai acontecer. Então eu Steidl, Eu vou selecionar, Vamos dizer web surdo e para mensagem, Eu vou digitar Olá do telefone e, em seguida, publicar mensagem. E como você pode ver agora, eu tenho essa web metade desta sala. Eu ajudo a partir do meu telefone. E também tenho esta notificação dentro das janelas. Então o que? Isso significa que se eu estiver atualmente no site, eu vou receber esse tipo de notificação que eu posso fechar se eu digamos fora do navegador ou eu apenas fechar o navegador completamente. E se eu receber uma notificação, deixe-me enviar outra e sim, eu posso ver que eu ainda vou ter notificação dentro de janelas ou dentro de seu
sistema operacional se ele é suportado. Então, isso é o que nossas mensagens de tempo riel desta forma você não pode se eu seus usuários para
envolvê-los . Então isso é basicamente sobre nossa aplicação, um monte de coisas para cobrir e eu vou torná-lo o mais abrangente possível. Acho que vai gostar. E eu vou te ver no próximo vídeo. Vamos começar. Vejo você lá.
98. As atualizações estão chegando !!: Olá pessoal. Neste vídeo, gostaria de fazer referência às próximas atualizações do aplicativo de
bate-papo. Ambos os projetos, Tic-tac-toe e Box Office, foram atualizados, mas as atualizações para
aplicativos de bate-papo ainda não foram lançadas. Para tornar a transição
das atualizações do Box Office para a versão
mais antiga do aplicativo de
bate-papo o mais
tranquila possível ,
este vídeo existe. O que vamos
fazer é usar o modelo que preparei
para nós. Temos esse repositório de aplicativos de
bate-papo para iniciantes. O link será compartilhado
com você nos recursos, para que você tenha acesso a ele. Você acaba nesta página, você vai para esta página, então o que você precisa fazer, você precisa clicar no botão
do código verde, então você clica em
“Baixar Zip”. Em seguida, você vai até o
local onde baixou o
arquivo zip e o descompacta. Acabei de pegar aquela pasta. Eu o coloquei em downloads e aqui estou o projeto. Então eu vou para o VS Code. Eu abro essa pasta como
o projeto no VS Code. Aqui, esse e eu vejo isso. Aqui você encontra
o projeto inicial. Você tem todas as
dependências necessárias instaladas,
como compilador Sass, biblioteca
rsuite.
As diversões são importantes. Em seguida, temos o roteador react e a biblioteca Firebase instalados. ESLint e Prettier estão
configurados aqui. Você não precisa se
preocupar com isso. Dentro da fonte, você
tem estilos aqui. Aplicativo básico com o React Router da versão
mais antiga que é usado
em vídeos de aplicativos de bate-papo. Você tem tudo
configurado, estilos importados,
está tudo pronto. A única coisa que você
precisa fazer é primeiro inicializar o Git aqui. Você digita git init
, adiciona
tudo ao stage e confirma isso. Logo depois disso, você
precisa associar esse novo projeto Git ao
seu repositório do GitHub. Você acessa o repositório do GitHub,
cria um novo repositório, obtém a URL do repositório
e, em seguida, faz git remote ,
adiciona a origem e a
URL do repositório que você
copiará ao criar um novo repositório aqui no GitHub. Logo depois disso, você
precisa instalar dependências. Como você pode ver,
não há pasta de módulos de nós. A única coisa que você precisa fazer é digitar npm install e ele instalará
todas as dependências listadas no pacote Jason. Depois disso, você está pronto. Você precisará usar o script start
executando npm run start e continuar com
o desenvolvimento. O resto permanece o mesmo. Continue assistindo ao aplicativo Chat e tudo ficará bem. É isso. Nos vemos lá.
99. Scaffolding projeto: Ei, bem-vindo. Agora vamos usar scuffled nossa proteção como antes, vamos usar criar aplicativo reator e para criar em seu projeto, precisamos abrir a pasta de todos para colocar o nosso projeto no terminal. Então, do meu terminal, eu vou executar e p x criar reagir, e então o nome da pasta, que vai ser Chad app. E então eu vou colocar uso NPM porque eu tenho fio instalado no meu sistema. E agora o projeto da UE será criado para nós. Vamos esperar até que tudo esteja feito. Tudo bem? Parece que terminamos. Agora vamos abrir o código V. E daqui, vamos abrir nossa nova pasta. Então, o que temos lá dentro como antes? Sob fonte, temos nossos arquivos iniciais para o pacote Jason. Temos nossos roteiros e assim por diante. Então vamos executar nossa limpeza inicial para que não precisamos de ap CSS. Então também não precisamos de tudo isso dentro do nosso componente de aplicativo. Então vamos limpá-lo como este leva a excluir este nome de classe, vamos colocar apenas Olá. Vamos Tillett logotipo e importação para nós. Sim. Tem arquivado então não precisamos AP Test GS do que quatro CSS índice. Bem, na verdade não precisamos dele também, então para o índice? Sim, vamos remover o modo de rua porque receberemos erros quando usaremos outras bibliotecas. É totalmente normal. Então vamos remover Índice CSS e vamos comentar Service worker por enquanto, assim, então não precisamos de logotipo SVG. Não precisamos de fazer testes e terminamos aqui. Agora, o que fazemos? Vamos instalar outras dependências, e vamos obtê-las a partir da pasta Ativos. Então vamos abrir esta pasta e abrir andaimes. Doug Jason. Então, a partir daqui vamos copiar comentários para instalar dependências. Então vamos copiar a primeira linha e colocá-la dentro do nosso terminal integrado assim . Agora, enquanto ele está instalando, vamos criar preacher e excelentes arquivos de configuração. Então, para excelente, vai ser,
sim, sim, terra RC. E para pregador, vai ser mais bonito, RC, e também vamos copiá-los do nosso andaime para o arquivo Jason. Então, para sim, inclinado nós temos aquele. Vamos colocá-lo aqui e salvá-lo. E por ano nós temos essa. Então, sim, fiapos e pregador são Don, vamos ajustar nosso roteiro NPM. Então vamos copiar tudo isso e colocá-lo dentro. Empacote Jason, dentro desta seção de script na parte inferior, exatamente assim. E também temos o script claro para limpar a pasta de contas. Então, logo antes de produzirmos nosso construído vamos correr e PM, Ron Clear como um morto. Tudo bem, então terminamos com os roteiros. O que mais temos dentro do arquivo de desdobramento do disco? Temos outra linha para dependências de instalação, que é notas. Bundas são traje reagir roteador e reator para burros. Vamos copiá-lo. E deixe-me explicar o que vai acontecer. Então, para o nosso sistema de estilo, usaremos o SAS com você. Eu biblioteca nomeados estão aqui, e podemos dar uma olhada no nosso terno se não avaliarmos a sua documentação oficial. Então, o que é uma biblioteca Y? É uma biblioteca que nos dá já bastante encontrar componentes que podemos usar. E é basicamente isso. Veremos que quando começarmos a usá-lo é bastante simples, e isso aumenta nossa velocidade de desenvolvimento. Você vai ver isso. Tudo bem. E sempre que vemos que o nosso terno não é suficiente para os nossos casos vamos usar diz Ok. Além disso, nós instalamos, reagir roteador e reagir Roterdão Tudo bem, então é basicamente isso. Mas uma coisa a fazer é também copiar esta pasta de estilos para o nosso projeto. Então, o que é essa pasta Styles? Então ele vem com Assad fora de classes pré-definidas. Então vamos realmente copiar esta pasta. Então eu vou copiar esta pasta. Então eu vou abrir esse arquivo em ah, revelar no Explorador de Arquivos, depois dentro de feridas. Vou colar esta pasta de estilos e vamos dar uma olhada. O que temos lá dentro? Então nós temos o nosso arquivo principal, que é basicamente o nosso índice CSS ou apenas o nosso arquivo principal para estilos aqui iria definir, digamos, realmente algumas classes off que vamos usar. Ele vai levar você olhar e eles Eles são realmente simples. Nada muito complicado. Em seguida, temos utilitário e você cores facilidade que importamos para Maine CSS. Então agora podemos gerenciar nossos arquivos. Então, para utilitário aqui temos classes que são semelhantes às classes utilitárias bootstrap, então vamos usá-las muito em nosso código. Então, por favor, dê uma olhada neles. Eles não são tão difíceis de gerenciar. Não tenho cores de utilidade. Estas são basicamente classes para cores. Nada muito especial aqui. E então nós temos override como ele SS. Então, este ano eu biblioteca tem certeza de que ele é destinado para aplicativos de desktop. Assim, alguns fora de seus componentes não são realmente bons para exibidos em dispositivos móveis e para ajustá-los para telas móveis. Eu modifiquei um pouco seu CSS Eu substituo suas classes um pouco. Então agora eles ficam bem em dispositivos móveis também. Isto é só para tornar tudo bom. A polícia dá uma olhada em tudo isso. É muito simples. Apenas certifique-se de que você sabe o que está acontecendo. Então, dentro de Abdel Gs, o que precisamos fazer, precisamos importá-lo. Então, vamos importar. Ah, nós somos estilos CSS principal assim. E também precisamos configurar nosso terno e avançar. Então, se navegarmos para seu site oficial e se formos para começar e se clicarmos em uso em Creta, reagir aplicativo a partir daqui, podemos ver que precisamos também importar suas soluções CSS padrão copiar esta linha de código e colocá-lo antes de importar nossos estilos principais assim. Então agora estamos prontos para ir com o nosso conflito por vocês. Uma coisa a fazer aqui é realmente conectar nosso projeto para obter ajuda. Então vamos abrir o terminal integrado e confirmar todos os nossos arquivos. Então, primeiro, vamos adicionar tudo ao estado do palco, e depois vamos nos comprometer. Digamos que andaime algo assim. Agora vamos abrir o Teoh. Vamos arranjar-lhe uma conta. Então vamos criar um repositório. Em seguida, vamos nomear seu aplicativo de bate-papo. Vamos torná-lo privado, e vamos criar um novo repositório Logo depois disso, podemos copiar este comando na parte inferior. Obter controle remoto na origem. Vamos copiar isso e passear no nosso terminal. Agora, nossos arquivos locais serão associados a este repositório remoto e precisamos colocar nossas mudanças locais on-line para obtê-la. Vamos usar a mostarda de origem push. E agora vamos dar uma olhada para que tudo seja implantado. Se atualizarmos a página, nosso projeto estará online. Então temos tudo. Chraidi. E no próximo vídeo vamos começar a construir. Vejo você lá
100. Crie e configure o projeto do Firebase: Ei, neste vídeo, vamos criar um novo projeto firebase e editar em nosso aplicativo. Vamos lá. Então vamos abrir o Google. E aqui vamos digitar base de fogo. Então vamos abrir primeiro o seu L e vamos acabar na base de fogo. Página oficial da Web. Como o Fire Base faz parte da plataforma Google Cloud, o Google gerencia tudo. Isso significa que não precisamos criar uma nova conta ou algo assim. Se tivermos uma conta do Google, o que eu acho que todo mundo tem, então vamos associar nossa conta do Google ao Firebase Project. Então, vamos clicar em Get Started e aqui nós clicamos em Add New Project. Em seguida, vamos especificar o novo nome do projeto, que vai ser chat Web app. Digamos que, em seguida, vamos clicar em Continuar. Então vamos desativar o Google Analytics. Na verdade, não precisamos dele. E vamos esperar alguns minutos até que nosso projeto seja criado. Ok, bom. Parece que o projeto está pronto. Vamos continuar. Depois acabamos no painel de instrumentos da base de fogo. Então, a partir daqui, vamos gerenciar tudo. E como você pode ver, estamos atualmente no plano de faísca, então isso significa que não seremos cobrados por nada. Muito bem, agora temos de adicionar a nossa aplicação Web ao nosso projecto firebase. Então, vamos clicar neste botão de configurações e, em seguida, escolher as configurações do projeto. Então, aqui na parte inferior, veremos nosso APS a partir daqui. Vamos clicar neste aplicativo de laboratório, e então vamos inserir o nome para o nosso aplicativo, que vai ser, digamos, apenas conversar e não vamos configurar a hospedagem firebase. Vamos clicar em Registrar. Também levará alguns segundos, e agora nossa aplicação está pronta. Vamos clicar em, Continuar a aconselhar. Agora precisamos configurar serviços que usaremos dentro de nosso aplicativo. Então, primeiro, vamos configurar o banco de dados. Então, vamos clicar nele. E nesta página, somos capazes de configurar a Cloud Fire Store ou a base de dados em tempo real, por isso certifique-se de que você não usa a nuvem Fire Store. Você usa um banco de dados em tempo real aqui na parte inferior, então vamos clicar, criar banco de dados e vamos selecionar start no modo bloqueado para que todas as nossas regras sejam olhadas para baixo. OK, então vamos habilitá-lo, e vai levar alguns segundos apenas para criar um novo banco de dados para nós. Tudo bem, está feito. Agora precisamos também configurar o armazenamento para o nosso aplicativo. Então, vamos clicar nele e começar. Vai pedir-nos regras. Vamos clicar em seguida. Então precisamos selecionar o local para o nosso armazenamento. É muito importante e realmente influencia essa velocidade, então basta selecionar o mais próximo de você. Para mim, é algo, penso
eu, com a Europa. Então eu escolho a Europa Oeste três. Então eu clico em Dung e vai levar alguns segundos para criar uma nova história para nós. Vamos esperar. Está bem, Perfeito. Parece que o depósito está pronto. Nossa última coisa é configurar a autenticação para o nosso aplicativo. Então, vamos clicar em autenticação aqui. Não temos usuários cadastrados. Por enquanto, vamos clicar em Sign and Method, e a partir daqui podemos ver todos os provedores de assinatura que podemos usar. Não usaremos e-mail, e a senha usará apenas o Google e o Facebook. Então, primeiro, vamos clicar nele. E, em seguida, vamos apenas clicar em habilitar assim. Então vamos selecionar suporte e e-mail e, em seguida, projetar o nome público enfrentando. Vamos talvez disse algo como bate-papo, aplicativo e vamos clicar seguro, e depois que ele vai configurar tudo automaticamente. Não precisamos nos preocupar com nada. O Google Sinan já está ativado. E agora o Facebook? Faça login Então, vamos clicar nele. E a partir daqui não teremos nenhuma configuração automática. Precisamos fazer isso manualmente. Então, vamos clicar em ativar aqui. Precisamos preencher APP, idéia app segredo. E precisamos usar isso. Redirecionar seu l Então, o que precisamos fazer dentro do Google? Precisamos digitar Facebook desenvolvedor. Então vamos ao Facebook para desenvolvedores. E aqui nesta página na parte superior, vamos clicar no meu APS e a partir daqui vamos clicar em Criar APP, permite selecionado. E este nome da peça vai ser algo como gráficos apenas tiro chorou. Tudo bem, então vamos clicar em Criar aplicativo I d. Em seguida, vamos executar verificação de segurança enviado e ah foram aplicativo Facebook será criado. Então, a partir daqui o que precisamos fazer precisamos ir para as configurações,
em seguida, ir para o básico E aqui vamos encontrar o nosso aplicativo I d e up segredo. Vamos chamar p app I d e, em seguida, acelerá-lo aqui. Então precisamos também obter o segredo do nosso aplicativo. Vamos clicar no show e vamos chamá-lo também e colá-lo aqui dentro da base de fogo. E também precisamos adicionar isso. Redirecione seu l aqui, vamos copiá-lo. Então vamos salvar nossas alterações. E aqui em Prokes, vamos clicar em sinal mais. Então, quando clicamos nele, precisamos selecionar o Facebook. Olhe e vamos clicar em Configurar. E, em seguida, precisamos selecionar que poderemos fazer login na Web, em
seguida, site seu l. Eu não sei. Coloque algo que realmente não importa. Na verdade, não, não
precisamos disso. Vamos clicar nas configurações porque já temos Facebook. Logan nisso Foi apenas um começo rápido da equipe do Facebook. Então aqui para estes redirecionamento válido o seu mais precisamos adicionar este seu l que temos na
base de fogo . Então, certifique-se de que está aqui. Então agora é editar. Vamos clicar em salvar as alterações. E agora a nossa aplicação no Facebook está pronta. Então, vamos salvá-lo. E agora o nosso Facebook em configurá-lo e nós configurá-lo tudo dentro do site firebase . Agora podemos realmente adicioná-lo ao nosso código. Então vamos voltar ao código V e a partir daqui. Vamos abrir o nosso terminal primeiro. Acho que precisamos de instalar o Global Seelye da base de fogo. Então, para isso, vamos digitar NPM instalar ferramentas firebase Dash G e instalá-lo. Já o tenho na minha máquina, por isso não vou instalá-lo duas vezes depois disso. Quando temos essas ferramentas de base de fogo, precisamos digitar base de fogo nele e isso é tudo. Depois disso, ele irá solicitá-lo. Autorize-se,
por favor, preencha as instruções. E depois disso, quando eu executar este comando, eu verei esta luz no trabalho. Então, estou pronto para prosseguir. Sim. Então eu preciso selecionar os serviços que eu quero inicializar. Então eu preciso apenas de banco de dados. Então eu navego com setas e eu seleciono com espaço e também eu preciso de hospedagem Onley. Aqueles dois não selecionam armazenamento. Então, eu apertei Enter Então eu vou escolher usar um projeto existente e, em seguida, eu vou selecionar chat Web app que eu acabei de criar. Eu selecionei qual arquivo deve ser usado para rolos de resíduos posteriores. Vamos pressionar apenas enter do que o diretório público que eu quero usar em vez de público. Vamos digitar construído e, em seguida, eu quero configurar meu aplicativo como um aplicativo de página única. Isso é verdade. Então, vamos clicar. Sim, e o HTML de índice construído já existe, certo? Sim. Eu quero que você anule. Tudo bem agora. A base de fogo é associativa. Digamos que o nosso projeto remoto que acabamos de criar que um associado com o nosso
projeto local podemos ver Firebase Jason Fire Besar See que contém o nosso projeto I d do que dentro das regras de
banco de dados. Temos nossas regras de banco de dados e dentro da base de fogo Jason, temos nossa descrição do projeto. Assim, para regras de banco de dados são implantados a partir desse arquivo para hospedagem, temos pasta pública, que é construído. Então temos ignorar arquivos que não vamos implantar para o firebase hospedagem e também reescreve. Lembra quando tentamos carregar nosso projeto no hip hop? Então, quando atualizamos a página, não
fomos encontrados. Então, isso é porque temos aplicativo de página única e Firebase resolve esse problema apenas
escrevendo todas as rotas e configurá-lo para rap de página única. Por isso, não teremos quaisquer problemas com isso. Tudo bem, então é isso. Agora podemos realmente instalar biblioteca em nosso projeto. Então, para isso, vamos apenas digitar PM instalar firebase. E vamos esperar até que esteja feito. Muito bem, temos a base instalada como uma biblioteca. Agora o que precisamos fazer sob pasta de código-fonte vamos criar em sua pasta que vamos nomear MISC e aqui vamos criar um novo arquivo firebase dot gs. Aqui vamos configurar nossa base de fogo dentro do nosso aplicativo. Então primeiro acho que precisamos fazer precisamos voltar para o site, em
seguida, novamente voltar para as configurações do projeto. E se descermos daqui, podemos encontrar esse conflito da base de fogo. Então vamos copiar isso. E aqui vamos criar um novo e valioso,
digamos, conflito constante e vamos colá-lo assim, agora capaz. Importar também bibliotecas do firebase. Então vamos digitar base de importação de fogo do aplicativo Firebase. É importante não importar do firebase porque ele irá importar toda a biblioteca
e toda a biblioteca é
realmente, muito grande, realmente, muito grande, e irá adicionar todos os arquivos a partir dele. Então nós nos certificamos de que só importou aplicativo firebase que o que precisamos fazer precisamos chamar fogo base dar inicializar aplicativo e dentro Precisamos votar nosso arquivo de conflito Então vamos colocar vir grosso. E agora isso para inicializar aplicativo retorna como uma instância fora do fogo aplicativo baseado. Então vamos colocá-lo em um valioso vamos atribuí-lo a, digamos, apenas um aplicativo assim. E estamos prontos para ir agora. Usando este aplicativo valioso, estamos prontos para acessar serviços firebase como up off ab abelhas nativas, função de loja de
fogo, mensagens de tudo isso. Então, mas isso é o que faremos no próximo vídeo para como somos feitos. A única coisa que eu quero fazer antes de terminarmos este vídeo, eu quero comprometer nossas mudanças para obter ajuda. Então vamos esquecer no ponto, então vamos colocar, obter commit e vamos dizer que o projeto inicializado da base de fogo algo assim. Tudo bem, Perfeito. Vejo-te no próximo.
101. Criando rotas particulares e públicas: Ei, agora temos a base inicializada dentro do nosso projeto. Vamos começar a construir o projeto em si. A primeira coisa que eu vou fazer eu vou abrir meu terminal e eu vou executar e PM Run começar a começar a desenvolver servidor. Mas logo antes de executar este comentário, eu vou criar um novo arquivo, que é dot e n v dot local e eu vou colocá-lo no diretório raiz e aqui rivais pacificar navegador para nenhum. Isto é para evitar e PM Ron começar a iniciar o aplicativo instantaneamente dentro
do meu navegador. Então eu realmente odeio esse comportamento. Se você gosta, não faça este navegador. Nenhuma coisa. Então agora eu vou executar este comando e eu preciso ir manualmente para o navegador e acessar o
host local 3000. Então aqui eu vou ver a mensagem Olá que eu especifiquei dentro de Abdel Gs quando o risco se desdobrou o projeto. Agora o que precisamos fazer precisamos definir nossas páginas no início. Mas nós não inicializamos reagir rotor quando o risco se desdobrou o aplicativo então vamos navegar para
togs índice e aqui para inicializar reator importará rotor navegador de reagir roteador burro e em seguida, precisamos envolver o nosso componente aplicativo em torno do navegador, componente rotativo. E agora somos capazes de usá-lo. Ok, bom. Vamos lá. Teoh Abdel Gs e ouvir quais rotas vamos definir. Vamos primeiro usar o interruptor em vez disso. Fora disso, Def. Então eu vou colocar interruptor de reagir mais rudes do que dentro do interruptor. As pessoas definem rota. E que rotas devemos colocar aqui? Bem, teremos algumas rotas para encontrar, e uma delas está assinando a página e a página inicial. E a coisa é que não seremos capazes de acessar a página inicial até que estejamos conectados
ao APP. Então precisamos definir algum tipo de truta privada que só pode ser acessada se estivermos
assinados . Então, o que vamos fazer a primeira coisa que as pessoas fazem isso irá criar uma nova pasta nas páginas de nomes acessíveis ao recurso. Aqui vamos criar dois novos componentes e que representarão nossas páginas. Primeiro vai ser um sinal na página e ela está aqui. Eu vou andaime e você componente com a extensão snipper. E vamos apenas assinar assim. Então eu vou criar outro componente, Holmdel Gs e eu vou fazer exatamente a mesma coisa. E eu vou nomear uma casa justa agora Como podemos definir essas linhas aqui? Podemos colocar rota e, em seguida, podemos colocar primeiro sinal em modo que esta rota é definida. Mas e quanto a casa? Como podemos torná-lo privado para isso irá criar outro componente. Vamos nomeá-lo rota privada e ele vai imitar este componente rota que vem de reagir Router. Mas será melhorado e verificará contra alguma condição. Então, sob feridas, vamos criar novos componentes de pasta Aqui vamos colocar uma nova rota privada de arquivo assim. Então ele irá imitar este componente de rota. Então, como é pacificar este componente de rota? Que problemas nós traçamos? O que as crianças fazem um caminho. Então precisamos especificar caminho. Então, para assinar, será só assinar. Agora, sobre o soldado Rauer. Então vamos definir como vamos usá-lo. Então vai ser uma rota privada para dentro. Precisamos derramar um componente ou apenas Crianças que queremos renderizar. Vai ser a nossa página inicial assim e para adereços. Precisamos também especificar que vamos renderizar este componente em apenas barra. Ok, agora dentro da rota privada. Sabemos que o que quer que passemos para este componente privado viajado como um adereço será realmente tipo de redirecionado para este componente de rota. Então aqui vamos estruturar tudo e colocá-lo dentro. Digamos que adereços de rota. A única coisa adequada que precisamos para obter é as Crianças reais que queremos renderizar. Então vamos d estrutura Crianças e tudo o resto estará disponível sob adereços de rota. E precisamos derramar uma condição simples aqui. Digamos que por enquanto. Já que não temos nenhum perfil, vamos criar o touro inestimável. Digamos que o perfil seja falso. E agora o que vamos fazer, vamos perguntar se o nosso perfil está definido como tolos. Se não temos nenhum perfil, então nós vamos retornar e você componente que não usamos antes que ele vai ser
redirecionada , que também vem de pacote de rotor reagir. E este redirecionamento será basicamente redirecionado para especificar passagem. Portanto, ele recebe apenas um adereço, que é para e para isso irá especificar. Então, se não tivermos sinais e dados. Se não tivermos um perfil, vamos redirecionar para a assinatura. Tudo bem. Bastante simples. Agora, se esta condição não ocorrer, então nós normalmente usaríamos nosso componente que passamos como Crianças. Então, em vez de retornar este def, vamos simplesmente retornar rota de reagir rotor de quatro adereços. Vamos especificar todos os adereços que o recolheremos daqui. Então vamos espalhá-los sobre este componente de rota com apenas esta sintaxe e dentro crianças
verbais assim. E se a guardarmos, vamos verificar. Se ele realmente funcionou agora, se eu vou tentar acessar barra uma página inicial barra, Eu vou ser instantaneamente redirecionado porque nós sempre temos condição falsa. Então isso significa que sempre seremos redirecionados para a página de login. Então, se eu disse que é muito verdade agora se eu vou tentar acessar home page, eu estarei lá. Então é isso. É assim que podemos fazer a rota privada. Além disso, quando tivermos sessão iniciada, não
queremos ver a página de início de sessão. Queremos ser redirecionados também para, digamos, para o nosso painel ou para a página inicial. Então, o que
podemos fazer, vamos criar outro componente que vamos nomear público público. Então vamos criar uma rota pública. Não Sim, e vamos realmente copiar tudo da rota privada. E aqui, vamos renomear rota privada para rota pública. E aqui a coisa será a próxima. Então, se temos perfil, então vamos ser redirecionados para a página inicial. Desta forma, se estivermos conectados, não
seremos capazes de ver a página de login onde será instantaneamente redirecionado para casa. Então a lógica é meio que a mesma. Mas é invertido agora como podemos realmente é descartável multidão realmente da
mesma maneira que usamos nosso privado eu vou. Então, aqui, em vez de apenas rota será pobre público Rauer que importamos da pasta Componentes. Agora não precisamos desta importação do roteador reagir. Vamos salvá-lo. E, na verdade, nada será alterado porque não temos dados para o perfil. Então é basicamente isso. É assim que somos capazes de gerenciar nossas multidões privadas e públicas no roteador reagir. Agora vamos confirmar nossas mudanças e terminar este vídeo, então vamos colocar tudo em cima, então vamos comprometer nossas mensagens criadas rotas públicas e privadas para a direita. No próximo vídeo, começaremos a construir a página de entrada. Vejo você lá.
102. Página de login - interação com o Firebase: Ei, bem-vindo neste vídeo, vamos começar a construir página de design. Vamos lá. Antes de começarmos. Só quero mencionar que vamos usar o traje de reação. Você. Por que a biblioteca que instalamos? Vamos utilizá-lo muito. Por isso, abra esta documentação no seu próximo passo, para que tenha sempre acesso a ela. Então vá para a página inicial e clique em componentes. E aqui nesta página você pode encontrar todos os componentes que esta biblioteca nos fornece para oeste. É muito simples de usar, e todos eles são principalmente intuitivos. Então, vamos dizer que se vamos para o componente botão a partir daqui em cada página da empresa, você pode encontrar um monte de exemplos diferentes e casos de uso. E também, se você clicar em mostrou a fonte, você confia como este componente pode ser usado em seu casaco. Você sempre pode copiá-lo e colá-lo. E também, se você só precisa saber qual componente recebe como adereços, você pode rolar para baixo até o fundo e você confia todos os adereços possíveis que podem ser passados para baixo para este componente específico. Tudo bem, então dentro do nosso código, quando eu vou escrever este material, eu não vou fazer referência pode ser algumas vezes, mas na maioria das vezes, porque é melhor intuitivo. Eu não vou explicar isso. Então, se você ainda não sabe o que vai acontecer, navegue até esta documentação. Tudo bem, então vamos começar. Então, vamos navegar para o nosso código e vamos abrir a página de login. E aqui nós vamos começar primeiro, vamos remover este def, e vamos colocar componente recipiente do nosso terno. Você pode pensar que é muito semelhante a contend de bootstrap porque é recipiente já nesta biblioteca. Não é. Só nos dá a exibição do Flex. Então vamos usar grão. E nesta biblioteca, grande é praticamente o mesmo que no Bootstrap. Mas ao contrário do Bootstrap, ele tem sistema de coluna 24. Ao contrário das botas, solte com 12 pentes. Tudo bem, então dentro da grade, nós temos crescer e dentro da linha, nós temos coluna exatamente como essa. Então, nosso cólon vai ser saúde fora de seu máximo com em dispositivos médios. Então, em dispositivos muito pequenos, vamos para pobres e velhas 24 colunas no meio e acima. Vamos colocar 12 agora, dentro desta coluna vamos colocar componente painel, e basicamente vai nos dar alguns tapinhas fora. Ok, então dentro vamos colocar def. E dentro deste difícil definir idade para marcar que vai dizer, Bem-vindo ao bate-papo Underneath vamos colocar Pitak que vai dizer, plataforma de bate-papo
progressivo quatro lutas de refeição, algo assim. Tudo bem, vamos verificar. Se eu atualizar a página, posso ver esse estranho, estranho fundo. Isso é porque eu importava coluna do nosso terno Leap Carrossel. Eu não queria isso. Isso é um pouco complicado quando você usa inteligência externa Essence certifique-se importado
apenas do nosso terno. Se eu guardá-lo agora, posso ver que realmente funcionou. No entanto, nosso texto não está centrado. Queremos torná-lo centro para que possamos usar uma de nossas classes de utilidade que nós pobres dentro utilitário, como aqui diz, e eles são quase como bootstrap, que
possamos definir o nome da classe, centro de
texto e ele vai trabalho. No entanto, podemos ver que, se inspecionamos, nosso componente não está completamente centrado em dispositivos grandes. No entanto, no celular, está
tudo bem. Isso é porque quando aplicamos este sistema de coluna 12, nosso elemento não é, Digamos tendo-lo. Temos de nos candidatar. Deslocamento. É novamente muito semelhante, como no Bootstrap. Então, para 12 colunas, precisamos aplicar Offset off seis colunas antes dele. Então vamos colocar o deslocamento vazio de seis colunas. E agora nosso grande elemento estará centrado, como podem ver por este estofamento aqui. Tudo bem. Parece bom agora sob uma Disney, se vamos colocar outra definição. E aqui vamos definir nossos botões, assinar com o Google e entrar com o Facebook. Então primeiro vou colocar o botão. Então, como adereços, eu passarei. Vai ser um botão de bloqueio. Ele vai tirar tudo com fora de seu pai. Então eu vou colocar cor, e eu vou colocá-lo em azul. E é isso por enquanto. Então, dentro deste fundo, eu vou derramar componente Aiken do nosso terno, e como
eu puder, eu vou especificar que eu posso apoiar quatro Facebook assim. E então eu vou colocar um texto simples, continuar com o Facebook, mas em maiúsculas e o mesmo que eu vou fazer para assinar com o Google. Vou especificar uma cor verde. E em vez de phrasebook, eu posso eu vou especificar Google Aiken e, em seguida, continuar com o Google apenas assim. Agora, o que é dar uma olhada? Está bem, parece bem, mas queremos adicionar alguma margem. Então, para a Disney, vamos colocar o nome da turma e a margem dos três melhores, algo assim. OK, parece bom. Agora precisamos torná-lo centrado verticalmente. Ou talvez em alguma margem para os elementos superiores. Então parece mais agradável. Então, para este grande componente, vamos definir o nome da classe, e vamos colocar margem na página superior. Então esta é a classe que eu defini em um fora dos arquivos utilitários, então ele apenas dá um monte fora de margem para os elementos. Então, se nós inspecioná-lo como você pode ver, margem superior nos dá 150 picos mais. Tudo bem, então parece bom. Agora, e quanto à funcionalidade? Como podemos realmente gerenciar nossa assinatura e finalmente começar a adicionar este Facebook e Google Science. Então, o que precisamos fazer dentro do Firebase gs onde inicializamos nosso aplicativo? Precisamos importar da biblioteca da base de fogo. Então aqui vamos importar a base de fogo assim. Então aqui sob o aplicativo, vamos exportar const disponível, que vai nomear apenas fora e vamos chamar app ponto off e ele vai nos dar o objeto que podemos usar para interagir com base de fogo. Então vamos guardá-lo dentro da assinatura. Nós vamos definir nossos manipuladores para eventos on click para botões. Então vamos colocar em primeiro lugar, digamos que o login no Facebook, e então eu vou fazer o mesmo para o Google no Google assinatura e sua funcionalidade é quase a mesma. Então eu vou criar 1/3 função que eu vou chamar dentro na assinatura do Facebook e dentro na assinatura
do Google. Então, vamos nomeá-lo algo como entrar com provedor e provedor como Facebook ou Google. Tudo bem, então como um argumento ele vai receber este provedor e então nós vamos fazer alguma idéia pensar. Então, dentro do Facebook, faça o login. Nós estamos indo para chamar, entrar com provedor e Rubble passar um provedor vai falar um provedor de luta em um momento e aqui também assinar com provedor agora como podemos realmente assinar assim dentro assinatura com provedor, nós pode apenas digitar fora e importado do nosso arquivo misc firebase este fora do objeto que temos
daqui se apenas colocar ponto da inteligência. Podemos ver muitas coisas acontecendo aqui. Podemos acessar o usuário atual. Podemos confirmar redefinir senha e diferente. Se escrevermos a assinatura, podemos ter coisas diferentes aqui. Nós entregamos com e-mail e senha com número de telefone com papa com redirecionamento. Então, muitas coisas acontecendo aqui nós estamos interessados em assinar com pop-up e se nós chamarmos isso montado dentro, nós precisamos passar o provedor e ele vai ser fornecido que nós vamos receber como um argumento. Então vamos colocá-lo aqui. Então, o que é esse provedor? Então este objeto provedor que precisamos importar de, digamos, biblioteca
firebase e é estático. Então o que precisamos fazer aqui, precisamos importar base de fogo do firebase barra AP novamente, é importante importar do firebase barra ap Então aqui, como provedor, vamos passar o novo firebase dot auth dot facebook off provedor e precisamos chamá-lo vai nos retornar e você provedor objeto que vamos passar como indocumentado para disfunção eo mesmo rebelde fazer para assinatura Google. Vamos colocar uma nova base de fogo fora, mas desta vez o Google fora do provedor assim. Agora, o que realmente associa isso? Manipuladores com botões. Então, para o evento clique para o padrão do Facebook vamos colocar na assinatura do Facebook e para Google, vamos colocar no clique no Google, Entrar assim. Tudo bem, parece bom. Agora esta assinatura com pop up se nós, no entanto, é uma promessa. Por isso, temos de esperar por isso. Vamos converter nossa assinatura com provedor para em uma função de pia e aguardar esta assinatura com Pope up. E então vamos colocar os resultados em resultado viável. E vamos Cônsul olhar e ver. O que recebemos, no entanto, se eu atualizar a página que eu abri conselho, então eu posso ver que respondeu com 400 Arkwright. Isso é bom. Vamos clicar em Continuar com o Google, por exemplo. Tudo bem, você pode ver que ele realmente está fazendo algo, e agora eu posso selecionar uma de minhas contas do Google. Certo, vamos selecionar a mente das minhas contas. E agora você pode ver que eu tenho resultado aqui. Então, é um objeto que tem três objetos diferentes informações adicionais do usuário para que possamos ver que este é o nosso novo usuário. Podemos receber um e-mail com nome, ideias
diferentes. Podemos obter uma imagem se o nosso e-mail for verificado. Então, esses dados vêm do Google e você pode ver provedor. Deponho isso ao Google. Em seguida, temos credencial, diferentes tokens de acesso e, em seguida, temos objeto de usuário. Portanto, este objeto de usuário representa o usuário conectado no momento. É geral. E a partir daqui podemos entender se o nosso usuário logou. Nós não estamos. Vamos falar sobre este objeto de usuário em detalhes nos próximos vídeos. Então agora o que podemos fazer Podemos realmente voltar para Firebase Weaken, Ir para autenticação. Aqui podemos recarregar nossa autenticação. Digamos que assine no banco de dados. E aqui nós confinamos nosso e-mail com provedor quando ele foi criado e criado Usuário I d. Então, primeiro lugar, este não é um banco de dados. Isto é como um pequeno banco de dados dentro desta biblioteca de autenticação. Ainda precisamos armazenar nossos usuários dentro do banco de dados. Isto é só para rastrear. Quantos usuários entramos em nosso aplicativo ou algo assim? Tudo bem, então agora vamos realmente modificar nosso código ligeiramente e vamos armazenar nosso usuário dentro do banco de dados. Então, primeiro de tudo, deixe-me colocar, tentar, pegar, olhar aqui porque trabalhamos com promessas e queremos ter certeza de que sempre lidamos com qualquer outro. E, a propósito, apenas para notificar o usuário que estamos atualmente conectados ou se tivermos algum erro, podemos usar o componente de alerta que vem novamente do nosso terno. Então, se tivermos algum erro, vamos chamar alerta, e então se colocarmos ponto podemos ver que podemos ter acesso a informações atter e
mensagens de sucesso e aviso . Então vamos colocar a mensagem. Então, como um primeiro argumento, vamos colocar erro essa mensagem, e então precisamos colocar a duração dessa mensagem fora desta mensagem de alerta. Então vamos pobre por segundos em especificado em milissegundos. E se formos assinados, colocaremos alerta. Digamos que sucesso. E então nós vamos colocar assinado com novamente tempo fora quatro segundos. Tudo bem. Parece bom. Agora o que podemos fazer com esse resultado. Como se lembra, recebemos um objeto. Recebemos informações adicionais do usuário e também recebeu objeto do usuário. Agora, verificando se informações adicionais do usuário é seu usuário,
então, se o nosso usuário é que está sendo assinado no momento, é um novo usuário irá armazená-lo dentro do banco de dados. Então, como podemos fazer isso? Vamos voltar para Firebase Thaci. Vamos importar outra biblioteca, que será o banco de dados de barras firebase para interagir com o banco de dados e semelhante ao off. Nós estamos indo para exportar banco de dados const ap dot banco de dados assim. Então, sob este banco de dados, valioso podemos interagir com o banco de dados. Vamos saborear a partir da assinatura interna, vamos referenciar o banco de dados, que importamos de diversos firebase. Então vamos colocar a Dot aqui. Precisamos especificar referência, que é basicamente caminho em nosso banco de dados no ritual armazenar nossos dados. Então vamos armazenar nossas informações de usuário sob perfis de barra barra usuário i d. Então vamos abrir interpolação de cordas. E como usuário I d. Nós vamos referenciar usuário ponto Nós podemos ter exibição de e-mail, nome atrasado e um monte de outras coisas relacionadas a este usuário. Mas estamos interessados no usuário I d. Então este usuário I d vai ser o mesmo que este usuário. Eu d dentro da biblioteca de autenticação. Então vai ser como se criássemos um novo usuário. Ele foi adicionado à autenticação o usuário I d é gerado automaticamente, e então vamos usar este usuário I d para armazenar o usuário dentro do banco de dados. Certo, então agora quando tivermos a referência, podemos colocar outro ponto e daqui, precisamos chamar o método SAT. E como você pode ver na descrição, ele grava dados neste local de banco de dados. Então, se eu chamá-lo aqui, vamos armazenar um objeto porque temos formas de dados adjacentes baseados. Então nosso objeto vai ficar assim. Teremos nome e nome vai ser nome de exibição do ponto do usuário. Então também teremos criado em que dirá, quando a conta tiver sido criada. Então, para colocar vamos um carimbo de data/hora apropriado para o nosso banco de dados novamente precisa usar algum estático. Vamos ver a propriedade que vem do Firebase Library. Então nós temos um relatório firebase dot banco de dados ponto valor do servidor ponto ponto carimbo de hora, e ele vai colocar carimbo de hora sanitizado para o nosso banco de dados. Tudo bem, então este ponto disse também retorna essa promessa. Então, sempre que fazemos alguma coisa com base de dados ou qualquer outra coisa, interagimos com qualquer coisa. Muito provavelmente, vamos interagir com promessas. Então é por isso que precisamos esperar e tudo será capturado por este bloco catch e usuário será notificado. Tudo bem, vamos guardar tudo isso porque parece, realmente muito. Agora vamos clicar em, Continuar com o Google. Vamos selecionar meu e-mail e agora estou conectado. Mas é realmente um muito estranho. Isso é provavelmente porque eu tenho esta conta já adicionado Aqui, talvez você me deixe lidar com esta conta. E agora vamos tentar mais uma vez porque precisamos receber um assunto. Tudo bem, então clicamos em, continuamos com o Google, depois selecionamos nossa conta novamente. E agora temos permissão negada esta noite. E não temos isso para colocar ponto na mensagem dela. Mas a coisa é que temos permissão negada e isso é porque se abrirmos nosso banco de dados , tudo bem, vamos clicar, criar banco de dados. Então vamos para as regras. E aqui criamos o banco de dados bloqueado por padrão. Então, o que quer que tentemos fazer com o banco de dados, teremos essa permissão esta noite porque, como vocês podem ver, nós temos permissão de leitura e direitos definida como cai para todos fora de nosso banco de dados. Então, para evitar que o que podemos fazer aqui antes de termos dito essas regras, vamos dizer isso para perfis, e precisamos desafiar, digamos, EBA
esque para nossas regras de segurança. E não é essa maneira padrão de definir algo com segurança, mas leva tempo para se acostumar. Confie em mim, é muito fácil de trabalhar. Então temos nosso caminho de perfis. Só precisamos seguir o passado. Então nós armazenamos nossos dados sob perfis de barra usuário i d. Então vamos colocá-lo como um objeto. Então temos perfis, então precisamos colocar uma chave. E porque vai ser algo dinâmico que vai mudar, vamos colocar um cifrão, e então podemos colocar algo como usuário, i d. Isso é apenas para referenciá-lo dentro do objeto aninhado. Deixe-me explicar o que quero dizer. Então, sob este passado, vamos abrir outra vez outro objeto, e dentro, vamos colocar outra chave que vai ser “dot treat” e dot “right”? Exatamente o mesmo que temos aqui. Então para o ponto Leia o que vamos fazer. Vamos fazer referência a esse usuário
que recebemos daqui. Agora ele vai como disponível. Podemos fazer referência dentro deste escopo. Digamos que eu apenas destaquei. Então, se o usuário I d que é que um é igual off e off aqui neste vamos dizer contexto fora regras é um valor global que podemos acessar para
que possamos ler dados de perfis barra usuário i d. Apenas um usuário i d. i d.
Apenas um usuário i d. poderíamos tentar acessar é igual a nós dot usuário i d. Então isso significa, na verdade, apenas o proprietário fora deste documento. Somente o usuário real pode ler seus próprios dados. Qualquer outra pessoa, qualquer outro usuário terá acesso negado. Certo, é assim
que definimos as regras para não tratar. Então vamos copiá-lo e vamos aplicar o mesmo para o ponto certo? Então, o que vai acontecer aqui? Como ele vai entender os dois anos assinados bem, vamos voltar ao código quando chamarmos este sinal com pop pop. Agora, nosso usuário está conectado internamente aos serviços do firebase. Então, quando tentamos acessar o banco de dados depois, firebase irá buscá-lo e este usuário I d será conhecido para o banco de dados e vai ser este usuário de ponto auth i d. E então vamos verificá-lo contra o caminho que escrevemos. Agora vamos clicar em Publicar. Certo, regras publicadas. Agora vamos voltar para o banco de dados e, na verdade, vamos copiar, Visite ALS e vamos colá-los, também. Regras do banco de dados para Jason. Então eles estão sempre lá. Certo? Em seguida, volte para a autenticação. Vamos excluir esse usuário e começar de novo. Então eu vou clicar em,
Continuar com o Google. Vou selecionar minha conta, e agora não tenho nenhum erro. Agora, eu assinei. Então, agora, se eu navegar de volta para o banco de dados, eu posso ver que eu tenho dados. Eu tenho perfis e que eu tenho usuário eu d exatamente o mesmo que temos aqui. Então é assim que funciona com base de fogo. Tudo bem, então se expandirmos,
podemos ver que temos o nosso nome, que é 16 gelado, que é o meu nome na conta do Google. E então nós criamos em que é milissegundos armazenados internamente pela base de fogo. Certo, agora criamos o usuário e gerenciamos nossa página de assinatura. Parabéns. Acho que não foi muito complicado para você. porque há muitas coisas para cobrir aqui. Assinar entrada que este banco de dados de regras de segurança. E tudo vai de uma só vez. Sei que é difícil, mas confie em mim, deixe passar depois de uma hora ou talvez um dia, quando você vai dar uma olhada em tudo isso
mais uma vez. Não será assim tão complicado. Tudo bem, então vamos cometer nossas mudanças e terminar este vídeo, então nós vamos puxar, pegar em tudo, e então nós vamos cometer algo como editar login na página e assinar e com Facebook Slash Go menina. Tudo bem. Perfeito. No próximo vídeo, continuaremos nossa conversa com autenticação e iniciaremos nosso gerenciamento de usuários. Vejo-te isso.
103. Criando o perfil - API de API de contexto e gestão global: Ei, neste vídeo, eu gostaria de falar sobre contexto, um p i e gestão global do estado. Quando se trata de gerenciar perfil de usuário como podemos abordar isso, sabemos que ele deve ser acessível globalmente a maior parte do tempo dentro de cada componente. Imagine um componente muito menos na APP. Este componente precisa exibir o nome de usuário que está atualmente conectado em questão é onde
gerenciamos esse usuário exatamente. Vamos supor no componente APP. Então, para obter nome de usuário, devemos passá-lo através dos adereços para cada próximo componente todo o caminho abaixo da árvore. Mas isso não é legal. Nós temos, como, 10 componentes acima, e cada componente está desempenhando um papel na medida em que isso é chamado de perfuração de prop. Quando algum valor está sendo passado para baixo, os adereços em um monte fora níveis profunda, isso não é bom e deve ser evitado para evitar problemas ajoelhados. Há contexto, um P I em reagir. Ele introduz o conceito off provedor e provedor de consumidor é um componente que fornece todos os seus filhos com algum valor ou contexto. Consumidor é um componente que consome o contexto e obtém o valor usando contexto. AP I. Podemos gerenciar facilmente o nosso usuário no componente provedor e, em seguida, consumidores. Em qualquer componente. Queremos evitar a perfuração de sondas e componentes intermediários. Nós iria criar contexto de usuário e colocar nome de usuário como seu valor. Em seguida, nós iria embrulhar componente em torno do provedor de usuário. Então, basicamente, todos os componentes têm acesso ao contexto do usuário para consumi-lo dentro do componente onde precisamos obter o valor de contexto que chamaríamos usar o gancho de contexto. Dessa forma, somos capazes de obter o nome de usuário de qualquer lugar dentro do nosso aplicativo. Não há limitações de uso de contexto. Nós somos capazes de colocá-lo em qualquer lugar no componente APP em torno da página inicial em torno de multi página formulário e assim por diante. Tudo bem, vamos realmente ver como o contexto AP I funciona no exemplo do nosso aplicativo de bate-papo. Vamos lá. Então, na pasta de recursos, vamos criar outra pasta que vamos chamar contexto. E aqui vamos colocar todo o nosso contexto criado. Vamos criar novo arquivo e nome móvel que talvez não contexto de usuário, mas contexto de perfil. Eu acho que é mais adequado no nosso caso, Então vamos colocar perfil ponto contexto cãozinho s. Então, qual é a nossa estratégia? Nós vamos criar este contexto e vamos colocá-lo dentro do nosso componente APP, para que qualquer outro componente dentro da nossa aplicação possa ter acesso a ele. Então, o que precisamos para criar um contexto? Nós simplesmente precisamos chamar criar contexto que vem do pacote de reagir. Então vamos colocá-lo disponível. E digamos que vai ser um contexto de perfil assim. Agora precisamos criar um provedor,
um componente, um componente, e que irá fornecer a todos os seus filhos com este contexto de perfil. Então vamos pobre exportação CONST. Provedor de perfil. E vai ser um componente. Então isso vai ser uma função assim. Tudo bem, agora o que precisamos para embarcar aqui? O que vai voltar? Ele vai retornar o provedor de pontos de contexto de perfil e, em seguida, dentro deste provedor, precisamos de suporte de todos os nossos componentes, o que quer que passemos por dentro. Por isso, vão ser os nossos Filhos. Este provedor de perfil é apenas um rapper, então vamos destruí-lo como um adereço aqui e colocá-lo dentro de um componente provedor
assim . Tudo bem, agora, se temos ou podemos ver que reagir deve estar no alcance. Tudo bem, deixe-me importar reagir. E algumas pessoas se livram desse aviso agora como somos capazes de fazer qualquer coisa. Então, como este é um componente, podemos fazer nossa gestão estadual diretamente aqui. Vamos navegar Teoh nossa rota privada, e aqui sabemos que colocamos isso por enquanto. Colocamos este touro em valor. Isso cai por padrão. Então vamos tratar disso e ele consumirá o nosso contexto. Então vamos colocar isso. Digamos, ouro. Dentro deste contexto, vamos criar, vamos ver perfil e dito Perfil como estado usado, que vai ser,
digamos, digamos, Abul em valor por enquanto, apenas para demonstrar como contexto funciona a fim de passar em valor para esses contextos, precisamos colocá-lo como um adereço para fornecer seu componente aqui. E precisamos passar nosso perfil assim e vamos conhecer o set profile. Não vamos destruí-lo assim. Tudo bem, estamos prontos para ir. É isto. É assim que podemos gerenciar nosso contexto agora para realmente usá-lo dentro de nosso aplicativo dentro de nosso componente. Precisamos colocá-lo aqui no componente aplicativo apenas em torno do interruptor. Então vamos digitar o que chamamos de provedor de arquivos raw. E é isso. E eles vão pensar sobre o contexto que ele pode ser muito personalizável porque este é apenas um componente. Vamos dizer que se precisamos obter usuário com específico I d. Podemos simplesmente passar este usuário i D como um adereço, e então podemos pegá-lo de adereços aqui e, em seguida, colocar o nosso A P I chamar ou qualquer outro
gerenciamento de estado relacionado a este usuário particular i Isso é
realmente, muito legal,
Tudo bem, Tudo bem, agora que nós fornecemos todos os nossos componentes com provedor de perfil sem pode consumi-lo. Então, como podemos fazer isso? Como você se lembra eu mencionei usar o gancho de contexto. Então, dentro de nossa rota privada, Em vez de fazer isso, podemos simplesmente fazer perfil constante igual a usar contexto que vem de reagir pacote e, em seguida dentro dos registros dentro pai é é que precisamos especificar contexto que criamos. Vai ser este contexto de perfil, e é realmente tedioso referenciar contexto de perfil cada vez que chamamos com
contexto de uso . Então, para evitar isso, podemos criar outro gancho, um rapper para contexto de perfil para torná-lo mais acessível. Então, a partir de contatos de perfil Sim, arquivo, poderíamos exportar Const. Digamos Use perfil Hook, que vai ser usado contexto, contexto de
perfil assim. E agora diz que não pode ser chamado. Oh, desculpe-me. Vai ser uma função que retorna o que quer que este contexto de uso retorne. E esse contexto de uso nos retorna um valor. Então, a partir do nosso código, podemos simplesmente chamar o perfil de uso e vamos remover o contexto de uso a partir daqui. E agora, esse perfil será esse valor que passamos aqui. Então agora podemos verificar se nenhum perfil, então vamos redirecionar e vamos fazer exatamente a mesma coisa para o perfil público. Então daqui, em vez de falso, vamos usar o perfil, e é basicamente isso. Agora eu já lancei o aplicativo,
Então, se eu tivesse um fresco, nada mudou. Como você pode ver, se eu tentar acessar a página inicial, estou sendo redirecionado para entrar para que nada tenha sido alterado. No entanto, agora gerenciamos nosso perfil como um estado global que podemos acessar de qualquer componente, não apenas da multidão pública. Assim, cada componente que está dentro do provedor de perfil pode acessar seu contexto. Tudo bem, com o contexto de uso, Gancho e nós criamos um wrapper em torno do contexto de uso com contexto de perfil, que é usado perfil. Então agora é ainda mais fácil de usar para nós acessar. Além
disso, é muito importante mencionar que digamos que criamos esse contexto de perfil. Ou talvez imaginemos que desfilamos algo como contra-contexto. Digamos que 12345 está bem, e dentro do nosso aplicativo. Em vez de usá-lo assim, usamos várias vezes. Então, digamos que para entrar na página que temos, digamos provedor contador de contexto contador como este tudo certo, eo mesmo vale para casa. Então nós temos isso assim. Agora temos dois contatos diferentes. Sua definição é a mesma, mas eles são diferentes. Então, se dentro de sinal na página, vamos dizer tentar acessar contexto fora do contador,
em seguida, vamos chegar a um. Bem, você, se tentarmos acessar o mesmo contexto com o contexto de uso, gancho dentro da página inicial, mas terá outro valor porque eles também, têm estados diferentes. Tudo bem, então é como conseguir separar estados, mas com uma definição faz apenas para apontar que é diferente. Então é basicamente isso no próximo vídeo, o que vamos fazer,
vamos continuar trabalhando com nosso provedor de perfil e as pessoas finalmente gerenciaram nosso usuário do
firebase conectado . Vejo você lá.
104. Gestão de estados globais com contexto: Ei, bem-vindo neste vídeo. Vamos gerenciar nosso usuário do firebase conectado com contexto. AP I Vamos No vídeo anterior quando chegamos a conhecer contexto AP I criamos
provedor de perfil . Então agora vamos usar o estado real em vez de apenas um touro em valor. Então vamos substituir false por null. E vamos também chamar, Vamos definir a função de atualização do perfil definido. Tudo bem, então vamos usar o ato Yousef para obter o usuário da base de fogo quando o componente for montado. Então vamos usar o seu fato e ouvir o que vamos fazer. Vamos cancelar o estado mudado. Então, da base de fogo, vamos usar nosso objeto. E se colocarmos ponto se
escrevermos, vemos que podemos usar em ambos os estados alterados. Então, isso no estado dos EUA mudou. Permite-nos subscrever o usuário atualmente conectado dentro da base de fogo. E dentro desta assinatura, somos capazes de acessar fora do objeto. Então vamos colocar assim e para análise. Cônsul
, desligue o objeto. Agora, se navegarmos de volta para o aplicativo se
abrirmos nosso conselho, veremos isso fora do objeto. E se expandimos é exatamente o mesmo objeto quando entramos com o Facebook
ou Google. Então é assim que ele pode ser gerenciado facilmente. Se fôssemos assinados para o aplicativo, não
veríamos esse objeto. Seria agora. Então, a questão é por que estamos vendo isso atualmente? Como os gerentes do firebase têm sessões para
nós, não precisamos implementar tudo. Uma vez que estamos conectados, autor, objeto será preenchido automaticamente para nós e gerenciado para nós. Nós não precisamos fazer tudo o que precisamos para apenas entrar ou sair
e, em seguida, o objeto do usuário estará aqui. Certo, usando essa informação, o que podemos fazer em vez de apenas Cônsul, , vamos perguntar se ambos os objetos existem. Se for preenchido com algum valor, então vamos fazer alguma coisa. Caso contrário, se este objeto do Earth não for o objeto, se ele ainda estiver, então o usuário não está conectado. Então este estado ligado mudou, chamado pelo menos uma vez quando o componente monta e se não estamos conectados, então ele vai ser definido para saber também se nós sair do aplicativo porque esta é a assinatura. Será atendido por esta chamada. Para trás e para fora do objeto será tal saber. Então, dentro disso, vamos definir perfil para agora e aqui quando temos o objeto que
podemos chamar, definir perfil e colocar alguns dados de perfil que vamos definir aqui. Então, nossos dados de perfil vai ser o próximo que vai ser o primeiro usuário I d. que vamos obter de ambos objeto ponto seu i d Que podemos ver aqui. E isso refletirá nosso usuário que eu d em muitas bibliotecas que vimos na base de fogo. E também eu era usuário I d dentro de banco de dados em tempo real. Então também queremos talvez e-mail. Então vamos passar o e-mail de ponto de objeto, e também, precisamos de nossos dados do banco de dados em tempo real, então precisamos realmente obtê-los aqui. Então o que vamos fazer como podemos ver, perfil já está declarado. Tudo bem, talvez menos. Basta nomeá-lo dados e disse dados de perfil. Ok, então aqui para obter dados reais do banco de dados para este usuário, precisamos chamar novamente o banco de dados do MISC Firebase. Então vamos colocar referência de novo, vamos fazer perfis. Então nós vamos derramar fora do objeto ponto seu i d Então nós mudamos aspas para a
população contador de cordas e então nós queremos derramar assinatura de tempo aéreo para o nosso líder de usuário. Então, se algo mudou, então queremos ser notificados sobre isso. Não queremos gerenciar tudo manualmente. Assim, com base de dados em tempo real e com realmente qualquer banco de dados e base de fogo, é muito fácil. Então, para obter dados apenas uma vez que chamamos ponto uma vez método para colocar uma assinatura em tempo real sobre
esses dados que precisamos colocar, então precisamos chamá-lo como uma função e primeiro argumento. Precisamos especificar o alvo, o evento. Digamos que sim no valor. Queremos executar este Colback. Então, sempre que nossos dados nesse caminho dentro do banco de dados mudam como qualquer coisa, esses Colback serão disparados como todas as vezes e receberemos um instantâneo. Então vamos tirar uma foto do Cônsul Sorte assim. Então agora estamos dentro de casa porque nós realmente temos alguns dados de perfil. E como você se lembra, dentro da rota privada, verificamos o perfil para que não vejamos a página de login. Ok, isso é bom. Então, nosso instantâneo de dados tem referência de nó chave e algumas outras coisas e metadados relacionados a esse snapshot nesses caminhos dentro da base de dados. Bem, dentro do instantâneo temos este método. Ele é chamado instantâneo ponto camisa snap valor, valor
escuro. E ele vai nos dar os dados do banco de dados, Informar fora do objeto JavaScript. Então, vamos dizer que dados de perfil são iguais a instantâneo, não valor. E agora vamos ver os dados do perfil do Salak como este. Vamos verificar isso. Agora. Se eu atualizar a página, eu posso ver ter um objeto com anúncio criado e nome, que é ela parece 16. Exatamente os mesmos dados que temos dentro do banco de dados. Agora, o que precisamos fazer? Podemos destruir este perfil. Dados enfraquecer estrutura D, nome e criou que assim. E aqui podemos mover esse objeto de dados para essa assinatura assim, e então o que podemos fazer. Também podemos mover isto nos dados do perfil para aqui. E para esses dados podemos colocar nome e criar exatamente assim. Então, o nosso perfil no final teremos nomeado criado em seu e-mail i D. Certo? Então é isso. E agora passamos esse estado de perfil de dados para baixo no contexto. Então, dentro do nosso privado, também
precisamos de alguma forma manter o controle se estamos sendo registrados no momento. Então precisamos colocar o estado de carregamento para colocar um girador ou outra coisa. Então vamos colocar outro estado que vamos nomear está carregando e definir está carregando por padrão. Vai ser definido como verdadeiro. E logo depois que dissemos que o perfil que vamos chamar de set está carregando e colocando-o em falso. Ou se não tivermos nenhum perfil, vamos ligar para o Set está carregando e colocar quedas também. Tudo bem, agora isso está carregando. Vamos passar com o nosso contexto. Então, em vez de apenas passar perfil dentro, vamos passar um objeto com está carregando estado e também perfil. Então, agora, dentro de nossa rota privada, quando usamos o perfil, recebemos um objeto com seu perfil e objetos de perfil dentro. Então nós vamos estruturar nosso perfil a partir dele e o mesmo celular fazer quatro usar perfil. Então agora o que podemos fazer aqui, dentro privado para fora nós podemos realmente usar isso está diminuindo. Então vamos D estrutura está carregando e o que vamos perguntar. Então vamos colocar outro se aqui, e vamos perguntar se nossos dados estão carregando e ainda não temos dados de perfil. Então vamos devolver o contêiner do nosso terno e lá dentro, vamos colocar a Lei Ordem. Vai ser um spinner, também um componente do nosso terno, e vai ser centrado. Ele vai ser centrado Vertical e tamanho lobo whoops. tamanho desligado é igual a M d. Então o conteúdo vai ser carregado, e a velocidade vai ser lenta. E vamos movê-lo para evitar que ele lhe emprestou. Vamos movê-lo para o topo assim. Muito bem, esta é a nossa primeira condição, e depois também precisamos modificar essa. Vamos perguntar se não temos perfil, e se não temos apenas estado de carregamento, então vamos redirecionar. Tudo bem, então vamos checar. Agora. Quando atualizamos a página, podemos ver o girador muito legal, certo? E somente quando obtemos os dados, nós realmente vemos a página inicial. Muito bem, vamos fazer exactamente a mesma coisa pela multidão pública. Então vamos copiar essa lógica e colocá-la aqui. Vamos Destructor está carregando e vamos perguntar se temos está carregando e não temos perfil então vamos colocar de novo estado de carregamento como este se tivermos perfil e, bem, pode ser um pouco complicado. Então, se temos o perfil e o carregamento está definido como falso, então vamos redirecionar. Tudo bem, é basicamente isso. Eu só quero Teoh fazer mais um passo importante aqui porque estamos trabalhando com assinaturas em reagir. Sempre que trabalhamos com ouvintes em tempo real para os dados, usamos uma assinatura. Portanto, sempre que tivermos uma assinatura, precisamos cancelar a assinatura dela quando não precisarmos dela. Então isso no palco dos EUA mudou. Se você pode ver ele retorna base de fogo cancelado. Então ele nos retorna uma função que precisamos chamar para cancelar a assinatura desta assinatura no estado
fora alterado. Então vamos colocá-lo, vamos dizer off no submarino e vamos cancelar isso no sub e nossa função de limpeza fora do
ato Yousef . Então vamos retornar uma função e aqui vamos cancelar. Então, apenas assim e o mesmo se aplica para nossa referência de banco de dados aqui. Então, neste passado, colocamos um ouvinte em tempo real que está no valor, e é o nosso Colback. Então nós queremos ter certeza de que nós cancelamos a assinatura dessa também. Então aqui, digamos, dentro deste uso de fato, vamos derramar, deixa uma referência de usuário. Em seguida, vamos atribuir Use uma referência para referência de banco de dados neste caminho como este e seguida, usuário áspero no valor. Vamos executar este retorno de chamada sempre que não temos nenhum dado. Se o nosso usuário não estiver conectado, Se não tivermos nenhum outro objeto, vamos perguntar se o usuário ref está definido. Então nós vamos ligar, usar ponto áspero fora porque se eu colocar ponto aqui, eu posso colocar eu poderia colocar uma vez e também eu posso adiar e isso fora como você pode ver desprende um retorno anteriormente ligado com em para que possamos. Desta forma, podemos cancelar a inscrição destes chamada de volta a partir destes caminho dentro do banco de dados. Na verdade, o mesmo que faremos dentro de nossa limpeza para efeito de uso. Então este sempre que assinamos e este sempre que nós quantificamos o componente, então aqui nós vamos perguntar se o usuário Rafa, então vamos usar um ponto ref fora de cancelar a assinatura desta referência de usuário. Tudo bem, então é basicamente isso. Espero que não tenha sido uma causa muito confusa para mim. Quando? Pela primeira vez. Quando eu vi,
era , mas no final, faz sentido. Tudo bem, vamos cometer nossas mudanças e terminar este vídeo. Vamos colocar em tudo. Então vamos cometer tudo com a mensagem. Algo como o usuário da idade do homem com contexto de perfil Put riel time subs algo assim. Muito bem, vemo-nos no próximo vídeo.
105. Começar a criar a barra de lateral e o painel: Ei, bem-vindo. Agora que temos o fluxo de assinatura completo, vamos finalmente começar a construir nossa página inicial. Vamos começar a partir do local esquerdo. Então primeiro vamos construir nossos botões do que a lista de chat e depois vamos para o Maine. Janela Shatt. Vamos para dentro de páginas em vez desta definição. Vamos definir a nossa coragem. Então ele vai ser grande componente, que vai ser fluido e classe Nome vai ser um Chuan 100. Vamos fazer com que seja em altura total. Então dentro vamos para o elemento de controle e, em seguida, vamos derramar elemento de coluna do nosso terno. Então, para dispositivos pequenos, levará todas as colunas, que são 24 colunas e começando a partir de dispositivos do meio. Vamos colocar algo como oito. Não saúde, mas oito. E dentro desta coluna vamos usar o componente da barra lateral, mas não o que vem do nosso terno. Aquele que nós mesmos criaremos. Vamos salvá-lo. E sob componentes, vamos criar um novo arquivo, que vamos nomear Sidebar cãozinho s. Vamos abri-lo e vamos pedir uma pasta para um rap. Dave, eu vou colocar o nome da classe fora da altura total e depois um pouco fora de bater no topo. Então, dentro vamos dividi-lo em dois elementos. Então teremos a parte superior com nossos botões e na parte inferior teremos uma
lista de salas de bate-papo . Então vamos primeiro criar def para a nossa parte superior e na parte inferior porque ainda não temos nenhuma conversa na lista. Vamos apenas resumir texto como este. Então, dentro deste diferente vai derramar malabarismo painel que irá criar em um momento e
salvá-lo . Então, outros componentes. Vamos criar nova pasta, que vamos nomear o relatório aqui. Bubble definiu dois arquivos. Primeiro vai ser togs indexados, que vai ser o nosso componente de painel, mas vamos gerenciar tudo, mas por enquanto vamos mantê-lo vazio. Então vamos nomeá-lo, relatório
pai e apenas colocar Olá insight e segundo elemento vai ser malabarismo painel. Então, aqui vamos definir o nosso botão e o próprio drover. Então primeiro queremos nos livrar do embrulho Div. Então vou definir um botão aqui, que vai ser o nosso Tobler. Digamos que vai ser um elemento de bloco. Vai ter colarinho azul e lá dentro vamos colocar Aiken que importamos do nosso terno. Aiken vai ser essa palavra. E, em seguida, o texto vai ser painel como este. Agora vamos realmente dizer com e vamos ver, o que temos? Então, se atualizarmos a página dentro da barra lateral, não
temos painel até ir, Vamos importar. E também dentro de casa, não temos barra lateral. Vamos importar também. Tudo bem, vamos verificar. Certo. Então temos o botão. Mas quando clicamos, nada acontece. Então vamos definir o nosso componente Drover em ou Drover, elemento aqui ao lado de Button. Eu vou colocar Drover que vem do nosso pacote de terno e não é um elemento tão fechante dentro. Nós realmente precisamos derramar elementos drover, mas vamos defini-los dentro deste arquivo NGS adulto índice. Então, para esta luta, nós só precisamos definir esta propriedade show e ele vai ser Deve ser um valor bowline que irá indicar quando este drover é aberto. Então precisamos definir sobre evento altura e, em seguida, também precisamos definir colocação. No nosso caso, ele vai ser à esquerda ou agora precisamos realmente definir nossos manipuladores ou estado para o nosso drover. Precisamos manter o controle de seu estado por conta própria. E uma vez que nós vamos ter um monte fora motéis ou drovers em nossa aplicação, e nós estamos indo para re usar um monte da mesma lógica, eu propus para criar uma esperança personalizada que vamos nomear o estado do modelo de uso e ele irá expor apenas três elementos está aberto na altura e no show. Então, sob MISC, vamos criar novos ganchos personalizados de arquivo GS. Aqui vamos definir uma nova função, que vai ser o nosso gancho, que vamos nomear usar estado modelo. Ele receberá o valor padrão. Digamos que o valor padrão, que será definido como false se for indefinido. Dentro, vamos definir estado, e por padrão este estado será o nosso valor padrão que passamos como um argumento e também aqui vamos definir algumas funções auxiliares. Digamos que sim. Primeira função vai ser aberto e será um envolto uso frio de volta com antecedência para torná-lo otimizado, e ele vai chamar, disse ST, e vamos defini-lo como verdadeiro e o mesmo que aplicaremos para fechar. Mas em vez de verdade, vamos derramar falso aqui e deste gancho, vamos voltar ao nosso estado. Talvez vamos renomeá-lo também está aberto, e o conjunto aqui está aberto. Então, a partir deste gancho, vamos retornar é aberto, aberto e fechar funções auxiliares. E não se esqueça de exportar o estado do modelo deste ano a partir de ganchos personalizados. Tudo bem, então dentro do árabe ou alternar, nós vamos usar este estado modelo de uso que nos retorna está aberto. Em seguida, ele nos retorna perto e aberto. Então agora podemos usá-lo. Então, na altura, vamos especificar com nossa própria função de roupas que definimos no show de ganchos. É um touro em valor, tão pouco especificar está aberto e também para o nosso botão. Quando clicamos nele, queremos mostrar o Drover. Então, para este botão para no evento clique, vamos especificar Apenas abrir. Tudo bem. E agora precisamos colocar algo dentro do Rover. Vai ser este elemento. Então vamos definir painel e você vai ver que ele será importado do ponto Isso significa que ele será importado da nossa pasta atual. Então por que colocamos o Índice Gs assim? Então, se o usarmos em qualquer outro componente, digamos dentro de páginas e a maneira como importamos, vai ser assim. Vamos importar de componentes. Esse relatório não especificará Dashboard Index GS porque ele é nomeado como índice. Sim, podemos especificar apenas o nome da pasta onde este índice pontos gs re sites e ele vai funcionar. Tudo bem, então agora vamos salvar tudo e vamos dar uma olhada. Agora, se eu clicar no painel, funcionou perfeitamente. Então eu acho que é isso para este vídeo. No próximo vídeo, continuaremos e tornaremos nosso mortal um pouco mais responsivo. Porque se eu vou apenas clicar nele, se eu vou,
você sabe, você sabe, apenas redimensionar a janela, você pode ver que ela permanece estática. Este não é um comportamento amigável, então vamos corrigi-lo mais tarde. Mas por enquanto, vamos confirmar nossas mudanças, e vamos dizer, começando ou começou a construir o componente da barra lateral. Tudo bem. Perfeito. Vejo-te no próximo.
106. Barra de sites responsivos usando media: Ei, bem-vindo nisso. Nós vamos fazer nosso trabalho,
er, er, que criamos no vídeo anterior responsivo. O que quero dizer é que agora, se tentarmos inspecionar nosso elemento e se abrirmos Drover, se redimensionarmos a janela,
ela permanece estática. Bem, não
é nada sensível ao que podemos fazer para consertar isso para Drover. Há esta sonda disponível, que está cheia, o que significa que Drover estará disponível para tela cheia. Vamos verificar esta propriedade completa e vamos ver, o que temos? Então, agora, quando abrimos quando estamos em dispositivos desktop, podemos ver que é tela cheia. No entanto, se estamos em dispositivos móveis, parece bom. Então, o que? Enfraquecer Dio? Idealmente, gostaríamos de habilitar essa propriedade de tela cheia somente quando estamos em
dispositivos móveis . Então precisamos que alguns determinem programaticamente bem, podemos realmente usar consultas de mídia, mas eles estão disponíveis apenas e CSS Mas com ganchos, podemos alcançar o mesmo resultado programaticamente. Então, vamos abrir o arquivo de ativos a pasta de ativos e aqui confinado usar media query gs. Vamos abri-lo e vamos copiar este gancho agora Vamos acelerar este gancho para nossos porcos personalizados dgs e vamos importar usar um fato de reagir. Então, agora, o que este gancho faz ele ganchos na janela muito mídia um p I, e ele nos permite manipular consultas de mídia. Programaticamente eu não vou mergulhar em detalhes aqui. Vamos ver como funciona. Então eu vou salvar o arquivo. Então vamos voltar ao Dashboard Tuggle. E aqui vamos chamar isso de usar gancho de consulta de mídia e dentro precisamos passar um
ponto de quebra de mídia . Então vamos dizer que vamos abrir nossas atenuações pais e vamos passar Max com 1992 pixels. E agora este gancho retorna em Bullen que indicará se é verdadeiro ou falso. Então, usando isso, podemos verificar se estamos no dispositivo com 992 pixels. Então vamos pobre é móvel e este Bullen vamos passar adereço
cheio de dentes. Então, quando estamos em dispositivos móveis, teremos a propriedade completa habilitada. Quando estamos em dispositivos desktop, isso será definido como falls e nós não teremos essa propriedade completa se nós salvá-lo. Vamos voltar ao aplicativo agora se estivermos em dispositivos móveis. Se o tamanho do nosso ecrã for inferior a 992 pixels, temos o nosso Drover completo e funciona perfeitamente. E se estamos em dispositivos desktop, temos este Drover estático que não é alterado. Bem, este é exatamente o comportamento que queríamos. Então aqui terminamos com nossa capacidade de resposta. Vamos terminar este vídeo e confirmar nossas mudanças. Vamos colocar tudo para o get e vamos nomear o nosso commit como editar usar gancho de consulta de mídia e fez Drover responsivo. Está bem, Perfeito. Vejo-te no próximo.
107. Criando o painel - parte 1: Ei, bem-vindo neste resgatável. Continue construindo nossa barra lateral e vamos começar a construir exatamente Dashboard. Vamos lá. Então, primeiro, vamos abrir togs índice e aqui em vez de visitar se vamos usar elementos Drover. Então, já que não temos nenhum rapper porque o definimos dentro do aeroporto alternar esses Drover, vamos usar o insight fragmento de reagir como este. Então nosso trabalho, elementos
er será drover dot não intitulado sobre ponto Heather Inside cabeçalho. Vamos ter título drover dot e porque off V s código casca com fragmento reagir Agora eu tenho essa duplicação de dados, mas isso é bom. Então em seguida você teve er nós teremos Drover Dot Body e então teremos Drover Dot Footer assim. Então dentro do corpo ia exibir os dados do usuário. Então, aqui vamos bombear. Digamos que h três elemento e, em seguida, vamos dizer, Ei, usuário ou temos perfil. Temos nome de ponto perfilado. Então este perfil será o nosso perfil que obtemos do gancho de perfil de uso. Esse é o nosso contexto. Então vamos chamar o perfil de uso e eu não tenho inteligência. Então vamos abrir o contexto do perfil. E agora, se eu colocar inteligência, será importante para mim. Tudo bem. Bom. Então dentro do corpo, temos texto exibido dentro do título. Vamos puxar apenas painel e rodapé dentro, vamos adicionar botão Sign out. Então vamos adicionar elemento botão. Vai ser um elemento de homem. Ele terá cor vermelha e para unclipped vamos especificar em Sign out e vamos
derramar Sign out como texto. Tudo bem, então talvez vamos apenas remover um clique por enquanto e vamos apagar este H3 tack na parte inferior. Vamos verificar isso. O que temos como resultado? Nós estamos certos. Perfeito. Então agora temos ódio. Ela parece ter 16 anos, que é o nosso nome de utilizador. E, em seguida, temos logout botão, mas ele não tem nenhuma funcionalidade ainda, então vamos adicioná-lo. Bem, quando sair do aplicativo, queremos que você também feche esta janela do modelo. Mas esta função próxima recita dentro do Data Board Togo. Então eu propus para definir um sair, função dentro do painel togo
e, em seguida, passá-lo para baixo para o componente painel. Então aqui vamos colocar Const em sinal de saída. E porque temos esse estado aberto aqui, toda vez que abrimos e fechamos o tempo todo. Teremos uma nova cópia fora desta função no logout. Então, queremos manter esta cópia. Queremos que você memorize. Então vamos usar chamada de uso de volta com antecedência e dentro vamos colocar a próxima lógica. Precisamos ligar para Sair, que está disponível no juramento. Objeto? Oh, não assinar. Apenas saia. E é isso. Isso vai sair completamente. Nosso usuário atual. Tudo é gerenciado pela base de fogo. Então precisamos colocar alerta, que vai ser um alerta para alerta. Vamos dizer, assinado fora. Vai durar quatro segundos e depois fecharemos o Drover também. Então, porque vem do nosso gancho personalizado, precisávamos passá-lo como uma dependência. Mas isso é bom. A função de roupas é memorizada dentro do estado do modelo de uso porque colocamos dentro. Use CLO de volta como você se lembra. Não, vamos passar. Sair no painel e no painel interno. Vamos consumi-lo. Sair. Está em maiúsculas? Sim, é. Então, quatro em diante. Sair. Clique. Vamos colocar a função de saída. Tudo bem? Parece bem. Agora vamos dar uma olhada. Se abrirmos nossa placa, se clicarmos em sair agora, estamos desconectados. E a questão potencial pode ser por que somos redirecionados para entrar na página. Isso é porque dentro do nosso contexto, temos isso fora do estado mudado. Então, quando sair porque é uma assinatura em tempo real, firebase irá buscá-lo. Ele vai sair do usuário, e este Colback será demitido. Então, quando não temos fora do objeto, chamamos set profile para saber. E quando temos definido perfil agora ou indefinido, se olharmos dentro rota privada, redirecionamos o usuário para entrar. Então é exatamente isso que está acontecendo. Então agora temos o sistema completo de assinatura e saída, que funciona perfeitamente. Tudo bem, então para verificar se tudo funciona. - Tudo bem. Vamos entrar mais uma vez e vou selecionar exatamente a mesma conta novamente. Agora estou redirecionado. Eu estou conectado e novamente, eu tenho ódio. Ela parece ter 16 anos. Tão perfeito. Funciona como deve funcionar. Agora vamos confirmar nossas mudanças e terminar este vídeo. Vamos bombear, pegar em tudo, então nos comprometemos. Começou a criar um painel e ele sair botão e exibir o nome do usuário. Muito bem, vejo-te no próximo.
108. Criando o painel - componentes reutilizáveis e editáveis (parte 2): Hey, bem-vindo neste líder foram continuar a construir que carne de porco e verbal criar um componente que vamos reutilizar várias vezes em toda a nossa aplicação em alguns lugares. Então vai ser uma entrada com os dois botões que enquanto eu estava muito editada. Então, quando o salvamos, nós realmente atualizamos dados dentro do banco de dados. Vamos lá. Então, primeiro, o que eu proponho é criar o componente real. Então, em componentes, vamos criar um novo arquivo credível na porta por enquanto. Deixe-o estar vazio. Vamos só pôr um “olá” aqui. Vamos primeiro definir como vamos usá-lo. Vamos abrir esse arquivo de palavras aqui em Ei, nome
do perfil. Vamos colocar o divisor do nosso terno. E, em seguida, vamos definir Edita ble importação. Então, o que? Adereços deve re passar insight. Então, primeiro de tudo, vamos passar o valor inicial, que será triste para a entrada. Então vamos colocar o valor inicial, que vai ser o nome escuro do perfil. Tudo bem, então também precisamos definir a função segura e que será disparado quando salvarmos a entrada. Então vamos colocar em segurança e vamos defini-la aqui. Então vamos colocar em seguro e esta função de retorno de chamada, ele receberá o mesmo valor que um argumento. Então vamos colocar novos dados e para o nosso vamos deixar esta função vazia. Além disso, queríamos relatar talvez algum rótulo na frente da entrada, então teremos a opção de passar um componente reativo como um adereço para o
componente amplo comestível . Então vamos definir algo como seis anos de idade. Talvez, vamos colocar que vai ser nome Nick e nome da classe vai ser margem inferior para porque queremos adicionar algum espaço entre o nosso rótulo e entre a entrada real. E também podemos passar outros adereços que serão redirecionados elemento de entrada Judy. Então talvez também possamos passar algo como nome, que vai ser, no nosso caso, apelido. Então, o que será inserido com o nosso apelido que seremos capazes de adicioná-lo? Tudo bem, Cool. Então vamos abrir nosso componente e começar a construir. Então primeiro temos valor inicial. Trabalhei em um dos principais adereços. Em seguida, vamos destruidor em seguro venerável também tem rótulo, que vai ser esta idade seis, e há uma chance e que este rótulo não será passado. Então vamos colocar agora VT dobra e, em seguida, também algumas outras coisas, como espaço reservado. Talvez assim. Vamos pobre espaço reservado. E por padrão, será dito, Escolha algo como certo, Seu valor. Tudo bem. E então também, o que eu proponho é derramar um adereço que representará nossa mensagem vazia quando alguém
tentar salvar nossa entrada e ela está vazia para que possamos colocar como um valor global que dirá que entrada está vazia. Mas e se quisermos personalizá-lo? Então, vamos também passá-lo como uma mensagem vazia prop. E por padrão, se não for especificado em adereços, diremos que será no tribunal, seu vazio tudo bem, e qualquer outro adereço será nossos adereços de entrada. Tudo bem, então para isso ao vivo o que vamos fazer Então aqui, logo antes do elemento de importação real, vamos portar rótulo. Tudo bem, então vamos derramar a entrada que vem do nosso terno. Então, para esta entrada, no primeiro adereço, vamos passar nossas colheitas de entrada, e vamos sobrescrever algumas delas. Então vamos sobrescrever espaço reservado, que vai ser este lugar titular de adereços. Então também teremos outras coisas que gerenciaremos dentro deste componente, como seu estado interno. Então, quando vamos editá-lo, vamos gerenciar tudo a partir daqui. Então vamos colocá-lo aqui com antecedência. Então vamos definir novo estado, que vai ser,
digamos, apenas entrada e, em seguida, definir em porta pelo valor inicial padrão. Será o nosso valor inicial que passaremos por aqui. Então vamos colocar o valor inicial. Tudo bem, então temos o próprio manipulador de mudanças que precisamos especificar. Então vamos derramar na mudança de entrada. Então normalmente, como você se lembra, ele recebe um objeto de evento. Mas em nosso terno, é um pouco diferente como o primeiro argumento para o evento de mudança. Então, se eu colocar inalterado aqui, se eu passar o mouse sobre ele, você pode ver que o primeiro argumento vai valor. Então, ele é apenas feito para nós para ser mais amigável, então nós vamos ter valor em vez disso, fora de referência até mesmo valor de ponto alvo. Então aqui, vamos colocar também usar chamada de volta porque não teremos qualquer dependência e queremos
otimizá-lo com antecedência a partir daqui. Bubble call apenas definir entrada para o seu valor assim. E para estes em mudança, nós vamos derramar sobre a mudança de importação, tudo bem. E também, não se esqueça de associar o valor real com nossa entrada, e estamos quase terminando aqui. Agora, nós também queremos fazer nossa entrada editar ervas. Então vai ser apenas um valor de barras que indicará então vamos criar o seu estado
credível é desejável e, por padrão, será definido como falso. Tudo bem, então esta entrada será desativada quando tivermos é credível, definido como falso. Então, quando comestível é tão verdadeiro? Seremos capazes de gerir o nosso inquérito. Então vamos criar botão real que irá indicar que Então vamos pobre grupo de entrada não vai colocar apenas botão porque teremos os dois botões dentro de nossa importação ou fechar ou editar . Então vamos colocar o grupo de entrada para fazer parecer tateado, sabe? Então grupo de entrada no botão e dentro deste botão, vamos colocar eu posso e isso eu vou ser o próximo. Então, se a nossa entrada vai ser comestível, exibição
venerável botão fechar. Então, caso contrário, quando vemos a entrada real e não pretendemos editá-la, vamos receber adicionado a Então este é apenas um ícone com, como ,
lápis, possamos ver que podemos adicioná-lo. Tudo bem, então para isso no botão clique, nós vamos derramar em editar clique e este clique não editado vamos definir aqui. Então, na edição Clique também irá citá-lo ao redor, use chamada de volta com antecedência porque não teremos dependências ou realmente com você. Mas não importa, Corneau. Então vamos colocar Set é credível para reverter o valor do nosso estado atual. Então vamos chamar essa função que irá reverter o valor do boliche. E também queremos ter certeza de que se clicarmos em cancelar, voltaremos ao estado inicial. Então, queremos também chamar set input e apenas no caso, defini-lo de volta para o valor inicial. Então agora ele aparece como uma dependência. Então, vamos colocá-lo aqui. E vamos realmente dizer com e ver o que está acontecendo aqui. Tudo bem, Cool. Então agora nós temos isso assim, e parece quase legal, mas parece que eu sou algo. Oh, sim, na verdade, porque usamos o grupo de entrada, precisamos envolvê-lo em grupo de entrada. Isso é culpa minha. Um grupo tão importante. E eu vou colocar isso no final assim. Agora, vamos dar uma olhada. Tudo bem, agora parece bom. Eu não posso adicionar entrada agora, porque é comestível tal cair. Então, quando eu clicar neste botão agora, eu serei capaz de adicioná-lo. Este botão. E como você pode ver, quando eu clicar neste botão, a função on edit click será disparada. Então, se não temos este valor inicial de entrada conjunto quando eu clicar neste botão, ele não será re definido para o valor padrão. Portanto, queremos ter certeza de que é sempre inicial se cancelarmos. Tudo bem. Então, o que mais precisamos fazer? Precisamos definir outra garrafa que será exibido quando realmente clicar em editar. Então, nós somos capazes de saborear aqui. O que? Nós vamos derramar. Nós vamos derramar. Se a nossa importação é credível, então vamos renderizar outro grupo de entrada inferior. Vamos copiar e colocar aqui. Então, para no clique, vamos colocar no clique seguro. Não vai ser o mesmo em Salve isso. Passamos como um adereço. Vamos definir outro “clique seguro “aqui. Por agora. Que seja assim. Então, para este botão, o que vamos para a sua mudança passiva de fogo. Eu posso, eu posso vai ser um Aiken estático. E isso eu posso é se eu me lembro que é cheque. Vamos dar uma olhada. Tudo bem, vá. Sim, é. Cheque. Parece que temos a marcação. Vamos realmente definir a funcionalidade para clique seguro. Então, o que vamos fazer aqui? Primeiro, vamos fazer uma validação muito primitiva. Primeiro, vamos obter o valor aparado para evitar espaços desnecessários ao redor do nosso texto. Então vamos colocar o valor aparado e ele vai ser guarnição ponto de entrada. OK, então vamos verificar se o nosso valor aparado vai ser apenas um espaço vazio. Então vamos alertar foi pacificado. Mensagem vazia como um adereço. Podemos colocar esta mensagem vazia aqui e vamos adiar quatro segundos. Tudo bem. Então, no final, vamos colocar Set é credível para quedas porque quando clicamos em seguro, queremos torná-lo não credível como era antes. E agora aqui, vamos verificar contra mais um. Acho que vai ser se aparado não vai ser o nosso valor inicial. Então vamos verificar se realmente editamos algo e nosso valor é diferente Onley, então vamos chamar nossa própria chamada segura de volta que especificamos aqui dentro do painel. Então ele vai ser em uma função de pia. Então vamos pacificá-lo, já que ele vai estar enfrentando vai ser uma promessa, então precisamos esperar por ela. Então vamos derramar uma pia e vamos derramar um peso no cofre que passamos aqui. E como você se lembra, este retorno de chamada receberá novos dados como um argumento. Então aqui precisamos passar nossa entrada real. Então vamos pobre não entrada ou talvez aparado para valor, porque não queremos colocá-lo com os espaços apenas desnecessários em torno dele. Tudo bem, então agora vamos verificar. E aqui, vamos vender-nos. Olha, novos dados para ver se realmente funcionou. Agora parece bem acabado. Talvez no futuro vamos ajustá-lo um pouco para atender às nossas necessidades. Mas, por enquanto, parece bom. Vamos abrir o painel. Vamos abrir, Cônsul, e vamos dar uma olhada. Então, agora, se eu editar, se eu cancelar, tudo ficará bem. Então, se eu clicar novamente no cofre, nada muda. E não temos essa ligação de volta no cofre disparado. Então, se eu mudá-lo e se eu salvá-lo agora, eu tenho o novo valor que está sendo Cônsul bloqueado a partir disso no manipulador seguro. Então, na verdade, funcionou. E acho que terminamos aqui no próximo vídeo. Vamos realmente aplicar alguma funcionalidade para este componente, ou talvez em torno deste componente. Então atualizamos nosso apelido riel. Mas, por enquanto, vamos terminar este vídeo e vamos cometer nossas mudanças. Então eu vou colocar criado reutilizável, entrada
credível. Tudo bem, Perfeito. Vejo-te no próximo.
109. Criando o painel - Update do usuário (parte 3): Ei, bem-vindo neste vídeo. Vamos continuar construiu nosso painel comestível atualizar nosso apelido real dentro do banco de dados Riel Time. Vamos lá. No último vídeo, criamos entradas credíveis. E nós definimos isso em função segura que passamos para editar a entrada de ervas. Então esta função de retorno de chamada vai receber a nossa entrada final quando clicamos no botão salvar Então vamos agora usar esses dados e atualizar nosso banco de dados. . Então, como antes, vamos usar nosso banco de dados, objeto para acessar banco de dados. Então precisamos escolher pacificar referência ao banco de dados. Então vamos colocar perfis, vamos usar um fio da polícia deles aqui. Vamos colocar o perfil. Não use, eu d. Agora precisamos atualizar apenas o apelido. Não queremos ter criado isso. Então precisamos ser mais precisos quando se trata de fazer referência a algo dentro do
banco de dados em tempo real . Então precisamos fazer referência a esse nome aqui. O que podemos fazer, podemos realmente referenciá-lo de duas maneiras. Podemos colocar sua barra aqui e colocar o nome ou eu prefiro outra maneira só de torná-lo, você sabe, mais amigável. Eu colocaria uma criança aqui e aqui. Eu também preciso especificar caminho, mas este caminho será um relativo ao caminho que especificamos dentro da primeira referência. Então vamos empurrar este nome. Então vamos especificar criança fora deste caminho dentro do banco de dados, tudo bem. Ou, na verdade, vamos colocá-lo em um valioso vamos colocá-lo, digamos, nome de
usuário Nick, ref. Então vamos definir um bloco try catch porque vamos trabalhar com
dados assíncronos e promessas. Então aqui nós vamos derramar, esperar, e então nós simplesmente chamar nome de usuário apelido ralf dot sat, que irá escrever dados para o banco de dados. E aqui vamos colocar novos dados que recebemos como argumento. Depois disso, não
vamos Se eu usuário com mensagem de sucesso e vamos dizer apelido tem Bean atualizado e novamente por segundos e para qualquer outro vamos colocar em sua mensagem onde vamos colocar nossa mensagem como seu texto e também quatro segundos. Tudo bem, parece legal. Vamos verificar isso. Vamos navegar de volta para o aplicativo quando eu clicar em editar deixe-me alterar meu apelido para entrar Seja do que eu clique seguro e apelido foi atualizado E se voltarmos para base posterior. Você pode ver que os dados reais são alterados. Vamos tentar mais uma vez. Vamos colocar apenas eu sei e eu clique seguro. O apelido foi atualizado. O banco de dados é atualizado. Tudo parecia bem longe. Se ainda tiver uma pergunta. Por que exatamente isso? Andy sendo atualizado quando atualizarmos os dados dentro do banco de dados. Mais
uma vez para explicações. Dentro do contexto de nosso provedor, usamos assinaturas, ouvintes em tempo
real para nossos dados. Então, para usar uma referência, que é o nosso caminho de banco de dados sob perfis, usuário I d. Colocamos ouvinte em tempo real estes chamada de volta. Então este frio é disparado toda vez que algo muda sob este caminho dentro do banco de dados. Então, se digamos que o nome muda sob o usuário I d que estes chamada volta será disparado e vamos atualizar o estado do perfil com este objeto de dados, que será novo no momento em que estes Colback é disparado. Assim, o mesmo se aplica para criado em ou para qualquer outro preenchido. Então, se tivéssemos algo como a idade aqui, e se a idade foi mudada, então esses Colback serão demitidos e então um certo, eu acho que tudo bem. E você entendeu. Agora vamos confirmar nossas mudanças e terminar o vídeo. Então vamos começar bem em tudo. Então vamos colocar Pete cometer, digamos que apelido atualizado dentro do banco de dados. Tudo bem. Parece bom. Vejo você na próxima.
110. Criando o painel - provedores de hiperligação (parte 4): Ei, neste vídeo, vamos continuar construindo o componente aeroportuário e vamos associar conta de usuário com vários provedores de assinatura ou vários métodos Sinan. Então, por exemplo, se eu me conectar ou se eu olhar com o Facebook e, em seguida, se eu olhar para fora e olhar para dentro com o Google, eu acabo na mesma conta. Não vou ter duas contas diferentes. Tudo bem, então vamos fazer isso. Primeiro, vamos voltar ao nosso código. E aqui no painel, vamos criar seu arquivo, que vamos nomear Provider Block por enquanto. Deixe-o ser um componente vazio e vamos editar para o nosso painel dentro Index GS logo após Hey Profile Name provedor Block. Perfeito. Agora, para continuar, precisamos saber como podemos realmente acessar nossos dados de usuário atuais onde dados de objeto de usuário para ser mais específico. Então, em vez de usar nosso gancho de perfil de uso para obter os dados, podemos realmente usar fora do objeto, e então podemos acessar o usuário atual. Então vamos bater nele e ver o que você recebe? Então, se eu agora ir para esse quadro, se eu olhar dentro do Cônsul agora, eu tenho o objeto de usuário desligado atualmente usuário conectado, então ele é gerenciado pela base de fogo. Aqui restringimos diferentes tokens de acesso, tokens de
atualização, nome de
exibição, e-mail e outros dados. Mas estamos interessados agora em dados de provedores que temos aqui. Então, é basicamente um array off provedores ou array off Simon métodos que estamos usando agora. Então, como você pode ver, agora, nós temos apenas um elemento, que é google dot com. Então, vamos usar essa informação para exibir que estamos conectados no momento não foram a este provedor
específico. E a coisa é que, se você se lembrar, colocamos ouvintes em tempo real para nossos dados de perfil. Então, sempre que atualizamos algo, ele é atualizado em todos os lugares com os provedores. Ele não funciona em tempo real, então precisamos gerenciá-lo usando estado de reação. Então, tudo bem, vamos voltar ao bloco de provedores. E aqui vamos definir um novo estado, que vamos nomear está conectado, e não vai ser um valor de boliche. Será um objeto que indicará se estamos conectados ao Facebook ou ao Google. Então vamos ter um objeto com duas chaves, google dot com e facebook dot com, que é Provider i d pode ser encontrado que dentro desta matriz, assim como você pode ver para o Google, é google dot com. Certo, então para o Google Dot com, vamos verificar se estamos conectados. Então vamos acessar os dados atuais do provedor de pontos do usuário. Então é uma matriz, e na chuva, podemos aplicar alguns para verificar se algum elemento é realmente justifica a condição. Então vamos ter aqui nossos dados, e vamos verificar se alguns dos nossos elementos de matriz onde tem provedor I D ou google dot com. Se provedor de dados I d é igual google dot com e o mesmo que faremos para o Facebook. Então vamos copiá-lo. E vamos substituir google dot com pelo facebook dot com. Tudo bem, bom. Desta forma, agora teremos disponível está conectado. Isso indicará o que estamos conectados ao Google ou Facebook. Agora vamos realmente definir o nosso marcador. Então, dentro desta definição, vamos derramar nossos botões ou ataques que irão indicá-lo. E aqui teremos uma carga off renderização condicional. Mas, por enquanto, escute. Desafio, marcação
estética. Então, primeiro vai ser elemento preso. Assim, o elemento pilha será perto, herbal, e terá cor verde porque vai ser quatro Google dentro, teremos Aiken. E isso eu posso ter eu posso fora do Google e ele vai dizer conectado. Tudo bem. E também agora temos esta manhã. Vamos colocá-lo aqui no topo da mesma forma. Vamos nos candidatar ao Facebook. Então vamos copiá-lo. E vamos substituir a cor pelo azul e eu posso pelo Facebook. Tudo bem. Parece bom. Agora vamos dar uma olhada. Se formos ao painel agora, estamos conectados. Então isso será exibido quando estivermos realmente conectados aos nossos provedores. Tudo bem, então vamos definir outras coisas que serão nossos botões para realmente se conectar a estes ou àqueles provedores. Então vamos colocar um pouco fora, fundir neste bloco, e então vamos definir nossos fundos. Então o primeiro botão vai ser para o Google. Então vai ser um elemento de bloco. Ele terá cor verde e dentro novamente. Vamos ver e eu venho e eu posso ser, Digamos, também Google e vamos nomear X ligado ao Google. O mesmo será para o Facebook. Vamos copiá-lo. E vamos substituir a cor pelo Lynn azul para o Facebook. E eu posso vai ser Facebook. Tudo bem, vamos verificar. Tudo bem. Parece bom. Então, vamos ter isso para botões de fundo para realmente se conectar ao provedor. E esses dois no dizer as pessoas têm quando estamos conectados. Tudo bem. Então vamos primeiro derramar nossa renderização condicional para o caso quando já estamos conectados. Então, para essas tags, vamos colocar se está conectado,
então, porque é um objeto, podemos acessar suas propriedades. Então, se eu estiver conectado ao Google Dot com no Lee, então eu vou renderizar este elemento tag e o mesmo, na verdade, vamos fazer para o Facebook. Então agora teremos um exibido em Lee quando estivermos conectados. Tudo bem. Parece bom. E para esses botões, aplicaremos o próximo. Então, se não estamos conectados ao Google que vêm, então vamos exibir este botão e o mesmo vai fazer quatro facebook. Então, se não estamos conectados ao seu Facebook, então vamos exibir esse tipo de botão. Tudo bem, vamos verificar. Se eu abrir meu painel, estou conectado ao Google e não estou conectado ao Facebook. Tudo bem, então agora a coisa é realmente fazer alguma funcionalidade para aplicar tudo com um estado. Certo, então primeiro precisamos definir os manipuladores. Então teremos no total para manipuladores, para manipuladores para UNL Inc do Google e Facebook, e dois manipuladores para um link para Facebook e Google. Então vamos defini-los primeiro vai estar em um link no link Facebook como este. Então teremos o Google desvinculado. Então teremos vinculado Facebook e LinkedIn Google e vincular Google assim. Tudo bem, primeiro, vamos talvez fazer a funcionalidade desvinculada, então será o mesmo, e é muito fácil de fazer. Então nós vamos criar outra,
como, como, uma função comum que nós vamos chamar dentro do link Facebook e permitir que o Google que nós
vamos chamar, você sabe, apenas no link, e então nós vai receber aqui provedor I d provedor. Eu gostava disto. Certo, então vamos chamar isso de desvinculado do Facebook desvinculado assim, e então colocaremos Facebook Dot com e o mesmo que faremos pela Gogol. Vamos colocar no link google dot com assim. Tudo bem, então você desvinculou o provedor de verdade. Vamos fazer a próxima coisa que vamos colocar primeiro try, catch block, e vamos perguntar em primeiro lugar se apenas um método de login é deixado para o usuário. Por isso, é possível que nós desvinculados do Google, e então acabamos com nenhum provedor de login em tudo dessa maneira, conta será abandonada e não terá qualquer método de login, então isso significa que será tipo de isso. Por isso, queremos evitar isso. E vamos verificar se o comprimento do ponto de dados do provedor do ponto do usuário atual do ponto é igual a um. E queríamos conectá-la. Então, temos apenas um método de login e clicamos em desvinculados. Vamos receber um aviso. Vamos lançar um novo editor, e nós vamos dizer que você não pode desconectar para, um provedor I d. que nós recebemos como um argumento aqui. E agora vamos pegar esse assunto que jogamos aqui, e vamos colocá-lo alerta e editor de arte, vamos dizer melhor mensagem por quatro segundos. Tudo bem, então se tudo está bem aqui e se temos, digamos, provedores conectados e queremos nos desconectar de um deles, é seguro. Então nós vamos cancelar ponto usuário atual ponto unlinked este método, se eu chamá-lo, você pode ver em links um provedor de conta de usuário e eu preciso passar provedor I D, que vai ser provedor I d de nossos argumentos. Então é uma promessa o que vamos fazer, vamos esperar. E porque é um pensamento aguarda índice, precisamos colocar um canto na frente da função. Então, depois que esperamos, precisamos atualizar nosso conjunto está conectado. Precisamos atualizar nosso estado local. Então, o que podemos fazer? Nós podemos realmente criar outra função apenas para atualizar o nosso estado para que possamos chamá-lo algo como esta atualização está conectada, e dentro podemos passar provedor I d e, em seguida, apenas valor se é verdadeiro ou cai. Então, aqui, provedor de
relatório i d. E quando
desvinculamos, queremos configurá-lo para forçar. Então vamos criar esta atualização está conectada vamos receber provedor I d. como um argumento. E então nós vamos receber realmente, o valor, algo assim. Então, dentro desta função que vamos chamar conjunto está conectado aqui, vamos receber valor anterior dentro do callback. E aqui precisamos retornar e você valoriza porque é um objeto. Queremos ter certeza de que mantemos a estrutura. Então, vamos voltar. Certo, vamos colocar mais explicitamente a partir desta semana de retorno e Alba Jet aqui, vamos fundir o estado anterior assim e depois atualizar o provedor real. Precisamos abrir esse tipo de parênteses. Então precisamos citar provedor I d como uma chave e, em seguida, revela pacificar o valor. Tudo bem, então desta forma, ele irá atualizar o objeto com o especificado de qualquer i d e valor. Tudo bem. Bom. Parece muito bem. Vamos talvez também, e outro alerta aqui com alerta, talvez apenas informações, e vamos dizer, desconectado do provedor desconectado do provedor eu d como este a menos que coloque quatro segundos aqui . Tudo bem. Agora, vamos realmente vincular esses manipuladores aos nossos botões, então precisamos desvincular o Facebook. Precisamos colocá-lo aqui para o elemento saco. Então aqui podemos ter isso em um evento próximo. Então, para este evento unclos, mastigável especificar no link Google, na verdade, eo mesmo para o Facebook. Então aqui vamos vestir roupas e vamos colocar no link Facebook desta vez. Tudo bem. Agora ele tem funcionalidade suficiente para testá-lo. Então vamos abrir o painel. Vamos clicar neste elemento próximo. Então, quando clicamos nele, você não pode desconectar do google dot com que porque nós só temos o método de assinatura Google apenas um deles. Então, se
desconectarmos dele, vamos fazer nossa conta que tudo certo para ir agora é realmente e nossa funcionalidade de link . Então, novamente
, será o mesmo quase o mesmo. Então vamos criar uma função comum como UNL Inc. Então vamos colocá-lo, talvez aqui e vamos nomeá-lo. Vamos ligar. Tudo bem, Então ele vai receber não um provedor i d. Mas o objeto provedor o mesmo que usamos dentro. Página de login. Vamos ver este novo provedor firebase Auth firebase. Tudo bem, então eu copiei. Então deixe-me comentar. E aqui vamos ligar para este link e depois assinamos. Precisamos passar objeto provedor que receberemos como um argumento. Então, para o Facebook, vamos chamar a nova base de fogo fora do provedor do Facebook. Vamos primeiro importar a base de fogo da base de fogo. Tudo bem, olha, o treinador e o mesmo vão fazer para Link Google. Então vamos copiá-lo. E aqui vamos chamar o provedor Google Auth. Tudo bem, parece bom. Agora vamos associar esses manipuladores com antecedência aos nossos botões. Então, no clique, vamos vincular o Google E para este botão clique em um link Facebook. Tudo bem. Parece bom. Então, agora qual será a nossa estratégia? Então é realmente muito, muito simples com base de fogo novamente, precisamos usar nosso objeto auth. E aqui vamos chamar o nosso usuário atual e, em seguida, ligar com link pop-up com pop-up. Precisamos especificar apenas o objeto provedor que recebemos como um argumento que vai ser um desses, tudo bem. Por
isso, mais uma vez, é uma promessa que temos de esperar. E depois que ele é atualizado com sucesso, o que é convertido para você função de corrida depois que ele é atualizado com sucesso, vamos notificar os usuários com alerta em quatro. Digamos conectados ou talvez ligados dois. Provedor. Vamos usar a preparação do Rincon. E porque ele está no objeto provedor. Desta vez este objeto provedor tem provedor I d como sua chave. E, novamente, especificaremos quatro segundos no caso de qualquer outro. Vamos colocar alerta na mensagem dela e colocaremos nossa mensagem aqui assim. E no final do dia, precisamos também atualizar nosso estado local. Então vamos chamar o mesmo que antes da atualização estar conectada. E desta vez vamos puxar provedor ponto provedor I D. E então nós vamos colocar a verdade porque nós ligamos nossa conta. Tudo bem agora, parece bem. Vamos verificar isso. Parece que temos todas as funcionalidades. Deixe-me checar duas vezes. Ok, parece bom. Agora vamos para o painel. Se eu clicar no link para o Facebook, vamos ver o que vai acontecer agora. Serei solicitado a olhar para o meu busto do Facebook porque eu já fiz login. Agora eu tenho ligado ao Facebook. Se eu for para autenticação e se eu tiver um novo, posso ver que eu tenho que entrar provedores associados a esse usuário. Então funcionou mesmo. Agora, se eu Vamos um clique em Desconectar do Facebook Agora, Eu desconectei do Facebook dot com. Se eu clicar no Google, você não pode se desconectar do Google porque ele é o único que resta. E se eu atualizar novamente, você pode ver o Facebook desaparecer. Então, na verdade, tudo funciona. Tudo bem, então foi muito, na verdade, acho que é a boa hora para terminar este vídeo. Então, vamos adicionar tudo ao estado do palco, e então vamos vincular o Facebook e o Google a um provedor criado pela conta Block Who? Muito bem, vemo-nos na próxima.
111. Criando o painel - criando o Avatar (parte 5): Ei, neste vídeo, vamos continuar a construir o painel, e vamos começar nossa gestão com avatares de perfil de usuário. Assim, neste vídeo vamos criar um botão e podemos selecionar uma imagem do nosso PC que então vamos fazer upload para a base de fogo e usar como nossa imagem de avatar. Vamos lá. Então, primeiro, vamos criar um novo arquivo em seu painel. Esse nome problemático de um carro aplaude Bt. Então vamos criar um componente vazio. Por enquanto, vamos colocar Olá dentro do que no Index GS, que é o nosso painel logo após a entrada comestível. Vamos fazer referência ao upload de Bt do avatar assim. Ok, bom. Agora vamos começar a construir nosso componente. Então o nosso elemento superior vai ser um desenvolvimento para o nome da classe. Vamos dar-lhe um pouco fora de margem na costeleta, que vai estar vazio três. E depois queremos manter tudo centrado. É por isso que colocamos o centro fiscal. Tudo bem, então nós precisamos especificar entrada fora do tipo de arquivo, mas nós não queremos usar o nativo porque ele não parece o melhor caminho. Então, por enquanto, vamos apenas mantê-lo como texto e talvez se você quiser, você pode mudá-lo. Para fazer isso. Precisamos colocar um dif aqui. Então vamos especificar o insight do rótulo. E dentro deste rótulo, vamos colocar um novo Avatar selecionado e também ao lado deste texto dentro do rótulo. Nós vamos colocar em adiar o tipo de arquivo, mas nós vamos dar a ele exibição fora nenhum. Então, na verdade, clicamos neste texto. No entanto, ao mesmo tempo, clicamos nesta entrada. Então vamos despejar na porta fora do tipo de arquivo assim. E também, vamos dar o nome da classe fora, exibir nenhum. E temos este aviso no rótulo dizendo que ele deve ser associado com o controle. Então, para esta entrada, vamos definir uma idéia algo como Al Atar upload. E vamos dar essa idéia para html quatro para dis label. Então HTM de quatro vai ser avatar. Aplaudir. Tudo bem. Também para esta gravadora, vamos dar o nome da turma deste bloco de jogos. Além
disso, ele vai ser ponteiro mais grosseiro, e ele vai ser um pouco acolchoado como este. Tudo bem, vamos verificar. Agora. Se eu for ao painel
, fica bonito. Agora temos este botão. Então, quando clicamos nele, podemos realmente selecionar arquivos. Vamos fazer desta forma que podemos selecionar apenas imagens por aqui. Então, para esta entrada, vamos colocar outro prop, que é, exceto e ele vai ser uma string fora de tipos de arquivos aceitos. Mas vamos especificar esses tipos de arquivo fora do componente. Então, no futuro, é mais fácil navegar dentro desse componente. Vamos amarrar tipos de importação de arquivos, e ele vai ser como beber fora tipos de arquivos referenciados por vírgula. Então primeiro vamos aceitar arquivos PNG do que arquivos J PAC e também J pack off off esta extensão. Tudo bem, então para isso exceto prop, vamos passar tipos de importação de arquivos e estamos prontos para ir Agora vamos conferir. Se clicarmos aqui, podemos ver os arquivos P e G e J de volta. Tudo bem. Parece bom. Agora, qual será o nosso próximo passo? Então, quando selecionamos uma imagem, queremos que um novo modelo seja aberto, e dentro deste mortal, vamos ver a pré-visualização. Então precisamos definir o motor de Indo. Então aqui, ao lado do rótulo vamos usar o elemento modelo do nosso terno. E dentro deste modelo, vamos colocar o modelo ponto Heather do que ao lado dele. Teremos corpo e também rodapé como este. Então, para o modelo, precisamos especificar show propriedade. É um marcador que indica se ele está aberto ou não do que no manipulador de altura quando este modelo está fechado. Então precisamos usar nosso próprio costume. Espero que criamos anteriormente usar estado mortal para realmente obter esses valores. Então, vamos importá-lo. E vamos D estrutura é aberta, aberta e próxima. Então, para no evento altura, vamos chamar Close Handler e para o show vamos especificar está aberto. Então dentro de Moto Heather, nós estamos indo para port model dot title Então este título vai ser um justo e aplaudir Talvez assim, aplaudir novo avatar e vamos remover este título na parte inferior aqui. Em seguida, dentro do corpo. Vamos especificar outra coisa. E dentro do rodapé, vamos colocar um fundo que vai realmente carregar o nosso avatar. Então vamos digitar aplaudir Novo Avatar e para esses botões irá especificar a aparência. Vamos dizer fantasma, e também vamos dar-lhe com off 100 especificando que ele vai ser um elemento de bloco . Tudo bem, então agora, como você pode ver, nós não temos nenhum gatilho para realmente abrir nossa moto. Precisamos determinar de alguma forma quando selecionamos o arquivo. Então, para isso, vamos usar no evento de alteração disponível na importação fora do arquivo tipo. Então vamos pacificar a própria mudança. E para esta mudança, vamos criar uma função que vamos nomear na mudança de entrada de arquivo. Tudo bem, agora, vamos criar aqui no topo e esta função porque é um manipulador para um evento. Esta função recebe um objeto de evento. Tudo bem, então este objeto de evento terá alvo e sob alvo. Podemos acessar arquivos reais que selecionamos, e sempre vem como uma matriz fora de arquivos. Então vamos colocar arquivos atuais em até mesmo arquivos de destino. Então, uma vez que será sempre uma matriz, precisamos verificar se selecionamos apenas um arquivo. Então vamos verificar. Se arquivos atuais desse tamanho é igual a um, então nós vamos aplicar nossa lógica. Então vamos primeiro pegar nosso primeiro elemento da matriz. Então vamos colocar arquivo, e vamos colocar arquivos atuais e referenciar o primeiro elemento. Então precisamos realmente verificar se o arquivo que selecionamos é o arquivo válido, porque não importa o que especificamos. Por aqui. Eu posso procurar qualquer arquivo e mudá-lo para todos os arquivos, e então eu posso comprar Maio bife upload, digamos adjacente. Então queremos verificar se este arquivo é realmente uma imagem. Então, aqui no topo, vamos especificar tipos médios que são acessíveis por nós. Para isso, vamos especificar qualquer tipo de arquivo disponível, digamos, aceito. Então, aqui nós estávamos indo para especificar um array fora de strings. Então, primeiro, nosso tipo de feixe vai ser imagem barra p e G. Então vamos ter imagem barra j pack. Então, se eu não estiver errado, é o correto. E também vamos ter imagem barra p j pack. Tudo bem, Bom. Agora precisamos criar uma função auxiliar que irá verificar se este arquivo satisfaz matriz fora tipos
médios. Então, se o nosso tipo de arquivo é um deles, então nós estamos indo para criar uma nova função auxiliar que irá nomear é arquivo válido e ele vai receber arquivo como um argumento, e ele vai verificar o tipo de arquivo contra esses valores. Então, vamos simplesmente verificar tipos de arquivos aceitos Inclui tipo filhinho de arquivo. Tudo bem, então ele retornará um valor booleano. Tudo bem, agora aqui, para dentro. Ah, eram manipuladores. Podemos perguntar se vamos perguntar se é válido, arquivar nosso arquivo, então vamos fazer algo. Caso contrário, vamos mostrar um erro ao usuário que. Oh, garoto, você selecionou a hora errada do arquivo. Então vamos colocar alerta. Então vamos colocar aviso, não um erro, e nós vamos especificar, talvez tipo de arquivo errado, e então vamos pobre tipo filha de arquivo como este, e vamos especificar quatro segundos. Tudo bem, então o que vamos fazer quando tivermos o arquivo válido? Primeiro de tudo, vamos abrir nossa janela móvel. Mas antes de abrirmos, precisamos de alguma forma definir a nossa imagem que aplaudimos. Então, para isso, vamos criar um novo estado. Então vamos criar um novo estado com estado de uso, que vamos nomear. Digamos apenas imagem e imagem definida por padrão. Será ajustado para agora. Mas quando temos desenvolvido imagem selecionada. Vamos chamar Set Image, e vamos colocar arquivo como nosso estado assim. Tudo bem, agora, vamos verificar. Então, se eu for para o painel, se eu selecionar um novo avatar, se eu carregar uma imagem, tudo bem, Motile abre. Agora, vamos fazer a mesma coisa. Mas vamos selecionar o arquivo Jason. Se eu clicar em abrir, tenho aplicativo de tipo de arquivo errado, Jason. Então funcionou mesmo. Tudo bem? Agora, qual será o nosso próximo passo? Nosso próximo passo é mostrar a visualização e ajustar a imagem. Então, como somos capazes de fazer isso, vamos usar reagir pacote editor avatar que vem de um PM Eu realmente gosto deste mini pacote. Isso nos dá a oportunidade de personalizar a imagem carregada. Nós não vamos mergulhar em muitos detalhes, mas nós apenas podemos dimensionar nossa imagem para precisar do tamanho dela. Então, primeiro, vamos instalá-lo. Então eu vou abrir meu terminal e a partir daqui, que eu tenho outro Tudo bem, tudo bem. Vou instalar o Avatar React, editor e vamos esperar até que seja instalado ou certo. Parece que o nosso pacote foi instalado. Vamos executar novamente o AP e P. M Run, começar e vamos ver como podemos realmente usar este pacote. Então deixe-me copiar o comando de importação. Deixe-me colocá-la aqui no topo. E como você pode ver, eu preciso usar este componente assim. Então vamos copiar isto. Vamos copiar este componente do que dentro do nosso código para o corpo do modelo. Vamos especificar este componente, mas primeiro, vamos verificar se temos nossa imagem definida dentro do estado. Então, vamos má imagem. Se tivermos imagem, vamos exibir isso sobre nosso componente editor e para imagem. Nós vamos especificar nosso arquivo que temos estado EUA para With e Height Mobile limitado a 200. Então, para a fronteira, vamos colocar, digamos, apenas 10. E esta é a borda por bordas do que não precisamos de cor. Não precisamos de escala, mas precisamos de um raio de fronteira. Queremos fazer circular. Então vamos especificar os rádios de fronteira 100. Tudo bem, agora, vamos verificar. Se eu atualizar a página que eu clicar no modelo Selecione novo Avatar. Se eu clicar neste carro e abrir agora, eu posso ver que eu tenho este elemento Converse, que é este pacote. E agora eu sou capaz de adicionar a minha imagem um pouco. Tudo bem, então parece bom, mas não está no centro. Isso significa que precisamos adicionar mercado adicional para esta imagem para este editor de avatar. Vamos colocar outra definição em torno dele assim. E para esta definição. Vamos especificar display flex. Então vamos colocar o display flex. Justifique, digamos, centralize, alinhe o centro de itens e vamos colocá-lo em altura total assim. Agora, se eu tivesse um fresco, vamos dar uma olhada. Deixe-me selecionar uma imagem novamente. Mas ainda assim, não
parece bom porque não é justificado. Centro. É um centro de conteúdo justificado. Agora, deixe-me tentar. Selecione Novo Avatar. Tudo bem, agora parece bom. Está centrado. Ok, então eu acho que este é o fim para este vídeo, e nosso próximo passo será realmente carregar a imagem. Mas ele vai ser o tópico para o nosso próximo vídeo sobre este passo. Vamos confirmar nossas mudanças e terminar este vídeo. Então nós vamos adicionar tudo a este estado de estágio que nós vamos obter commit, e nós vamos colocar vamos dizer, começou a trabalhar com avatar usuário. Aplaudir. Tudo bem. Parece bom. Vejo-te no próximo.
112. Criando o painel - Uploading do Avatar para o Firebase (parte 6): Ei, neste vídeo, vamos continuar a trabalhar no upload de avatar entre componentes, e vamos terminar o upload de que sera waters. Vamos lá. A primeira coisa questionou você ia definir um manipulador para um evento de clique para aplaudir seu botão de avatar. Então vamos pacificar no evento clique e vamos criar uma nova função que vamos nomear no upload . Clique. Em seguida, vamos colocar este manipulador logo após a alteração de importação de arquivo, e agora precisamos de alguma forma obter acesso à imagem real. Desta vez, esta imagem é editada. Então precisamos ter acesso a esse elemento de conversa. Então, se nós
inspecioná-lo, é um converse dentro Dom porque é sobre o nosso componente editor que usamos a partir do pacote. Tudo bem,
então, para entender o que está realmente acontecendo, como podemos obter a imagem que precisamos para navegar para a documentação deles, do que se rolarmos para baixo , limitamos um exemplo acessando a imagem resultante. Aqui confinamos este método obter imagem escalada para conversar. Mas como podemos ver a partir deste exemplo, ele usa componente baseado em classe, e também usa algo chamado referências. Então referências em reagir é a maneira de acessar elementos Dom diretamente ou reagir
diretamente elementos onde mais apropriadamente seria dizer programaticamente. Então vamos descobrir como podemos realmente colocar uma referência em nosso componente editor avatar dentro de
um componente baseado em função. Então, primeiro, precisamos importar um gancho que não vimos antes de reagir, que é usado ref, que significa referência de uso. Agora precisamos criar uma nova referência, e vamos nomear este gráfico editor de avatar de referência, e vamos chamar este gancho assim. Agora, precisamos passar esta referência para este componente. Então nós vamos especificar Rafa, e então vamos derramar editor avatar áspero. Então agora nós somos capazes de acessar este, digamos, avatar, componente
editor usando esta referência, que é nossa água eu fiz muito áspera. Então, clique no upload. Vamos colocar Vamos dar uma olhada. Temos de aceder a este editor. Obtenha habilidade de imagem para examinar para acessar o valor real fora desta referência. Precisamos colocar o próximo, então vamos colocar o converse, e vamos dizer que vamos acessar Avatar Edita Ralf dot current. Portanto, é elemento atual fora desta referência porque também pode ser indefinido. Então nós nos certificamos de que acessamos o elemento atual. Então, em seguida, podemos acessar o método real, que vai ser obter imagem escalada, duas câmeras. Então, vamos chamá-lo. E agora podemos realmente ter o nosso elemento de conversa. Mas a coisa é que não podemos trabalhar com a conversa. Não podemos enviá-lo. Não podemos fazer nada com isso. Então primeiro precisamos convertê-lo para algum antigo que possamos aplaudir para fogo base para que possamos realmente converter Converse em um arquivo blob. E um arquivo de cara é apenas um pedaço fora do arquivo representado em formato binário. Então, usando este formato, podemos aplaudir. Então, em cada elemento inverso, temos este método que é chamado para bloquear, ea coisa com isso para bloquear método que ele só aceitar callbacks. Não podemos usar promessas. Então, para isso, eu quero converter este método baseado em Colback para uma promessa. Então, para fazer isso, vamos fazer o próximo aqui no topo. Nós estamos indo para definir uma nova função que vamos nomear get bloco, e esta função vai receber uma conversa como esta e esta função vai retornar e você promete objeto. Então vamos colocar o retorno novo, eu prometo. Então, não vimos isso antes. Então, para criar uma promessa real, precisamos colocar uma visão de retorno de chamada que recebe dois argumentos, resultado e rejeição. Então vamos chamar esse método para realmente resolver ou rejeitar a promessa. Então, aqui dentro, o que vamos fazer? Vamos chamar Converse para Bluff. Então vamos especificar esta chamada de volta com o resultado que será o blefe
real. E dentro deste frio atrás, vamos verificar. Se o nosso sangue existir e tudo estiver bem, então vamos resultar desta promessa que vamos resolvê-lo. Então resultado e valor vai ser o verdadeiro conselho de explosão. Se não temos quaisquer elementos de bloco estavam indo para rejeitar com novo erro e para
mensagem de erro , vamos dizer de algo como protestos de arquivo nunca. Tudo bem, então usando desta maneira agora, nós convertemos um método frio e baseado em
volta em uma promessa. Então agora podemos usar isso explodir e o que podemos fazer, vamos colocar para tentar pegar o bloco aqui e agora o que vamos fazer vamos chamar isso explodir assim. Então vamos colocar lona lá dentro. E porque é uma promessa, agora precisamos esperar. E no caso de termos algum erro, será apanhado por estes quarteirões aqui. Então, porque usamos aguarda, Index, precisamos converter esta função para qualquer função. Tudo bem, então o resultado será nossa explosão que podemos aplaudir ao armazenamento de arquivos agora sobre armazenamento . Como podemos fazer isso. Ainda não enviamos nada. Bem, vamos voltar para Firebase Doggy S. E aqui, vamos importar outra biblioteca do Firebase. Desta vez ele vai ser firebase barra armazenamento agora para realmente acessar o armazenamento exatamente da mesma maneira que estamos indo para exportar, const armazenamento app ponto tudo bem. E a torta de armazenamento A é muito semelhante ao armazenamento de banco de dados. Precisamos especificar a referência que é realmente o caminho para o arquivo, e então precisamos aplaudi-lo. Então, agora aqui. Primeiro, vamos especificar o caminho sob o qual vamos armazenar nossa imagem. Vai ser,
digamos, digamos referência de arquivo
avatar como este para que nós íamos acessar nosso objeto de armazenamento de diversos firebase. Então vamos colocar Dot e então vamos chamar a referência. Então vamos armazenar nossos arquivos no passado deles, que é perfil de barra barra usuário I d. Então precisamos levá-lo lá. Eu d Então vamos usar gancho perfil, Então const perfil, vamos começar a partir de perfil de uso. Então nós vamos especificar o perfil dot seu i d e vamos convertê-lo para interpolação de cordas . E então, na verdade, vamos acessar criança e criança vai ser avatar. Certo, então o que estamos fazendo aqui, nós realmente especificamos esse caminho dentro do nosso armazenamento, então ele representará nossa pasta e essa criança será um arquivo chamado Avatar. Nós não vamos colocar qualquer extensão porque ele será automaticamente apanhado pela base de fogo. Tudo bem, agora, próxima coisa balbuciou, você vai realmente carregar o arquivo. Então vamos colocar resultado const upload avatar. Então vamos colocar um arquivo de avatar de peso que Arraf dot colocou. E, em seguida, se o
chamarmos, podemos ver que podemos realmente colocar ou blob ou matriz de buffer. Então vamos realmente colocar nosso blub aqui, e então vamos também segundo argumento. Podemos especificar metadados. Então, para dados de matéria, vamos especificar cabeçalho de controle de caixa. Então nós podemos realmente descontar nossas imagens dentro do navegador. Então vamos colocar um controle de dinheiro. E para controle de dinheiro, vamos especificar público que Marx Age. Vamos para a porta 3600, o que representa uma hora em segundos. Então vamos multiplicar por 24 para obter o valor real de um dia, e então vamos multiplicar por três. Então agora temos marcas de idade fora. Três dias especificados em segundos. Tudo bem, então agora que temos ah, Petar, resultado do
upload deixe-me remover esta coluna Sammy daqui. Agora que temos um resultado de avatar Plourde, precisamos obter o Não carregue seu l do nosso arquivo para que possamos salvá-lo em nosso banco de dados. Então aqui vamos colocar um download constante, Ural. Então vamos fazer upload da nossa referência de ponto de resultado de água. Não se
engane, e não ligue diretamente para baixar o seu l Porque, como você pode ver, é obsoleto ID para usar referência que obter não carregar euro. Então vamos ligar para o Ralf, e só depois vamos ligar. Não carregue euro. Retorna uma promessa. Então vamos esperar por isso. E agora podemos realmente armazená-lo lá dentro. Nosso banco de dados permite avatar usuário pobre Raff que irá representar nossa referência dentro do
banco de dados em tempo real . Então, qual vai ser o banco de dados Daut Ralf do que vai ser? Perfis cortam o perfil e depois vamos colocar o filho de um carro. E agora vamos chamar o usuário Avatar Raff, definir, não carregar euro. E logo depois disso, vamos chamar informações de alerta de um carro que foi aplaudido. E vamos colocar quatro segundos. E no caso de qualquer editor, vamos alertar o que quer que seja e diremos nossa mensagem com quatro segundos também. E também antes de salvarmos este arquivo, vamos realmente especificar o estado de carregamento também. Então aqui nós vamos simplesmente criar está carregando e definir está carregando que por padrão, será definido o seu falso. Então, quando realizamos todas as operações logo antes disso, chamamos set está carregando para true. E então quando
terminamos, chamamos set is loading to false E no caso de
falharmos, também chamamos Set is loading to false agora quando realmente o usamos, nós realmente usá-lo para este botão para torná-lo desativado. Então desabilitado será somente quando tivermos o estado de carregamento habilitado. Tudo bem, então foi muito. Agora, vamos realmente testá-lo. Então deixe-me atualizar a página. Deixe-me abrir, painel. Deixe-me selecionar Novo Avatar. Agora vou clicar neste carro. Vou clicar em Aplaudir novo Avatar, e posso ver que Avatar foi aplaudido. Muito bem, agora vamos primeiro verificar dentro da nossa base de dados. Parece que agora temos um avatar aqui. Como podem ver agora, temos esse público que está doente, que leva ao armazenamento da base de fogo. Vamos verificar isso. O nosso armazém. E aqui podemos ver uma pasta. Vamos clicar nele. Então temos o usuário I d. e dentro temos o arquivo Avatar. Então, quando clicamos nele, você pode ver que temos este seu l que podemos clicar, e ele vai nos abrir a imagem em você toque. Mas a coisa é que agora nós carregamos com sucesso o arquivo para o armazenamento base de fogo. Certo, então agora como podemos exibir essa imagem? Bem, eu acho que este é o tópico para o nosso próximo vídeo, porque agora ele está ficando muito longo. Tudo bem, então vamos salvar tudo para obter o sistema. Vamos chegar nossas mudanças e digamos que o Avatar do Usuário foi carregado. Muito bem, vemo-nos na próxima.
113. Criando o painel - início de Avatar do usuário (parte 7): Ei, neste vídeo, vamos exibir a imagem do avatar enviada dentro do nosso painel. Vamos lá. Primeiro, quero mostrar o componente do nosso traje, que é alcatrão de Alá. Então eu navegou para sua documentação, e eu abri Alit estão sob exibição de dados. Então aqui a coisa legal sobre este componente que ele pode realmente mostrar as iniciais de nome se
não tivermos nenhuma imagem. Então vamos abrir um exemplo. E vamos ver como podemos realmente colocar as iniciais de nome se não tivermos nenhum arquivo fonte. Então precisamos simplesmente passar essas iniciais para Avatar Component. Então, o que eu propus fazer, eu propus criar um wrapper em torno deste componente. Então, sempre que não tivermos uma imagem rebelde, as iniciais de nome de exibição. Então, sob componentes, vamos criar novo arquivo, que vamos nomear perfil Avatar. Então deixe ser um componente que retorna este Ah, o que é componente que vem do nosso terno assim? Então, quais adereços devemos especificar para esses Avatar? Então vamos precisar do nome fora do usuário, então vamos passá-lo como adereços. Então vamos nome do destruidor e o que quer que vá para esses componentes, ele será redirecionado para o componente avatar de nossa série. Então vamos colocar, Teoh Avatar adereços. E então vamos espalhá-lo por todo o elemento. Tudo bem, Bom. Agora, dentro deste avatar, precisamos portar as iniciais de nome. Mas digamos que nosso nome é algo como Andrew, e algo vai depois. Então, como podemos obter as iniciais de nome real vamos criar uma função auxiliar. Então vamos deletar isso. E sob MISC, vamos criar um novo arquivo que vamos chamar ajudantes cãozinho e hittable definir todas as nossas funções
razoáveis que nos ajudarão durante o código. Então vamos criar uma nova função que vamos nomear, digamos, obter iniciais de nome. Ele receberá nome de usuário como um argumento, e nossa lógica será a próxima. Primeiro, vamos dividi-lo em vários prêmios, e então vamos verificar se temos duas ou mais palavras em nosso apelido, então vamos receber as primeiras letras primeiro para as enfermarias. Então vamos primeiro pegar a área real. Vamos dar um nome,
digamos, nome dividido. Então vamos fazer o nome Dot para a ópera. O caso será convertido em maiúsculas com antecedência, e então vamos dividi-lo por espaços vazios. Assim, desta forma, vamos acabar com uma matriz fora de palavras. E então vamos verificar se o comprimento do doc da matriz de nome dividido é maior que um. Então, se tivermos dois prêmios, pelo
menos devolveremos o nome Split, Primeira palavra. E a partir da primeira palavra, precisamos pegar a primeira letra. Então vamos abrir os segundos colchetes, e vamos colocar o primeiro elemento. Então vamos colocar um sinal de adição para vir cortar em um distrito. Então vamos colocar contra o nome Bleidt desta vez referência Hubble. O segundo elemento. A segunda palavra. Então vamos colocar uma e outra vez, vamos fazer referência à primeira letra. Colocamos zero. Certo, no caso de termos apenas uma palavra por padrão, vamos retornar. Basta dividir o nome zero, que é Primeira Palavra. E, em seguida, primeiro elemento primeira letra. Tudo bem. E vamos também explorar esta função a partir daqui. Agora, dentro do nosso avatar de perfil aqui dentro de colchetes, nós podemos realmente chamar, obter o nome e ele mostra, e podemos passar o nome que recebemos de adereços. Tudo bem, agora, vamos para Avatar. Aplaudir Bt e componente. E aqui, vamos usar este componente. Então vamos colocar o perfil do carro de Allah como fonte. Vamos especificar o avatar do ponto do perfil e, em seguida, para o nome. Vamos especificar o nome do ponto do perfil. Assim, desta forma, quando temos um arquivo de origem, então o arquivo de origem será exibido. Se não o tivermos, nossas iniciais estarão lá. Tudo bem, vamos guardá-lo e vamos dar uma olhada. O que é que nós temos? Vamos voltar para o painel e agora posso ver que não tenho nenhuma
imagem de avatar . Tudo bem, talvez um Vamos enviar um. Vamos abri-lo. Vamos enviar o novo Avatar Avatar foi carregado, e ainda assim eu posso ver quaisquer dados. Tudo bem, então isso é porque na verdade, nós não modificamos nossos contatos. Nossos contatos de perfil. Vamos para o contexto de perfil e dados que passamos aqui não tem nenhum Ah, o que são além de Al Atar Applaud BT na fonte dos EUA. Eu especifiquei o perfil Avatar. Este perfil vem do contexto de perfil de uso. Então, o que precisamos fazer agora que nós re dados do banco de dados? Podemos destruí-la daqui do nosso instantâneo, certo? Tão simples quanto isso. Então também passaremos para nossos contatos. Tudo bem, vamos salvá-lo. E agora vamos dar uma olhada. Se eu for ao meu painel agora eu tenho essa imagem. Mas antes de tudo, parece muito estranho, então vamos modificá-lo um pouco. Vamos ao perfil Avatar e, por padrão, logo antes de espalharmos todos os adereços. Vamos colocar círculo para que ele seja circulado por padrão. Vamos verificar isso. Agora está circulado, mas o tamanho é muito, muito pequeno. Então o que, nós podemos dificar dentro do botão de upload do avatar? Podemos aplicar nomes de classe e isso irá corrigi-lo. Sabemos que a nossa imagem, nossa conversa que especificamos para o nosso editor de tar é 200 por 200. Então vamos aplicar com 200 altura 200 pixels, aquelas classes que você confinou dentro de classes de utilidade. Então vamos salvá-lo. E se formos para o painel agora, temos o tamanho correto para conta-gotas M A. Mas a imagem em si é realmente pequena, então precisamos recitar a imagem real. Por isto. Eu criei este nome mais que você também pode encontrar dentro utilitários, que é imagem de tamanho completo, e ele vai dar com uma altura 100% para a imagem. Então agora parece bom. No entanto, há um pequeno problema. Se atrasei esta imagem, vamos entregá-la daqui agora. Como podem ver, se não tivermos nenhuma imagem, recebo as iniciais de nome, mas também são muito pequenas, então precisamos ajustar o tamanho do telefone. Então, para isso, vamos colocar o tamanho enorme da frente e tudo ficará bem. Vamos verificar isso. Agora. Também tenho o tamanho correto para o meu texto. Então agora talvez vamos mudar o apelido e colocar duas palavras. Vamos colocar e ser. E vamos verificar se temos duas letras como nossas iniciais e em Será que nós temos um exibido aqui ? Legal. Vamos tentar aplaudir o carro de New Allah. Vamos selecioná-lo. E Avatar foi carregado, parece agradável e funciona perfeitamente. Ok, bom. Acho que é a boa altura para terminar este vídeo. Então vamos confirmar nossas mudanças com mensagem. Algo como exibido tem um avatar usuário tar. Está bem, Perfeito. Vejo-te no próximo.
114. Adicione o botão de quarto crio e funcionala: Ei, bem-vindo neste vídeo. Nós vamos adicionar um novo painel de billow inferior que vai adorar a criação de uma nova sala de bate-papo . Vamos lá. Vamos navegar de volta para o código e outros componentes. Nós vamos criar um novo arquivo que vamos nomear Criar quarto bt n motile Não. Sim, vamos completar este componente por enquanto. Deixe ser apenas um olá e vamos realmente usá-lo dentro. Dentro da nossa barra lateral, vamos abrir a barra lateral. E aqui abaixo painel Tuggle, vamos colocar criar quarto Bt e Moto. Tudo bem, agora não vamos nos envolver com o oponente do disco. E aqui vamos definir um botão que vai abrir uma janela modelo com formulário dentro que
vamos preencher para realmente criar uma sala de bate-papo. Então vai ficar tudo bem, talvez um componente diff. Então, dentro vamos colocar o botão que será o nosso puxão para abrir a janela da garrafa. Então vamos colocar eu posso à vista. Então isso eu posso ter ícone desligado pode ser criativo, e o texto vai estar criando uma nova sala de bate-papo. Tudo bem, então este botão vai ser um bloco elementos terá cor verde e no clique
vamos , Teoh, abra nossa moto. Então vamos realmente usar nosso gancho personalizado para gerenciar o estado mortal. Então este gancho é usado estado modelo a partir daqui começou, infra-estrutura é aberta,
aberta e, em seguida, fechar. E para clicar no botão, vamos abrir. Muito bem, agora, vamos definir a nossa janela móvel. Então vamos colocar o elemento modelo do nosso terno. Teremos, como sempre, Heather
mortal. Então teremos corpo e vacilar. Tudo bem, bom. Então, dentro da Heather, vamos colocar o título mais. Eles vão pontuar o título e dentro. Vamos colocar algo como uma nova sala de bate-papo e vamos remover este ídolo daqui. Tudo bem, dentro do corpo, vamos definir o formulário e dentro do pé, ou vamos colocar o botão para enviar o formulário. Então vamos primeiro criar o botão. Então ele vai ser um elemento de botão. Vai ser bloqueado. Componente e aparência serão primários. Ok, eu acho. Aparência definida como primária por padrão. Mas vamos manter como está. Tudo bem? Criar uma nova sala de bate-papo. Agora vamos salvá-lo e vamos ver, o que temos? Então agora temos isso criar uma nova sala de bate-papo, já. Nós não temos a margem, então vamos. Então, para este rígido, vamos colocar o nome da classe e vamos adicionar margem superior dois. Tudo bem. Parece bom agora dentro deste corpo iria definir a nossa forma. Então vamos pobre elemento de forma do nosso terno. E dentro deste nascido, vamos definir nossos elementos de entrada, e eles são agrupados sob componentes de grupo formados. Então vamos grupo de forma pobre e dentro desta forma. Mas aberto terá o primeiro rótulo de controle. E então vamos colocar o controle de formulário, que vai ser a importação real em si. Vamos atuar assim. Então, dentro rótulo de controle, nós estamos indo para porta nome da sala em primeiro lugar e controle de formulário vai ser
nome, nome e espaço reservado vai ser um espaço reservado vai ser algo como entrar
nome da sala de bate-papo e três patos, e ele vai ser um componente auto perto porque é uma entrada. Tudo bem, então se eu passar o mouse neste grupo de formulários, ele diz que não define, então vamos importá-lo do nosso terno. Tudo bem, então vamos definir nossa segunda entrada. Digamos que realmente e ver, o que temos. Então, se vamos clicar em criar nova sala de bate-papo, nada vai acontecer porque não especificamos show prop for motile window. Então vamos colocar é aberto e em altura, vamos colocar manipulador de roupas. Tudo bem, parece bom. Agora vamos verificar e eu vejo que nós adicionamos muito fora do espaço aqui. Então vamos pobre margem superior um tudo agora é. Certo, vamos abrir. E aqui podemos ver que temos nossa entrada, mas está um pouco fora, não cheio com. Então vamos corrigi-lo rapidamente. E quatro dias formam elementos. Vamos fazê-lo para que ele vai fazê-lo tirar tudo com fora do elemento wrapper. Tudo bem, parece bom. Agora vamos seguir em frente e vamos criar o segundo Grupo Estrangeiro, que vai ser a descrição do quarto. Então, para este grupo de reforma, também, vamos copiar rótulo de controle no controle de formulário como este Para este rótulo de controle, vamos especificar descrição, e para este controle de formulário, vamos derramar um componente de área de texto. Então vamos propriedade de classe componente pobre. Vai ser uma área de texto que a Rose dela. Por padrão será igual a cinco. O nome vai ser a descrição. E o espaço reservado vai ser Digamos que entre em Roma. Descrição. Tudo bem. Parece bom. Agora, vamos dar uma olhada se eu clicar nele. Tudo bem. Eu tenho uma descrição. Eu tenho um nome verdadeiro. Ok, agora, talvez vamos definir nosso estado para os dados reais. Então aqui o quê? Vamos Ford,
vamos definir o seu estado que vamos nomear,
formar, formar, valorizar e definir valor estrangeiro como a função de atualização. Então seu estado vai ser o próximo ele vai ser um objeto, e eu o que eu sugiro que eu sugeri para colocá-lo fora do componente porque nós vamos recitá-lo para o valor inicial quando vamos enviá-lo. Mas vamos enviar o formulário. Então vamos colocar o formulário do show. E vai ser um objeto com conhecimento de nome e descrição. Tudo bem. O mesmo que temos nome prop para a nossa entrada. Tudo bem, então você ficou por aqui. O padrão será a forma inicial. Tudo bem? Além disso, as pessoas precisam do estado de carregamento. Vamos defini-lo com antecedência. Vamos usá-lo quando vamos enviar o formulário. Então o seu estado vai ser falso. Tudo bem, agora, primeiro precisamos lidar quando tivermos que pegar os dados. Então, quando usamos o próprio evento de mudança Então vamos quatro const na mudança de formulário e a coisa com nosso terno, quando usamos no evento de mudança, ele automaticamente nos dá o valor como seu primeiro argumento, não o objeto de evento. Então teremos valor aqui. Então vamos derramar valor de forma CET como valor. E, na verdade, é um pouco diferente com nossas formas de terno. Quando temos um componente de formulário em nossa certeza, ele automaticamente não dá o valor da entrada real que você adicioná-lo. Mas dá-lhe o valor de todo o formulário, por isso é realmente conveniente usá-lo com o estado de uso. Tudo bem, então sobre isso na mudança de formulário, nós estamos indo para portar para o nosso componente de formulário. Então, no manipulador de mudança vai estar na mudança de formulário. Agora. Nós também precisamos de alguma forma validar nossos dados e primeiro, vamos associar o estado real com o formulário. Portanto, ele tem essa propriedade chamada valor de forma. Portanto, deve ser um objeto que interage com o com a forma apenas o nosso estado. Tudo bem, então nós vamos ter um valor de forma ruim. E isso no evento de mudança nos dará o novo valor de formulário quando atualizarmos qualquer elemento fora deste formulário. Então, qual será o nosso objeto no final? Tudo bem. Então, como eu disse antes, agora precisamos de alguma forma validar os dados, o formulário quando enviamos. Bem, nosso terno nos fornece se com métodos auxiliares para conseguir isso, podemos definir um esquema que podemos submeter ao nosso queimado, e então nosso terno irá verificar contra este esquema. Então vamos definir o nosso esquema. Eu aqui no topo para a nossa forma, Vamos defini-lo modelo. E aqui vamos usar o esquema que importamos do nosso terno do que vamos colocar modelo. E dentro deste modelo, precisamos colocar um objeto que representará nosso estado. Então teremos nome. Deve ter a mesma forma que o nosso estado. Então nome vai ser tipo string, que vem realmente de tipos de esquema. Então vamos fazer estrutura-lo string ou talvez tipos de ponto de esquema a partir deste objeto, vamos para d tipo de cadeia de estrutura. Em seguida, vamos usar o tipo de string para definir que o nome vai ser um encolhimento. Então tipo de string, então vamos colocar é necessário para executar a validação e outra mensagem vai ser filmada. Nome é necessário tudo certo, eo mesmo vai fazer. Quatro descrições. Vamos copiá-lo. Vamos renomear para descrição e digamos que a descrição é necessária o legal Pense sobre esta validação esquema
moral que ele será validado em tempo real. Agora precisamos enviar este esquema para o nosso formulário. Então vamos encontrar este componente de formulário. E aqui como motile, vamos especificar nosso esquema Moto, nosso objeto modelo aqui. Tudo bem, agora precisamos realmente criar a função de envio. Então, primeiro de tudo, vamos na verdade mudar de formulário. Não é otimizado aqui porque temos um monte fora estados que mudam constantemente, por exemplo, é de valor aberto e estrangeiro. Então, cada vez que teremos em mudança de formulário sendo criado e você copiar esta função. Então vamos memorizá-lo com antecedência para torná-lo mais otimizado. Tudo bem, e agora vamos realmente criar nossa função no envio. Então vamos chamá-lo, digamos, no envio e vai ser uma função de pia
com antecedência e aqui o primeiro passo será realmente validar dados. Então, como podemos fazer isso? Como ele pode validar nossos dados em relação ao esquema que definimos aqui. Precisamos realmente usar uma referência para fazer referência ao nosso componente formulário e, em seguida, usando esta referência, podemos chamar seus métodos internos para validá-lo. Então, o que podemos fazer agora? Sabemos que podemos usar ref de reagir. Então vamos colocá-lo aqui. Vamos nomeá-lo forma, ref, e então vamos chamar use ref de reagir. Então vamos passar este formulário ref para este componente formulário. Tão áspero vai ser forma, respiração e ouvir. O primeiro passo vai ser se formulário ref ponto atual verificação de ponto. Então este método de verificação está disponível neste componente de formulário que acessamos diretamente aqui , Então esta verificação irá validar esses dados irá validar o nosso valor de formulário, que é o nosso estado contra o esquema que definimos aqui. Então, se tudo estiver bem, ele retornará ao verdadeiro valor de Bullen. Se não
for, será falso. Então vamos verificar se a nossa verificação de valor de formulário não passou. Então, se temos um valor falso, então vamos simplesmente retornar desta função como conselho. Vamos atualizar nosso banco de dados com o novo quarto. Então vamos derramar CET está carregando para true antes de qualquer tarefa assíncrona. E aqui vamos criar um novo objeto que vamos salvar no banco de dados. Então, digamos novos dados da sala. Na verdade, vai ser,
ah, ah, onde o nosso estado forma valor. Mas também vamos upend outra propriedade que vai ser criada em então aqui vamos
espalhar todo o valor de forma que temos , e então nós vamos colocar criado em
e, em seguida, nós vamos importar base de fogo da base de fogo para cima e, em seguida, aqui criou em nós estamos indo para derramar firebase dot banco de dados dot valor do servidor data e hora. Então agora temos os complexos dados de neurônios que precisamos salvar no banco de dados. Então vamos colocar try catch blawg antes de qualquer tarefa assíncrona. E no caso de sair melhor, vamos servir. CET está carregando para falso, e nós vamos matar alerta ponto melhor mensagem de erro com quatro segundos. Tudo bem. Parece bom. Agora vamos chamar o banco de dados Aguarde para o Projeto do Firebase. Então vamos colocar o Dr. Ralf para este árbitro. Nós vamos especificar apenas quartos para que nós vamos manter nossos quartos sob quartos, caminho dentro do banco de dados e empurrar. E você, digamos valor dois banco de dados para que a chave seja gerada automaticamente. Vamos chamar o método push, então e dentro das escolas íamos passar novos dados da sala. Então, depois de termos dados dentro do nosso banco de dados, vamos definir está carregando duas quedas e vamos redefinir nosso estado inicial. Então vamos chamar o valor do formulário de satélite. Vai ser a forma inicial, e depois disso temos de garantir que também fechamos a janela do motel. Então, vamos também chamar roupas. E então vamos colocar outro alerta com informações e vamos dizer valor estrangeiro. Deixe-me abrir citações aqui. Vamos dizer nome de ponto de valor estrangeiro ou, na verdade, deixe-me chamá-lo antes disso assim. Então o valor da forma vai ser vamos dizer que foi criado. E então, novamente, quatro segundos como sempre. Tudo bem, então parece bom. Agora nós realmente precisamos usar está carregando e no formulário enviar. Vamos colocá-lo para este botão que vamos colocar no clique aqui e vamos passar submeter assim. E agora para usar isso é o estado de carregamento. Vamos usá-lo para este botão. Vamos torná-lo desativado quando temos está carregando definido como true. Tudo bem, foi muito. Agora vamos realmente testá-lo. Agora deixa-me refrescar-me só para ter a certeza. Deixe-me entrar. Olá, então vou colocar outra coisa. E aqui, se eu deixá-lo vazio, você pode ver que a descrição é necessária. O formulário está realmente sendo validado em tempo real. Isso é porque definimos o esquema. Tudo bem, vamos pobre Olá. E vamos adiar a descrição desta sala. Vamos clicar em Criar nova sala de bate-papo e podemos ver que alerta não é uma função. Tudo bem, talvez vamos movê-lo como este Alerta. Tudo bem. Erro de ponto de alerta era o problema real. Eu chamei apenas e r R, mas é erro. Então essa é a minha aposta. Tudo bem, agora, vamos tentar mais uma vez. Criar uma nova sala de bate-papo. Vamos colocar “Olá descrição”. Ei, três novas permissões para bate-papo hoje à noite. Tudo bem, porque também precisamos definir regras de segurança para nosso banco de dados. Então vamos abrir regras e aqui vamos definir nosso próximo esquema. Então, próximos dois perfis, vamos copiar isso. Vamos portar também quartos e para salas que vamos especificar. Então, para ler e escrever para tudo dentro daqui, vamos permitir isso somente quando o usuário é autenticado. Então,
ao invés disso usando essa verificação, vamos dizer que a permissão de leitura e gravação só é permitida quando desativada, não é igual agora e o mesmo que faremos para basicamente tudo aqui, vamos colocá-la aqui em vez de ideia futura, vamos ter, digamos, quarto I d. E, em seguida, também para leitura. Vamos pacificar o autor, não igual neve e fora, não igual agora. Tudo bem. Parece bom. Vamos copiá-lo. E vamos também sincronizá-lo com nosso arquivo local, que é regras de banco de dados. O Jason. Vamos salvá-lo. E vamos dar uma olhada. Então agora nossas regras são publicadas. Se eu clicar em criar nova sala de bate-papo agora, hello foi criado. E se você olhar dentro do banco de dados agora em salas, nós temos uma nova chave que foi automaticamente gerada pelo banco de dados. E então temos nossos dados criados na descrição e nome. Tudo bem. Parece perfeito. Acho que é a boa altura para terminar este vídeo. Deixe-me cometer tudo. E, em seguida, vamos especificar botão criar para criar nova sala de bate-papo. Ou talvez no novo botão na parte inferior para criar uma nova sala de bate-papo. Muito bem, vemo-nos na próxima.
115. Criando listas de salas de Chat - Parte 1: Ei, neste vídeo, vamos começar a criar Chatham List Inside barra lateral aqui na parte inferior. Vamos lá. Vamos esperar dentro de Bardo GS em primeiro lugar. E aqui, logo após uma criatura em Bt e Moto, vamos colocar o componente divisor do nosso traje e dentro bolha passado. Juntar texto de conversa. E também, vamos mover esta importação para o topo para evitar um excelente aviso. Vamos verificar isso. Parece bom. Agora precisamos realmente definir componentes. Então, na pasta Componentes, vamos criar uma nova pasta que as pessoas nomeiam salas aqui. Vamos colocar dois arquivos novos lista de sala de bate-papo ponto GS e item de quarto. Não Sim, então o item do quarto vai estar vazio agora. E, na verdade, o mesmo se aplica para a lista de chat dentro do lado Bardo Gs Aqui na parte inferior. Em vez desse texto que usamos como espaço reservado, vamos usar a lista de salas de bate-papo. Tudo bem, vamos salvá-lo. Vamos dar uma olhada. Podemos realmente ver o texto Olá para que funcionou. Perfeito. Agora vamos definir o mercado. Vamos esperar que em Chatham Lista e aqui vamos colocar componente suficiente do nosso terno para os adereços passará aparência Satel. Então ele vai ser vertical e invertido. E para o nome da classe, passaremos o próximo. Então precisamos fazer este componente este elemento rastejar um ble. Então vamos passar o transbordamento por quê? Acessar rolagem. Então vamos ver a barra de rolagem sempre. E também vamos passar Alfândega Corvo para torná-lo estilizado. Tudo bem, e então dentro da bolha passado ponto itim suficiente e então item de quarto como esse. Tudo bem, vamos dar uma olhada. Está bem. Parece perfeito. Podemos agarrar o pé-de-cabra, e podemos ver que é um pouco estilizado. Ok, bom. Agora vamos definir nossa marcação para o item de sala. Então vamos dividi-lo em dois. Dave está dentro de cima, parte e baixo, parte dentro. Na parte inferior, vamos definir o nosso texto. Então nós vamos colocar elemento girado, e nós vamos colocar nenhuma mensagem ainda por agora e para o nome da classe. Nós vamos especificar que ele vai ser display flex alinhar itens centro, e vamos aplicar texto preto off 70% capacidade. Está bem. Para a parte de cima, vamos colocar aqui o nome do quarto e há quanto tempo? A última mensagem foi publicada. Então vamos definir classe. Nomeie off display flex
e, em seguida, justifique o conteúdo entre dois espaços publicitários entre nossos elementos e alinhe o centro de itens . Certo, então nosso primeiro elemento será três anos com o nome do quarto dentro. Então primeiro vamos definir texto estático, e quando tivermos os valores dinâmicos reais, vamos esfregá-los. Então, para H três, vamos especificar texto desaparecido para evitar estouro. E o segundo elemento é realmente vai ser um novo componente que as pessoas instalam. Então, por enquanto, vamos colocar espaço e vamos dar uma olhada no navegador primeiro. Vamos verificar isso. Como parece, está bem, parece bom. Mas em vez deste x X, vamos usar o tempo atrás React para mostrar que um tempo relativo como este foi publicado há cinco minutos. Duas horas atrás. Um dia vai. Então vamos instalá-lo. Vou abrir cães e copiar este elogio. Depois vou parar o meu aplicativo e instalei este pacote. Vamos esperar e depois continuaremos. Ok, o pacote foi instalado. Vamos começar o up novamente e vamos usar esses pacotes. Então, a partir da documentação, eu vou copiar esta importação. Então eu vou importar para o quarto item e vamos copiar a própria empresa. E vamos colocá-la em vez dessa extensão para que não precisemos localizá-la. Então vamos usar o novo encontro por enquanto. Em vez disso, fora desta data beber apenas para mostrar a hora atual. Tudo bem, então vamos atualizar o aplicativo e vamos dar uma olhada. Ok, então agora nós temos apenas agora perfeito. E eles vão pensar sobre esta biblioteca que irá atualizar este temporizador, digamos em tempo real, mas eu não gosto da aparência deste texto. Então eu vou mudar o nome da turma fora do tempo atrás, componente um pouco. Então, ele vai ser formado normal. E também texto preto. Digamos 45 opacidade. Vamos dar uma olhada agora. Tudo bem. Parece muito melhor. Ok, vamos seguir em frente. E nosso pensamento final aqui será realmente fazer este componente tornar esta lista de sala de bate-papo altura
completa. Então, para isso, precisamos calculá-lo porque nosso chat é de página inteira. Então, como podemos fazer isso? Como podemos abordar isso? Sabemos que a nossa página inteira é 100%. Podemos obter a altura fora da parte superior fora da barra lateral, e então podemos subtrair esta parte superior de 100, então vamos ficar a conhecer a altura do resto, que é a nossa lista de salas de chat. Vamos lá. Por isso, não vamos passar o Bardoczky S e a nossa parte principal é este elemento Def. Para obter a altura real disso, def, precisamos usar referências. Então vamos criar uma nova referência, que vamos nomear topo, Bar Arraf e vamos usar usar o gancho ref. Então nós vamos passar este lado de cima desprovido para esta respiração def vai ser topo por árbitro , e nós vamos colocar altura para o estado, então vamos manter o controle disso. Então vamos definir você palco, que vai nomear altura e sentou-se apertado
por agora, por padrão, será tal para agora ou 20 que realmente não importa dentro uso efeito. Nós vamos pegar a altura real fora desta definição e então disse para o estado. Então, vamos colocar efeito de uso. E dentro deste efeito de uso, vamos perguntar o próximo. Então, se nós temos top side por ref dot atual porque ele pode ser indefinido em alguns momentos, então vamos verificar se ele realmente definido, então vamos definir altura para cima por Ralf, não altura de rolagem de ponto atual. Então, quando tentamos acessar topo desprovido de corrente, é como se tentássemos acessar elemento quando obtê-lo com documento. Obter elemento por i t. Por isso, é muito útil em alguns casos como este. Nós também queremos executar esta função de retorno de chamada efeito sempre que nosso foram top side. barra F muda. Muito bem, agora vamos passar este estado desta altura para a lista de Chatham para podermos calcular a altura real . Então vamos passar acima altura elemento como altura e dentro lista sala jato vai d estrutura acima altura elemento e, em seguida, o que vamos fazer. Nós vamos aplicar estilo no estilo Lyons, que vai ser altura, incurável, usar CSS calcular função. Então vamos porco alc. Então vamos usar 100% idade menos acima do elemento acima da altura do elemento e no final, vamos colocar pixels porque esta altura acalma em pixels. Agora vamos dar uma olhada. Se o aplicativo for atualizado, nada acontece de fato. Isso é porque nós não cascata eram altura de página inteira. Então, o que está acontecendo que dentro de casa desonesta está aqui? Quem disse h 100 em Lee para o grande componente, mas para fazê-lo trabalhar para um componentes aninhados também. Precisamos definir a altura de 104 crianças para todos os componentes aninhados. Então, para a linha, vamos especificar a idade 100 e para a coluna fará o mesmo Agora. Dentro do fio lateral, já
aplicamos H 100 ao seu elemento de educação, por isso funcionará. Agora vamos dar uma olhada e vamos inspecionar o componente. Como você pode ver, já
temos altura total e é calculado automaticamente e não teremos nenhum estouro. Ele sempre caberá na altura da página inteira. Então, se inspecionarmos este elemento, podemos ver que a altura é calculada automaticamente para nós. Então temos 138 pixels, que é altura fora da parte superior. Fora da barra lateral. Tudo bem, então parece legal. E eu acho que é isso para este vídeo e o próximo vamos continuar. Então vamos adicionar tudo ao estado do palco e vamos cometer começou a trabalhar com
lista de salas de bate-papo . Vejo-te no próximo
116. Criando uma lista de salas de Chat - contexto (parte 2): Ei aí. Neste vídeo, vamos continuar trabalhando em Chatham List. Da última vez definimos Mark. Desta vez vamos criar e gerir o estado. Vamos antes de entrarmos em código. Quero definir como vamos acessar este estado. Então salas de bate-papo. É algo dívida que vamos acessar globalmente dentro da página inicial. Então vamos usar contexto a p I para ser capaz de acessá-lo a partir de dentro componente barra lateral, mas também a partir de dentro janela de bate-papo que ainda não criamos. Vamos navegar para a pasta de contatos e aqui vamos criar o contexto de salas de arquivos. O G s. Aqui vamos criar novo contexto indatável quartos dame contexto com criar função de contexto que vem de reagir. Então precisamos definir um componente,
um provedor que irá fornecer a todos os seus filhos com o contexto. Então vamos exportar provedor de salas de const como um argumento. Ele receberá Crianças e ele vai retornar quartos contexto provedor ponto, e vamos colocar Crianças dentro como um valor. Por enquanto, vamos colocar uma corda. E se a temos neste componente, diz, reagir deve estar no alcance. Então vamos importar reagir de reagir. Tudo bem. Bom. Agora vamos definir o estado. Por isso, vai ser simples. É por isso que podemos usar o estado de uso. Então vamos definir salas e salas de satélite por padrão. Ele será definido para montar, e teremos nossos dados dentro do efeito de uso quando o componente monta. Então vamos para o efeito de uso e dentro primeiro, vamos armazenar nossa referência para as formas de dados. Então, se
abrirmos o banco de dados, lembramos que armazenamos nossos dados em salas, barra na sala I d. e então vamos dados. Então, o que vamos fazer, vamos colocar um ouvinte em tempo real nas salas para que possamos obter atualizações em tempo real. Vamos criá-lo valioso que vamos nomear lista de quartos áspero e vai ser banco de dados quartos ref
ponto. Então agora temos a referência. Então vamos colocar um ouvinte em tempo real usando ponto no método. Então vamos ligar para a lista de salas. Ralf pensou no valor e, em seguida, para o retorno de chamada. Quanto a agora, ele recebe camisa de pressão. Quanto a agora, vamos Cônsul olhar, valor de ponto
instantâneo certo. E porque é um ouvinte em tempo real, precisamos cancelar a assinatura dele porque esta é uma assinatura. Então vamos fazer isso dentro da função de limpeza. Efeito fora de uso aqui. Nós vamos colocar a lista de quartos ponto áspero fora ele vai separar todos os ouvintes em tempo real desta
referência dentro do banco de dados. Tudo bem, vamos salvá-lo. E vamos realmente usar esse contexto. Vamos navegar até a página inicial. E aqui vamos embrulhar tudo em torno de provedor de quartos. Ok, vamos dizer com e vamos dar uma olhada. Se eu ir para o console, eu posso ver que eu tenho valor instantâneo, que é um objeto onde cada chave é idéia sala e, em seguida, vai dados. Então temos esse capataz porque temos o banco de dados baseado no Jason. Mas estes não são exatamente os quatro meses com que queríamos trabalhar. Precisamos de uma via aérea. Então vamos criar uma função auxiliar que irá transformar este tipo de objeto em uma matriz. Então vamos definir uma nova função dentro de ajudantes togs que vamos nomear. Vamos uma matriz transformar dois com I d. Ele receberá valor instantâneo como um argumento e ele irá retornar. A próxima coisa primeiro é verificar se o valor do instantâneo existe. Se os nossos dados não forem agora, se tivermos algum dado. Então, se esse for o caso, então vamos colocar a lógica. Caso contrário, voltaremos e esvaziaremos. Certo. Então, qual será a nossa estratégia? Vamos chamar objeto de método do beijo para colocar todas as idéias de sala em uma matriz. E então vamos mapear cada valor, cada quarto que eu d para esses dados. Vamos lá. Então vamos colocar chaves de ponto de objeto fora do valor instantâneo para obter todas as crianças como uma matriz. Então vamos mapear cada valor desta área onde cada elemento é a sala que eu d para um objeto que será todos os dados da nossa sala. Nós podemos acessá-lo com valor instantâneo fora da sala I D. E então nós vamos anexar i d outra propriedade, que vai ser quarto I d. Tudo bem, vamos navegar duas salas contexto e aqui em vez disso, off usando o valor de ponto instantâneo, vamos realmente transformá-lo menos grandes dados novos e valiosos aqui. Vamos colocar transformação em matriz com i d. e vamos passar o insight do valor do ponto instantâneo. Tudo bem. E vamos CTA consular mais tarde para ver o que realmente recebemos. Agora, Como eu posso ver, eu tenho uma matriz fora dos quartos e eu tenho dados e também eu tenho I d como uma propriedade. Tudo bem, então é isso que eu quero. Agora, vamos atualizar o estado. Vamos chamar salas e colocar dados dentro. E então vamos passar este estado para o contexto como nosso valor de que são salas. Tudo bem, é
isso por enquanto. Eu acho que no próximo vídeo, vamos terminar isso e vamos exibir nossos quartos do banco de dados. Mas, por enquanto, vamos terminar este vídeo confirmando nossas mudanças. Obter commits traço M e para o relatório de mensagem criado salas contexto. Está bem, vejo-te no próximo.
117. Criando uma lista de salas de Chat - exibira como links (parte 3): Ei aí. Neste vídeo, vamos exibir salas de chat que armazenamos dentro do banco de dados, usando a marcação e o contexto que criamos nos vídeos anteriores. Vamos,
vamos abrir nosso código. E aqui vamos abrir componente de lista de salas de bate-papo. Aqui as pessoas consomem o nosso contexto. E novamente como antes, em vez de usar o contexto de dicas e, em seguida, especificar o contexto importando o arquivo, vamos criar um gancho auxiliar dentro de salas, contatos. Vamos exportar. O Const. Vai nomeá-lo. Use salas, e vai ser uma função que nos retorna o valor de contatos. Então vamos colocar para usar o contexto e pacificar o contexto dos quartos. Desta forma, vamos evitar chamar dicas contexto com salas, contexto cada vez, mas usar salas. Tudo bem, então dentro de componentes da lista quebrando. Vamos chamar este gancho de salas de uso e agora temos o valor de contexto. Agora a coisa é que essas salas podem ser nulas no momento em que tentamos acessá-lo, porque nosso estado inicial é maçante e somente quando componentes monta obtemos os dados reais. Então precisamos colocar corrida condicional, beber e checar isso aqui dentro. Suficiente. Vamos colocar se não temos quartos. Então vamos mostrar o componente Lauder que vem do nosso terno. Ele será centrado, e será centrado. Vertical E. Além
disso, terá conteúdo, o que dirá carregamento e terá baixa velocidade. Tudo bem. E também, vamos especificar tamanho para tamanho médio. Tudo bem, citação. Agora, vamos exibir segunda renderização condicional para realmente mostrar dados vamos mapear cada elemento da
matriz, que é salas que transformamos com transformação para chegar com I d a um j seis elemento. Então vamos perguntar se temos quartos e quartos ponto terra é maior que zero Onley. Então vamos ligar para a sala, começar o mapa dentro, vamos ter o pequeno Tim e temos um mapa. Este quarto eu tento a amar componente item como esse. E não se esqueça, quando usamos este mapa de pontos, precisamos especificar a chave prop. Então vamos colocar o quarto escuro. E então vamos passar o objeto da sala como um quarto,
propriedade para quarto item como este. E então vamos passar o objeto da sala como um quarto, Tudo bem. Parece bom. Agora vamos abrir o item da sala no próximo aqui, vamos destruir o chur ou a própria propriedade, e dentro do componente, vamos conseguir o nosso equilíbrio novamente, estruturando o objeto da sala desta vez. Então, teremos criado em e também teremos o nome do quarto. Então, em vez deste imposto estático, vamos exibir o nome da sala que nós D estrutura e também quatro vezes atrás componente. Se não tivermos mensagens, mostraremos o tempo quando esta sala tiver sido criada. Então vamos apenas passar Nova data criada em tudo certo, Vamos salvar e vamos dar uma olhada. Perfeito. Agora podemos ver que o quarto foi criado há um dia e o nome do quarto é Olá, Talvez vamos tentar criar mais um quarto. Então, vamos clicar no nosso Moto. Vamos passar se eu sabia o nome Roll e qualquer relatório para descrição. Se você clicar sobre isso, podemos ver que os dados estão sendo atualizados em tempo real, então tudo funciona perfeitamente. No entanto, eu também quero transformar esse componente em um link. Então, quando clicamos nele, nós realmente ir para a página de bate-papo. Tudo bem, então vamos voltar para o código e vamos para a lista de salas de bate-papo aqui para este item de rapé. Primeiro. Acho que eu quero fazer, Eu quero especificar classe componente para que ele irá renderizar este item suficiente usando este
elemento fornecido para uma classe competente. Vai ser um componente ligado que vem do roteador do reator burro para este
componente de ligação , vamos pacificar sua propriedade, que é também. Então vamos colocar dois. E vamos usar interpolação string para especificar qual caminho haverá se clicarmos nele. Então, vai ser chats barra sala I d. Então vamos abrir cadeia contar população e vamos colocar idéia quarto. Tudo bem, legal. Vamos verificar isso. Agora. Se eu clicar nele, você pode ver que o Ural muda e nós realmente temos a funcionalidade. Mas eu também quero tornar este item ativo sempre que tivermos o caminho correto correspondente
ao link. Então o que precisamos fazer como antes com bilheteria, precisamos obter nossa localização atual. Então, vamos usar gancho de localização que vem de reagir Router pacote para baixo. Agora, para este rapé, vamos passar mais uma propriedade, vamos passar mais uma propriedade,
que vai ser chave ativa, então chave ativa vai ser localização, não nome do caminho. Então precisamos pacificar ou, digamos, associar cada item de amor à sua corrente. Vamos uma chave. Então, para isso, precisamos passar mais uma propriedade, que vai ser chave de evento. E ele deve corresponder à chave ativa,
que é o nome do caminho do ponto do local. Então, será bate-papos de
barra, sala de barra I d. Então, para chave de evento, vamos especificar exatamente o mesmo que para a propriedade. E agora vai funcionar. Vamos verificar isso. E agora, quando a nossa localização corresponde, temos a animação legal e temos a chave ativa. Então funciona perfeitamente. Mas eu quero modificar um. Pense em vez de bate-papos, eu quero usar apenas bate-papo como este. Certo, vamos checar mais uma vez. Se eu mudar para a página de bate-papo, eu tenho este elemento ativo. Tudo bem. Bom. Então é isso. Vamos terminar o nosso vídeo. Vamos colocar tudo para o estado do palco, e então vamos chamar, obter commit com as salas de bate-papo exibidas. Tudo bem, legal. Este é o fim para este vídeo. Da próxima vez vamos construir nossa parte direita fora do site e vamos começar a construir janela de bate-papo. Vejo você lá
118. Criando o layout aninhado para a página de página: Ei, Neste vídeo, vamos criar Lee nosso para a página inicial. Então, por enquanto, já construímos a parte esquerda, qual barra lateral? Agora vamos definir o nosso papel certo, e vamos ver como eles vão jogar um “vamos” responsivo. Então vamos abrir o arquivo dos togs domésticos. E aqui teremos um ninho, uma seca. Então, quando clicamos em uma sala de bate-papo, podemos ver que vamos para a sala de bate-papo barra i d. Para isso, precisamos criar um acidly out porque vamos mostrá-lo na página inicial. Então o que eu propus para dio aqui em vez de apenas usar um arquivo diretamente, vamos criar para não a pasta home. E aqui vamos colocar todas as secas do Nestor e a DGS em casa vai estar dentro de togs índice . Então vamos criar nova pasta home dentro vamos colocar casa do que vamos renomeá-lo para indexar pontos gs. E aqui nosso ninho a seca vai ser página de bate-papo. Então vamos criar um novo arquivo que vamos chamar Chat Doggy S. e, por enquanto, ele vai estar vazio. Porto solícito. Alô? Tudo bem, então dentro deste índice Se nós o salvarmos, vamos atualizar Não é possível abrir o diretório. Tudo bem, talvez vamos reiniciar o aplicativo e ele vai funcionar. Deixe-me refrescar. Tudo bem, agora parece bem. Bom. Vamos continuar. Então nosso primeiro passo será definido. Ah, onde? Nestor Seca. Então aqui, ao lado desta coluna, vamos definir instrução switch e aqui vamos derramar a rota de bate-papo e a barra lateral Ele será persistido porque é o nosso layout. Então, dentro disso, que vamos derramar e porque nossa página inicial já é privada, não
precisamos derramar secas ninho. Também rotas privadas. Podemos usá-los como públicos porque nossos pais são privados. Isso significa que eles já estão protegidos. Então ele vai ser rota exata eo caminho vai ser barra chad slash chat I d para seguir a grade. Também precisamos colocar uma coluna aqui. Então vamos colocar coluna e dentro vamos derramar chat e vamos também importado desta pasta. Então deixe-me especificar o chat e vamos usar o chat. Tudo bem, agora parece bom. Vamos definir como Maney colunas a página de bate-papo vai levar. Assim, em pequenos dispositivos, levará todas as 24 colunas e em dispositivos médios. Vamos tirar o resto disto, por isso vai ser 16 e, em seguida, o nome da classe também vai ser uma igreja 100. Agora vamos dar uma olhada e vamos ver. Tudo bem, temos Olá, vamos inspecionar e vamos tentar rece gelo. Tudo bem, então vemos que quando estamos em pequenos dispositivos, temos isso, digamos, de cima para baixo, Lee fora. Não é isso que queremos. Queremos esconder esta saudação em pequenos dispositivos e porque precisamos não apenas esconder isso, também
queremos ter certeza de que sempre que vamos para a sala de bate-papo, não
vemos a barra de navegação. A barra lateral. Então é por isso que precisamos colocar algum tipo de ah, digamos condição complicada. Então, primeiro de tudo, precisamos definir nosso ponto de interrupção quando estamos na área de trabalho, e isso é quando temos 992 pixels. Então, primeiro vamos definir é desktop, e vai ser o resultado do uso gancho de consulta de mídia que definimos anteriormente. E aqui vamos perguntar se homens com IHS 992 pixels, certo? Então, neste caso, teremos desktop. Além disso, precisamos tomar nossa segunda condição quando estamos exatamente na página inicial para que possamos mostrar a barra lateral em pequenos dispositivos, não na página de bate-papo, para que ele fique escondido. Então vamos definir é exatamente assim. Vamos destruí-lo do uso, não do uso. Media Query usado muito rota. É outro gancho que vem de reagir roteador, o mesmo que usar local. Mas este cozinheiro nos dá, digamos, pensamentos relacionados à nossa rota atual e jogo de seca. Então, um desses adereços é exato e ele vai dizer se estamos atualmente nesta
rota definida , que é home page. Então, quando vamos estar em apenas barra ele vai nos dar é exatamente igual à verdade. Tudo bem, então agora vamos definir nossa condição. Então vamos pobre pode renderizar barra lateral e vamos perguntar se ele é desktop para se ele é exatamente passado em Lee, então nós seremos capazes de renderizar barra lateral. Então, agora aqui, vamos derramar a próxima lógica. Então, se pudermos renderizar barra lateral, então vamos colocar esta coluna e agora aqui precisamos também definir, digamos, um quatro por quatro horas ou se alguém abrir uma página de bate-papo quebrada, podemos vivê-la vazia e tudo ficará bem. Mas vamos fazer isso chique e vamos parar aqui e aqui. Vamos perguntar se é só para desktop. Então nós queremos mostrar a coluna, e ele terá, eu acho, o mesmo lee aqui fora. Então vamos copiá-lo. E lá dentro, vamos puxá-lo. Digamos que apenas o texto que dirá Por favor selecione o chat e o nome da classe vai ser tributado centro e margem superior direitos Fage. Agora vamos dar uma olhada. Então, sempre que agora estamos em bate-papos barra menos espaço eu d. Podemos ver apenas conversa na página. Se eu remover isso e navegar para a página inicial, eu posso ver apenas barra lateral, por isso parece bom. Se eu redimensioná-lo, eu posso ver os dois para que eu possa ver minha sala de bate-papo, mas em vez disso fora do bate-papo real. Sempre que não estiver selecionado, eu posso ver a seleção da polícia tiro no total de volta para fora, então ele funciona como 404 e se eu selecionar um dos chats, eu posso ver a janela de bate-papo real. Acho que este é o fim para este vídeo. Da próxima vez, continuaremos. Mas, por enquanto, vamos apenas cometer nossas mudanças. Vamos colocar, Obter em tudo. Obter commit e digamos que criado nós nosso para home page e criou página Shat para a direita. Incrível. Vejo-te no próximo.
119. Criando o layout/Component: Ei,
neste vídeo, vamos criar Lee para conversar página que podemos ver à direita em vez disso . Alô? Vamos lá. Vamos voltar para decodificar. E aqui na pasta Componentes, vamos cumprimentar e sua pasta e que vamos nomear Shatt Window dentro. Vamos criar mais três pastas e cada uma representará cada parte desta página. Então nós vamos ter primeiro Pasta vai ser mensagens. Então nós vamos derramar cima e baixo assim, dentro de
um lugar de bolha, todos os componentes correspondentes. Então, dentro de baixo, vamos colocar togs índice e ele vai ficar vazio por agora do que o mesmo que vamos fazer para o resto. Então aqui nós vamos colocar togs índice, mas um nome que ele mensagens que vamos colocar mensagens dentro, vamos salvá-lo e fechar. E o nosso último componente será esta palestra. Então vamos criar outro índice togs. E vamos colocar o topo com a visão de texto superior. Tudo bem, vamos salvá-lo e vamos navegar para a página de bate-papo. Então aqui, dentro desta definição, vamos derramar outro def. Isso será um rapper para o Chat Top, e vamos importá-lo em um segundo. Então vamos servir outro Dave. E dentro vamos colocar mensagens e o mesmo. Vamos aplicar para o fundo do Chade, todos os direitos e para cada um destes Daves. Se abrirmos filha principal um CSS. Aqui temos o gráfico de classes superior, fundo
do Chade e meio tiro. Então vamos usá-los para o nível superior do Porter chat Top quatro mensagens. Vamos colocar um cara no meio e para mas,
um, um, vamos colocar o nome da classe Chad Bottom. Muito bem, agora, vamos importar estes componentes. Então, primeiro, vamos importar o chat. Contar a partir de Vamos navegar dois componentes, janela de
bate-papo e topo. Então vou copiar três vezes. Então eu vou usar o fundo e as mensagens, e então eu vou substituí-los com o fundo do bate-papo e mensagens. Tudo bem, parece bom. Vamos dar uma olhada. Então, agora, se com um novo que
podemos ver, temos mensagens superiores e inferior e vamos remover este embrulho, def. E vamos dar uma olhada mais uma vez. Agora temos mensagens de topo e de baixo na parte inferior. Tudo bem, bom. Agora vamos definir nossa lógica inicial para a página da sala de bate-papo. Então, primeiro de tudo, vamos pegar este Chad I D. De nossos perímetros como você se lembra dentro da home page com pacificado-lo como apenas chat I d. Então vamos agarrar a partir de programas de uso gancho que podemos usar usando pacote de rotor reagir. E então podemos pegar todos os nossos quartos que temos dentro do contexto, como você se lembra. Então vamos usar salas de uso gancho que criamos anteriormente. E agora vamos realmente obter nossos dados atuais da sala. Então, o que precisamos fazer? Primeiro de tudo, precisamos verificar contra esta sala porque pode ser não por padrão, como você se lembra. Então vamos perguntar se os quartos não existem ou se este valor é agora, então nós vamos derramar componente lei ordem que vem do nosso processo. E novamente ele será centrado verticalmente como antes. Ele terá tamanho médio. Ele terá carregamento de conteúdo e a velocidade vai ser lenta. Tudo bem. Nosso próximo passo é conseguir nosso quarto atual deste quarto é uma tarifa. Então vamos porta const sala atual vai ser quartos ponto encontrar vamos ter item quarto. Então nós vamos perguntar de i d é igual a chat. Eu d tudo bem. E no final, se não tivermos espaço atual. Então, se colocarmos um aleatório seu l que não existe dentro da matriz desta sala, então vamos retornar H seis elemento com o nome da classe, centro de
texto e margem de página superior. Isso vai dizer, Chad, eu não encontrei. Tudo bem. Parece bom. Vamos remover isso, Lauder. Vamos mover esta importação para o topo. Vamos salvar. Vamos dar uma olhada. Tão carbonizado, este não foi encontrado. Tudo bem, estou correndo aqui. Deixe-me colocar a negação na frente dela. Então agora vai funcionar. Tudo bem, então nós conversamos mensagens no fundo. E se colocarmos um psiquiatra aleatório aqui, mas seremos baleados não encontrados. Está bem, Perfeito. Então é isso para este vídeo no próximo vídeo, eu gostaria de falar sobre problemas de contexto e por que é uma má idéia usar diretamente salas, gancho. Vamos cometer nossas mudanças e terminar essa. Então vamos em tudo o que você começa sistema que vamos cometer nossa mensagem e vamos dizer criado Klay, nossa página de quatro carbonizados. Tudo bem, bom. Vejo-te no próximo.
120. Problema de API de texto e uma solução Potencial: Oi contexto. AP é incrível, não é? Mas sempre com qualquer boa ferramenta, há também um lado negativo. O problema com o contexto é que podemos selecionar uma parte de seu valor. Não podemos definir um seletor por essa razão. Sempre que o contexto é consumido com o gancho de contatos de uso, mesmo que o valor não seja usado e ele muda, o componente será renderizado. Imagine o contexto que passa para baixo e objeto com a próxima estrutura. Em um componente em que Título é exibido, gostaríamos de obter apenas imposto sobre o título, certo para que possamos destruir o texto do título do valor do contexto e parece que tudo bem. No entanto, para o contexto, não
importa se ele é destruidor ou você tentando selecionar parcialmente elementos. Ele sempre lhe dá todo o valor de contexto a partir de agora, uma vez que o componente título recebe o valor sempre que qualquer coisa dentro do nosso objeto muda. Por exemplo, pesquisando colocar, o componente título será renderizar, e isso é ruim. Para resolver isso, podemos realmente dividir o contexto em dois provedores de contexto separados, um por chave de objeto. Dessa forma, dividimos responsabilidades e renderização não será acionado porque vamos consumir apenas o que precisamos dentro de um componente provedor não foram limitados a você. Apenas um contexto pode combinar vários contextos em um provedor. É muito útil quando passamos pelos contatos, por
exemplo, exemplo, o resultado do estado de uso,
estado e sua função de atualização para eles. Serão dois contextos separados agrupados em um provedor. Então, agora, se dentro de um componente consumimos contexto que fornece o componente de função de atualização
não será renderizado. Quando esse estado muda, ele só será renderizado se o valor real fora do contexto consumido for alterado, que é a função de atualização. Neste caso, isso funcionará para a maioria dos casos. No entanto, há situações em que gostaríamos de passar um objeto grande através do contexto, e criar um novo contexto para cada chave será um exagero. Para estas situações. Há um seletor de contexto de uso do pacote que nos fornece funcionalidade para selecionar parcialmente o valor do contexto. Ele vem com as poucas limitações, mas quando usado sabiamente, renderizações podem ser evitadas em tudo. Só para salientar, tudo isso é atencioso ao usar patos credo em vez de contexto um P I. Para a gestão do estado, no entanto, Redox tem uma curva de aprendizagem e traz mais complexidade, dependendo da aplicativo. Você provavelmente não precisa disso. É por isso que usamos o contexto. A p i no próximo vídeo que vamos instalar usar seletor de contexto e vamos ver como ele pode nos ajudar a ver que
121. Problema de API na prática - criando o contexto da sala atual: hi nesta mídia irá criar contexto para sala de bate-papo aberto atualmente usando cues Context Lecter pacote. Antes de começarmos, vamos explorar como tudo vai ser tratado. momento, há salas de contexto que rouba toda a página inicial. Dados de contexto são lista de salas de bate-papo com assinatura em tempo real. Isso significa que se alguma coisa mudar em qualquer contexto fora da sala, o valor será atualizado dentro de salas sombra GS. O contexto está sendo consumido. Então qualquer atualização em qualquer sala causará uma rendição. Duas páginas de chat atualmente abertas, mesmo que a data AB não tenha sido relacionada a ela. Portanto, dentro de Chad Ogea s, vamos fornecer um novo contexto que vamos nomear contexto de sala atual e vamos passar atualmente abre dados de sala para esses contextos. Vamos usar o seletor de contexto. Imagine uma situação quando o nome da sala atualmente aberto é atualizado. Ele criará uma rendição para sala atualmente aberta e valores que passaremos para o contexto atual da
sala também serão evitados. Há um componente que consome o contexto atual da sala e ele exibe apenas a descrição, não o nome, porque fora o seletor de contexto de uso, esse componente não será renderizado. As alterações afetarão em Lee o componente que exibe o nome. Certo, vamos colocar tudo em prática. Eu já abri oficial obter página web feliz para uso pacote seletor de contexto E se eu rolar para baixo a partir da parte de instalação, eu posso ver que eu preciso copiar este comando. Então vamos fazer isso. Vamos navegar de volta ao código e dentro do Terminal Integrado eu vou executá-lo e vamos esperar até que ele seja instalado. Aperfeiçoe os pacotes lá. Agora vamos executar o aplicativo e não vamos voltar para a documentação. Assim, a partir da parte de uso, podemos ver que na verdade não é diferente de como usamos o contexto de criação normal. Então, vamos navegar de volta ao código. E aqui em seu contexto, pasta menos grande arquivo novo que vamos nomear contexto sala atual. Desonesto. Sim, aqui. Vamos criar contexto de sala atual e vamos usar criar contexto, aquele que vem de não reagir. Vamos converter Teoh uma jóia de seis meses e do seletor de contexto de uso. Tudo bem, então a próxima parte será criar o componente provedor. Então vamos colocar exportação const provedor de sala atual para que ele vai receber Crianças e, em seguida, também ele vai receber dados para que ele vai levar alguns dados que vamos passar para este provedor. Então aqui vamos retornar atual do provedor Context Dar. E nós vamos crianças pobres lá e por valor. Vamos pausar os dados, então o componente do provedor vai ser como um intermediário. Tudo bem, então se temos nossa reação, devemos começar o escopo. Então vamos importar reagir de reagir ou eu vou. Agora vamos realmente ver como podemos selecionar alguns dados daqui? Então precisamos usar contexto de uso, seletor. Então precisamos fornecer contexto que queremos consumir. E então nós fornecemos o Colback que irá aumentar nosso valor onde o argumento é nosso
estado atual . Então vamos navegar um pouco para baixo daqui. Podemos ver que podemos realmente usá-lo assim. Então vamos copiar isso e vamos colocá-lo aqui no contexto atual da sala. Então o que vamos fazer, vamos transformá-lo em nosso próprio gancho personalizado. Vamos importar usar o seletor de contexto do próprio pacote, e então vamos transformá-lo em um gancho. Então vamos convertê-lo para funcionar. E em vez do primeiro nome, vamos usar o quarto atual e também vamos exportá-lo. E para este uso sala atual, vamos apenas passar seletor. Então vamos passar seletor aqui. E em vez de contexto pessoal, vamos derramar contexto de sala atual e para seletor, vamos fornecer seletor. Já estamos aqui. Agora, não
vamos voltar para nossa página de bate-papo. E aqui, em vez desses colchetes vazios em vez de fragmento reagir, vamos usar esse provedor. Então vamos colocar o provedor de sala atual, e precisamos passar os dados que colocaremos neste contexto. Então vamos colocar dados E para dados, vamos criar um objeto que vamos nomear, digamos dados atuais da sala. Então aqui vamos criar este objeto, e aqui vamos passar os próximos valores. Então, da nossa sala atual, vamos atingir o nome e a descrição destruindo os valores. E então vamos passar nome e descrição para corrente a partir de dados que passarão para o contexto
D. Tudo bem, então se salvarmos e salvarmos tudo aqui agora, se voltarmos ao nosso aplicativo, nada realmente será mudado. No entanto, se vamos dizer que vamos para o chat top aqui, vamos usar o gancho de sala atual que criamos. Então vamos talvez selecionar um nome e para seletor vamos passar Estado e do estado, vamos escolher o nome ou talvez não, estado. Vamos colocar inveja por valor assim. E agora, em vez de cima, vamos exibir esse nome do contexto. Tudo bem, então se eu disser isso, se eu atualizar, eu posso ver Olá o nome do quarto que passamos para os contatos e se eu mudar, ele será mudado. Então é isso. É assim que podemos realmente atingir valores de pico a partir do contexto. E também é muito importante notar que esses valores que escolhemos do estado que
escolhemos do contexto é importante entender que podemos selecionar objetos porque
objetos são comparados por referências. E se abrirmos a documentação para este pacote, se rolarmos para baixo até limitações, podemos ver que o gatilho de provedor renderiza Onley se o valor de contexto for preferencialmente alterado, então os objetos são preferencialmente mudou. Por isso, temos de ter cuidado com isso. Precisamos selecionar apenas tipos primitivos que o objeto não é. E também, se olharmos para dentro das limitações, precisamos envolver nosso componente em torno de reagir, mamãe. Então vamos também importar mamíferos de reagir e vamos envolvê-lo em torno dele assim. Então agora o nosso valor está memorizado. E se algo mudar para esta corrente a partir de dados, vamos uma descrição. E dentro deste componente superior, só consumimos nome. Este componente não será atualizado quando a descrição for alterada. Então é isso. Uma coisa a apontar aqui é que, como mencionei anteriormente, se consumirmos ambientes dentro deste componente, e se algo mudar, todo
o componente será renderizado. Então, incluindo este chat top mensagens e chat bottom. Mas porque usamos mamíferos aqui, Teoh, memorizamos nossos componentes. Reduzimos significativamente a árvore de atualização para que somente essas quedas de embalagem sejam atualizadas em cada alteração. Componentes subjacentes mensagens de bate-papo up na parte inferior do bate-papo não serão renderizadas. Então é isso. Esta é a caverna. Está fora do contexto. AP I Vamos terminar este vídeo. Então vamos confirmar tudo e vamos colocar a próxima mensagem criada contexto de sala atual com seletor de contexto de
uso. Muito bem, vejo-te no próximo
122. Criando o Chat inicial: Olá. Neste vídeo vamos começar uma página de chattel de construção. Vamos,
Vamos navegar de volta para o código e vamos abrir togs índice que representa na parte superior aqui. Em vez deste nome, vamos derramar outro def. Isso será outra parte superior. Então, para este difícil nome de classe sair no display flex, justificar o conteúdo entre o centro de itens de linha dentro vamos puxar a idade quatro aderência e dentro exibição rebelde Ah, foram nome do chat. Então aqui de um nome vocal e nome de classe para este pan será texto desaparecer e também
vamos colocar e eu posso aqui na frente deste texto quando estamos em dispositivos móveis para que não
possamos voltar para a página inicial. Então aqui, vamos embarcar e eu posso e classe competente vai ser um link que vem de reagir Router burro do que o próprio Eiken vai ser círculo de seta. O tamanho esquerdo vai ser duplo X E porque é um componente de link, também
precisamos fornecer a propriedade que levará à página inicial, certo? E também vamos derramar o nome de classe condicional para este Aiken. Então vamos perguntar se estamos em dispositivos móveis. Então vamos colocar nomes de uma classe. E se estivermos na área de trabalho, vamos colocar outros nomes para isso. Vamos usar o gancho de consulta de mídia que usamos mais cedo, e vamos criar o Bullen, que é móvel. E, em seguida, vamos usar Media Query a partir de ganchos personalizados e dentro de uma porta de bolhas marcas com off 992 pixels. Tudo bem, então quando estamos em dispositivos móveis, vamos puxar o display no bloco de linha do que rebater vai ser margem zero direita para texto azul e Lincoln estilizado para fazer nosso elemento link totalmente em estilo. E se estamos em dispositivos desktop, então nós simplesmente não exibimos este Aiken. Então vamos economizar e inspecionar. O que temos nós? Agora temos o nome do quarto. Se eu inspecionar e redimensionar a janela, posso ver este botão aqui. Quando eu clico nele, eu volto para a página inicial para ver Chatham. Tudo bem, parece bom. Vamos continuar. Então aqui, ao lado deste h quatro, vamos colocar barra de ferramentas de botão que vem do nosso terno, e isso ia ser nosso para fazer Então também, vamos colocar o nome da classe fora Ws No rap. Tudo bem, unificado um novo. Tudo bem, então isso é para fazer no próximo dia se vamos colocar outra definição e vai ser a nossa parte
inferior. Então, para esta parte inferior, vamos colocar,
exibir, exibir, flexionar, justificar o conteúdo entre e alinhar itens no centro. Vamos derramar como elemento divertido que também será nosso para fazer. E também, vamos colocar um botão aqui, então quando clicarmos nele, uma janela modelo se abre e podemos ver a descrição do quarto. Então vai ser outro componente que vamos criar e vamos chamá-lo Noivo Info, BT e Moto Dar g s tudo bem. Por enquanto, vai ficar vazio. Vamos usá-lo lá dentro. Índice de togs aqui. Nós vamos derramar de informações BT e Moto, certo? Digamos com e agora vamos definir nosso componente. Primeiro de tudo, aqui vamos mostrar a descrição do quarto e o nome do quarto também. Então, para isso vamos usar o contexto, Eleitor. Então, primeiro de tudo, vamos má descrição aqui, e ele vai ser usado carro e gancho jogado. Então obtemos o nosso valor e do valor crescemos descrição. E você se lembra que eu lhe disse que é importante não selecionar objetos porque eles são comparados referencial e Então isso significa que se precisamos selecionar vários valores de um objeto , precisamos selecioná-los separadamente. Então eles se tornam um valor primitivo porque a descrição é uma string. Por isso, é um tipo primitivo. Então, também precisamos exibir o nome. Então vamos fazer exatamente a mesma coisa. Use a sala atual, e nós vamos ter o nome do ponto da sala. Muito bem, agora, dentro da nossa marcação, vamos despejar um elemento de botão do nosso fato dentro. Nós vamos derramar informações de quarto e aparência vai ser piscar e classe Nome vai estar batendo em X acesso é zero agora, porque nós temos um motile que vamos usar novamente nosso próprio gancho personalizado, que é usado estado mortal. Então deixe-me importá-lo. E a partir deste gancho que vamos agarrar está aberto, fechado e aberto. Agora, ao lado deste botão elementos que podemos pagar um componente moral do que para o show propriedade que
vamos definir está aberto para na altura. Vamos colocar roupas. E dentro deste mortal, como sempre, teremos o ponto mortal Heather. Então teremos corpo e rodapé. Então vamos substituir esses valores
, Peito dela. Ok, então para a modelo Heather, nós vamos colocar o título do ponto modelo e para o título, nós vamos derramar sobre o nome do quarto do que para rodapé. Vamos colocar outro botão que vai fechar a moto. Então vamos colocar roupas, então vamos especificar em Click vai ser roupas e também vai ser um elemento de bloco, certo? E nós somos corpo, o que vai especificar algo simples, que vai ser um seis tack. E vamos colocar a descrição e o nome da classe vai ser margem inferior em seguida, irá a descrição em si. Então vamos colocar a descrição. E agora vamos salvar e remover essa def e substituí-la pelo contexto de reação . Vamos também mover a importação para o topo. E também não usamos esse manipulador aberto. Vamos colocá-lo por dias. Botão no clique vai estar aberto. Tudo bem, vamos guardá-lo e vamos dar uma olhada. Agora temos o botão de informações da sala que se parece com um link. E quando clicamos nele, temos uma janela moral que diz sobre Hello. Descrição Descrição. Ei, perto. Vamos testá-lo em seu próprio nome novamente. Temos uma descrição estranha e tudo funciona bem. Então, este é o fim para este vídeo. Vamos cometer nossas mudanças. Deixar que as pessoas cheguem a tudo e depois se comprometam. Digamos que, começou a construir Chat Top Criou uma descrição da sala. Modoff. Tudo bem, Perfeito. Vejo-te no próximo.
123. Denominação de dados - criando o fundo de Chat: Olá. Neste vídeo, vamos começar a criar fundo carbonizado. Vamos antes de começarmos. Quero mencionar que no vídeo anterior, quando começamos a criar o chat Top, esqueci de mencionar alguns detalhes. Primeiro de tudo, precisamos adicionar mais alguns nomes de classe e vai ser esta era para Element. Então vamos colocar o nome da classe e vamos colocar o texto desaparecer para evitar o excesso de impostos se
for muito longo. E então vamos adicionar os sinalizadores de exibição e alinhar o Centro de Itens para garantir que, quando
estamos em dispositivos móveis, este Aiken e texto estão centralizados verticalmente, direita e também mais um detalhe. Se abrirmos a sala para Betty Inamoto, usamos o seletor de contexto, então para fazê-lo funcionar, também
precisamos esfregar o elemento em torno de mamífero. Isso é o que nos esquecemos de diligir. Então vamos colocar memorando aqui na parte inferior e também vamos importar de reagir Agora use contexto. O seletor funcionará como esperado. Tudo bem, vamos seguir em frente e vamos começar com Chad Bottom. Vamos navegar Teoh Index Dodgy s dentro da pasta inferior. E aqui vamos definir nosso mercado para Primeiro de tudo, vamos colocar em grupo e dentro deste grupo de entrada, vamos colocar a entrada real com espaço reservado, certo? E você mensagem aqui e três pontos no final. Ao lado desta importação, vamos despejar um elemento de botão. Então, vamos definir o botão Importar Grupo Dar. E este botão terá cor azul e aparência Primária dentro deste grupo celeiro, vamos derramar. Eu venho e posso vai ser enviado. Tudo bem, vamos dizer esperar e vamos ver, o que temos? Então agora temos essa importação e temos o fundo. Então, quando clicarmos neste botão, a mensagem será enviada. Muito bem, agora, vamos definir a nossa funcionalidade. Então, em primeiro lugar, precisamos de estado. Então vamos criar importação e disse em pobre, e por padrão ele será definido para um encolhimento vazio. Em seguida, precisamos especificar no manipulador de alterações para no evento de mudança para a nossa importação. E também precisamos associar nossa opinião com o estado real. Então vamos definir o valor. Vai ser importador. E para um evento de alteração, vamos especificar na alteração de importação. O Heller. Vamos definir isso na alteração de importação e podemos otimizá-lo com antecedência onde eles usam callback porque temos o estado de entrada que muda com freqüência e na alteração de importação não
terá qualquer dependência. Então este evento inalterado nos dá valor como o primeiro argumento e evento. Então precisamos obter o valor real a partir daqui, e então vamos chamar disse, importar com valor. E só para mencionar que porque usamos essa entrada que vem do nosso terno como um componente , é por isso
que recebemos valor como o primeiro argumento. Em qualquer outro caso, receberemos apenas o objeto do evento. Agora precisamos adicionar funcionalidade ao nosso botão para realmente enviar a mensagem. Então é por isso que vamos especificar uma nova função que vamos nomear em Send Click. Ele vai ser o nosso manipulador para no clique Evento neste botão. Então vamos pacificar. Então foran clique, vamos derramar em enviar clique E primeiro de tudo, aqui vamos fazer uma verificação simples Se eu estivesse no porto. Se a nossa mensagem não está vazia, então vamos especificar importação ponto guarnição é igual a mensagem vazia. Se for o caso, então simplesmente sairá da disfunção. Em seguida, precisamos montar a mensagem. E no futuro também teremos mensagens arquivadas. Então, para isso, vamos criar uma função comum que será chamada para montar a mensagem para que ele irá anexar propriedades comuns à nossa mensagem. Então, aqui no topo, vamos criar nova função que vamos nomear,
montar, mensagem, mensagem, e como um argumento ele vai receber perfil de usuário. E vamos dizer Chad, eu d ok, e então ele vai nos dar um objeto com o quarto i d que vai ser verificado, I d. Então teremos objeto autor e aqui vamos de dados normalizados antes de continuar. Deixe-me explicar a estrutura que teremos. Então, se abrirmos nosso banco de dados agora, temos salas e perfis e nossos dados agora são planos e muito fáceis de gerenciar. No entanto, agora temos salas e precisamos criar mensagens. Como podemos abordar isso? Podemos, obviamente, colocar mensagens dentro deste objeto, No entanto, com dados em tempo real baseados porque somos inquéritos limitados, precisamos decidir sabiamente sobre a nossa estrutura. Assim, com base de dados em tempo real, é realmente importante manter a estrutura o mais plana possível. Isso significa que, idealmente, não
queremos criar objeto aninhado. Então é por isso que vamos criar outro Vamos ver, rota objeto que vamos nomear mensagens e insight. Vamos colocar os dados da nossa mensagem e, em seguida, referir-nos que esta mensagem pertence a esta sala
em particular. Nós vamos especificar o quarto que eu d dentro desta mensagem. E também vamos de Normalized Data de Normalização significa que vamos copiar e duplicar nossos dados. Isso é para evitar a realização de várias consultas em nosso banco de dados quando precisamos exibir algo. Por exemplo, bate-papo com mensagem de bate-papo. Também queremos exibir o nome do perfil do usuário, Avatar e outras coisas. Então, quando mostramos a mensagem, se não duplicarmos dados, precisamos enviar uma segunda solicitação para nosso banco de dados e obter o perfil de perfil real. Então, para evitar a realização de várias solicitações, vamos duplicá-lo. Então isso é normal em nenhum banco de dados SQL. Vamos lá. Então, para montar mensagem para autor, vamos derramar nome que vai ser perfilado o nome então vamos derramar também o seu i d , que vai ser perfil seu i d então criado em vai ser perfil criado em, e também precisamos derramar avatar condicional. Então, se você não tem nenhum árbitro, nós não colocá-lo dentro deste objeto para isso. Vamos derramar três pontos. Então vamos ter um perfil ruim do Avatar, e vamos perguntar se o dom existe. Então vamos colocar a chave do avatar com o avatar da porta do perfil. Então, caso contrário, vamos derramar um objeto vazio. Então, quando o avatar do perfil existe, vamos especificar este objeto. E porque fora de três pontos, não
podemos espalhar este objeto para este objeto global. Assim, desta forma, ele irá anexar esta propriedade a este objeto. Caso contrário, espalharemos o objeto vazio, que não adicionará nada. Ok, então próximo seu autor, vamos adicionar, criado em e aqui vamos especificar firebase. Mas vamos importar em primeiro lugar. Deixe-me colocar base de importação fogo do aplicativo firebase, e ele vai ser valor de servidor de banco de dados firebase. Carimbo de data/hora Muito bem, agora, vamos usar esta mensagem de montagem e vamos colocá-la aqui. Então, vamos criar um novo disponível que irá nomear dados de mensagens. Então vamos ligar, montar mensagem com o perfil e o Chad I D. Então vamos conseguir o perfil do nosso contexto. Então vamos perfil pobre de usar perfil Gancho que temos de contexto perfil, usar perfil. E também, precisamos de ter uma ideia de chat. E podemos obtê-lo com a ajuda fora usar Paramus que vem de reagir programas de juventude Router . Tudo bem, bom. Agora, para os dados da mensagem, precisamos anexar o texto da mensagem real. Então aqui, vamos pacificar a mensagem. Texto de dados vai ser a nossa entrada. Tudo bem. E agora a coisa é que precisamos executar uma operação atômica para atualizar dados em vários lugares dentro do banco de dados com base de dados em tempo real. É muito fácil de fazer, e eu realmente amo isso. Espere. Então, o que vamos fazer? Vamos criar uma nova mensagem dentro caminho mensagens. E também, vamos atualizar os quartos. E aqui vamos colocar outro adereço, nome
vegetal, última mensagem. Esta é para exibir a última mensagem aqui dentro desta lista de salas de bate-papo. Tudo bem, então o que vamos fazer, vamos criar um novo objeto. Será um objeto vazio por padrão, que vai ser atualizações. E a lógica será a próxima dentro deste objeto que modelamos nossos dados de atualização dentro do banco de dados relacionado Lee para a rota fora do banco de dados. Então, teremos a passagem de atualização como uma chave. E para esta chave, teremos os dados atuais atualizados, e então vamos chamar essas atualizações para a rota fora do banco de dados, e ele irá executá-lo como uma operação atômica. Eu realmente gosto desse jeito. Então o que eu quero dizer é que primeiro nós precisamos definir uma nova mensagem que eu d com antecedência. Então, para isso, vamos criar nova mensagem variável I d.
Aqui. Vamos colocar o banco de dados. Desta vez será o banco de dados que vem de Deixe-me novamente, como importá-lo, certo? Não funciona. Vamos fazer isso manualmente. Então vamos importar banco de dados do MISC. Muito bem, vamos voltar para as pastas. Certo, mais
um nível. Base de fogo Misc. Tudo bem, Perfeito. Então, banco de dados, então nós vamos precisar especificar referência para nossas mensagens. Em seguida, vamos empurrar chão, e então vamos ficar manter desta forma que podemos obter e chave única do banco de dados de tempo Riel sem criar o documento real. Ok, Agora precisamos atualizar este objeto de atualizações. Então vamos colocar atualizações e nossa primeira propriedade será mensagens. Então nós vamos especificar a mensagem que eu d aqui. E para esta mensagem, eu d. Nós vamos pacificar dados da mensagem do segundo objeto vai ser salas, barra chat I D e barra última mensagem e para última mensagem, vamos pacificar todos os nossos dados de mensagem e também Em cima disso, nós vamos anexar mensagem i d. Então mensagem I d vai ser mensagem que eu d como esta. Agora precisamos atualizar o banco de dados real. Então aqui, vamos colocar para tentar, pegar bloco, e aqui vamos chamar uma espera e vamos converter disfunção Teoh uma função de pia. Vamos ligar para a nossa base de dados com o Treff. Então nós obtemos referência à estrada fora do nosso banco de dados sem especificar o caminho, então o que vai chamar atualização e nós vamos passar nosso objeto de atualizações, e ele vai pico Todas as atualizações passadas de Keys, e ele vai atualizar esses passados dentro o banco de dados logo após nossos dados serem atualizados. Vamos chamar o set input para uma string vazia novamente, e também colocaremos um erro de porta de alerta e vamos especificar alguma mensagem de doca, ok? E também talvez vamos definir o estado de carregamento. Então, ao lado desta importação, vamos criar está carregando e triste está emprestando, que será definido como false por padrão. Então vamos chamar disse está carregando antes de fazermos qualquer tarefa assíncrona. No caso de
falharmos, vamos chamá-lo de Satya Falls. E quando terminarmos, também vamos chamar False. Agora vamos usar dis loading state para este botão. Então vamos colocar o Onley desabilitado quando nossos dados estão carregando agora, talvez vamos salvar e vamos dar uma olhada. O que você tem? Então, se eu enviar qualquer mensagem para o banco de dados, eu tenho permissão esta noite e isso é porque nós não especificamos nenhuma regra de segurança. Vamos navegar para as regras. E então vamos copiar tudo isso. Vamos colá-lo aqui no fundo. Vamos renomeá-lo para suas mensagens e vamos especificar mensagem I d Vamos salvá-lo e vamos sincronizá-lo com nossas regras locais. E agora vamos tentar enviar uma nova mensagem. Então, se eu clicar agora, vamos abrir nosso banco de dados e aqui eu posso ver um novo caminho, que é mensagens que eu tenho chave recém-gerada, que é na verdade esta mensagem que eu d que nós criamos com esta linha de código. Se abrirmos aqui, criamos em pertencer guisado Esta sala I, d autor texto, é a próxima pessoa e dentro de quartos. Se
abrirmos agora, também perdemos uma mensagem, que é essa mensagem que enviamos. Então, parece muito bem. A única coisa que eu quero fazer aqui é na verdade eu quero talvez em um novo manipulador para on key down evento. Então, quando também clicamos em Enter Button, a mensagem está sendo enviada. Então, para esta importação, vamos também colocar em chave para baixo evento e vamos especificar na chave para baixo manipulador, Vamos colocá-lo em seguida, Teoh na mudança de entrada. E isso em Qi para baixo vai ser Ou talvez vamos colocá-lo aqui na parte inferior, ao lado de on enviado clique dentro na tecla para baixo. Vamos receber um objeto de evento desta vez, e vamos perguntar se evento Kiko ou igual a 13. Se o nosso botão que pressionamos é enter,
em seguida, primeiro vamos chamar evento prevenir padrão para evitar qualquer funcionalidade padrão definido para este botão. Então nós vamos chamar no clique enviado. Tudo bem, agora, vamos tentar mais uma vez se eu disser olá de novo. Se eu clicar em digitar a mensagem direita foi enviada e o banco de dados foi atualizado. Então acho que é isso. Vamos terminar este vídeo. Vamos comprometer todas as nossas mudanças chamando de bom em tudo. Em seguida, obter commit e, vamos especificar criado fundo carbonizado Mensagens enviadas para o de chat. Esplêndido. Vejo-te no próximo.
124. Exibição de última mensagem na lista de sala: Olá. Agora que temos mensagens dentro do nosso banco de dados e temos apenas propriedade mensagem disponível em dados da sala de bate-papo, podemos exibir esta última mensagem dentro da lista de sala de bate-papo Dentro elemento sala. Vamos fazer isso. Vamos navegar de volta para o código e vamos abrir componente item sala aqui no topo, onde nós d estrutura em torno de propriedades. Vamos também d estrutura última mensagem do que primeiro aqui dentro do tempo atrás, em vez de exibir você data criada em Vamos perguntar, se perdemos dados da mensagem, então vamos exibir nova data fora da última mensagem criada em então quando esta mensagem foi criado. Caso contrário, vamos mantê-lo como estava antes de vamos exibir quando a sala foi criada, então aqui abaixo, onde não exibimos mensagens. No entanto, em vez disso, vamos má renderização condicional. Então, se tivermos a última mensagem, então vamos exibir a última marcação da mensagem. Caso contrário
, será como antes. Vamos mostrar espaço. Sem mensagens ainda. Então, dentro deste fragmento de reação, vamos colocar o primeiro usuário Avatar e, em seguida, a mensagem real. Então esta definição vai ser rapper para o componente de avatar de perfil que criamos mais cedo, como você se lembra. Então vamos importá-lo e para adereços. Vamos especificar fonte vai ser a última mensagem. Vamos dar uma olhada. Última mensagem Filha autor Nora al atar ponto autor Senhor Avatar Nome no caso se Avatar
não está definido vai ser última mensagem Autor ponto nome e tamanho vai ser fumaça. E para este surdo vamos derramar para exibir Flex e um centro de itens de linha. Certifique-se de que o elemento avatar é 10 para ler verticalmente. Em seguida, você decide se vamos nos livrar desta casca para reagir fragmento ao lado deste
avatar perfil . Vamos exibir outro surdo com tags de nome de classe desaparecer para evitar ataques de estouro e margem esquerda. Vamos pôr-te lá dentro. Vamos colocar def. Isso vai dizer última mensagem nome do ponto do autor do ponto. E no próximo ano depois do nome, vamos ficar mal. Última mensagem, texto do
cão e em direção ao nome do autor, vamos exibir texto itálico apenas para distinguir entre o nome do autor e a última mensagem. Tudo bem, vamos salvar tudo. Não vamos voltar à nossa candidatura. Posso ver isso inesperado. Tudo bem, então novamente, este fragmento de reagir. Agora, se eu disser o que posso ver, eu tenho a mensagem real. Posso ver o nome do autor. Eu posso ver minha mensagem e eu posso ver minha ninhada Ah. Agora talvez. Vamos tentar uma nova mensagem. Então deixe-me dizer olá do futuro. Se eu enviar esta mensagem, posso ver que a mensagem foi enviada. Agora de novo, meu avatar, meu nome e olá do futuro. Tudo bem, então é isso. Foi bem fácil, certo? Vamos cometer nossas mudanças. Vamos colocar tudo para obter sistema e vamos comprometer dizendo exibir última mensagem dentro do item da sala,
na verdade. Vejo você na próxima.
125. Trabalhando com dados desnormalizados: Ei, agora temos uma mensagem de luxúria dentro da lista de estilhaços. Mas aqui está o problema porque nós duplicamos dados agora. Se digamos que eu vá para o meu painel e atualizo meu apelido para outra coisa, vamos salvar para mostrar a aparência 16. Então eles também atualizam meu avatar. Se eu fizer o upload, ele estará sendo carregado. Mas a última mensagem não está sendo atualizada porque esses dados são duplicados dentro do banco de dados. Então precisamos cuidar disso quando atualizarmos os dados reais. Se fizermos algumas alterações, nos certificaremos de que também atualizamos todas as referências que duplicamos. Não vamos voltar ao código e vamos navegar para o painel,
Vamos para Dashboard Togo e, em seguida, ir para o painel. E aqui, em vez de este apelido de usuário áspero definir novos dados. Precisamos achar um jeito de atualizar todas as referências. Então, o que eu propus fazer, eu quero propor a criação de uma função auxiliar que irá obter todas as referências dentro do nosso banco de dados, e então nós podemos atualizar nosso banco de dados com antiga referência. Na
verdade, será o mesmo que fizemos dentro do fundo do Chad quando criamos este objeto de atualizações e
especificamos vários passados para executar uma operação atômica, por isso será basicamente o mesmo. Então podemos chamar essa função assim. Vamos definir como vamos fazê-lo. Então, em vez de um apelido de usuário de peso Raff definido, vamos chamar, Vamos dizer que vamos receber atualizações e porque vamos acessar nosso banco de dados, ele será em uma operação de sentença. Vamos nomeá-lo. Digamos que obtenha atualizações de usuários dentro. Vamos passar Usuário I d que vai ser perfil adoro seu i d. Então vamos passar a chave que precisamos atualizar. Então, no nosso caso, será o nome e, em seguida, passaremos o valor real, que vai ser novos dados como este. Então agora precisamos criar disfunção. Vamos navegar dois ajudantes, ela s e aqui na parte inferior, vamos exportar função de nome problema obter atualizações do usuário. Então ele vai ser qualquer função e ele vai receber usuário i d. Em seguida, ele vai receber chave para atualizar e também ele vai receber valor. E talvez vamos também passar o objeto de banco de dados junto com nossa função. Então aqui vamos passar também este objeto de banco de dados que temos dentro misc lareira apenas por conveniência como esta. Então agora dentro de ajudantes, nós também podemos ter banco de dados aqui. Agora vamos criar um objeto vazio. Atualizações de carvão indefiníveis que a nossa primeira atualização serão o valor real que estamos
tentando atualizar para atualizações. Em seguida, irá perfis barra usuário i d que barra chave para atualizar, e ele será definido como valor. Agora precisamos obter as referências reais. Então, nossas referências são Vamos dar uma mensagem de olhar I D. Que autor
do que avatar criado em também quartos. Última mensagem. Então, o que vamos fazer? Vamos definir algumas promessas porque existem várias promessas. Não queremos torná-los um por um. Queremos executá-los de uma vez. É por isso que vamos definir nossas promessas. E então vamos esperar todos eles com o ponto de promessa Toda a nossa primeira promessa vai ser receber mensagens e vai ser db dot Ralf dar mensagens, em
seguida, para obter mensagens onde digamos que este autor, eu d igual a você nosso usuário, Precisamos primeiro fazer o pedido completo por criança. Então precisamos especificar qual criança. Fomos para referência. Então, em nossas mensagens de referência caso Então nós temos o objeto de mensagem. Então temos autor barra usuário i D. Então vamos colocar ordem por autor barra usuário i d. E então esta chave será igual ao usuário i d. Que recebemos como um argumento e, em seguida, vamos colocar o valor de um para obter o valor real . Então nossa segunda promessa será obter salas de usuários, que serão salas de barra de referência DB. Então, novamente, precisamos colocar ordem por criança. E desta vez, se
abrirmos as salas, temos menos mensagem barra autor barra usuário i d. Então vamos menino última mensagem Autor, usuário I d. E então igual ao usuário i d. E novamente uma vez valor. Agora que temos essas duas promessas em estado não resolvido, precisamos resolvê-las. Por esta razão, vamos criar uma promessa de peso que tudo dentro precisamos passar uma série de promessas que vai ser receber mensagens e obter quartos como este e receber mensagens vai nos retornar instantâneo fora mensagens e obter quartos devolva-nos um instantâneo fora dos quartos. Então aqui vamos estruturá-los. O primeiro elemento é obter mensagens. Então vamos primeiro receber mensagem, instantâneo ou mensagens. Camisa de pressão. Um segundo vai ser quartos, camisa de
pressão, que vamos nomear correspondente Klay am sequestrador e Air Snapshot. Em seguida, para cada mensagem que temos com a idéia do usuário, vamos chamar para cada instantâneo de mensagem para cada mensagem que
recebemos, vamos obter instantâneo de mensagem, e aqui vamos chamar atualizações. Então nós vamos mensagens pobres barra mensagem instantâneo ponto chave, que representa a mensagem i d. Então vamos ter um objeto com todas essas mensagens, e chave vai ser esta idee off mensagem. Tudo bem, então chave de mensagem barra autor chave barra para atualizar. Então, dessa forma, nós referimos mensagens autor eo garoto que queremos atualizar, se é Allah carro nome seu eu d ou criado em. E então para que esta chave seja atualizada, vamos colocar valor e exatamente o mesmo que faremos para o nosso instantâneo. Então vamos realmente copiá-lo. E em vez de m instantâneo, vamos tirar fotos de ar ruim, que é quarto, camisa de
pressão e, em seguida, para atualizações, vamos colocar quartos,
em seguida, vamos obter a chave de ponto instantâneo quarto, que vai Seja o quarto i d. Então aqui teremos a última mensagem. Em seguida, teremos autor e, em seguida, chave para atualizar com valor. Tudo bem. E logo depois vamos retornar o objeto de atualizações que criamos. Agora vamos dizer o que Vamos navegar até você painel permite e comentou, e vamos realmente importante este objeto de ajudantes, mas parece que ele pode ser importado automaticamente. Então vamos importar obter atualizações do usuário de Vamos referenciar nossos ajudantes misc helpers e
parece que não foi encontrado certo, então chegar lá. Atualização. Tudo bem, te levo lá. Atualizações assim. Certo, Perfeito. Agora que temos atualizações, em vez de chamar esta função aqui e em vez de referenciar os dados reais, podemos realmente chamar apenas o banco de dados dot ref porta atualização com atualizações. Então esperaremos e removeremos tudo isso e também tudo isso. Agora vamos salvá-lo e vamos realmente também abrir. Aplaudir Bt, em que carrega o nosso avatar e vamos encontrar a lógica. Então aqui novamente, como então nós ouvimos dentro painel permite copiá-lo e, em vez disso, off novamente a referência ao elemento filho e, em seguida, atualizar como este. Vamos colocar atualizações iria obter suas atualizações do que para perfil i d. Nós vamos atualizar avatar desta vez e Avatar vai ser Não carregue euro assim. Agora vamos remover esta referência. Vamos remover este conjunto de avatar do usuário. Vamos ser apanhados a essa lógica. Vamos colocá-lo aqui e agora vamos dar uma olhada. Se realmente funcionou, vamos voltar ao código. Deixe-me o fresco apenas no caso de eu ir para o painel, se eu clicar em mudar, meu apelido Ok, talvez eu vou dizer olá. Novo nome. Se eu clicar em apelido seguro foi atualizado e eu ainda tenho e para estar aqui. Está bem, talvez me deixes ver o Dashboard 1. O meu tempo. Eu tenho nome aqui. Vamos registrar as atualizações do Cônsul e vamos dar uma olhada. O que há de errado aqui? Se eu inspecionar, eu vou para o console Eu atualizar meu apelido. Recebi este tipo de atualizações, mensagens, perfis, tudo bem, mas não atualizo minha última mensagem. Então isso é estranho. Vamos navegar Teoh ajudantes. E aqui vamos dar uma olhada. Chave de autor para atualizar. Certo, camisa de
pressão perdida. Autor, seu I D Vamos verificar nosso banco de dados. Última mensagem. Autor, Seu I D Que é o usuário I d que passamos. Oh, desculpe-me. Aqui não deve ser o último aqui. Deve ser menos mensagem. Vamos salvá-lo. E agora mais uma vez. Vamos mudar nosso apelido. Tiu. Digamos que ela parece 22. Se eu atualizar meu apelido, ele está sendo atualizado aqui. Perfeito. Agora vamos procurar por Al Atar Se eu enviar uma nova imagem novamente, Avatar foi evitado. Vamos olhar lá dentro. Última mensagem. Sim. Ah, O que são foi atualizado? Certo, só para o caso de mais uma vez. Aplaudir. Avatar foi atualizado. Perfeito. Vamos dar uma olhada. Sim, ele foi atualizado, então ele realmente funcionou. Tudo bem. Perfeito. Agora vamos remover a sorte do Cônsul que colocamos aqui e vamos cometer nossas mudanças. É isto. Vamos embarcar tudo para o estado do palco e vamos nos comprometer. Atualize todas as referências de usuário se os dados forem atualizados. Ok. Perfeito. Vejo você na próxima.
126. Exibindo mensagens de bate-bate-: Ei aí. Neste vídeo, vamos exibir mensagens de bate-papo aqui no meio dentro da página de bate-papo. Vamos,
vamos navegar de volta ao código e vamos encontrar as nossas mensagens da janela de bate-papo da pasta. E aqui temos togs índice já menos grande, e você arquivo que irá nomear item mensagem. Por enquanto
, estará vazio. Então vamos colocar “olá” lá dentro. E vamos deixar assim dentro de mensagens aqui, em primeiro lugar, vamos definir nosso estado que vamos gerenciar com o estado de uso. Então vamos nomear mensagens e mensagens de satélite. E, por padrão, será tal saber. Então também precisamos pegar nosso chat que nós abrimos atualmente. Então, para isso, vamos usar Paramus Hook que vem de reagir rotor e vamos ter criança, eu d agora dentro efeito de uso. Vamos fazer uma ligação para o nosso banco de dados. Primeiro, vamos pegar nossa referência ao caminho do chat dentro do banco de dados, que são mensagens. Então vamos mensagens ruins ásperas. Então vamos chamar o banco de dados, mas não o que vem do pacote Firebase um que vem de RGs baseados em fogo. Então, vamos importar essa. Em seguida, vamos especificar mensagens de barra de referência. Agora vamos colocar um ouvinte em tempo real em mensagens de espera que estão relacionadas ao bate-papo aberto . Então vamos ver mensagens pacificantes, Ralf, ordem de
porta por criança. E aqui vamos pacificar a sala I D. E esta é uma propriedade que temos em cada mensagem, que é o quarto
I.D. I.D. Então isso da idéia será igual ao chat i d que recebemos de Paramus. Agora, ele apareceu como uma dependência, então vamos editar. E logo depois disso, vamos colocar um ouvinte em tempo real, então vamos colocar valor e honrados pacificar o retorno que vai receber instantâneo. Agora, como você se lembra, este instantâneo será um objeto onde cada chave é mensagem I d. e então nós obtemos os dados reais. Então precisamos transformá-lo. E nós já fizemos isso com a transformação para matriz com a função I d. Então vamos chamá-lo mais uma vez. Então vamos dados pobres e, em seguida, vamos colocar transformar em matriz com i d. Em seguida, vamos chamar o valor de ponto instantâneo e passá-lo para esta função. E então vamos atualizar o estado com dados como esse e porque é um
ouvinte em tempo real . É uma assinatura que precisamos cancelar. Então vamos usar Ah, estamos função de limpeza para efeito de uso. E aqui vamos despejar mensagens, bote e cachorro fora, e podemos especificar o valor. Assim, vamos cancelar a assinatura de todos os ouvintes em tempo real nesse caminho. Muito bem, agora, o nosso próximo passo é realmente exibir dados. E primeiro, precisamos obter alguns valores de bullying que nos ajudarão a renderizar nossas
mensagens condicionalmente . Então o nosso primeiro será disparado vazio e carbonizado. Vazio vai ser apenas quando temos mensagens definidas e, em seguida, mensagens ponto comprimento é igual 20 Então nós carregamos todas as mensagens, mas não há mensagens em tudo. Certo, então nós também podemos ter pode mostrar mensagens que indicarão se podemos renderizar nosso item de
mensagem que criamos. Então, se tivermos mensagens e mensagens, o comprimento do ponto é maior que zero. Então nós poderíamos colocar essa condição diretamente aqui dentro de nossa marcação, mas só para ser mais legal, você sabe, nós colocamos aqui. Então, dentro desta definição, vamos colocar a próxima lógica. Em primeiro lugar
, não vai ser uma diferença. Vai ser um U L. Então o nome da classe vai ser lista de mensagens e também os costumes crescem que dentro vamos derramar é carbonizado vazio. Então vamos mostrar um elemento aliado porque temos você, eu e vamos dizer sem mensagens ainda. E então, se pudermos mostrar mensagens, então vamos derramar mensagens, Doc mapa e vamos mapear cada mensagem para item de mensagem. Vamos abrir para um item de mensagem de inteligência. Ele vai ser a porta da mensagem i d. E então vamos passar a mensagem com uma mensagem como essa Agora dentro da mensagem precisamos de
estruturar esta propriedade. Então vamos colocar mensagens e aqui no nível inferior D estrutura de mensagens, mas não de mensagens. Desculpe-me da mensagem. Vamos mudar o nome para mensagem. Vamos salvar o que também é alterado na mensagem. E a partir desta mensagem vamos destruir o autor problema D estrutura criado em e vamos destruir texto. Agora ele vai ser um elemento l i e terá o nome da classe fora separado e margem inferior um. Então colocaremos Dave aqui. Essa será a parte superior da nossa mensagem. E então vamos colocar outro def. E dentro deste diferente vai colocar espaço que irá exibir nossa própria mensagem detecta e nome
da classe vai ser Ward quebrar tudo para evitar que o texto de estouro se for muito longo. Então, para a nossa parte superior, vamos especificar o nome da classe fora exibir bandeiras alinhar itens fonte central vai ser mais ousado e margem inferior um, então aqui vamos derramar Primeiro perfil Avatar, Vamos abri-lo. Perfis todos Matar. E agora vamos usar inteligência para importar. Então, como fonte, estamos ficando mais baratos. Autor dot avatar para nome. Vamos nos dar ou ao Doc. Nomeie o nome da turma quatro. Vai ser margem esquerda. Um tamanho vai ser excesso. E, em seguida, ao lado deste avatar, vamos colocar elemento Spawn se vamos exibir o nome e o nome da classe vai ser margem esquerda para e depois que lombada irá exibir quando esta mensagem foi criada. Então vamos colocar o tempo atrás. Então vamos abrir o item da sala. Vamos pegar essa importação fora tempo atrás. Vamos colocá-lo na costeleta. Vamos ligar para a mesma hora atrás e colocá-lo aqui em vez desta data. Hora que mostraremos. Apenas criado em e para o nome da classe para normal e texto preto. Vamos mantê-lo como está, mas também vamos mostrar margem esquerda para quem? Foi muito. Agora vamos dar uma olhada. Como podem ver, temos as nossas mensagens. E agora, se eu digamos, executando sua mensagem, vamos dizer oi lá. Você pode ver que ele apareceu aqui. E também é aparecido aqui dentro da última mensagem. Então agora nós realmente temos nossas mensagens sendo exibidas. E funcionará também para qualquer outra sala de bate-papo. Vamos dizer olá daqui. Agora temos uma mensagem aqui. Está bem. Perfeito. Então, este é um vamos cometer nossas mudanças. Vamos esquecer tudo. Vamos colocar, se comprometer. E as pessoas nomeiam mensagens exibidas dentro da página de bate-papo. Muito bem, vemo-nos na próxima.
127. Exibição de dados de perfil de usuário: Olá. Neste vídeo, vamos adicionar uma nova janela modelo. Então, quando clicamos no nome de usuário de alguém, podemos observar o perfil do usuário. Não vamos voltar ao código. E aqui na pasta Mensagens, vamos cumprimentar seu arquivo. Nome vegetal Informações do perfil. BT e Moto GS. Vamos criar um novo componente. E por enquanto, vamos mantê-lo vazio. Vamos abrir o item da mensagem. E aqui, em vez do elemento span onde exibimos o nome do autor, Vamos exibir perfil em para BT e Moto e para este componente porque precisamos obter
dados do usuário , precisamos exibi-lo dentro. Passaremos o perfil e passaremos. Apenas autor e tudo o resto será gerenciado de dentro do componente. A partir daqui, vamos destruir o seu perfil por enquanto e vamos definir o mercado. Então, primeiro de tudo, vamos colocar botão e este botão vai dizer nome curto fora do nosso usuário. Então vamos criar novo viável aqui que vamos nomear nome curto e ele vai apenas jogar em Lee o primeiro alcunha afastado. Então, se é um nome completo como primeiro nome segundo nome, vamos exibir apenas o primeiro nome. Então vamos colocar o nome do trabalho no perfil. Então vamos dividi-lo com espaços vazios e então vamos pegar o primeiro elemento. Agora vamos exibir apenas o primeiro nome porque ele vai ser modelo. Também precisamos de um estado mortal. Então vamos usar o nosso gancho, que é usado estado modelo. Aqui vamos receber está aberto, fechado e aberto. Muito bem, agora ao lado deste corpo e vamos servir modelo. E dentro deste modelo, vamos primeiro definir a propriedade do show que vai ser aberto e no esconderijo vai ser roupas do que dentro desta moto. Teremos uma filha mortal, Heather, como sempre. Então teremos corpo e teremos rodapé como este. Então, dentro de Heather teremos o título da porta mortal e dentro do título moral vamos
exibir o perfil do nome curto, então dentro do corpo ou talvez dentro do rodapé, fundo da exibição da
bolha que vai ser um elemento de bloco no clique Ele irá fechar nossa moto e será apenas sobre apenas para fechar este mortal do que dentro do corpo. Primeiro vamos colocar a classe Nome fora do centro de texto, então dentro de uma bolha pobre exatamente a mesma imagem de avatar que fazemos em Avatar. Um BT de sangue em que é sim, este avatar perfil. Então vamos copiá-lo e colocá-lo aqui. Agora vamos importar o perfil Avatar. E ao lado dele, vamos exibir H quatro onde vamos exibir o nome completo desse usuário. Então vamos primeiro pegá-lo. O Const. O nome vai ser retirado do perfil. E talvez vamos também pegar Avatar e vamos dizer criado em Então agora nós não precisamos Teoh a estrutura ou nós não precisamos especificar perfil aqui. Então, para esta idade, para nós vamos derramar margem conversa para adicionar alguma margem no topo. E então vamos exibir membro desde e, em seguida, vamos derramar membro desde variável que vamos criar. Então vamos pobre membro const desde e vamos colocar nova data criada em e, em seguida, vamos simplesmente chamar para cadeia dia local para ex-nossa data. Não. Então não usamos aberto. Então vamos colocá-lo para isso no clique. Ok, bom. Agora vamos abrir o item da mensagem. Parece bem. Parece bem. Agora vamos dar uma olhada. Então, como podem ver agora, temos o botão. Quando clicamos nele, podemos ver que ela parece 22. Programe nossa imagem, nome
completo, cenas de
membros e feche Perfeito. Mas eu não quero ser exibido assim. Então, vamos apenas algumas coisas. Então, tudo o resto que será passado para este componente como um prop será redirecionado para adereços de
botão. E também, vamos nos livrar desse def como um elemento de rap. Deixe que seja apenas um botão no final, para que todos os adereços sejam passados para este botão. Então vamos espalhar Bt e adereços objeto sobre este componente assim. Então, para este perfil em quatro batidas e modelo, podemos passar aparência, que vai ser link. E também podemos passar o nome da classe. Vamos adicionar estofamento. Zito Dan. Vamos adicionar margem esquerda e também texto preto. Vamos guardá-lo e vamos dar uma olhada agora. Parece bom. Se eu tenho ou eu posso ver que é algo que clicável. Se eu clicar nele, posso obter dados do usuário. Está bem, Perfeito. Então é isso. Agora vamos cometer nossas mudanças. Obter tudo, obter commits. Digamos que os dados do usuário exibidos com janela maro. Muito bem, vejo-te no próximo
128. Adição de presença em tempo real - parte 1: Olá. Neste vídeo, vamos gerenciar a presença do tempo do rial em nossa aplicação com base de fogo. É muito fácil de fazer. Vamos descobrir como podemos lidar com isso. Vamos ao Google e vamos digitar Firebase Riel Time Presence. Então podemos ir para o primeiro link construído presença e loja de fogo nuvem. E aqui já temos uma solução usando presença em banco de dados em tempo real. Então nós precisamos apenas pego ser este trecho de código e, em seguida, usá-lo em nossa aplicação. Então vamos primeiro copiar está offline e on-line para objetos de valor do banco de dados e vamos navegar para o contexto
do perfil. Este é o lugar onde vamos lidar com tudo, porque aqui podemos ter acesso à autenticação. Objeto com assinatura em tempo real. Tudo bem, então vamos colocar apesar de um bles aqui no topo, e vamos substituir Var por Constant. Agora vamos dar uma olhada. O que precisamos fazer a seguir? Precisamos adivinhar o banco de dados com informações conectadas. Então, isso é como uma maneira geral no caminho do banco de dados que podemos acessar e podemos obter
presença em tempo real fora atualmente assinado no usuário. Então vamos apenas copiá-lo. Ou talvez vamos copiar tudo isso assim, e vamos colocá-lo aqui dentro. Se objeto de autenticação, Denver executará nosso gerenciamento de presença em tempo real. Então aqui precisamos obter referência a interligados em vez de banco de dados Firebase. Vamos usar a base mais tarde que temos dentro misc. Base de fogo. Então nós temos referência para inferir conectado no valor que é convertido em uma função estreita do que nós recebemos. Snap. Claro, se instantâneo esse valor for falso. Vamos pobres e três pessoas igualdade do que o status do usuário. Referência do banco de dados Então vamos dar uma olhada. Isto é tão valioso que podemos copiar. E este é o lugar literal armazenar nosso status dentro de nosso banco de dados em tempo real. Então, o que precisamos fazer, porque vai ser uma assinatura em tempo real, precisamos também cancelar a assinatura dela no futuro. Então vamos colocá-lo aqui dentro Yousef agir como um novo viável vamos chamá-lo usuário startles banco de dados áspero. Vamos remover o banco de dados e vamos apenas colocar o status do usuário, ref. Em seguida, vamos atribuir usuários iniciantes ref para o status do banco de dados Ralf e você idéia, Vamos colocá-lo aqui no topo, assim como, e em vez de você idéia. Vamos usar o seu i d e substituí-lo pela interpolação de cordas. Então vamos ter ambos objeto dot seu i d como este, então, porque é uma assinatura. Quando somos olhados para fora. Vamos verificar se temos o status do usuário. Árbitro, se
tivermos feito isso, vamos cancelar a assinatura dele. E o mesmo que faremos para nossa função de limpeza sobre estudos de usuários de heróis. Rough off. Certo, perfeito. Agora vamos gerir esta parte. Então, vamos remover todos os comentários. Vamos remover tudo isso. E aqui vamos colocar o usuário começou a cinta. desconexão está offline para banco de dados e,
em seguida, função. Vamos converter-nos para uma função adulta. Então vamos substituí-lo pelo seu status. Ref. Sad está online para banco de dados, então é basicamente isso. Agora vamos dar uma olhada. Temos fogo. Base não está definida. Vamos dar uma olhada. Base de dados Firebase. Tudo bem. Menos base de fogo de importação do aplicativo firebase para que possamos obter acesso ao valor do servidor. Tempos temporários. Vamos guardá-lo e vamos dar uma olhada. Agora, se estivermos lá dentro, temos permissão negada. Isso é interessante. Deve ser algo com regras de segurança. Então vamos dar uma olhada onde escrevemos nossos dados. Uh huh. Exatamente. Então nós escrevemos nossos dados para cortar o status de você I d. Então vamos novamente corrigir regras de segurança para este banco de dados passado dentro. Então, temos status. Então vamos chamá-lo de “este caminho”. Faremos assim. Então aqui teremos o usuário I d. e então seremos capazes de escrever para esses lugares em Lee. Se nos desligarmos, eu seria igual a usar suas idéias tão maliciosas Copie essa lógica e colá-la aqui assim. Agora vamos guardá-lo e vamos dar uma olhada se realmente funcionou. Se eu para refrescar meu aplicativo, eu posso ver agora que eu não tenho avisos. Então vamos chamá-lo de naves P e vamos cantar os gritos com nossos dados locais como este. Agora vamos navegar de volta aos dados e vamos verificar aqui. Dentro do nosso banco de dados, temos New Path, que é estudos que eu tenho meu usuário, eu d. E então eu tenho menos mudança e fiquei online. Agora vamos dar uma olhada. Se eu sair do aplicativo, eu fiquei online, então isso é porque quando nós sair, nós não
colocamos um geológico para o nosso banco de dados, então Onley quando entramos. Deixe-me continuar com o Google e deixe-me selecionar minha conta. Está bem? Estou assinada. Você pode ver que a última alteração foi alterada. Você viu a frota baleada, certo? Então, o que está acontecendo? Que realmente funciona quando entramos, mas não quando saímos. E a coisa é porque nós definimos nossas regras de segurança dessa forma, nós podemos escrever e ler em Lee quando nós temos fora de você I d. Então, quando nós registramos nosso de nosso aplicativo quando nós sair, este objeto autor será definido como agora, Então isto será disparado. E se colocarmos nossa lógica aqui quando sairmos dessa maneira, teremos permissão esta noite porque no momento, quando tentaremos direitar-nos para o banco de dados do objeto será definido como agora. A solução aqui é apenas ir para o painel. Vamos ao Dashboard Tuggle aqui. Precisamos derramar essa lógica. Então, logo antes de sair do Mobile direto para o banco de dados. Então ainda temos acesso às nossas regras de segurança. Então ainda podemos ter acesso ao objeto autor. E só então vamos sair do nosso usuário. Então, qual lógica deve ser colocada aqui exatamente o mesmo que despejamos aqui dentro iniciadores de usuários. Refs, isto é. Ah, voando em busca de dados. Então, o que eu propus a você daqui em diante, nós vamos exportar o CONST. É um vôo para banco de dados. Então vamos copiar essa lógica. Então, logo antes de sair do nosso aplicativo, vamos colar essa lógica. Então vamos importar está offline para banco de dados. Então vamos colocar o banco de dados Dodds Ralf, então vamos colocar status que barra. Então vamos mudar as citações e pique nosso usuário atual. Eu d então nós vamos derramar set, e então nós vamos definir um vôo para o banco de dados algo como isso em Lee, então porque é uma promessa. Então, vamos fazer por aqui. Só então vamos sair do nosso usuário. Vamos alertar o nosso utilizador, e vamos fechar a nossa candidatura. E no caso de algum erro, nós também vamos notificar nosso usuário, mas melhor. E vamos dizer uma mensagem melhor. Tudo bem, agora, vamos realmente dar uma olhada. Então deixe-me atualizar o aplicativo só por precaução. Vamos dar uma olhada no banco de dados. Agora temos o status online, e se eu sair, estou desconectado. E agora fiquei fora da linha. Então, muito legal agora se eu assinar novamente, eu estou conectado e status foi alterado. E agora, se eu fechar meu aplicativo, se eu fechar minha guia, eu posso ver o estado é um vôo, então ele realmente funciona. E é isso. Então é assim que ele pode ser tratado com o aumento de fogo. Foi bem fácil, certo? A única coisa aqui que eu quero fazer é que eu quero realmente cancelar a inscrição também de referenciado ou info dot connect quando estamos assinados fora. Então vamos sair quando estivermos assinados o nosso e também vamos colocar o mesmo para a
função de limpeza só por precaução. Então, desta
forma, lidamos com todas as assinaturas em tempo real e tudo funciona bem. Bem, isso é tudo para este vídeo. Então, vamos nos comprometer. Nossa mudança vai adicionar tudo ao estado do palco. E então eu vou cometer tudo com mensagem. Eu vou dizer uma presença de tempo riel, ouvinte para um usuário. Perfeito. No próximo vídeo, vamos exibir uma presença em tempo real para os usuários dentro da janela de bate-papo. Vejo você lá
129. Adição de presença em tempo real - Parte 2: Ei aí. Neste vídeo, vamos exibir presença em tempo real para cada usuário que vemos no chat. Ele será exibido como um dar na frente do usuário Avatar. Vamos antes de começarmos com isso. Quero salientar que no vídeo anterior,
quando conseguimos a presença em tempo real para cada usuário aqui, fizemos essa comparação. Se o valor do instantâneo de igualdade tripla for igual a falso, então isso não é completamente correto porque esse valor pode não ser um boliche. Então, para evitar isso, vamos colocar negação dupla para convertê-lo em uma linha de boliche. E agora tudo ficará bem. Tudo bem, agora vamos começar. Então, o que precisamos para ir primeiro? Vamos criar um gancho personalizado que nos dará a presença de usuários particulares. Então, vamos navegar para ganchos personalizados. E aqui na parte inferior, vamos exportar e você funciona, que vai ser usar presença. E este gancho receberá o usuário I D. que queremos tirar a presença. Então vamos criar nosso estado para a presença. Vamos nomeá-lo presença e dito presença. Ele vai ser estado de uso simples, que por padrão, será dito para saber. Então dentro de você o fato de que vamos extrair nossos dados de usuário. Então primeiro precisamos obter referência. Então vamos grande gráfico de status do usuário const ia ser banco de dados de firebase dot treff seguida, começou um status ruim cortar seu I d que temos como um argumento, então precisamos derramar uma matriz de dependências do que precisamos passar o seu i d dentro. Então nós vamos pobre status de usuário Rough Dar no valor. Então vamos encurtar, e logo depois disso, vamos verificar se o instantâneo existe. Então, se houver algum registro dentro do banco de dados para este caminho, então vamos derramar dados const igual valor de ponto instantâneo. E então vamos definir presença para dados, tudo bem. E dentro da função de limpeza, vamos cancelar a inscrição do status do usuário Raft, início
do usuário. É áspero. E a partir deste gancho, vamos voltar a presença, certo? Perfeito. Parece bom. Agora, vamos criar um componente que será um ponto onde vamos exibir a presença do usuário. Então vamos para os componentes. E aqui menos grande. Você arquiva a presença de nome vegetal pontuando os Gs então dentro deste componente vamos chamar nosso cozinheiro personalizado, que é usar presença. Então vamos má presença const é igual a presença de uso. E nós vamos passar o seu I d. que vai receber como um adereço para este componente como este. Então, dentro da marcação, vamos colocar a próxima, vamos abrir a documentação do traje. Então vamos procurar a dica da ferramenta. Vamos abri-lo. Vamos encontrar um exemplo de acionar eventos pairando. Então precisamos exatamente dessa funcionalidade. Vamos para exemplos e vamos copiar esse. Então, dentro do nosso tribunal, vamos colocá-lo assim. Vamos importar sussurro do nosso vidente e em vez de botão, vamos exibir um lote e dica de ferramenta não vai ser esta dica de ferramenta. Vai ser este componente. Vamos copiá-lo e vamos baseá-lo assim. Agora precisamos também importar a ponta da ferramenta e dentro da ponta da ferramenta. Não vamos colocar nada. Por enquanto, no entanto, ele diz que o componente vazio nós mesmos fechando e você está bem dentro. Nós vamos colocar distintivo também do nosso terno e dentro do lote Bem, na verdade não colocar nada. Será apenas um dardo de alguma cor. Então agora precisamos obter o que vamos colocar dentro da ponta da ferramenta. E o que vamos colocar dentro do lote que cor irá exibir? Bem, nós realmente precisamos executar alguma lógica, e o melhor lugar para lidar com isso é realmente criar uma função personalizada que vamos chamar a partir daqui. Então, para este distintivo, vamos mostrar o nome da classe fora do carro, senhor. Apontar ela e cor de fundo estilo vai ser obter cor que vamos criar em um momento e dentro vamos passar presença como esta e para dica de ferramenta para o nosso texto. Vamos passar, receber mensagem. E também vamos chamar isso de presença como esta. Então agora precisamos criar essas duas funções, então vamos navegar aqui até o topo. E primeiro, vamos criar “get color”. Vamos receber presença. E primeiro, se a presença é indefinida ou se é agora. Então, se não estiver definido, então vamos retornar uma ótima cor, certo? Então vamos colocar declaração switch e então vamos alternar entre Dar presença. Vamos abrir o nosso estado de ponto de presença de banco de dados. Então, se tivermos caso online, então vamos retornar cor verde. Se tivermos caso fora de mentir, então vamos exibir cor rad e, por padrão, vamos exibir também grande como este. Então, para cor, nós já agora vamos criar isso para texto. Então vamos definir obter texto com presença também. E, novamente, verificamos sem valor. Então, se não temos presença, então não vamos mostrar em nenhum estado. Então vamos voltar a presença dos Estados Unidos. Se for igual a dois online, então vamos voltar online. Caso contrário, vamos retornar a luxúria on-line do que vamos abrir interpolação de cordas do que colocar nova presença de data. A luxúria mudou. Dois encontros locais bebem assim. Está bem, Perfeito. Agora vamos realmente usar este componente. Vamos navegar até o item da mensagem. E logo antes de exibir perfil Avatar, vamos usar presença não. E vamos passar-lhe idee como autor ponto seu I d. Agora vamos dar uma olhada. E, na verdade, se o meu aplicativo agora está na frente do meu perfil, eu posso ver ponto verde e se eu passar o mouse, eu posso ver online. Então, como podemos agora testar contra vários usuários? Bem, deixe-me sair e me deixar olhar com o Facebook para que ele vai criar eu e seu perfil de usuário e nós vamos vê-lo Então agora você pode ver o papai. É estado desconhecido E isso é porque, como você se lembra, no vídeo anterior, nós definimos regras de segurança para status barra usuário I d. que
possamos ler Onley nosso usuário atual. Eu d igual a dois usuários I d que estamos tentando acessar dentro de oito sempre. Então agora temos permissão esta noite. Bem, para consertar isso para certo, vamos mantê-lo como está. Mas para os Regionais, vamos nos ajustar e diremos, se não for igual neve em Lee, então seremos capazes de ler os dados dos usuários. OK, agora vamos copiá-lo e sincronizá-lo com nossos dados locais. Vamos dizer onde e agora vamos dar uma olhada. Se eu atualizar meu aplicativo agora, ele ficará bem. E se eu pairar eu posso ver o último on-line nesta data para que ele realmente funciona. E se eu disser olá, posso ver que atualmente estou online e outro usuário está offline. Então é isso e funciona muito bem. Vamos cometer nossas mudanças. Vamos derramar, pegar em tudo terra, nos comprometer e vamos servir esta peça para presença em tempo real, para um fato. Vejo-te no próximo
130. Adição de gaveta: Olá. Neste vídeo, vamos adicionar Drover para chat para cima onde podemos adicionar informações de sala, como quarto, nome e descrição. Vamos lá. Não vamos voltar ao código e vamos encontrar a nossa pasta principal. E aqui dentro do índice de togs foi apenas abri-lo ao lado daquele arquivo. Vamos criar qualquer um que vamos nomear Editar quarto BTM Drover Inside vamos colocar o próximo mercado. Então, primeiro de tudo, vamos usar elemento botão e dentro vamos colocar apenas uma carta que significa admin. Em seguida, o nome da classe vai ser fronteira rádios círculo do que o tamanho vai ser pequena cor vermelha e no clique. Vamos colocar um manipulador aberto que as pessoas pegam de usar o modelo State Hook que usamos
muitas vezes. Quanto a agora, então vamos largar está aberto, aberto e fechado. Agora precisamos criar a janela moral. Então vamos saudar de Drover. Vamos importar de RC ou assim dentro deste rover, nós vamos derramar propriedade show que vai ser é aberto do que on. Hyde vai ser roupas e colocação vai ser certo e o mesmo que para modelos. Drover tem Drover Header corpo e por isso vamos criar esses componentes. Dentro do rodapé vamos derramar outro botão que será apenas para fechar o Drover para que seja um bloco elementos e no clique vamos fechar nosso Drover dentro Heather, vamos derramar, dirigiu ou título e para Drover título, Nós vamos despejar a Sala de Edição Tudo agora, na verdade, para Drover Body antes de defini-lo. Vamos realmente usar este componente dentro dos componentes superiores. Então vamos abrir engrenagens de índice dentro da pasta superior e aqui dentro. Mas na barra de ferramentas Vamos usar no quarto VT e Drover, é
isso. Agora dentro do nosso corpo iria definir para importar elementos um para o nome do quarto e 14 quarto descrição e nós vamos usar nossa entrada edita ble que usamos anteriormente. Então vamos abrir este componente e então vamos ser importantes. Então, para a entrada de Ed Izabal, precisamos passar o valor inicial. Então vamos pegar essa do contexto atual da sala. Então aqui no topo da placa Blacks, nome é igual a usar sala atual e vamos selecionar o nome do ponto de valor e o mesmo que faremos para descrição. Então vamos pegá-lo. E também, vamos enrolar este componente, mamífero. Então deixe-me colocar um memorando aqui e deixe-me importá-lo assim. Tudo bem? Agora precisamos realmente definir nossos componentes. Então, para editar importação Herbal para a primeira entrada, que vai ser sobre o nome, vamos passar o nome do valor inicial do que devemos fornecer na função segura e deixá-lo ser no nome seguro. Quanto a agora, então vamos colocar rótulo e rótulo vai ser Ahh, seis elementos com classe. Nome fora da margem, dois de
baixo. Então vai ser o nome. E também mensagem vazia vai ser chamado Pode ser vazio. Tudo bem. O segundo em pobres vai ser uma área de texto no porto. Então vamos pacificar a classe competente. Ele vai ser a área de texto subiu por padrão será cinco. Então nós vamos derramar também valor inicial como descrição do que nós vamos colocar inseguro, que vai ser na descrição segura e também mensagem vazia vai ser descrição não pode ser vazio. Tudo bem, agora, vamos salvar e definir essas funções. Então, primeiro de tudo, vamos criar no nome seguro, e então criaremos a própria descrição segura. E como nossa funcionalidade é muito semelhante, vamos criar uma função comum que será chamada dentro de cada uma dessas funções. Então, ele vai ser, digamos, atualizar dados de dados de dia, e ele vai receber chave. Ou digamos campo o que precisamos atualizar e também o valor real que será triste para esta chave. Muito bem, agora, dentro do próprio nome Save. Vamos chamar dados de atualização com o nome como uma chave e também novo nome, que vai ser passado como um argumento para esta função porque passamos este manipulador para entrada credível. E como você se lembra, se abrirmos,
ele nos dará o valor final. Tudo bem, então o mesmo que faremos na descrição segura aqui, vamos colocar a descrição e o novo. Digamos que a mesa vai ser nova mesa. Então, dentro dos dados, vamos chamar objeto de banco de dados. Então nós vamos especificar referência aos quartos barra sala I D ou chat i d. Então vamos pegar aquele de usar Haram. Então vamos pegar share i d de programas de uso. Vamos má importação para o topo. E, em seguida, para esta referência, vamos especificar criança vai ser conjunto de chaves vai ser valor. Depois disso. Quando terminarmos com a gravação de dados no banco de dados, vamos chamar alerta, e vamos especificar sucesso atualizado com sucesso e vamos colocá-lo por quatro segundos. E no caso de termos algum erro, vamos também disse alerta, mas desta vez melhor. E vamos colocar a nossa mensagem assim. Tudo bem, parece bom. Vamos apagar este espaço vazio. Vamos economizar e vamos dar uma olhada. Agora temos este botão A no topo, à direita. Vamos clicar nele. Temos Drover, e o primeiro problema. Eu posso ver que não temos nenhuma margem aqui, então se nós
inspecionamos, podemos ver que se abrirmos o grupo de importação e temos que fazer, Dave está aqui e eles basicamente não têm nenhuma margem. Então vamos abrir nossa importação credível. Então precisamos derramar algum espaço para esta definição, ou pode ser uma opção. Então, o que eu propus a fazer, podemos passar outro argumento para entrada credível, que vai ser o nome da classe ladrão e, por padrão, ele estará vazio. Então vamos passar esse nome de classe rapper para o nome da classe do ladrão e o que vamos fazer, vai dizer com uma maldita navegação, você é uma entrada credível. E para a área de texto começou um nome de fechamento rapper especificar vai ser margem superior três para adicionar algum espaço em cima disso, vamos dar uma olhada. Agora eu posso ver que parece bom. Agora vamos realmente editar alguns dados. Pode ser o novo nome de Roma. E se eu disser onde posso ver bem sucedido, atualizado e nome do quarto foi atualizado. De fato. Ok, frio. Mas há um problema para nós. Lembre-se, com ladrões, eles não são exatamente responsivos. Então, o que precisamos fazer? Precisamos passar toda a propriedade para este robur quando estamos em dispositivos móveis. Então vamos usar o gancho de consulta de mídia aqui no topo. Vamos especificar que o celular dele vai ser usado. Consulta de mídia. E aqui nós vamos especificar marcas com off 99 2 pixels. Então vamos passar. Isso é mais bile para a propriedade completa e será ativado somente quando estivermos em
dispositivos móveis . Então, agora, se abrirmos e precisarmos da janela
, ainda ficará bem. Ok, então é isso, eu acho. Agora vamos cometer nossas mudanças. Deixe as pessoas tudo para o palco. Estado é sempre e, em seguida, ficar comprometido. Adicionada sala de edição. Drover. Tudo bem. No próximo vídeo, adicionaremos mais segurança à nossa sala porque, como você pode ver, por enquanto, podemos adicioná-lo. Esta sala, mesmo que não estamos admite porque não temos nenhuma permissão de usuário. Então este é o nosso tópico para o próximo vídeo. Vejo você lá.
131. Regras baseadas de acesso e segurança baseados em confiança: Ei aí. Neste vídeo, as pessoas gerenciam nossa segurança baseada em funções em preenchimentos específicos. Quando tentamos adicioná-lo. Informação do quarto, vamos. Então, primeiro lugar, como vamos definir nossos papéis. Se abrirmos nossa estrutura dentro dos quartos, podemos ver que criamos na descrição, última mensagem e nome. Então aqui vamos também adicionar outra propriedade, que vai ser admite. E com base de dados em tempo real, podemos prejudicar uma raça ou podemos. Mas eles são realmente mal gerenciados porque fora de seu pobre sistema de construtor de consultas, porque fora de suas consultas pobres em banco de dados em tempo real, vamos colocar nossos Edmonds como um array fora de ID de usuário. Então, se o usuário pertence a esta matriz, isso significa que o usuário é um administrador e não irá colocá-lo como uma matriz. Nós vamos criar um objeto dentro do nosso banco de dados, e cada chave vai ser usuário i d. E se este usuário é um administrador, então ele será definido como verdadeiro conselho. Este usuário não estará dentro do banco de dados. Certo,
então, primeiro de tudo, o que precisamos fazer, precisamos adicionar um usuário aos nossos dados. Vamos para, digamos novo nome do quarto. Ou talvez vamos mudar o nome para algo mais específico. Vamos dizer legal, vamos salvá-lo. E agora vamos navegar através desta base de dados aqui. Vamos adicionar novo campo que vamos criar admissões do que vamos clicar no sinal mais aqui. Então precisamos colocar o nosso usuário I d O que podemos fazer, podemos ir para o contexto do perfil. E então quando saímos do objeto, vamos Cônsul Acusador i d para obter o nosso usuário i d. Então agora eu posso me pegar pelo usuário I d e colocá-lo dentro do banco de dados e, em seguida, sat value to true e, em seguida, editar para os dados da sala Então parece assim. Agora, para restringir o acesso, precisamos definir regras de segurança, então vamos navegar para regras. E aqui vamos fazer a próxima coisa para o nosso caminho quartos. Nós vamos remover a propriedade certa para que ele será pego a partir daqui para que ninguém pode realmente direito dois quartos caminho, mas eles são capazes de ler quartos do que para o quarto I d. Em vez disso, off escrevê-lo assim. Não podemos recriar a regra, mas também para a última propriedade de mensagem, que é assim. Nós nos deixamos pacificar, certo? Regra disse para fora não é igual a Não, deixe-me para lama assim. Isto é devido a, se você se lembrar, quando atualizamos dados em vários lugares, também
atualizamos a última mensagem dentro da nossa sala. Então, basicamente, todos os que escrevem para o chat podem atualizar a última mensagem dentro da sala, mas não outros campos como quarto, nome e descrição. Aqui vamos definir modelos para exatamente aqueles sente assim para idee sala, somos capazes de escrever dados primeiro quando os dados não existem. Quando tentamos criar e você quarto, vamos especificar se os dados. Então, esses dados são novamente um objeto global dentro das regras de segurança e representam os
dados atuais que estamos tentando acessar. Então, se os dados existem por isso é um bowline foram capazes de escrever para estes passado quando os dados não existem. Tudo bem,
Então, quando estamos tentando criar uma nova sala com a sala específica I d, ou se somos um administrador, só então seremos capazes de escrever e editar esta informação. Então, como podemos fazer isso? Então sabemos que armazenamos em adicionar homens, então temos usuário I d e verdadeiro. Com base de dados com regras de segurança, funciona assim. Abri documentação para dados em tempo real, basicamente rituais. E aqui eu confinei essa informação. Se eu rolar um pouco para baixo, eu posso encontrar esta informação que eu posso acessar alguns preenchido usando esta abordagem. Então eu vou usar exatamente o mesmo padrão e o que eu vou fazer. Vou perguntar se os dados que estamos tentando acessar têm admissão de crianças. Então, dentro disso, em Mons Child, temos outro filho que será nosso usuário. E podemos obtê-lo de ambos os objetos. Então vamos perguntar se a criança fora do ponto seu valor i d ponto é igual a dois. Verdadeiro. Então, se tivermos um registro para o nosso usuário dentro Edmunds preenchido, então seremos capazes de escrever para esse caminho. Agora, vamos guardá-lo e vamos dar uma olhada. Agora, se eu sou um administrador deste grupo frio, eu vou clicar nisso. Poderei editá-lo porque editamos nosso usuário I d para o banco de dados. Digamos que algo aleatório agora atualizá-lo com sucesso. OK, agora vamos para outra sala quando não somos administradores, deixe-me tentar editá-la. Olá mundo. Agora, se eu tentar saborear, vou conseguir permissão esta noite, então nossas regras de segurança funcionam e isso é muito legal. E por causa disso agora restringimos o acesso ao nosso banco de dados. Mas também precisamos gerenciá-lo programaticamente precisamos adicionar homens etc. Então vamos também fazer isso. Então vamos navegar para criar quarto, modelo de mão de
praia. E aqui a água servirá. Quando vamos criar uma nova sala, vamos adicionar a nós mesmos para adicionar homens. Então aqui, quando definimos em seus, um, dados, nós também adicionaremos um novo objeto adicionado feijão. E nós vamos nos especificar. Vamos importar em primeiro lugar. Sim, ele foi importado do usuário atual, seu I d está definido como true. Agora, sempre que adicionamos em seu quarto, nos
definimos como administradores. Depois, quando lemos os dados da sala, precisamos saber quem são exatamente de Adnan. Então vamos navegar para Chatel gs e aqui para uma sala atual. Vamos fazer a próxima coisa porque é um objeto e precisamos trabalhar com I raise Idealmente, quando trabalhamos dentro do nosso código, precisamos transformar este objeto em uma matriz. Então vamos criar aqui. Novos e valiosos anúncios e ajudantes internos. Vamos definir uma nova função que irá transformar nosso objeto em apenas uma matriz. Então vamos nomeá-lo exatamente da mesma maneira que fizemos com esta função. Mas nós vamos dizer, basta transformar em array aqui. Vamos receber valor instantâneo novamente e deixe-me definir teclado função, e esta função será muito simples. Então, se Snapshot 12 existir, então vamos retornar chaves de objeto fora deste valor de snapshot para que vamos obter uma matriz fora ID de
usuário. Caso contrário, comece um retorno e esvazie Agora vamos dizer que este ajudantes e vamos usá-lo dentro. Chatterjee está aqui. Vamos nos transformar em matriz. Digamos que a porta atual da sala Adnan e agora temos a administração. Mas também queremos saber se estamos atualmente conectados usuário é um administrador. Então o que? Nós viemos até você. Podemos criar um novo valioso é administrador e vamos simplesmente perguntar se admissões inclui fora que o usuário atual ponto seu i d e como podemos passá-lo esses dados junto com o contexto. Então vamos passar, admite e é admin. A partir de agora, seremos capazes de exibir este drover Onley quando formos admitidos. Então agora vamos navegar Teoh nossa parte superior. Vamos navegar para indexar togs dentro da pasta superior e ouvir do contexto. Vamos pegar seu administrador usar o valor atual da sala. Valor é administrador assim. E agora vamos perguntar se somos um administrador Onley, então vamos exibir em seu quarto Bt e Drover. Agora vamos dar uma olhada dentro desta primeira sala onde somos o administrador. Podemos ver esse Drover, e somos capazes de adicioná-lo. Informações do quarto atualizadas com sucesso. Mas na sala onde não estamos admite, não
seremos capazes de ver este Drover. E também não seremos capazes de atualizá-lo porque dissemos regras de segurança. Vamos copiar as regras de segurança. E vamos sincronizá-los com os locais de
guerra. Vamos abrir regras de base de dados e colá-las aqui. Tudo bem. Parece bom. Que haja mais uma coisa nas nossas regras de segurança. Se inspecionarmos nosso conselho, podemos ver que temos essa base de fogo avisando que seus dados estarão diminuindo e filtrando em declínio. Considere terminar o índice na ideia da sala nas mensagens. Então vamos fazer isso. Isso é para tornar nossas consultas ainda mais desempenho. Então, vamos navegar para regras. E, vejamos, considere adicionar índice na sala I d. em mensagens. Vamos copiar isto. E essa mensagem é Vamos adicioná-la aqui assim. Agora vamos saborear e dar uma olhada se ainda podemos ter esse aviso, ok? Neste momento, o nosso conselho está claro. Não vejo nenhum aviso. Vamos novamente copiar nossas regras e colá-las. Teoh, nossas regras de banco de dados, Jason assim. Ok, então este é o fim para este vídeo. É assim que vamos gerir a nossa segurança. Agora vamos cometer nossas mudanças. Vamos em tudo para o estado do palco. E, em seguida, vamos confirmar alterações com as regras de segurança de atualização para permissão baseada em função. E isso é tudo. Muito bem, vejo-te no próximo.
132. Gestão de acesso baseado em função: Ei aí. Neste vídeo, vamos adicionar botão, a fim de ser capaz de gerenciar a permissão baseada em função. Então, quando clicamos no perfil de usuário de alguém, se estamos atualmente e
estivemos fora deste grupo, somos capazes de criar este usuário e tinha sido para Não vamos voltar ao código. E vamos abrir, eu acho. Item da mensagem. Então aqui vamos fazer uma pequena modificação para informações de perfil, BT e modelo. Então vamos abri-lo. E aqui queremos exibir este botão aqui na parte inferior. Como podemos fazer isso? Bem, na
verdade é fácil. Podemos passar algumas Crianças para este componente e elas serão exibidas aqui. Então aqui no perfil lateral em quatro bilhões modelo, nós também vamos d estruturar Crianças e, em seguida, essas crianças que vamos exibir no rodapé logo antes do nosso botão de fechar. Agora vamos salvá-lo. Não vamos envolver um item de mensagem. E aqui para perfil em para Betty Anne Morrow, vamos passar outro fundo para que este fundo será um elemento de bloco, e no clique vai ser algo que vai definir em alguns segundos. Além
disso, ele terá cor azul e texto vai ser o próximo. Então, antes de tudo, precisamos definir quando este botão será exibido. Talvez, vamos comentar. E aqui vamos criar algumas maçãs podres e vamos primeiro movê-lo para a conversa assim. Certo, primeiro precisamos definir se podemos conceder permissão ao administrador. Então, para isso, precisamos obter nossos dados contatados. Então vamos começar é admin de usar sala atual. Deixe-me abrir o carro no contexto da sala, em
seguida, deixe-me importar o gancho e do valor Begin um pico é admin. E também precisamos de outras admissões também. Então use o valor atual da sala. O valor admite assim. Em seguida, vamos envolver o nosso item de mensagem em torno de memorando, porque usamos o seletor de contexto e aqui vamos fazer o próximo. Primeiro precisamos saber se o autor da mensagem é um administrador. Então vamos criar o administrador do autor da mensagem e vamos perguntar Edmunds Inclui autor, porta do
autor você eu d. Então precisamos saber se somos o autor da mensagem para que possamos criar seu autor de comestível e podemos perguntar-nos atual. Vamos importar fora do usuário atual ponto seu eu d igual autor indoor você eu d como este. E então podemos criar outro comestível que nomeará, digamos, pode conceder acesso ou pode conceder admin. E somos capazes de conceder permissão de administrador se formos adicionar Mons nós mesmos. E também, se não somos autores de mensagens então agora podemos usar todos esses objetos de valor para exibir nosso botão condicionalmente. Então, primeiro, vamos ficar pobres. Se pudermos conceder admin apenas feito, vamos exibir esta parte inferior e também para a mensagem Nós vamos colocar sua mensagem, administrador
autor. Então vamos dizer “remover permissão de administrador”. Caso contrário, vamos dizer, dê ao administrador nesta sala algo assim. Ok, agora, na verdade, vamos ver o que fizemos. Deixe-me refrescar. Apenas no caso de eu abrir este perfil, Eu posso ver dar administrador nesta sala. Então, quando eu clico, nada acontece porque nós não definimos nenhuma funcionalidade. Então, vamos navegar aqui e toda a funcionalidade que vamos derramar dentro de mensagens componente, e então vamos passar essa funcionalidade para o item de mensagem. Ok, então para o item de mensagem aqui, vamos ter digamos lidar com a função admin que vamos passar que vamos ter. E para este administrador identificador. Vamos passar. Vamos dizer, autor ponto seu I d. Tudo bem, agora nós precisamos obter este identificador admin de adereços e vamos navegar para mensagens. E aqui vamos definir administrador identificador constante, e vamos otimizá-lo com antecedência com uso de chamada de volta porque nós passá-lo para baixo para
elemento filho . OK, então este administrador identificador receberá o seu i d. E, em seguida, vamos primeiro definir o nosso Edmunds ref dentro do banco de dados para que possamos um
objeto de banco de dados chamada . Então referência vai ser quartos do que vai ser Chat I d. Que já temos de usar perms e, em seguida, cortar avanço. Tudo bem, agora precisamos adicionar idéias de bate-papo e ouvir o que precisamos fazer. Precisamos realmente obter o nosso valor anterior, a fim de ativá-lo. Então, se clicarmos neste botão e queremos conceder a permissão, então ele será nele. Caso contrário, se esse usuário já tiver a permissão, queremos revogá-la. Então, na verdade, para fazê-lo com base de dados em tempo real, se
abrirmos sua documentação, podemos ver esta seção sob leitura de dados direita salvar seções Estrin dados. Então, usando desta forma, somos capazes de obter acesso ao valor anterior e podemos atualizá-lo. E o mais importante, é transação. Isso significa que os dados não serão corrompidos. Então vamos realmente usar exatamente a mesma abordagem. Então deixe-me copiar tudo isso e o que eu vou dio eu vou chamar de esperar o que é converter esta função de corrida
problema. Vamos chamar evade adicionar transação Ralf Dar masculina. Então nós recebemos nosso valor atual ou anterior, que vai ser admissão e ouvir o que vamos colocar. Vou colar o mesmo código que cooperei e aqui vou perguntar se as admissões existem . Só então executarei minha lógica. Então, se admite existir, então eu quero perguntar se admite, você eu existiria. Então quero revogar o acesso. Então eu vou definir admite que você eu iria saber. E quando definimos valor para saber para banco de dados em tempo real, ele será excluído do banco de dados porque você realmente pode armazenar nenhum valor lá. Agora, se não tivermos permissão, vamos grunhir. Então avance seu i d será definido como True. Agora vamos remover o resto do código. E no final, vamos devolver as admissões, e vai fazer a sua coisa. Certo? Chamada. Agora, precisamos notificar o usuário se revogamos ou concedemos o acesso. Então vamos colocar a porta de alerta e o que deve reportar aqui? Como podemos especificar se revogamos ou concedemos acesso a isso? Podemos criar disponível aqui que vamos renunciar. Digamos que mensagem de alerta. Então, quando
revogarmos o acesso, vamos pôr alerta. Mensagem para o administrador. Permissão removida. E para ser verdade, comece uma mensagem de Miller especificada. Permissão de administração concedida, algo assim. Então vamos passar essa mensagem de alerta para informações de alerta, e eu precisamos passar esse administrador para o item da mensagem. Então, vamos lidar com o administrador. Manuseie o administrador Agora, vamos dar uma olhada. Vamos navegar de volta para o nosso aplicativo. Se eu clicar neste usuário, dar admin nesta sala. Permissão de administrador concedida. Agora tenho permissão para remover administrador. Se eu clicar nele, posso ver a permissão de administrador removida. Vamos navegar no nosso banco de dados. Vamos encontrar este quarto, que é espaço para aquele quarto. Agora. Se eu conceder acesso, você pode ver um novo valor dentro do banco de dados. E se eu remover o acesso, posso ver que ele foi removido do banco de dados. Tudo bem, acho que é tudo sobre segurança e gerenciamento baseado em funções. Vamos realmente confirmar nossas mudanças e terminar este vídeo. Mas antes de fazermos isso, vamos mover essa importação para o topo, e então vamos confirmar as alterações. Então pegue tudo, então se comprometa e vamos dizer botão adicionado para conceder ou revogar o acesso de administrador. Tudo bem, Perfeito. Vejo você na próxima.
133. Adição de uso programático com anzóis: Olá. Neste vídeo, vamos adicionar gramaticais práticos aos elementos do gráfico, e ele servirá como base para os próximos vídeos. Vamos começar. Nossa gramatical, no entanto, será gerenciada por um gancho personalizado, e nós confinamos esse gancho na Internet. Então vamos abrir o Google e vamos apenas digitar usar ganchos e, em seguida, usar o mouse. Então vamos abrir o primeiro link que permite obter o snippet de código e vamos copiar este gancho. Vou copiar toda essa função. Então eu vou voltar ao código do que dentro de ganchos personalizados no final. Vou mudar esta função, e vou exportá-la daqui. E também preciso usar rascunho para isso. Então deixe-me importar. E como posso ver, tenho essa dependência desnecessária. Mas isso não é exatamente verdade. Então vamos adicionar Sim, Lind, aviso para esta linha. E também vamos modificar este gancho um pouco em vez disso fora condicionalmente retornando a função de
limpeza. Vamos levar esse retorno até o fim. Tudo bem, agora estamos prontos com o gancho. Vamos navegar para o item da mensagem e aqui vamos usar esse gancho. Então, no topo. Nós vamos criar um novo valioso, e nós vamos chamar de uso, no entanto, Gancho. Então este usa Howard Hook. Ele nos retorna uma matriz fora exatamente dois elementos onde primeiro elemento é a referência que precisamos atribuir ao elemento. Então vamos nomear-se referência e, em seguida, na verdade, o marcador valorizado que indica se este elemento está atualmente pairado ou não. Então vamos chamá-lo de auto ref e vamos passá-lo para este elemento L I. Então a referência vai ser auto ref. Agora nós podemos realmente usar este valor de barras e podemos fazer algo, mas assim por agora o que eu proponho fazer, eu só quero Teoh mudar a cor de fundo sempre que estamos pairados. Então vamos agrupamento dinâmico pobre para este elemento aliado. Então vamos roubar este psiquiatra entre parênteses e vamos usar a exaltação Rincon. E primeiro eu vou adicionar carros são um ponteiro para este elemento aliado. Então sabemos que sempre que pairarmos, algo vai acontecer. E depois vou perguntar se o nosso aliado é o Howard, deixa-me mudar para Harvard. Então eu vou mostrar o fundo preto de 0,2% cada. Caso contrário, nenhum nome de classe. Agora, se eu voltar para o código, eu posso ver que sempre que eu, no entanto, eu posso obter meu passado. Então é isso. E esse é o fim deste vídeo. Vamos cometer nossas mudanças. Vamos colocar tudo no palco ficou. Então vamos nos comprometer com o pairar gramatical pro de edição. Muito bem, vemo-nos na próxima.
134. Criando o IconControl: Likes (parte 1): Olá nestes dois vídeos vamos lidar com gostos em nossa aplicação. Neste vídeo, vamos criar um componente que vai ser um wrapper em torno de controle. Eu venho que vamos adicionar ao item da mensagem. Vamos, vamos voltar ao código e vamos primeiro definir como vamos usar este componente. Então vamos abrir a mensagem I, Tim, e vamos colocá-la logo depois de um tempo atrás. Então aqui vai ter um componente, algo como eu posso VT e controlar. E então este componente Bem, exceto nos próximos adereços. Então primeiro vamos definir se vai ser visível ou não. Por enquanto, que seja visível. Então vamos colocar eu posso nomear e por enquanto, que
seja difícil para os nossos gostos. Então também, teremos dica de ferramenta que dirá algo como esta mensagem. Além
disso, ele terá um manipulador no manipulador clique. Então, por enquanto, que
seja uma função vazia e também terá dois adereços condicionais. Então primeiro vai ser cor e depois vai ser conteúdo de bancada. Eventualmente ele terá que Aikens fechar Aiken e, como eu conferir como eu posso queremos exibir inclinado com conteúdo. Então é por isso que vamos colocar o conteúdo em lote como um problema adicional. E por enquanto, digamos que terá cinco gostos de algo assim. Tudo bem. Agora vamos realmente criar este componente e vamos ver como ele vai ficar assim aqui Sob mensagens, Vamos criar Aiken, VT. E Controle. E vamos definir como será antes de fazermos qualquer marcação. Vamos primeiro pegar os adereços assim que temos é visível. Então também temos eu posso citar. Temos dica ferramenta que temos no Click, e temos maneira conteúdo crachá. Outros adereços que armazenaremos sob adereços. Objeto. Ok, então ele vai ser um diff com classe Nome da margem esquerda para digamos que estilo vai
ser o próximo. Então vamos colocar o suporte de visibilidade, e ele vai ser visível em Lee quando é visível, definido como verdadeiro. Então, se é visível, então visível, caso contrário oculto. Está
bem, está bem dentro desta definição. Precisamos derramar. Digamos que um conteúdo de lote condicional um componente condicional, e aqui está um pequeno truque. Como você pode fazer isso. Não é realmente um primitivo ou óbvio. Digamos que se aproxime. Como criar um componente de renderização condicional fora dentro de um componente. Então é o truque. Primeiro nós derramamos aqui, e você componente, digamos crachá condicional como este, ele receberá uma propriedade, que vai ser, digamos, condição onde um valor que nós queria exibir. Então aqui nós vamos derramar distintivo condicional e como um adereço, nós vamos passar condição e esta condição vai ser o nosso conteúdo do crachá. E aqui vamos perguntar se temos uma condição, então vamos para o lote de guerra com conteúdo fora de condição, que vai ser o nosso valor real. E depois vamos rapper em Children assim. Caso contrário, devolveremos crianças. Então, sim, este é o truque. E precisamos pegar crianças de nossos adereços também. Então, será algo parecido com isso, mas posso ver que algo está errado. Então, o que está acontecendo aqui? Esqueci o suporte. Tudo bem, então é isso. Agora, se tivermos muito conteúdo, este lote condicional será processado caso contrário, temos Crianças, que é todo o conteúdo que passamos dentro. Está bem, mas lá dentro vamos passar. Esporão e sussurro é o componente do nosso fato que eles usaram para algo como ponta de ferramenta . Então, por um sussurro, vamos passar. Vamos uma costeleta de colocação. Então vamos passar o Delay. Ele também tem um atraso de zero que dilly. Hide também vai ser Zito. DemaLay show vai ser também zero gatilho vai ser gritar e alto-falante. Vamos passar a dica de ferramenta e a mensagem de dica de ferramenta. Vamos passar uma propriedade culpada como esta dentro deste sussurro ou por um gatilho, vamos mostrar ícone componente normal do nosso terno. E pelo menos Aiken, botão, vamos derramar todas as colheitas que recebemos aqui, e então teremos no manipulador de cliques e vamos passar no clique que recebemos. Então vamos colocá-lo como um tamanho de círculo vai ser muito pequeno. E também eu posso em si vai ser eu posso vamos importar. E para a ICANN, vamos colocar o ícone. Posso nomear que também recebemos como uma propriedade. Agora parece pronto dentro do item de mensagem. Podemos ver que eu conveniente não está definido. Vamos importar e vamos realmente ver como ele se parece. Então, agora, se abrirmos nosso aplicativo agora, temos gostos. No entanto, não
temos cor. Então, o que propus fazer aqui, vamos derramar uma coleira condicional. Então, quão vestível fazer isso? Já fizemos isso. Para que possamos servir algo assim. Podemos espalhar nosso objeto se nossa condição for verdadeira ou podemos espalhar um objeto vazio. Neste caso, não
passaremos qualquer propriedade. Então vamos colocar algo como se nossa condição for verdadeira, então vamos derramar a cor do vermelho. E caso contrário, vamos colocar um objeto vazio para que ele funcione, e ele vai pensar. Agora, se eu tivesse um fresco você pode ver que eu tenho cor vermelha quando a condição é verdadeira. Caso contrário, eu tenho falso. Ok, bom. Então funciona. E a propósito, se você está se perguntando para onde ele vai, ele vai aqui para esses adereços. E esses adereços serão passados para o botão Aiken. Então, basicamente, nós dissemos cor para este botão Aiken. Ok, Então é isso para este vídeo no próximo vídeo, vamos exibir os gostos e móvel na funcionalidade. Mas, por enquanto, vamos terminar este vídeo comprometendo nossas mudanças. Leva em tudo para o estado do palco e, em seguida, obter commit. Criador, eu posso VT no componente de controle como este. Está bem, Perfeito. Vejo você na próxima.
135. Funcionalidade de letras): Hey lá nesta bolha de vídeo, adicionar funcionalidade para o botão como. Vamos lá. Vamos primeiro navegar para o banco de dados e vamos ver como vamos lidar com nossa
estrutura de dados . Então, dentro de cada elemento de mensagem, vamos criar mais duas novas propriedades. First Property vai ser como Count que irá indicar o número total off curtidas
nesta mensagem particular. E então teremos,
digamos, digamos, gostos será uma matriz fora de valores com os IDs de usuário que gostaram desta mensagem. Mas em vez de armazenar e Ray iria usar um objeto da mesma maneira que fizemos com Rooms admite, vamos navegar para o aplicativo. E aqui vamos abrir o primeiro item da mensagem. Aqui vamos receber manipular como função e este manipulador como função. Vamos passá-lo para este próprio manipulador clique aqui. Nós vamos chamar este identificador como e para lidar, como se nós vamos passar mensagem ponto i d. Ok, agora vamos navegar para baixo em têxteis gs E aqui quando nós criamos e você mensagem, nós vamos anexar uma nova propriedade como count, e por padrão ele será definido como zero. Ok, agora vamos navegar para as mensagens para indexar os desonestos e aqui, vamos definir Const lidar como manipulador deixa o rapper entrar. Ele foi chamado de volta com antecedência. E agora vamos definir nossa lógica. Nós vamos passá-lo para o item de mensagem à luz de velas como, então ele vai receber mensagem I d. E a lógica realmente será o mesmo que com o administrador identificador porque nós vamos usar uma transação. Então vamos realmente pego ser tudo a partir daqui e vamos colocá-lo dentro lidar como, mas em vez de avanço,
ref, ref, nós estamos indo para mensagem pobre, ref e mensagem Ref vai ser banco de dados Ralf do que mensagens. E então, em vez de idéia de bate-papo, vamos usar mensagem I d. Ok, então precisamos também converter esta função para em uma função de pia para transação em vez de admite que vamos receber mensagem. Então nós vamos perguntar se a mensagem existe então se a mensagem ponto gosta e mensagem Dar gosta de você , eu d off nosso usuário atual. Então vamos pegá-lo de outro objeto. Vamos usar fora do usuário atual e vamos levá-lo i d. Então, se temos, como por este usuário em particular, então vamos primeiro excluir este como e também queremos diminuir o nosso como Joan. Então vamos corrigi-lo para a mensagem Dog Gosta. Então vamos diminuir,
tipo, tipo, contar por um. Então vamos garoto, meu nariz é igual a um. Uma mensagem de alerta será, como removida. Ok? Caso contrário, quando queremos derramar e você gosta, vamos colocar uma mensagem como Conan Plus é igual a um e porque podemos ter esse
objeto gosta dito,
você sabe, você sabe, ele pode ser inexistente dentro de bancos de dados comunidade também lidou com isso. E se tentarmos adicionar algo ao objeto não existen, teremos um erro. Então primeiro vamos perguntar se nenhuma mensagem gosta. Então, se não temos este objeto, então vamos inicializá-lo como um objeto vazio. Assim, os gostos de mensagens vão ser um objeto vazio. E só então seremos capazes de definir a mensagem. DOT gosta de seu i d igual a verdade. E, em seguida, a mensagem vai ser como ele. Está bem, Perfeito. Agora vamos dizer espere e vamos dar uma olhada. Se vamos tentar clicar nesta mensagem, teremos transação falhou, e isso é porque ele tenta atualizar como, count, propriedade inexistente para mensagens existentes. Então, o que eu propus fazer, eu quero povoar toda essa passagem é apenas para limpar um pouco o banco de dados. Então agora podemos colocar uma nova mensagem com as novas propriedades. Então vamos colocar uma nova mensagem. E agora ele tem cinco como o Conde e nós podemos realmente consertar isso. Mas por enquanto, se clicarmos nele e pudermos ver,
tipo, tipo, editar se formos ao banco de dados, se abrirmos nossa mensagem, podemos ver, como contagem um e gostos contém nosso usuário i d. E se clicarmos nele mais uma vez, podemos ver que gostos é diluído e, como, contar tal para Zito. Está bem, Perfeito. Agora vamos realmente corrigir o nosso você eu Não vamos esquecer de mensagem item aqui. Precisamos passar adereços, Teoh, eu posso estar no controle. Então, primeiro de tudo, quando temos cor fora de vermelho quando nossa mensagem é apreciada, certo, Então vamos pobre é luz valiosa que vai criar aqui no topo const sua vida e como
podemos definir isso. Então primeiro precisamos ver se esta mensagem tem algum tipo de gostos. Então vamos agarrar, gostos e como contar da nossa mensagem. E aqui vamos perguntar se a nossa mensagem tem gostos. Então vamos colocar as chaves de objeto fora. Estes gosta de obter matriz fora idéias do usuário e, em seguida, podemos pobres inclui, Digamos off Dar usuário atual, não é? Eu d Assim, desta forma, podemos detectar se nossa mensagem é apreciada por este usuário em particular. Certo, então vamos passar. Este é gostado de enfraquecer exibido aqui. Vamos colocá-lo dentro da condição, e então vamos colocar cor vermelha. Certo, então temos essa propriedade visível. E isso é realmente para a capacidade de resposta fora de nossas mensagens. Então, se recitarmos nossa janela, acabamos em dispositivos móveis. Então, em dispositivos móveis, não
queremos ocultar nossos ícones. Queremos exibi-los sempre. Então, para isso, podemos usar consulta de mídia para detectar isso. Então, primeiro, vamos colocá-lo aqui logo abaixo usar o mouse que vamos colocar é móvel. E então vamos usar Media Query, e vamos perguntar se temos marcas com 992 pixels. Então, se temos é móvel, vamos realmente criar novo viável. Que vamos dizer pode mostrar de Aiken Então, se temos é móvel ou se o nosso elemento atual é pairado para que vamos vê-los Somente quando temos ela na mensagem Só então podemos exibir Aikens assim para é visível Nós vamos puxar pode mostrar que eu vem para no clique Nós E para o conteúdo do banco em vez de cinco vamos colocar nossa corrente como contagem Ok, bom. Agora vamos dar uma olhada Se temos onde podemos ver, temos ícone Se redimensionarmos a janela E se estamos em dispositivos móveis foram capazes de ver o Eiken. Está bem, Perfeito. Agora, se eu clicar sobre esta mensagem como, eu posso ver como contagem e, bem, ele está sendo exibido na cor off vermelho. É isto. E parece bem legal. Algum tamanho de fogo de novo? De volta à minha bílis. Posso vê-lo sempre. É isto. E acho que vamos cometer nossas mudanças. Deixe-me abrir minha pista terminal Poor obter em tudo o que poderia cometer mensagem Handle gosta Ok, Perfect. Vejo-te no próximo
136. Operação de exclusão: Ei aí. Neste vídeo, vamos lidar com delish em off chap mensagens para que escombros em outro Aiken Bt no controle para item de mensagem. Vamos lá. Vamos navegar até o item da mensagem Dodgy? Sim. E aqui ao lado de gostar, posso começar o controle. Deixe outro Aiken entre controle para excluir a mensagem e ele será visível em Lee para a mensagem. Autor. Então o autor da mensagem Onley pode fazer isso. Então vamos copiar isso e vamos condicionalmente tornar nosso próximo Aiken se tornou o controle. Então, se formos autor fora da mensagem, só então seremos capazes de ver isso. Então não precisamos de cor. Brad, precisamos que seja visível. Posso dizer que vai ser perto. Dica de ferramenta vai ser adiada Esta mensagem Nós não precisamos de conteúdo veg. E para unclip vamos adicionar alça dill que vamos receber de adereços. Certo, acho que terminamos aqui. Agora vamos dar uma olhada se eu,
no entanto, eu posso ver entregue esta mensagem, ok, Muito legal. Agora não vamos envolver duas mensagens em togs de texto. E aqui vamos definir essa função. Vamos puxar o punho const dill -lo e rápido em uso chamada de volta com antecedência. Vamos também não esquecer as dependências e vamos passá-lo com antecedência para o item da mensagem. Ok, bom. Então este identificador delete recebe uma ideia de mensagem como um argumento. Então vamos pegá-lo e eu vou definir nossa lógica em primeiro lugar. Vamos perguntar se você realmente pretende entregar esta mensagem. Talvez ele só tenha clicado. Então vamos perguntar se janela confirmar, entregar esta mensagem. Então, se o usuário clicar em não, então nós vamos simplesmente retornar da disfunção. Então precisamos executar algumas operações aqui quando atualizarmos o banco de dados. Porque, como você se lembra, quando nós deliberamos mensagem aqui, nós também precisamos considerar nossa última mensagem propriedade dentro do item da sala. Então também precisamos atualizá-lo, e precisamos executar uma operação atômica. Para isso, vamos criar um objeto de atualização
e, em seguida, vamos atualizar nosso banco de dados a partir da raiz, como fizemos antes. Ok, então vamos criar novas atualizações, objeto, que está vazio por enquanto. E então vamos colocar as primeiras atualizações do que as pessoas atualizam mensagens. Em seguida, vamos atualizar a mensagem. I d Annable disse que ele vai apagar a mensagem original que quando a nossa mensagem é última, queremos atualizar as informações do nosso quarto. Então primeiro precisamos detectar quando nossa mensagem é perdida. Para isso, vamos criar um novo valioso aqui, que vamos nomear é o último, Vamos colocá-lo acima atualizações. E vai ser uma comparação entre o nosso estado atual e a mensagem I D. Então vamos nos referir a mensagens. Em seguida, mensagens ponto comprimento menos um. Vamos pegar a última mensagem da nossa matriz de estado que eu d é igual a duas mensagens I d. Então, se isso for verdade, então nossas mensagens estão bem, então aqui vamos perguntar se nossa mensagem é luxúria do que para essas atualizações. Objeto. Vamos especificar salas de
barra, bate-papo
e depois a última mensagem é igual à próxima. Então ele vai ser o objeto anterior ao lado do nosso objeto dilatado atual. Então precisamos pegar mensagens de comprimento de ponto menos dois, o objeto anterior, certo? Então vamos espalhá-lo por toda a última mensagem. Então vamos encaminhar mensagens do que as mensagens ponto comprimento menos dois. E também precisamos especificar a mensagem i d. Como lembrar para a última mensagem. Então nós também vamos colocar mensagens, mensagens sobre comprimento menos dois pontos i d. E porque estamos tentando acessar mensagens comprimento ponto menos dois, isso pode ser agora ou este objeto não pode ser existência. Por isso, temos de verificar isso. Então podemos fazer isso simplesmente colocando aqui. Se a nossa mensagem é última e mensagens que o comprimento do pensamento é maior do que um Onley, então nós nos certificamos de que este objeto não existe. Certo, então nosso próximo caso a considerar quando tivermos apenas uma mensagem na sala de bate-papo. E quando
atrasamos, queremos apagar a última mensagem dentro de informações para isso. Vamos verificar se a nossa mensagem está perdida e as mensagens são iguais a um no Lee. Então vamos puxar para a última mensagem Mel Value para entregá-lo. E no final, atualizaremos nosso banco de dados. Então vamos colocar tentar Kage. Olhe para aqui. Então nós vamos chamar, esperar banco de dados ponto rascunho atualização porta com objetos e vamos convertido para qualquer função . E também vamos especificar matriz de dependências. Então precisamos pastar idee e mensagens. E também para evitar este aviso, supressor da
Colette assim. E também vamos colocar alerta aqui para notificar o usuário que excluímos a mensagem. Então a mensagem tem bean dilatado e não mensagens mensagem. E para qualquer erro, vamos colocar porta de alerta, inserir erro, mas mensagem. OK, parece bom. Agora vamos dar uma olhada. Deixe-me adicionar algumas mensagens novas. Alô? Eles estão altos. Certo, então se eu apagar a última mensagem dentro do banco de dados, posso ver que as informações do quarto estão sendo atualizadas. E agora eu tenho a última mensagem definida para lá, o que está correto. Agora, se eu fizer isso não é a última mensagem, mas uma dessas. Vamos dizer olá. Posso ver que a última mensagem dentro do item da sala não foi atualizada. Isto está correcto. Agora, se eu apagar a última mensagem, eu tenho novas mensagens. E se eu tiver apenas uma mensagem dentro do banco de dados e se eu apagar essa, ainda não tenho mensagens em ambos os lugares. OK, então isso é bom. E é assim que vamos lidar com isso. Tudo bem, vamos cometer nossas mudanças e terminar este vídeo. Vamos esquecer tudo e depois nos comprometemos. Lidar com mensagem dilatada cooperação. Muito bem, vejo-te no próximo.
137. Adição de componente de Upload - Parte 1: Santificar. Neste vídeo, vamos começar em funcionalidade para upload de arquivos. Vamos,
vamos navegar para a pasta inferior e vamos abrir togs índice. Aqui vamos adicionar um novo ícone, inferior à nossa importação. Aqui à esquerda, ele abrirá o modelo Window e a partir daí faremos upload de nossos arquivos. Então vamos criar um novo arquivo dentro. Esta pasta irá nomeá-lo Anexo BT e Moto Gs. Vamos pobre Olá dentro e vamos usá-lo aqui dentro togs índice logo antes dos
elementos de entrada estavam indo para exibir anexo Bt e Moto. Ok, agora vamos definir o nosso mercado. Então, aqui precisamos derramar em baixo grupo Dar porque quando usamos grupo de importação dentro, precisamos derramar no botão de grupo porta, a fim de trabalhar e olhar bem. Então, para este importante botão de grupo, vamos especificar Aiken, que vai ser apego agora precisamos para você lidar com o estado moral. Então vamos usar usar o gancho Estado Moto e vamos crescer seu aberto perto e aberto. Então, quando
clicarmos neste fundo, vamos abrir nossa janela móvel. Certo, perfeito. Ao lado deste botão, vamos definir a janela mortal real. Então vamos importar modelo. E dentro de Moto, vamos especificar Mortal Heather, corpo e rodapé. Muito bem, bom para este modelo. Vamos especificar que a propriedade do show, que está aberta e também em altura, vai ser próxima para Heather. Elemento dentro, vamos derramar título Moto dentro do título Mortal que vamos exibir são arquivos pavimentados. E vamos tirar este dinheiro daqui para um rodapé modelo. Vamos pacificar um fundo para aplaudir nossos arquivos. Então vamos derramar novo elemento botão e dentro vamos derramar um Plourde. Ou talvez, digamos, enviado para conversar. Então, por enquanto, ele terá apenas uma propriedade clique. E ao lado deste fundo, vamos exibir pequeno elemento e dentro dele vai dizer que arquivos Onley menos de cinco megabytes são permitidos. E vamos alinhar este pequeno elemento pelo site certo. E também, vamos dar um pouco fora da margem superior. Está bem, vamos guardá-lo. E para o corpo, vamos especificar olá por enquanto. E vamos levar um local para ser metade. Então agora podemos ver que temos esse estranho mercado por causa dessa definição. Nós não precisamos dele. Precisamos reagir. Fragmento. Certo, mais
uma vez. Agora temos fundo Quando clicamos nele, temos esse tipo de moto enviar para o Chad e onde apenas arquivos com menos de cinco megabytes são permitidos. Nosso elemento de aplaudo é carregado. O componente vai ser reativo. Então vamos procurar um plodder e vamos descer para manualmente. Então este é o tipo de componente que vamos tirar do nosso terno. Se abrirmos o snippet de código, vamos chamar P tudo isso e vamos usá-lo lá dentro. Ah, use o corpo em vez de “olá”. Vamos importar um porteiro. E aqui vamos derramar do chão igual a dois. False que ação vai ser apenas uma string vazia, porque vamos lidar com isso manualmente para evento inalterado. Vamos especificar a mudança, Heller, que irá criar. Nós não vamos usar qualquer referência porque vamos lidar com tudo manualmente. Em seguida, seremos capazes de fazer upload de vários arquivos e também menos digitar. Vamos especificar o texto da imagem. Ok, agora nós precisamos realmente tratar nosso estado para arquivos enviados. Então vamos criar um novo estado aqui que vamos nomear,
arquivo, arquivo, lista e definir lista de arquivos por padrão. Vai ser uma taxa vazia e esta lista de arquivos. Precisamos passar para este componente de aplaudir. Então vamos passar lista de arquivos como estado de lista de arquivos. Agora precisamos definir isso sobre mudança, manipulador. Então vamos criar essa função aqui e este evento de mudança se tivermos nos dá
lista de fogo , que é arquivado tipo. Então nós basicamente temos um array off arquivos que temos que aplaudir. Mas a partir deste raio, precisamos de um filtro de algumas coisas. Então, primeiro de tudo, precisamos permitir arquivos Onley com menos de cinco megabytes de dados. E também queremos restringir o número máximo de arquivos carregados. Digamos 25 Então primeiro precisamos definir nosso tamanho em bytes para restringi-lo. Então precisamos obter cinco megabytes em mordidas para fazer isso. Então aqui no topo, vamos criar o tamanho do arquivo Max valioso, e aqui vamos colocar Então primeiro vamos pegar 1000 que representa uma mordida. Então vamos multiplicar por 1024 para obter um megabyte em mordidas e depois multiplicado por cinco para obter cinco megabytes em mordidas. Tudo bem, então dentro deste manipulador inalterado permite pobre filtrá-lo, digamos valor ou valioso. Em seguida, vamos chamar o filtro de ponto matriz de arquivo Aqui vamos receber elemento. E para este elemento, vamos perguntar se este elemento blob arquivo ponto tamanho ele vai nos dar o tamanho fora do
arquivo atual menor ou igual ao tamanho máximo do arquivo Onley. Em seguida, será adicionado ao nosso estupro filtrado. Além disso, a partir desta matriz filtrada, queremos que Onley pegue cinco elementos. Então vamos colocar fatia e a partir da fatia vamos especificar Onley 1st 5 elementos como esse. Então, logo depois disso, vamos chamar a lista de fogo e vamos derramar uma visão filtrada como essa. Certo, se dissermos que estamos agora, temos esse sinal de igual no fundo. Vamos salvar tudo. Vamos navegar de volta para o APP Vamos clicar neste botão e podemos ver que ele não está cheio com. Então vamos consertar isso rapidamente para aplaudi-la. Nós vamos especificar o nome da classe fora com 100. Agora, que poupança? E vamos dar uma olhada mais uma vez. Então, quando eu clicar neste botão, Eu vou fazer upload, Eu posso ver que ele está cheio com eu posso selecionar vários arquivos. Digamos que eu vou selecionar todos eles. Mas apenas os primeiros 5 arquivos serão selecionados. 12345 Eu posso ver que ele realmente funciona. Agora eu preciso adicionar funcionalidade para enviar para o botão de bate-papo, a fim de fazer upload de todos eles. Eu também posso gerenciá-los a partir daqui. Está bem, fixe. Então vamos criar E você, manipulador, que vai ser o nosso manipulador para isso no clique enviado para o botão de bate-papo. Então vamos criar, digamos, em um Plourde ele vai estar em uma pia, função e insight. Primeiro, vamos definir, digamos, o estado de carregamento. Ok, então vamos criar está carregando e set está carregando por padrão. Será falso. E isso está carregando. Vamos servir para este fundo. Então, para deficientes que vamos colocar está carregando para no clique. Vamos especificar um Plourde. E também vamos fazer o nosso aplaudido ou deficiente. Se pudermos fazer isso, eles desativaram. Quando é o carregamento? Está bem, Perfeito. Então, para um Plourde, faremos a próxima coisa. Vamos puxar, tentar pegar o bloco em primeiro lugar. Então sabemos que temos lista de arquivos como uma matriz fora tipos de arquivos. Isso significa que vamos aplaudir vários arquivos para o nosso banco de dados. Então, a fim de lidar com múltiplas promessas, vamos usar o ponto de promessa Tudo Mas primeiro, precisamos obter uma série de promessas para isso. Vamos criar quaisquer promessas valiosas de aplaudos e vamos mapear a nossa lista de arquivos para prometer, a fim de receber matriz de promessas. Então lista de arquivos mapa ponto vai ser arquivado. Então precisamos acessar nosso armazenamento. Então vamos colocar um depósito. Então vamos usar o objeto de armazenamento da base de fogo MISC. Então vamos puxar a referência, e vamos colocá-la. Teoh, vamos HR bater papo. Certo , assim. Agora precisamos pegar o gráfico I D. Mas é muito simples. Podemos obtê-lo usando pistas, Paramus Hook usa programas. A partir daqui vamos obter gráfico I d Reagir roteador. Vamos movê-lo para o topo. E para esta referência de armazenamento, então vamos especificar permite que um filho. Então vamos derramar um nome de arquivo e, a fim de chegar com o nome aleatório, podemos colocar simplesmente data agora e então, digamos que arquivo solha nome escuro para torná-lo mais ou menos aleatorizado. Ok, então que o seu Plourde, nós vamos despejar porta e nós podemos realmente usar este arquivo de bloco que temos de
objetos de arquivo . Vai funcionar. OK, então é quase isso. Mas para este arquivo, eu quero especificar o controle de caixa. Heather, a
fim de descontar dentro do nosso navegador para o porto, nós vamos especificar o segundo perímetro. Vai ser objeto off, fez um dado. Então aqui vamos especificar o controle de dinheiro e vamos fazer o próximo então vai ser público e depois marca a idade. Precisamos especificar aqui, Max, idade em segundos. Então vamos especificar três dias em segundos. Então vamos colocá-lo para fortalecer a exaltação viagem. E agora vamos fazer a nossa lógica. Então, primeiro, vamos ter uma hora em segundos, que é 3600. Então vamos multiplicar por 24 para obter um dia em segundos e depois multiplicado por três para obter três dias em segundos. Ok, bom. Logo depois disso. Na verdade, não se esqueça de retornar a partir dessa função de retorno de chamada. Então teremos a próxima coisa. Então vamos colocar um const, um Plourde instantâneos, um Plourde instantâneos que vamos chamar de “Aguarde Promessa”. Então arquivos de uma hora são carregados. Vamos receber uma matriz fora de aplaudir instantâneos. Então, como você se lembra de obter seu arquivo l quatro carregado para obter público disponível, você sabe, também
é uma promessa que precisamos chamar Gedo e baixar a aura. Então, é uma promessa. Então, novamente, vamos acabar com outra área de promessas. É por isso que, novamente, precisamos mapear um novo conjunto de promessas. É por isso que vamos dizer que vai ser promessas de forma. E aqui vamos chamar “Aplaud Snapshots” Mapa de Pontos e a partir daqui vamos receber camiseta
de ritmo, e esta camiseta vai nos dar a próxima. Então, vamos retornar um objeto que vai ser tipo de conteúdo snap-shore metadados tipo de
conteúdo. Então teremos o nome, que vai ser arrancado. Nome do ponto de meta de dados em terra. Vai ser o nome do arquivo carregado, nome do
arquivo, e então o seu próprio vai ser um peso que podemos agarrar porta de referência curto ponto get Não carregue a Europa assim. Então, esses serão nossos dados que vamos armazenar dentro do banco de dados agora para esta rua promessas que vamos criar novos valiosos, que vamos nomear arquivos. Então vamos chamar uma filha prometida de peso de promessas, e eu teria nossos arquivos que precisamos dizer para nosso banco de dados. Então, para essa cirurgia de índice interno, sim, vamos criar uma nova função que vamos gerenciar no próximo vídeo para fora. Vamos chamá-lo com antecedência. Então, a partir de adereços aqui, vamos receber uma função após um Plourde, e isso após o upload irá gerenciar arquivos carregados e disse que eles para o banco de dados. Então vamos ligar, esperar depois de um Plourde e por disfunção, vamos passar nossos arquivos dessa estrutura. Depois da chamada de volta, vamos definir o carregamento para falso. E também vamos fechar nossa janela móvel assim. E no caso de termos algum erro que vamos chamar disse está carregando. E então vamos alertar melhor a porta com mensagem de erro. Tudo bem, então este é o fim para este vídeo. Infelizmente, não
podemos testá-lo ainda. Nós podemos, mas ele só vai carregar arquivos para este armazenamento. Então, no próximo vídeo, vamos continuar a trabalhar nisso. E vamos criar isso após a função de upload. Mas, quanto a agora, vamos cometer nossas mudanças e terminar o vídeo. Então, pegue tudo e então se comprometa. Anexo criado, inferior com um componente flutuante. Muito bem, vemo-nos na próxima.
138. Loja de arquivos de upload no banco de dados - Parte 2: Ei aí. Neste vídeo, vamos definir após a função de upload que mencionamos no vídeo anterior Vamos Navegar para Índice Togs Inside Bottom Folder e aqui na parte inferior direita antes de definir marcação. Vamos criar depois de um Plourde envolto em função de retorno de chamada de uso. E também, vamos especificá-lo até dependências como vazio cada Então vamos passar isso depois de um Plourde
com antecedência . Teoh apego Bt e mortal. E isso após o upload recebe arquivos que precisamos derramar dentro de um debate para lembrar este anexo batendo Moto tem seu próprio estado de carregamento, e este é Onley dentro do modelo. Mas dentro em exulto. Sim, também
temos o estado de carregamento desta vez para a entrada real. Então, logo antes de fazermos qualquer operação no banco de dados, vamos também chamar disse, está aplaudindo para verdadeiro dentro togs índice. Ok, então, o mesmo que para no clique enviado. Precisamos definir uma operação atômica, então vamos criar atualizações como um objeto vazio. E vamos copiar esta lógica para Digamos, quatro dados de mensagens aqui e essa tecla push agora porque temos vários arquivos que
precisamos carregar e esses arquivos estão na taxa que vamos chamar arquivos para cada um olhar sobre cada arquivo dentro este direito receberá o arquivo. E para cada arquivo recebemos uma mensagem ruim e também, vamos definir dados da mensagem. Então vamos pegar essa lógica a partir de enviar Clique e colocá-lo para cada arquivo. Então, reúna a mensagem. E em vez de texto, vamos especificar arquivo e para arquivo vamos especificar objeto de arquivo que criamos dentro anexo modelo BT, que é este objeto. Ok, agora temos a mensagem I d. Temos atualizações com os dados das mensagens. Parece legal. Agora precisamos também superar se eu desejo mensagem como fazemos aqui, então dentro em algum clique é muito fácil. No entanto, agora que temos, digamos que este objeto de atualizações preenchido com esses dados, como podemos pegar a última mensagem? Embora seja realmente muito fácil, leva algum tempo para entender a lógica. Então, primeiro vamos pegar última idéia mensagem, que vai ser chaves de ponto de objeto de atualizações e, em seguida, a partir desta matriz fora, vamos dizer mensagem idéia. Vamos estourar o último elemento que será a última mensagem. Tudo bem, então vamos colocar atualizações, salas,
bate-papo, bate-papo última mensagem. E em vez de dados de mensagens, vamos chamar atualizações última mensagem idee. E para a mensagem I d. Nós vamos especificar a última mensagem. bem Tudobem, e depois vamos copiar isto. Tente pegar o bloco daqui, e vamos colocá-lo bem aqui. E vamos converter essa função para qualquer coisa. Função. Assim, um banco de dados ref atualiza atualizações. Ok, Said está diminuindo Nós não precisamos em pobres e parece tudo bem agora, vamos realmente especificar matriz de dependência é com chat I D e perfil e agora estamos prontos para testá-lo. Agora, não
vamos voltar para o APP. Deixe-me clicar no upload do arquivo. Vou selecionar todos esses arquivos do que abrir. Depois vou enviá-los para o Chad e posso ver mensagens vazias. No entanto, se olharmos dentro do banco de dados, eu posso ver quatro novas mensagens e nós temos arquivado, como, contagem criado em nós temos autor. E se abrirmos arquivo, podemos ter conteúdo, tipo, nome e referência euro para o nosso armazenamento. Então é isso. E funcionou mesmo. Parabéns pelo próximo vídeo. Vamos exibir todos os arquivos que carregamos. Mas, por enquanto, vamos entrar em nossas mudanças. Vamos esquecer tudo. Obter commit e,
digamos, armazenar arquivos aplaudidos para D Data Maze. Muito bem, vemo-nos na próxima.
139. Exibição e download: Ei,
neste vídeo, vamos exibir todos os nossos arquivos enviados. Vamos,
Vamos navegar de volta para o código e vamos abrir mensagem Bytom componente o lugar onde nossos elementos são renderizados. E aqui na parte inferior em vez desta panela com apenas texto dentro, vamos colocar renderização condicional. Mas primeiro, vamos pegar não apenas texto para mensagem, mas também, digamos arquivo Agora, dentro deste diferente, somos capazes de fazer renderização condicional. Então, se temos texto dentro da nossa mensagem sobre Lee, então vamos exibir mensagem fiscal. Para se tivermos arquivo dentro da nossa mensagem, então vamos criar uma função personalizada para renderizar arquivos. Então vamos nomeá-lo, renderizar mensagem de arquivo e dentro, vamos passar o nosso arquivo, em
seguida, aqui no topo para fora deste componente, vamos definir esta função, renderizar mensagem arquivada para que ele vai receber arquivo e esta função, por padrão, nos retornará apenas um link. E dentro deste link, vamos derramar o nome do ponto do arquivo de download. Se o nosso arquivo não é uma imagem e para um treff, nós vamos despejar arquivo porta Europa. Ok, bom. Agora, se o nosso arquivo é uma imagem, nós armazenamos o tipo de conteúdo dentro do banco de dados para que possamos verificar esta propriedade. Então, se o tipo de conteúdo do arquivo inclui imagem, então vamos retornar elemento dif Dentro desta def, vamos derramar uma imagem como um botão. Então, quando clicamos nele, abrimos a janela Moto. E também teremos esta vista inferior original para nos levar ao outro toque e ver o tamanho
completo. Então, para este dia, se vamos especificar o nome da classe fora da altura para qualquer 20 e, em seguida, dentro, vamos criar imagem Bt em Moto e para isso no maior entre modelo, vamos passar feridas, que vão ser arquivadas. Seu nome de arquivo e também vai ser arquivado. Nome do pato. Agora precisamos criar essa imagem, beleza e Moto. Então, mensagens internas. Vamos criar nova imagem de arquivo VT no Moto Don't Yes. E como sempre, vamos servir um modelo. Mas vamos envolvê-lo em torno de fragmento reagir do que dentro. Em vez de botão, vamos colocar na porta fora do tipo de imagem. Ele faz este ato de importação como um botão, mesmo que seja uma imagem. Então, para alternativa, começar a especificar este arquivo e para propriedades, vamos especificar fonte e nome do arquivo. Então vamos fonte pobre e nome do arquivo. E como posso ver, peguei o nome do arquivo errado. Então deixe-me substituí-la por Image Bt em mortal. E deixe-me renomeá-lo com imagem Bt e Moto. Ok, então importe o tipo de imagem para fonte. Vamos especificar a fonte para no clique. Nós vamos especificar dívida aberta vai agarrar de uso estado modelo usar estado mortal assim é aberto, aberto e fechar. E também vamos especificar se vocês nomes de classe aqui, que é Max com 100 no máximo, escondam 100. E com vai ser alfa. Certo, bom é para a entrada. É isto. Agora vamos realmente definir motile. Então vamos pobre componente mortal do que Mortal Door Heather, corpo e rodapé, corpo e rodapé. Então, dentro da Heather, vamos mostrar o título mortal da porta modelo e vamos colocar o nome do arquivo dentro e vamos lidar com mortes. E isso agora dentro er comida vamos especificar apenas um link para uma torneira externa. Então vamos colocar um e um treff vai ser fonte e vamos especificar alcatrão, ficar em branco para a nova guia. E também precisamos especificar relacionamento. Sem abridor, sem rap Ferrer. Sim, assim, eu acho. E este componente não é auto-fechamento. Vamos colocar a visão original dentro e dentro da vista. O corpo do modelo ia exibir a imagem
real. Então vamos colocar uma etiqueta de imagem Dan, para feridas. Vamos especificar feridas. E para a altura, digamos, 104 com ,
Digamos, também 100 fora vai ser deixa arquivo. Ok, agora vamos usar Isto é aberto para mostrar propriedade na altura vai ser perto e parece OK agora vamos mover esta importação para o item de mensagem superior e interna. Vamos importar este componente. Tudo bem, agora vamos dar uma olhada. Se eu atualizar o aplicativo, eu posso ver não carregar arquivo,
nome, download, download, nome do
arquivo e eu posso ver imagens. Então, vamos corrigir rapidamente disse Em vez desses colchetes, vamos ambos os colchetes. E agora vamos dar uma olhada para que temos fazendo carregar este arquivo. Não conheço esse arquivo. Se clicarmos nele, vamos realmente começar a baixar, e eu sempre vejo que temos imagens e quando clicamos nele. Temos essa visão original, e quando clicamos nela, chegamos ao novo toque. Está bem, parece muito bom. No entanto, em mensagens de luxúria, temos espaço vazio, então vamos corrigi-lo rapidamente. Vamos navegar até o item da sala e aqui dentro do texto da última mensagem. Vamos colocar o próximo. Então, se não temos última mensagem de texto,
em seguida, vamos especificar última mensagem ponto nome do arquivo ponto e é isso. Agora vamos dar uma olhada. Temos o nome do arquivo .
Muito legal. E é basicamente isso. Agora vamos terminar este vídeo e confirmar nossas mudanças. Vamos esquecer tudo. Obter commit e digamos exibir arquivos carregados de fato. Vejo você na próxima.
140. Gravação e uploads - Parte 4: Olá. Neste vídeo, adicionaremos uma opção aos registros de um usuário Plourde diretamente do navegador, para que
possamos enviar mensagens de áudio para o chat. Vamos lá. Então, como eles vão lidar com isso? Bem, já que já temos o código para upload de arquivos, será relativamente fácil. Só precisamos achar uma maneira de gravar a voz do usuário. Por isso. Vamos usar reagir, Mike Library. É uma biblioteca que oferece para gravar voz do usuário e, em seguida, visualizá-lo. Mas não vamos usar essa opção de visualização. Só precisamos da gravação. Então deixe-me instalar esta biblioteca. Vou copiar este elogio do que dentro de mais terminal. Vou executá-lo. E enquanto ele está executando na pasta inferior, vamos criar novo nome vegetal arquivo. Digamos que mensagem de áudio Bt em esque cãozinho. Por agora vai ser apenas um Deve vazio. E vamos usar isso dentro de togs índice na parte inferior. Então aqui, logo após anexo, Beat e Moto Vamos usar rodeio meu disse que você é TTN e também vamos passar após o upload porque vamos enviar mensagens de áudio. Então, dentro deste componente, receberemos após o upload. E agora vamos definir bem o nosso mercado. Vai ser quase o mesmo que para apego bater Moto. Então vamos copiar o fundo do grupo de entrada a partir daqui e colado como nosso mercado. Então, vamos importar o botão de grupo de importação para unclipped. Teremos o nosso próprio manipulador e vamos também importar ícone. E por que eu posso usar meu telefone corvo? Ok, bom. Agora como somos capazes de usar isso reagir meu Kleiber Vamos para uso e exemplo. Então vamos copiar a parte de importação e colocá-la aqui no topo. Então vamos realmente usar o componente. E vamos dar uma olhada em que tipo de adereços precisamos passar. Então, primeiro temos este registro e se eu pairar sobre a propriedade, disse muito verdadeiro para começar a gravar. Então precisamos que o Estado controle. Quando quisermos começar a gravar, vamos criar uma. Então ele vai ser é gravar em. Bullen está gravando por padrão, ele será definido como false e nós vamos passar este estado para gravar propriedade que para o
nome da classe , vamos colocar display none, a fim de exibir qualquer reagir Mike Element, mas para usar sua funcionalidade. Então, por uma vez, pare. Este vai ser o nosso encarregado quando tivermos a gravação e quisermos enviá-la. Então, para isso, vamos criar um manipulador Plourde. Então vamos colocar em um Plourde e com antecedência, vamos colocá-lo em uso chamada de volta. Então, por enquanto, vamos deixá-lo vazio assim e nos dados, não
precisamos desse porque se rolarmos para o uso, podemos ver que quando os dados são opcionais, chamados quando uma ordem de tosse do canal está disponível não
precisamos dessa. Nós não precisamos jogar cor e cor de fundo porque nós simplesmente não exibir este componente que também precisamos passar. Digo, digite esse componente para garantir que recebamos o MP 3. Ex. Então vamos passar o tipo médio e então vamos pacificar áudio MPA três. Ok, bom agora, pronto para ir. Então, primeiro, vamos definir isso no clique. Então vamos colocá-lo aqui na loja e vamos otimizá-lo com o uso frio de volta com antecedência novamente porque vamos simplesmente chamar Said está carregando e vamos reverter nosso valor Bullen
aqui . Ok, bom agora para o upload, nós vamos derramar a próxima lógica. Vai ser correlativo Lee o mesmo que dentro de Attachment BT e Moto. Então, vamos precisar de referência de armazenamento para que possamos copiar esta lógica a partir daqui do que vamos
colocá-lo dentro. Tente pegar o bloco aqui. Vamos receber esta promessa de aplaudir. Então precisamos convertê-lo em uma função de pia. Então verificação de referência de armazenamento, eu d. Vamos também pegar chat I d. De usar Paramus Hook do que para armazenamento. Precisamos importá-lo da base de fogo da ISC do que para a criança pelo nome do arquivo que vamos derramar. Não este nome de arquivo, mas vamos servir. Digamos que áudio do que sublinhar. E então vamos abrir dados de interpolação de cadeia de caracteres agora e, em seguida, no final, vamos colocar filha MP três do que para arquivo blob. O que precisamos especificar para o arquivo real se formos reagir? Mike on stop propriedade nos dá este registro de dados. Então, porque usamos javascript, não temos nenhum tipo. E não podemos verificar que tipo de dados recebemos aqui. Mas o que podemos fazer, podemos realmente colocar uma função diretamente aqui para obter a inteligência. Então recebemos esses dados aqui. E se eu colocar dados dar, eu posso ter blub aqui. Então este é desenvolvido tipo off objeto que podemos carregar para armazenamento firebase. Então vamos colocar o controle de dinheiro do cão de dados. Vamos deixá-lo como está agora. Precisamos também especificar o arquivo real que vamos colocar dentro do banco de dados, não dentro do armazenamento. Então vamos pegá-lo a partir daqui de anexo, bt e modelo. Vou copiar esta estrutura de objetos. Então eu vou criar um arquivo verdadeiro e então eu vou colocá-lo assim. Então instantâneo, dados de
mídia. Hugh R L Ok, bom. Agora precisamos realmente chamada Onley depois de um Plourde com matriz de arquivos que queremos aplaudir porque temos apenas um. Podemos colocar apenas um array vazio e depois colocar nosso arquivo dentro. Então agora temos algum tipo de em uma taxa, certo. Então, para quaisquer erros, vamos colocar alerta Dar erro erro mensagem ponto, em seguida, para a área de dependências. Vamos passar após o upload e compartilhar I d. Vamos passar após o upload e compartilhar I d. Além disso, precisamos definir algum tipo fora de um estado de carregamento. Então vamos criar uma nova dívida viável. Vai dizer que está carregando Deixe ser dito que está aplaudindo. Então, por padrão, será falso e vamos chamar essa função antes de um Plourde e defini-lo como verdadeiro. Então, depois de aplaudir ou talvez logo antes dele, vamos dizer, está aplaudindo para falso e também no caso de qualquer arável também chamado set está aplaudindo para falso. Então agora para o grupo de entrada Bt e podemos passar desativado Onley quando está carregando. E também precisamos de alguma forma notificar o nosso utilizador quando fazemos a gravação para que ele possa compreender isso. OK, sua voz está sendo gravada para isso. Vamos pegar um nome de classe condicional. Então, se temos está gravando, então nós vamos especificar qualquer piscar de companheiro. E este é o nome da classe com a animação CSS que eu defini em uma das classes CSS . Então agora parece bem e tudo o resto parece bem. Agora podemos realmente testar a funcionalidade. Eu não iniciei, então deixe-me executar o AB agora podemos ver iniciando o servidor de desenvolvimento. Ok, vamos esperar alguns segundos até que o APP seja executado. Ok, está carregando. Agora vamos tentar gravar essa. Então, se eu apertar este botão, você pode ver que agora, aqui eu tenho Estes guia está usando sua câmera. Nós microfone este ícone. E também, se eu não tivesse permissão para usar microfone, teria me pedido isso. E agora fui notificado de que tudo bem, minha voz está gravando agora. Então, quando eu clicar neste botão mais uma vez, eu posso ver que eu tenho um novo upload de arquivo aqui. E se formos para o depósito da base de fogo do que para o Chade, podemos ficar com todos os nossos arquivos. E também mensagem de áudio. Ok, então é isso. No próximo vídeo, falaremos sobre como podemos exibir essa mensagem de áudio no primeiro que enfraquece diretamente. Ouça esta mensagem antiga dentro do navegador, mas por enquanto, vamos confirmar nossas mudanças. Deixe-me ligar, obter em tudo, então quem fez cometer e vamos especificar, opção
adicionada, uma opção para gravar e um pobre arquivos de áudio. Muito bem, vemo-nos na próxima.
141. Exibição de arquivos e exclusão - Parte 5: Ei aí. Neste vídeo, vamos exibir os registros de áudio do usuário carregados. E também, vamos corrigir outro problema que surge quando começamos a lidar com o upload de arquivos. Nunca vamos voltar para o código e vamos abrir o item de mensagem o lugar onde renderizamos nosso elemento. Então, aqui nós verificamos contra o tempo do arquivo de conteúdo. Então vamos adicionar outra declaração se aqui e vamos verificar com áudios. Então vamos pedir um arquivo. O tipo de conteúdo inclui áudio. Então, se este for o caso, vamos retornar um elemento de áudio para que para esta ordem será capaz de usar controles. E também vamos pobre elemento fonte que vai ser um elemento auto fechamento. A fonte vai ser arquivada, Senhor, o seu “L “e tipo vai ser Odio MPA três. E se isso não for suportado pelo navegador, então vamos exibir seu navegador não suporta o elemento de áudio. Ok? E vamos tirar o Odeon daqui. E agora temos este ano emagrecido elementos de mídia de aviso, como um áudio deve ser deve ter uma faixa para legendas. Tudo bem, mas não temos canelas de policiais. É por isso que precisamos desativar este aviso. Vamos fazer isso. Vamos guardá-lo e vamos mover este supressor. Agora podemos ver que temos esta faixa para que possamos tocá-la. Eu posso ouvir minha voz, então ela está realmente funcionando e é isso para mensagens de áudio. Era muito simples agora sobre outros problemas que surgem quando começamos a lidar com Philip O. Quando estava doente ID a última mensagem ou uma das mensagens com arquivos do que nós só fazê-lo mensagem dentro do banco de dados. Mas os arquivos do armazenamento não estão sendo diluídos. O que quero dizer é que me deixe tentar apagar esta mensagem antiga. Então, se eu excluir aquele que eu vou para o armazenamento, eu atualizá-lo. Posso ver que é roubar deles para consertar isso. Precisamos consertar nosso casaco. Então, vamos navegar de volta para o índice togs. Mensagem interna é o lugar onde entregamos. Nossa mensagem é assim que esta é a função da aldeia tratada. Então aqui precisamos de alguma forma também executar delish arquivo em como wearable para fazer isso. Então, dentro do item de mensagem quando chamarmos, vamos encontrá-lo. Quando chamamos manipulado, excluído, passamos mensagem i D. No entanto, não
sabemos se esta mensagem tem um arquivo ou é apenas uma mensagem de texto. Então vamos também arquivo pobre para esta função de exclusão identificador. Então, agora sabemos que, se houver qualquer arquivo tão dentro, como até que a tampa também receberá arquivo e logo depois de dill mensagem dentro banco de dados. Nós também podemos colocar outra tentativa, pegar bloqueio aqui, e podemos fazer a próxima coisa. Então, se tivermos arquivado, então colocaremos este bloco Tentar captura aqui dentro, e vamos primeiro pegar a referência ao arquivo dentro da história da base para que possamos chamar , digamos, arquivado. Podemos chamar de armazenamento de referência do seu inferno e se ele retornar promessa ou não saber, parece não tão referência do seu L. E então nós vamos especificar a porta do arquivo, você está fora. Então podemos simplesmente chamar arquivo ref porta dill isso Então isso definitivamente vai ser uma promessa. E no caso de qualquer outro, vamos especificar alerta sempre erro de alerta. E aqui está um momento muito importante para pegar. Imaginemos que entregamos a mensagem e isso falha. Então, se esse falhar. Isso tentará excluir a mensagem. Então, para ter certeza de que, se isso falhar, o próximo código também falhará. Precisamos retornar a partir desses bloco catch sempre que temos um erro. Então agora temos este um dissipador em uma função esperada nenhum valor de retorno. Podemos suprimir novamente o aviso sim, Lind para todo o arquivo. E agora parece bem. Então vamos primeiro excluir manualmente essa mensagem de odor que gravamos. E se eu tentar dilatar a última mensagem aqui, se eu dilatar mensagem foi apagada. E se você olhar dentro do meu banco de dados, eu tenho duas imagens. Mas se me refrescar agora, só
tenho um. Então, tudo foi corrigido com sucesso. Ok, agora vamos cometer nossas mudanças. Vamos pegar tudo, então obter commits. Digamos que as mensagens de áudio exibidas e corrigir o arquivo deleite quando a mensagem está sendo entregue. Tudo bem. Perfeito. Vejo-te no próximo.
142. Feed de Chat conversa de grupo por datas: Hey lá neste vídeo mensagens de bate-papo em grupo móvel por data, então vamos ser capazes de dividir o bate-papo ajuste em mensagens relacionadas à data. Tudo bem, nunca
vamos voltar ao código e vamos ver como vamos abordar isso. Então, primeiro de tudo, precisamos de algum tipo de função que agrupe nossas mensagens por datas. Então vamos criar um. Vamos abrir togs ajudantes. E aqui na parte inferior, vamos criar nova função que quem irá nomear grupo buy Ele receberá uma matriz como o primeiro argumento, e então ele vai receber a função chave de agrupamento. Vai ser uma volta fria e deixe-me explicar como vamos usar essa garota por função. Então vamos chamá-lo assim. O primeiro argumento vamos passar mensagens,
matriz e, em seguida, agrupamento. A função de chave é um retorno de chamada que receberá um item fora desta matriz. Então, em nosso item de mensagem de caso, então o que retornarmos deste callback será nossa chave de agrupamento. Então, no nosso caso, é um encontro. Então vamos transformar a mensagem que eu criei em algo assim. Depois cresceu, vai nos devolver um objeto onde cada chave vai ser essa chave de agrupamento que retornamos desta chamada
de volta. Então, se retornarmos data que ele vai agrupar mensagens dos EUA por data. Então vamos dizer algo como nós temos data como esta e, em seguida, vamos ter matriz off mensagens relacionadas a esta data e assim por diante, e assim um. Certo, acho que está claro. Agora vamos criar essa função. Deixe-me incomum,
pai, pai, e vamos usar a matriz de pontos reduzidos para que não reduza, recebe uma chamada de volta. E segundo argumento é o valor inicial do estado inicial. Então vai ser apenas um objeto. E para o co volta primeiro argumento é acumulador vamos usar Vamos um resultado e, em seguida, o valor atual item atual apenas indo para o item ok de cada iteração vamos retornar resultado e, em seguida, vamos executar a próxima coisa Primeiro, vamos derramar chave de agrupamento valioso, e vamos chamar função chave de agrupamento e vamos passar insight item. Então, dessa
forma, seremos capazes de acessar o item de mensagem dentro desta chamada de volta. Ok, bom. Agora vamos verificar contra o Vale Nulo ou vale inexistente. Então, se o resultado agrupamento propriedade chave não existe, então vamos inicializá-lo como de outra forma. Vamos receber um aviso ou um erro se tentarmos executar algo no objeto não existente . Então vamos colocar chave de agrupamento de resultados e, em seguida, vamos citá-lo como uma matriz vazia. Tudo bem, então, se isso existe, então vamos colocar o resultado de agrupamento ponto-chave empurrar item atual e é isso. Agora somos capazes de usá-lo. Vamos abrir mensagens, indexar togs, e vamos encontrar o lugar onde renderizamos mensagens. Então agora é apenas esta função de mapa por aqui. Vamos copiá-lo e dilatar. E em vez dessa função de mapa, vamos para nossas próprias mensagens de renderização funcionais personalizadas. A morte criará. Então aqui vamos const mensagens grandiosas e vai ser uma função, e dentro dela vai colocar este mapa de mensagem. Mas vamos comentar por enquanto. E aqui vamos chamar grupo por Então vamos grupos pobres de const. Então vamos chamar o grupo por. Vamos passar mensagens nosso estado do primeiro argumento e, em seguida, grupo na função chave para que ele vai receber item de mensagem e grupo de problemas por datas. Então, para especificar item criado em mas criado anúncio como lembrar, é apenas um carimbo de data/hora do banco de dados. Não é um objeto de data que podemos usar ou exibir dentro JavaScript. Então vamos convertê-lo em objeto tardio
e, em seguida, estamos em conformidade com este objeto data com a cadeia de data. Tudo bem, agora temos grupos e precisamos criar elementos que vamos empurrar e exibir dentro do J 6 dentro do cão. Então vamos criar chaves de objeto,
em seguida, especificar grupos e para cada método. Então, o que está acontecendo aqui que nós vamos repetir cada data, cada chave dentro de grupos objeto. Então vamos ter um encontro aqui e para todos os dias. Primeiro, vamos criar uma matriz de itens. Então deixe ser deixar itens que vamos modificar. E para estes itens, primeiro, vamos empurrar o nosso primeiro elemento. Isso vai ser um encontro. Elemento L I. Então vamos criar novo l I dentro rebelde exibido data e nome da classe vai ser margem do
centro de texto não seria um e pad e também precisamos especificar chave, que vai ser data, e é único dentro deste. Os grupos organizam. Tudo bem. Agora, precisamos também enviar todas as mensagens relacionadas a essa data específica para que possamos criar novas mensagens. Todos e nós vamos usar esta função de mapa aqui. Então vamos derramar data de grupos para acessar todas as mensagens relacionadas a essa data específica que estamos iterando atualmente. Então grupo ST dot map e nós vamos mapear cada mensagem para mensagem item a partir daqui. Vamos copiá-lo e apagá-lo. Não precisamos mais dele, então vamos mapeá-lo assim, e no final, vamos simplesmente chamar itens de gato escuro e depois mensagens, certo? E na verdade é isso. E no final desta função, vamos devolver itens, e eles serão renderizados para os idiotas. Então diz que os itens nunca são resignados. Tudo bem, então vamos colocar Const, vamos salvá-lo e vamos dar uma olhada. Agora, se navegarmos, não
vejo nenhuma mensagem. Deixe-me tentar uma sintaxe ligeiramente diferente. Agora, se estivermos bem frescos, podemos ter Aikens. Ok, então vamos usar esse em vez de gato. Então o que estamos fazendo aqui com espalhar todos os nossos itens em push. Então eles são tratados como argumentos separados para empurrar. Então, em vez de passar mensagens encolheradas assim, passamos assim. 12345 Muito bem, isto é o que este operador de propagação faz neste caso. Ok, então agora temos,
digamos, quinta-feira, 18
de junho, se eu colocar “oi”. Agora eu tenho 19 de junho, então ele realmente funciona. E agora temos esse pequeno agrupamento. Tudo bem, então é isso. E acho que terminamos aqui. Vamos terminar o nosso vídeo. Vamos servir, pegar tudo, então você fica um pouco. E vamos especificar mensagens agrupadas por datas para efeito. Vejo-te no próximo.
143. Paginação e controle da posição de rolagem: Olá. Neste vídeo vamos lidar com a paginação dentro do chat. Agora, carregamos todas as mensagens do banco de dados e isso não é muito bom. Então, neste vídeo, vamos descobrir isso e também vamos corrigir esse problema. Quando atualizamos a página ou alternamos entre bate-papos, não
vamos rolar para a parte inferior. Vamos lá. Então a questão é como você é capaz de lidar com a paginação na base de fogo? Bem, existem algumas abordagens e o mais comum é apenas você re inscrever Teoh novas
mensagens de bate-papo Toda vez que carregar uma nova porção, Esta é a abordagem que tomamos. Podemos tomar outra abordagem Teoh baixar apenas mensagens antigas sobre o Senhor inicial e, em seguida, assinar novas atualizações. No entanto, essa abordagem não funcionará porque se carregarmos mensagens antigas no Lee uma vez e atualizarmos uma das mensagens, ela não será atualizada em tempo real. Então este não é o nosso caso. Queremos atualizar todas as mensagens e todas elas devem ser em tempo real. É por isso que vamos usar a primeira abordagem. Então, vamos navegar para indexar pontos gs dentro de mensagens e aqui na parte superior, vamos primeiro especificar nosso tamanho para a página. Deixe que seja o tamanho da página de 15. Agora precisamos criar ficou dentro do nosso componente que representa o nosso limite atual. Então vamos criar limite e definir limite. E, por padrão, esse estado será igual ao tamanho da página. Ok, bom. Agora vamos olhar lá dentro. Use o fato de onde buscamos nossas mensagens. Então nós temos esta mensagem, ref, que não está limitada a este uso de fato ou componente dias porque ele não usa quaisquer valores
internos, que
possamos movê-lo com segurança aqui para o topo. Tudo bem, Bom. Agora vamos ter que funções aqui para atrair mensagem inicial e ao Senhor mais mensagens quando clicamos no botão no topo. Então vamos criar uma nova função apenas para compartilhar a lógica. Então aqui, antes de usar o fato de criarmos uma nova função mensagens Senhor e vamos envolvê-la em uso Chamar volta com antecedência para otimizá-la. E vamos colocar essa lógica aqui dentro das mensagens do Senhor. E não apague essa assinatura. É realmente importante para cancelar a inscrição do fato do usuário também. Então agora temos esta criança RG aqui como uma dependência vamos editar. E sempre que você recarregar suas mensagens, também
nos certificamos de que cancelamos a assinatura de mensagens antigas e assinamos as novas atualizações . Então aqui, logo antes de recebermos nossos novos dados, vamos chamar a mensagem ref dot off para cancelar a assinatura das atualizações anteriores. Tudo bem, agora, dentro deste fato de usuário, vamos chamar mensagens do Senhor, e vamos especificar dentro de uma matriz de dependências, e vamos remover o chat I d. porque de agora em diante, não é Partir fora deste efeito de uso. Ok, bom. Agora, e quanto ao limite? E quanto à funcionalidade Lord More? Vamos grande nova função ao lado de mensagens Senhor que vamos chamar mais baixo também permite rapper em uso chamar de volta. E o que devemos colocar lá dentro? Vamos simplesmente chamar mensagens do Senhor com o nosso limite que temos dentro do estado. Então agora precisamos especificar mensagens do Senhor e limitar como dependências e é isso. Isso é tudo por essa função. Agora, dentro mensagens senhor recebemos limite que queremos aumentar quando clicamos em Lord More. Então aqui teremos um limite. E quando tentamos novas mensagens para o nosso construtor de consultas, podemos especificar essa propriedade chamada limit to last. Então o número fora de notas para incluir nesta consulta e nós vamos especificar limite ou porque já temos limitado audível declarado vamos chamá-lo limite para não e vamos
passá-lo aqui. E no caso de não termos nenhum valor em todo o legis pacificar o tamanho da página, apenas um pequeno zagueiro
aqui . E toda vez que baixamos uma nova parte das mensagens, precisamos aumentar nosso limite atual. Certo? Então, quando clicarmos neste botão, nosso próximo limite será nosso limite atual mais o tamanho da página. Então aqui nós vamos derramar limite definido, e então nós vamos fazer referência anterior, anterior mais tamanho da página. Ok, agora nós precisamos definir este fundo, e nós precisamos colocar este descarregar mais manipulador para este fundo. Então aqui no fundo onde renderizamos nossa marcação, vamos colocar a próxima lógica. Então, temos que perguntar se temos mensagens e mensagens Don't Length é maior ou igual ao nosso tamanho de
página Onley. Então vamos exibir um outro elemento l I dentro vamos colocar botão e dentro inferior
vamos derramar mais baixo. Agora vamos adicionar alguns nomes de classe. Então, para este aliado, vamos colocar uma margem de centro fiscal no topo dois e na margem inferior também. E também para no clique, vamos especificar própria mais baixa. E também vamos colocá-lo com a cor verde, não vermelha. Eu não gosto dessa. Tudo bem, Bom. Agora vamos dar uma olhada no que fizemos. Se abrirmos nossa página agora, como eu, atualize-a mais uma vez. Podemos ver agora temos Onley 15 mensagens e se eu clicar em carregar mais, você pode ver que mais mensagens foram carregadas. Então é isso. Isto é o que está acontecendo. Então, agora, quando carregamos nossa página inicialmente, temos nossa assinatura inicial Onley tamanho de quatro páginas, que é atualmente 15. Então, quando clicamos em Lord More, isso está sendo lançado com nosso limite atual que aumentamos e ele vai ser aumentado para 30 e vamos cancelar a assinatura dessas atualizações e vamos assinar novas atualizações. Então é isso que está acontecendo em segundo plano. Tudo bem, agora, e o nosso pergaminho? Como você pode ver, ele está muito quebrado porque quando baixamos novas mensagens. Nós feijões rastejamos para o topo toda vez. Isto não é bom, por isso temos de o controlar de alguma forma. Bem, para isso, precisamos usar referência para obter o elemento real para que possamos manipular sua
posse de pergaminho . Para isso, vamos criar uma nova referência aqui. E vai ser,
digamos, digamos, auto ref com gancho ref usado. Ok, então vamos passar essa referência para o nosso elemento “você”. Então a referência vai ser auto-referência. E agora vamos começar a manipulá-lo. Então, em primeiro lugar,
para o nosso efeito de uso inicial, quando
carregamos nossa página inicialmente, queremos rolar até o fundo, certo? Então aqui nós vamos especificar nota e nós vamos referência auto ref ponto atual para obter a referência
real para o nosso elemento. E aqui, logo após carregarmos nossas mensagens, podemos derramar nó rolagem superior igual a nenhuma altura de rolagem. E vai ser coisa do Lloyd. Eu sempre tive o problema com essa abordagem é que porque essas mensagens do Senhor são uma operação
assíncrona e isso é síncrono, então isso pode ser executado antes que essas
mensagens do Senhor tenham feito com seu pensamento, então é importante colocá-lo como qualquer pensamento operação para isso. Vamos envolvê-lo em torno de tempo definido nosso e nós vamos especificar algo como 200 milissegundos. Dessa forma, garantimos que isso esteja sendo executado em Lee quando as mensagens do Senhor são feitas e quando todos os elementos que estamos tentando exibir são exibidos na página. Tudo bem, então agora vamos dar uma olhada. Se eu atualizar a página, eu posso ver que eu não pensei, mas eu estou rolando para a parte inferior. Sim, eu posso ver isso. Um pequeno atraso de 200 milissegundos. Mas tudo bem, certo? Não há nada de errado com isso. No entanto, agora estou sendo deslocado para o fundo. Ok? Nossa próxima abordagem é realmente manter esta posição de corvo quando clicamos em Lord More. Então não estamos rabiscados até o topo. Bem, por isso dentro, Senhor, mais em primeiro lugar. Vamos novamente referenciar nossos elementos atuais. Então nota vai ser auto ref atual. Então, antes de clicar em Lord More, precisamos saber a altura anterior do nosso elemento de rolagem fora da nossa posição de rolagem. Então, quando baixamos novos elementos, obtemos a nova altura e então podemos subtrair esses valores. Então aqui vamos derramar a velha altura valiosa. E aqui vamos derramar altura de rolagem do nó. Tudo bem, então, depois das nossas mensagens, vamos ligar para o dito Tempo de novo para tornar a nossa operação assíncrona novamente. Com o tempo fora 200 milissegundos e, em seguida, dentro, vamos especificar nova altura, que vai ser nenhuma altura de rolagem. E, em seguida, vamos especificar nó rolagem superior igual a nova altura menos altura antiga. Tudo bem, agora, vamos salvá-lo. Vamos remover esse ritmo e vamos dar uma olhada. Agora estamos rolando para o fundo, e quando eu clicar em Lord More, você pode ver que esta posição de corvo é mantida. Ok, então parece muito bom. Como você está? Há mais um caso para resolver. Sempre que escrevo algo no chat, vamos dizer olá. Você pode ver que eu não estou rolando para o fundo. Então precisamos consertar isso. E, idealmente, queremos fazer algo assim. Então, se nós rabiscamos mais de 50% dentro do nosso chat e
escrevemos algo, queremos rolar para o fundo. No entanto, digamos que se procurarmos algumas mensagens antigas. E se escrevermos algo ou outra pessoa digitar, não
queremos rolar até o final. Para isso, precisamos também definir nossa lógica por essa razão. Aqui no topo, vamos criar uma nova função que irá nomear certeza rolar para baixo, e ele vai receber esta auto ref corrente. Então aqui vamos colocar nota, e aqui vamos colocar a próxima lógica. E também podemos especificar segundo argumento, que vai ser digamos limiar, que vai ser, digamos, 30% de por padrão. Ok, então aqui vamos calcular a porcentagem de nossa posição de rolagem, e então vamos retornar a comparação. Vamos transformar o touro em valor se a nossa percentagem que definimos aqui for
maior do que o limiar que foi pacificado. Ok, então porcentagem vai ter a próxima lógica. Então, primeiro de tudo, vamos multiplicar nosso valor por 100%. Então vamos dividir esse valor por nenhum mineiro de altura de rolagem, nenhuma altura de cliente, e essa lógica nos dará a porcentagem. E como uma volta completa, vamos fornecer apenas zero. Ok? Então agora podemos usar disfunção para detectar se realmente precisamos rolar para o fundo se
odiarmos o limiar. Ok, então deixe-me copiar isso e vamos às mensagens do Senhor e ouvir o que vamos fazer. Comece a pacificar Const novamente. Vamos dizer nó e então nós vamos referenciar auto Ralf corrente escura e o que ele vai fazer. Vamos colocá-lo logo depois de definir mensagens. Então vamos perguntar se devemos rolar para o fundo com nosso nó atual e vamos manter o limite como 30% Onley. Então não vamos falar de pergaminho e depois não temos altura de rolagem, está bem? E na verdade, quer saber? Podemos colocar esta nota no topo para reutilizá-la. OK, assim. Agora vamos dar uma olhada. Então deixe-me carregar mais mensagens. Deixe-me ir até o topo. E agora, quando escrevo uma nova mensagem, não
sou enrolado para o fundo. No entanto, se eu rolar mais de 30% e se eu digitar caminhada, eu posso ver que eu estou sendo rolar para o fundo. Então esse é um cara. É assim que podemos lidar com a paginação. E é assim que podemos controlar nossa posição de rolagem. Ok, eu acho que não foi muito confuso porque para mim, à primeira vista, tudo bem, então vamos cometer nossas mudanças. Vamos puxar para obter tudo, obter commit e digamos que ele paginação e controle posição de rolagem. Perfeito. Vejo você na próxima.
144. Implantação na hospedagem do Firebase: Hey, Como para agora, nosso aplicativo de bate-papo tem todas as funcionalidades principais implementadas. A única coisa que está faltando é realmente notificações de tempo. A fim de implementá-lo, algumas coisas têm de ser feitas para disparar Ways Project. Vamos falar sobre isso na próxima seção e para terminar esta seção em uma boa nota, vamos implantar nosso atual Chad usando firebase hospedagem aberta Fire Base que Jason localizou na pasta de estrada para o objeto de hospedagem. Vamos adicionar pré-implantado gancho NPM executar construído Bill Script é definido no pacote Jason. Agora é tão fácil quanto digitar Firebase implantar a partir do terminal. Este comando irá implantar todas as partes do projeto que foram detectadas no firebase o Jason . Estes incluem regras de banco de dados e hospedagem. Nós também poderia implantar partes separadas executando Firebase implantar, Dash Dash apenas hospedagem após o Commander terminar, podemos ir para o host na seção dentro Firebase Dashboard. Aqui podemos encontrar um euro para acessar nosso aplicativo Bab. Haverá dois deles. Use o que você gosta mais ambos funcionarão. Firebase também mantém o controle de implantações e podemos reverter para qualquer registro de implantação no histórico de
lançamentos Vamos abrir o aplicativo para ver se ele realmente funciona. - Legal. Parece bom e muito rápido. No entanto, Logan do
Facebook falhará se alguém além de nós tentar entrar para corrigi-lo. Vamos ao Google e ao Time. Facebook para mortes, Clique no meu abs do que selecione aplicativo de bate-papo. Vá para configurações básicas para a política de privacidade. Euro Copy site Cuple e colado aqui do que rolar para a parte inferior. Clique em e plataforma e certifique-se de que você adicionou sua rapsódia. Clique em salvar Alterações do que ir para o painel e virou este que na parte superior para se certificar de que exibe a vida. E é isso. Muito bem, este foi o último vídeo desta secção. Na próxima seção, vamos falar sobre backend lareira personalizado com funções de nuvem. Vejo você lá.
145. Plano de projetos do Firebase: Olá. Esta seção é dedicada a notificações em tempo real e funções de nuvem. Notificações em tempo real são implementadas com mensagens em nuvem baseadas em fogo que exigem
retorno personalizado . E é por isso que usamos funções de nuvem. Para que possamos continuar, precisamos atualizar nosso projeto de corrida de fogo para a planta Blaze com
atualizações recentes de preços do firebase a partir de agora, chamadas funções exigem plano Blaze como o uso de alguns dos serviços de nuvem do Google que não são disponível no plano Platt Blaze livre é passado. Você vai de moto e isso não significa que devemos pagar. Todos esses serviços são dados com realmente generais. Pastor, confie em mim com as quotas dadas, você nunca vai aquecer a fronteira pagante, mas é totalmente com você. Por favor, leia mais sobre Blaze Plan na página de preços base fogo para operar para o plano Blaze. Ir para painel firebase, Clique em atualizar na parte inferior e selecione plano Blaze. Se você ainda não tem fonte de pagamento, Google irá pedir-lhe os detalhes do seu carro e depois disso atualizará o projeto para verificar qual plano? Cortando usos do projeto. Basta olhar para a parte inferior esquerda. Agora todos nos dizem que no próximo vídeo, vamos falar sobre funções de nuvem e arquiteturas de servidores menos. Vejo você lá
146. O que são sem servidor e containers?: Ei, vamos falar sobre menos servidor. Soa bem legal, certo? Para entender melhor o que é sem servidor. Vamos re sábio como o servidor normal funciona de volta é implantado servidores executando e aguardando conexões. Nada está errado aqui, mas aqui está uma pequena desvantagem. Nós não temos usuários, enquanto servidor continua a Ron e recursos de consumo. Não é muito benéfico que ele serviria a menos que um servidor implantado seja executado sob demanda. Ou é melhor dizer que o código é executado sob demanda em Lee quando é necessário. Se o acesso de ninguém na decodificação, ele não é executado. Na maioria das vezes, abordagem
sem servidor é apresentada. Servidor informal Últimas funções. Cada função é implantada separadamente e tem seu próprio contexto de execução. Quando a função é implantada, ele tem seu próprio Http, seu l que é usado para investigar a função. Seu L é como um gatilho para executar o código. Não há nenhum servidor real no final. Há apenas código que é executado sob demanda. Sob o capô, toda a magia é alimentada por contêineres portuários. Um contêiner é um pacote pequeno como exaltado fora Seja o que for colocado dentro com máquinas virtuais, todo
o sistema operacional é tão exaltado com contêineres em Lee. O conteúdo que é colocado dentro dele permite executar vários contêineres em um sistema operacional . Cada função implantada, com todo o seu código e dependências é colocada dentro de seu próprio contêiner que transa sob demanda quando a função é acionada. Mas os contêineres também devem ser hospedados e implantados. Samba direita Isso é controlado e gerenciado pelo provedor de nuvem. Não precisamos nos preocupar com isso. E como tudo é gerenciado para
nós, também não precisamos nos preocupar com dimensionamento e manutenção. Os militantes implantados serão dimensionados automaticamente com base em chamadas de número fora. Agora sabemos que cada servidor menos função é pedaço separado de código que é executado em Lee quando realmente usado uma função não está ciente de outra como somos capazes de compartilhar algum código através de várias funções. Por exemplo, todas as funções implantadas devem acessar alguma variável compartilhada ou outra função. Depende e provedor de nuvem com fogo. código de funções da Base Cloud é compartilhado no escopo global. Quais são as desvantagens que o principal é chamado de início quando o código não é executado por um tempo, que o recipiente funções vai para o sono. Quando alguém tenta acessar o contêiner de código gira e leva algum tempo. Isso é chamado de começo a frio. Depende de múltiplos fatores. Por exemplo, qual é o tamanho da decodificação para essa função? Ou quantas dependências atesta depois que um código é executado, o contêiner permanece no estado aquecido por um tempo e aguarda por solicitações subseqüentes. Isso significa que o começo a frio não ocorrerá. Mas depois de algum tempo, quando não há pedidos, recipiente irá dormir, e da próxima vez veremos o frio. Comece com o servidor Menos. O preço é avaliado com base em chamadas de número fora e em quanto tempo cada execução cobiçada. As funções da nuvem do Firebase têm acesso livre a milhões de invocações gratuitas por mês, e isso é incrível. Agora sabemos o que está servindo menos e quais são as funções de nuvem. Espero que tenha gostado. Vejo-te no próximo.
147. Mensagem de nuvem - como tudo conectado: Olá. Vamos falar sobre mensagens na nuvem do Firebase. O que é isso exatamente? O sistema de mensagens na nuvem nos permite arejar notificações em tempo real para os usuários. Se estivermos no site, podemos receber uma notificação pop-up do nada. Se o site e o navegador estiverem fechados, podemos obter notificações nativas do sistema operacional no celular. Será uma notificação como se fosse um aplicativo móvel real sob o capô, ele usa navegadores, Boucher, FBI e a principal desvantagem de ter suporte limitado e navegadores e alguns
sistemas operacionais . Está bem, deixa-me explicar o ciclo completo das mensagens da Firebase na nuvem. Portanto, cada usuário tem um token exclusivo que representa o dispositivo do usuário. Nós obtemos este token do usuário e armazená-lo dentro do banco de dados. Este token não deve estar disponível publicamente mais tarde. Fire Base usará esse token para enviar uma notificação ao dispositivo do usuário para receber notificações no dispositivo. Vamos montar um trabalhador de serviço. Como você se lembra. É um script intermediário que fica dentro do navegador. Trabalhadores colonos são frequentemente usados para realizar algumas tarefas em segundo plano. As notificações são um bom exemplo. Ele irá interceptar mensagens recebidas e usando navegadores. Bush ap I Ele irá exibir a notificação. De fato. Agora você sabe como funciona. No próximo vídeo, vamos chegar ao bode. Vejo-te isso
148. Armazenando dispositivos na base na base: Ei, neste vídeo, vamos obter token de dispositivo de usuários e armazená-lo no banco de dados. Mas antes de fazermos isso no vídeo anterior, quando implantamos nosso aplicativo, recebemos esse dinheiro de hospedagem e também modificamos fogo baseado em Jesus. Então, primeiro de tudo, vamos abrir e ser ignorados. E vamos adicionar ponto firebase fuller para obter ignore para garantir que não rastreamos esta pasta . Tudo bem, Bom. Agora vamos confirmar nossas alterações e digamos,
obter commit, obter commit, Implantar o aplicativo Perfect Now Eu já abri a documentação para mensagens em nuvem do firebase, e a partir daqui precisamos obter credenciais da Web. E estes são chave de identificação voluntária do servidor de aplicativos. Então esta é a chave insípida que precisamos para configurar o Firebase Cloud doméstico em primeiro lugar. Então vamos para o painel do que vamos para abordar as configurações e, em seguida, para o sistema
de mensagens na nuvem a partir daqui. Em configuração da Web, precisamos gerar novo par de chaves. Então, vamos clicar nesta parte inferior e esta é a nossa chave vazia que vamos usar. É público para que possamos compartilhá-lo. Quero dizer, não compartilhe, mas está disponível publicamente Agora vamos para a nossa aplicação. Vamos realmente executá-lo. E então vamos Oakland Firebase Doggy s em primeiro lugar. Então aqui vamos importar mensagens Firebase, e aqui na parte inferior. Vamos verificar se ele é suportado pelo navegador, para que possamos anti exportação const. Mensagens. Então vamos perguntar se Firebase morreu. As mensagens são suportadas. Então, se for, então vamos chamar o aplicativo de mensagens de ponto para obter a instância. Caso contrário, será dito que não, então, na parte inferior. Precisamos configurá-lo para usar essa chave vazia que geramos. Então vamos perguntar se temos suporte para mensagens. Então, se tivermos a instância, então vamos chamar mensagens, usar chave vazia pública. Você pode encontrar isso em sua documentação. Certo, então vamos copiar esta chave e colá-la aqui. Ok, bom. E eu preciso configurar um manipulador para nossas mensagens. Então deixe-me explicar. mensagens ou notificações estão disponíveis em dois tipos, primeiro plano e mensagens em segundo plano. Mensagens em segundo plano são aquelas mensagens que são manipuladas quando nossa guia ou navegador é fechado e mensagens em primeiro plano são aquelas que são visíveis quando estamos rolando o site, então mensagens em primeiro plano devem ser tratadas dentro do aplicativo. As mensagens em segundo plano são tratadas pelo service worker. Então aqui vamos chamar mensagens na mensagem e para conhecimento é mantê-lo como está. Dados do consulado. Então, essa assinatura, digamos, vai lidar com nossas mensagens de primeiro plano. Certo, digamos com e agora vamos decodificar para salvar o dispositivo do usuário no banco de dados. Então vamos abrir o contexto do perfil. Então este não é o lugar quando olhamos para o nosso usuário. Então aqui, precisamos gerenciá-lo. E se eu abrir novamente a documentação, eu posso ver que eu posso copiar este pedaço de código para obter token de registro atual. Então, na verdade, quer saber? Deixe-me copiar isso e vamos colar em algum lugar aqui no fundo. Mas primeiro, precisamos garantir se as mensagens existem. Então vamos verificar se as mensagens existem, que eu importei da base de fogo da MISC. Então, se esse for o caso, então eu vou acelerar esse código, e talvez você me deixe convertê-lo em um sumidouro aguarda o índice. Então deixe-me colocar um bloqueio de tentativa de captura aqui. Então eu vou colocar mensagens, pegar token. Então será Const Tokcan. Digamos que o token atual é igual a aguardar mensagens. Obter token e vamos convertido para a função de enfrentamento. Está bem, Perfeito. Então vamos verificar se o token atual existe. Vamos copiar tudo isso. Então, se esse símbolo atual existir, então vamos fazer algumas coisas. Nós não precisamos mesmo dele do que em caso de erro vamos exibir dentro do console e no nosso ocorreu. Ok, bom. Agora vamos fazer isso. Tudo isso. E aqui vamos nós. Agora precisamos armazenar esse token dentro do banco de dados. Para isso, podemos chamar longe formas de dados Dar gráfico eo lugar ou o caminho que vamos começar nossos tokens é igual a dois FC m tokens barra token I d e, em seguida, barra usuário i d. Assim, com estes abordagem, podemos facilmente consultar engasgar na parte de trás. E tudo bem, então ele vai ser FC m tokens. Então vamos para o token atual, e como uma criança, vamos derramar fora do usuário porta objeto. Eu d eu d. Desligado usuário atual. Ok. Perfeito. Agora rolando a documentação para baixo, posso ver que o token também pode ser atualizado, então também precisamos lidar com isso para isso. Vamos copiar este pedaço de código e colocá-lo ao lado deste bloco greve Hedge como este e este próprio token atualizar é uma assinatura. Então, isso significa que precisamos cancelar a assinatura dela no futuro para isso novamente. Aqui, Anti chop dentro de ti, o facto de o pobre Joe poder refrescar o meu submarino, está bem? E nós vamos derramar em token ou fresco para aquele terrível. E aqui na parte inferior, quando
terminarmos, vamos verificar se brinca e atualiza no submarino, então vamos chamar essa função dois meses depois e o mesmo celular faz na função de limpeza. Ok, bom. Agora o que precisamos fazer aqui, vamos também converter-nos a qualquer coisa. Função. Então aqui, vamos colocar um canto, e na verdade, a lógica será a mesma, então podemos facilmente copiá-lo e colocá-lo aqui assim. Ok, bom. Agora estamos prontos para ir, mas como diremos ao banco de dados para o caminho que não adicionamos às regras de segurança, precisamos modificá-las ligeiramente. Então vamos para o banco de dados, então vamos para as regras. E aqui, vamos adicionar uma nova entrada. Então deixe-me copiar o status do disco assim, então eu vou substituir o status por tokens FC M. Então vamos ter uma piada. E eu D e móvel permitir Ler nunca. Porque não queremos permitir que ninguém acesse nossos tokens. E para o direito Onley o usuário, que é atualmente Sinan é capaz de armazenar seu próprio token. Certo, então vamos verificar se o novo valor do ponto de dados. Então, se o usuário i d que nós escrevemos para este token, eu t igual a dois fora de você. Eu d,
ok. Bom. Agora vamos saborear e parece bom. Agora vamos para a nossa aplicação. Vamos refrescar. Certo, agora perfeito. Vamos abrir o conselho para ver se não temos avisos. Ok, nós temos o editor True. Foi toking, não
foi possível registrar o service worker padrão. Ok, então isso é bom. E porque ainda não temos nenhum trabalhador de serviço, temos essa entrada. Isso é bom, mas esse erro diz que funciona. Agora vamos cometer nossas mudanças. E no próximo vídeo, vamos configurar o service worker. Então, vamos derramar, pegar em tudo e vamos verificar que tipo de outros devem ser recebidos. Declaração inesperada do Conselho. Certo, isso é bom. Vamos nos comprometer. E digamos editar mensagens firebase e armazenar token de usuário estrangulamento no banco de dados. Perfeito. Vejo-te no próximo
149. Adição de trabalhador de serviços: Ei aí. Neste vídeo, continuaremos configurando mensagens na nuvem do firebase e configuraremos um service worker. Então eu já navegei até a documentação do firebase e, em seguida, escolhi mensagens recebidas. Então, nesta seção, eu posso ler e você pode ler mais sobre mensagens de primeiro plano e segundo plano, mas estamos interessados no arquivo do service worker. Então não vamos esquecer o nosso código e a primeira coisa que vamos fazer, mas realmente pegou as regras que criamos no vídeo anterior com tokens FC M. Então vamos copiar tudo isso,
em seguida, ir para banco de dados tolos Jason e Colar todos eles aqui agora sobre service worker. Então, como você pode ver, este é realmente o código do service worker. Vamos chamar de ser isso. E dentro da pasta Pública, vamos criar novo arquivo firebase serviço de mensagens Worker doggy s. Portanto, ele deve corresponder a este nome de arquivo. É muito importante porque este é o nome que será reconhecido pela base de fogo como decadência . Agora vamos colar tudo o que temos aqui e podemos realmente fazê-lo. Todos esses comentários assim, então não precisamos da mensagem. Incrível. E também, vamos desativar es fiapos para todo o arquivo. Ok, bom. Agora, para esses conflitos aqui, precisamos inicializar nosso conflito que inicializamos dentro de nossa aplicação. Então vamos abrir a base de fogo Dodgy. Sim. E vamos apenas copiar este objeto e colocá-lo aqui para que ele irá inicializar firebase sdk dentro do service worker. E também devemos garantir que a versão que importamos aqui deve corresponder à nossa versão sdk dentro do pacote Jason. Então vamos abri-lo. E aqui temos 7.15 agora vamos esperar no trabalhador de serviço, ele tem 7.15. Tudo bem. Agora vamos salvá-lo. E eu já cuido do laboratório. Agora vamos voltar para o APP. Deixe-me atualizá-lo agora, como podem ver dentro do conselho, não
tenho avisos, então vamos navegar até o nosso banco de dados. E como você pode ver agora eu tenho tokens FC m aqui. Se eu abri-lo, eu tenho este bastante longo usuário I d token e que eu tenho meu usuário i d e isso é realmente ele antes de nós confirmar nossas alterações porque nós usamos um novo service worker com
mensagens em nuvem firebase dentro. Na verdade, não precisamos de service worker criando app reagir. Por isso, aquilo que propus fazer no futuro, vamos precisar disso. host local é valioso? Então vamos copiá-lo daqui e colocá-lo dentro de ajudantes como este e vamos exportar a partir daqui . Agora vamos salvá-lo E vamos excluir serviço, arquivo de
trabalho e dentro após GS ou dentro de togs índice. Vamos excluir esses comentários. Não precisamos mais deles, e agora podemos fazer nossas mudanças. Então, novamente, vamos embarcar em tudo e depois nos comprometer. E digamos que, trabalhador
de serviço que disse Perfeito, te
vejo no próximo.
150. Configurar funções de nuvem e Node: Ei aí. Neste vídeo, vamos configurar funções de nuvem dentro de nosso projeto firebase. Vamos lá. Vamos voltar para o código V. Vamos abrir o terminal. E aqui só precisamos digitar base de fogo. Você precisa de funções. Em seguida, ele irá nos fazer algumas perguntas. Vamos bater. Sim. Então vamos escolher Javascript. Então quatro anos Lind, vamos selecionar. Sim, e vamos instalar todas as dependências. Ok, bom. Se olharmos dentro das funções, alguns arquivos foram criados para nós. Sim, Lynn RC com conflito já pré-definido. Não vamos mortificá-lo. Então temos que ignorar Index Dodgy s e empacotado Jason, Então índice de pontos gs em funções de nuvem é um ponto de entrada de togs índice. Arquivo RealAge para exportar funções de nuvem separadas que serão implantadas separadamente. Ok, dentro da bicicleta. É o Jason. Aqui podemos encontrar algumas dependências. Então sim, Lind e também firebase admin e funções. Estes dois pacotes nos permitem acessar base de fogo a partir de backend e também podemos encontrar alguns scripts. Definir aqui servir para realmente Ron funções emulador no ambiente local do que temos algo chamado Shell e é shell firebase para realmente testar nossas funções e também seguida, temos logs e outras coisas, como implantar e iniciar para iniciar script de início . Já que vamos testar nossas funções localmente, propus ao Ron servir em vez da Shell. Então vamos colocar isso para servir e vamos salvar nosso arquivo. E também porque vamos acessar nosso banco de dados localmente e pela base de fogo. Ele é reconhecido como um ambiente não confiável. Precisamos fornecer algum tipo de autenticação ou credencial, a fim de fazê-lo funcionar. Então, para isso, precisamos navegar de volta ao nosso painel. Então precisamos ir para as configurações do projeto e ir para as contas de serviço a partir daqui. Não precisamos baixar a nova chave privada. Então vamos criar um. Vai dar-nos um ficheiro do Jason. Vamos abri-lo e copiamos o conteúdo. Vamos voltar para o código. E aqui dentro funções, vamos criar nova conta de serviço de arquivo, faz Jason e vamos colocar tudo o que temos Koppett. Agora,
por favor, certifique-se de adicionar este arquivo para ser ignorado. Isto é muito importante. Então, aqui nós adicionamos conta de serviço que Jason, então este arquivo não deve estar disponível publicamente. Isto é apenas para nós, para o desenvolvimento local. Ok, bom. Agora, se abrirmos novamente as contas de serviço aqui podemos encontrar um pequeno trecho de código, então vamos copiá-lo e vamos abrir o ponto de índice Js. Então aqui temos funções no topo e funções firebase. Vamos colocá-lo assim. E vamos também pegar o administrador e substituir VARS com constante Good. Agora precisamos especificar um caminho de conta de serviço que é este e, em seguida, colocá-lo dentro, admin initialize em quando usamos funções de nuvem. Antes que possamos fazer qualquer coisa, precisamos inicializar firebase admin como deteriorado e para o desenvolvimento local, precisamos inicializá-lo assim, a fim de acessar os dados reais, a fim de acessar o
banco de dados riel . É basicamente isso. No entanto, há uma coisa importante para as funções de nuvem. Se abrirmos o pacote do Jason aqui, confinamos os motores. Nó oito especificar. A coisa é que as funções de nuvem do firebase são suportadas no Lee dois sem versões GS, oito
ou 10 e recentemente eles deixaram de suportar para a versão do nó oito completamente. Agora as funções da nuvem do firebase estão basicamente disponíveis sem versão SIG. Ted, isso pode ser um pequeno problema agora. Nós não usamos Js versão 12 e precisamos de alguma forma gerenciar nossas funções de nuvem com nota versão 10. Para isso, precisamos alternar entre diferentes versões conhecidas Jess. Para isso, precisamos não baixar software adicional, que é chamado de No Version manager. Este é um software que nos permite alternar entre diferentes versões desligadas. Nenhum GS em um comando. Certo, vamos ao Google. E, em seguida, vamos apenas digitar e VM que Vamos para anotar o gerenciador de versão no get hop. E este repositório está em lee para usuários Linux e Mac OS. Siga este tutorial e instale e VM em sua máquina. Se você vem de janelas para baixo, role para baixo para duas janelas parte E aqui nós confinamos inveja M para janelas e, em seguida, clique em download. Agora você vai acabar nesta página, em
seguida, clique em N V M. Configurar arquivo zip e, em seguida, instalar inveja M. Ok, Depois de ter inveja M instalado em sua máquina, vá para o seu terminal e, em seguida, basta chamar inveja M versão ou inveja em. Versão Dash. Está bem. E a versão VM depois disso, a fim de instalar No, apenas a versão 10. Deixe-me executar o meu comando e a lista M. Ele irá listar todas as minhas versões sem GS instaladas localmente. Então, para funções de nuvem, precisamos de alguns fora da 10ª versão. Então vamos chamar inveja M instalar e, em seguida, 10.20 ponto um. Após essa versão de nota, Manager irá instalar e principalmente tudo para você. Você não precisa se preocupar com nada, então para alternar entre diferentes versões desativadas. Sem GS enfraquecer, simplesmente digite e VM usada. Digamos 8 16 para. E agora estou usando esta versão fora da nota. E se eu digitar e VM usar 10.20 ponto um agora estou usando esta versão. É isto. É assim que podemos gerenciar diferentes versões fora. Não Gs, certifique-se de que você tem este instalado porque caso contrário, se você não tiver nenhuma versão 10 instalada localmente, não
poderemos executar suas funções localmente. Tudo bem, agora, para terminar este vídeo, vamos cometer nossas mudanças. Então vamos esquecer tudo. Em seguida, cometa e digamos, configure as funções da nuvem com inveja. M perfeito. Vejo-te no próximo
151. Fluxo de notificações no nosso aplicativo: Olá Neste vídeo, quero explicar rapidamente o fluxo para enviar uma notificação. Em primeiro lugar, nos dados, por favor. Para cada sala, haverá um outro campo chamado usuários do FC M. Será nas idéias do usuário Rafe que receberão notificações na parte de trás. E vamos criar uma função de nuvem que vai chamar a partir do nosso aplicativo de bate-papo como uma definição de administrador dois, juntamente com o pedido que enviaremos de poderoso nome e mensagem de notificação. Em seguida, usando Crew my D, vamos obter IDs de usuário que recebem notificações usando suas idéias. Vamos consultar seus tokens de dispositivo e, em seguida, enviar uma notificação usando os tokens do antes de
começar . Eu só quero salientar que existem três tipos diferentes de funções de nuvem. funções ingénuas a pedido e gatilhos a pedido têm o seu próprio euro enviar em um pedido. A utilização do euro é a única forma de aceder à função. Chamar um intestino Funções também têm o seu próprio neural, mas no cliente firebase como decadência, o que usamos no navegador, existe um método especial para chamar este tipo de função pelo seu nome, não por euro e também chamável funções automaticamente analisar e validar tokens JWT do usuário. Firebase usa tokens JWT para autorizar usuários, e nós não lidamos com eles diretamente. As funções de gatilho não têm seu próprio neural, e eles respondem em Lee dois eventos de documentos de banco de dados diferentes, como criação própria na atualização e Illit propriedade. Poderíamos especificar que cada vez que um documento é criado nesse caminho, esta função de nuvem será executado sempre. No nosso caso, só
precisamos de um tipo de funções crédulas, fáceis de acessar e usuário fora de seu protesto para nós. Agora, você tem uma idéia melhor do que vamos fazer. Vejo-te no próximo.
152. Criando função de nuvem FCM: Santificar. Neste vídeo, vamos criar nossa própria função lavada para enviar mensagens de notificação. Vamos lá. Primeiro de tudo, vamos abrir esses códigos do que vamos para funções, togs
índice e, vamos incomum, esta função de nuvem de dobra que já bastante encontrar para nós. Vamos salvar este arquivo. Em seguida, vamos abrir o terminal e navegar para a pasta Funções em pacotes e temos NPM executar script de
início. Então vamos executá-lo e vamos dar uma olhada no que vai acontecer? Então, em primeiro lugar, ele não vai diminuir todos os emuladores necessários para diferentes serviços fora da lareira, como AM um líder para funções. Isso é bom. Depois disso, você verá esse tipo de mensagem, e ele vai dizer que a primeira função http é inicializada e disponível nestes Ural e também temos este host local para 1000 funções. Então vamos copiar essa. Vamos para o navegador e vamos abrir este campo para verificar o que vai acontecer. Isso é como um painel onde controlamos quais serviços desenvolvemos localmente. Então agora temos apenas funções. Sou um líder e está disponível nesses portos, e se formos para registros, podemos ver isso. Agora temos uma função http inicializada para que possamos copiar este ano. E então podemos acessar essa função. E pela resposta, podemos ver olá da base de fogo. Isto é o que temos dentro desta função. A Defiant. Então é isso. Isso é o que nossa nuvem funciona. Mas agora, vamos parar o emulador. Nós não precisamos dele. E vamos também excluir esse tipo de função porque este é um duas vezes um e nós não precisamos dele. Mas antes de fazermos isso, eu só quero salientar que cada função que exportou do oci indexado sim, é tratada como uma função. Então, o que ele fará dentro das funções. Vamos criar uma nova pasta chamada “Ser C Inside”. Nós vamos derramar novo arquivo FC M cãozinho s Daqui, vamos exportar nossa função e, em seguida, vamos re-exportá-lo a partir daqui. Ok, então vamos mantê-lo como está. Talvez nomeemos essa função com antecedência. Digamos que mande o FC M. E, por enquanto, vamos comentar. Ok. Bom. Agora dentro do FC M. Vamos importar funções e administrador. E daqui, vamos exportar nossa primeira função. Vai nomeá-lo. Exportações exporta e fc M. Então precisamos chamar funções. Então precisamos derramar https, e então precisamos colocar em serviço. Então esta função que vem por padrão foi no tipo de solicitação de função que eles querem, mas vamos criar vai estar em chamada. Ok, então isso na função fria recebe dois argumentos. Então, se no entanto, podemos ver dados e contatos, Então dados são esses dados que passamos junto com solicitação e podemos acessá-lo dentro do contexto contém algumas informações de contexto, como informações do usuário e usuário JWT Token. Vá. Agora. Desde que exportamos esta função do arquivo do FC M Dodgy s, podemos importar dentro togs índice. Então aqui podemos digitar Const. Deixe-me digitar f igual exigir do que vamos referenciar pasta fonte e, em seguida, f c M g s. Então, a partir da disfunção, nós exporta e FC M Agora precisamos destruí-lo. E, em seguida, a partir deste índice togs, nós vamos voltar a exportá-lo assim. Então as exportações areia FC M vai ser enviado FC M função que obtemos a partir do arquivo FC M. Tudo bem. E temos este aviso dizendo esperado uma linha vazia. Ok, deixe-me colocar assim. Agora precisamos escrever nossa função. Ok, então primeiro de tudo, precisamos verificar se nosso usuário está presente. Se a pessoa que tenta acessar esta função é realmente autenticada, já
temos usuário analisado e validado por este tipo de função, que é culpável. Agora precisamos apenas verificar se o usuário é realmente analisado. Então, se o usuário não é analisado, isso significa que o usuário não está presente. Ok, para isso podemos criar uma função auxiliar aqui que vamos nomear check se off check. Se autenticado dentro desta função, vamos passar o contexto, e então vamos chamá-lo de nossa função assim. Verifique se desligou e depois passaremos o contexto. E a partir deste cheque se desligado, faremos o próximo. Se o ponto de contexto auth ele tem fora do objeto dentro. Então, se eu derramar contexto e, em seguida, dar aqui confinado fora. Então, se este contexto não está desligado é indefinido. Então, se não temos nenhum objeto fora, então vamos lançar novas funções. Dar Https. Erro http Então este é Paschall. Digamos que sintaxe que dará um erro para recusar nossa razão será autenticado e mensagem vai ser. Você tem que estar conectado. Ok, bom. Aqui estamos feitos. Nosso próximo passo é acessar os dados que obtemos a partir do pedido. Ele está disponível sob este objeto de dados. Por aqui. Já está analisado para nós. Então, a partir deste objeto, podemos destruir os próximos valores, vamos lixar o Chad. Eu d, em seguida, título fora da sala ou deixa o título da mensagem. E então também, vamos enviar mensagem. Ok, bom. Agora precisamos de obter os dados da sala usando esta cadeira. Ok, apartir daqui
,
vamos ter uma foto do quarto. Ok, apartir daqui
, partir daqui
, E agora precisamos acessar. Nosso banco de dados pode ser acessado a partir do ambiente de servidor usando firebase admin como decayed. Então aqui no topo, vamos colocar um novo banco de dados viável, e então vamos chamar o banco de dados administrativo. Usando banco de dados do ambiente de servidor é muito semelhante à forma como acessá-lo de recusado. Ok, então agora podemos chamar o banco de dados, então nós colocamos áspero, e agora nós precisamos acessar de dados. Então nós passamos por salas que sala de corte I D. que vai ser chat, i d. No nosso caso, ele retorna a promessa. É por isso que podemos guardar aqui. E também vamos colocar uma pia para torná-la válida. Então, depois de termos referência, nós chamamos uma vez e, em seguida, nós mau valor. Agora temos o instantâneo do quarto, então podemos fazer a verificação simples se o quarto Snap Shore existe. Então, se não existir, então vamos devolver False. Ok. A partir desta função, ele irá enviar apenas solicitação falsa de volta para o cliente. Quando vamos chamar essa função, então precisamos obter dados da sala para obter um ID de usuário. Então, para isso, vamos os dados do tribunal e, em seguida, vamos gravar a partir do valor da porta instantânea. Agora, precisamos verificar se nosso usuário atual é um administrador. Então nós podemos realmente enviar a mensagem porque esta função pode ser chamada por algum usuário dentro do Chad. Mas este usuário não é um administrador
e, portanto, este usuário não é capaz de enviar a mensagem. Ok para isso, precisamos verificar contra o usuário admite então primeiro, Como você se lembra, todos os nossos uma corrida nos trabalhos são armazenados são objetos, então precisamos transformá-los em matrizes javascript normais para que Inside ajudantes. Já temos disfunção transformada em matriz. Vamos copiá-lo daqui e colocá-lo aqui no fundo. Agora podemos criar uma função auxiliar para verificar se o usuário realmente pode enviar a mensagem. Podemos criar uma nova função na parte inferior novamente, e vamos nomeá-la. Verifique se permitido. E novamente ele receberá contexto. E também receberá o chat admite. Ok. E aqui vamos fazer quase a mesma verificação. Então, se não, digamos Chad, adicionar Mons cão inclui contexto off, e então você i d. Então, se o usuário que está tentando acessar esta função de nuvem está na lista fora de Chad Adnan. Então, se este não for o caso, então novamente nós vamos enviar exatamente a mesma mensagem para cá. E talvez digamos acesso restrito. Tudo bem, Bom. Agora podemos chamar essa função aqui. Verifique se permitido, vamos passar contexto dentro, juntamente com transformar para matriz dados sala admite. Certo, perfeito. Nosso próximo passo é obter ideias reais de usuários que receberão notificações. Por isso. Vamos colocar novos e valiosos usuários do FC M. E novamente, vamos chamar transformar em matriz, e vamos colocar dados de sala usuários FC M. Ok, agora vamos obter todos os tokens de usuário. Por isso. Propus criar novamente uma função auxiliar que chamaremos de obter tokens de usuário. Então vamos rolar para o fundo. E aqui vamos criar uma nova função, obter tokens de usuário para que ele receberá o usuário I D. E ele receberá todos os tokens de usuário. Então vamos chamar nossas formas de dados, e receberemos tokens de usuário. Snapshot. Ok, então vai ser uma função inocente e a lógica será a próxima. Então vamos chamar o árbitro do banco de dados. Então vamos fazer referência aos tokens FC M. Então vamos ordenar por valor, e vamos colocar igual ao usuário I d. e, em seguida, para obter tokens antigos, vamos chamar valor uma vez. Está bem, Perfeito. E não se esqueça de esperar no início. Agora temos camisa de encaixe de token de usuário. Então, se não temos tokens de usuário, snap short tem Crianças. Então, aqui nós verificamos se realmente este usuário em particular tem algum token. Se este usuário não tiver nenhum Filhos, isso significa que este usuário não tem nenhum token. Então podemos simplesmente devolver um vazio, Eric. Então, se o usuário tem tokens, então chamamos chaves de ponto de objeto e, em seguida, token de usuário valor de ponto instantâneo. Porque, como você se lembra, nós armazenamos nosso aumento de A nos caminhos-de-ferro como objetos. E ao chamar este objeto de chaves, obtemos os tokens de usuário reais. Ok, bom. Agora podemos chamar isso de obter tokens de usuário da nossa função de nuvem e para o pai, porque precisamos obter tokens de usuário para vários usuários precisamos usar Promise que tudo para torná-lo o mais otimizado possível. Ok para isso Aqui, vamos criar um novo usuário valioso. Fichas, promessas. E o que faremos. Vamos mapear todos os usuários do FC M. Vamos mapeá-lo. Então, cada usuário i d vai ser mapeado para obter tokens de usuário prometidos. E dentro dele vai ter este usuário eu d. Ok, bom. Agora vamos receber o nosso resultado. Ou digamos que vamos receber o resultado de tokens de usuário e vamos chamar, aguardar promessa. Nem todos os tokens de usuário promete, mas a coisa é que a promessa de que todos nos retorna uma matriz fora de resultados como esse e nossos tokens de
usuário promete, então cada promessa de tokens de usuário nos retorna uma matriz fora de tokens de usuário. Então, desta forma, vamos acabar com matriz aninhada assim. Então, para o primeiro usuário, teremos esses tokens. Então, por segundo, podemos obter estes e assim um e assim por diante. Então, para evitar isso, precisamos achatar nosso Eric. Para isso, podemos chamar ponto reduzir método disponível em uma corrida e achatar a área. Ok. Para isso, vamos chamar o resultado de tokens de usuário, em seguida, reduzido, para que ele receberá uma função de retorno de chamada. E o segundo argumento é o valor inicial. Então o poço inicial vai ser um array vazio. E este uso de doutrina primeiro é o valor acumulador, que vai ser, digamos, acumulado, Filkins. E o segundo será o valor atual, que é tokens de usuário. Portanto, esta função será executada para cada token de usuário para cada elemento. OK, e aqui vamos simplesmente fundir. Estes dois apagam usando o operador de propagação. Então vamos chamar tokens de acumulador,
mais tokens de usuário. Assim, desta forma, vamos acabar com um plano e matriz onde cada token como é um
valor normal . Está bem, vai agora. Vamos seguir em frente, então vamos verificar se o comprimento do ponto tokens é igual a zero que retornará a partir desta função porque não temos nenhum token para enviar dois. E como a questão é que temos fichas, como somos capazes de enviar nossas mensagens para que possamos navegar para fogo por sua documentação. Então este é o que eu tenho de vídeos anteriores. Mas se eu ir para o ambiente de servidor à esquerda e, em seguida, criar solicitações enviadas aqui, você pode encontrar várias maneiras. Como posso enviar uma mensagem para especificar o dispositivo? No entanto, precisamos apenas de um que é enviado mensagens para vários dispositivos porque temos vários tokens e temos uma mensagem para enviar. Então deixe-me copiar a mensagem, na verdade, e eu vou colocá-la aqui, e eu vou chamá-la de mensagem F C M. Então eu estava dados não vai se parecer com isso porque cada mensagem também pode ter
estrutura diferente . Ele pode ter este tipo de objeto com tópico de dados e tokens têm sempre Este é Onley para notificações
personalizadas. Não precisamos de nada personalizado. Precisamos de uma notificação normal para isso. Precisamos modificar um pouco este objeto. Então, em vez de dados, vamos objeto de notificação ruim dentro. E esse objeto de notificação tem duas chaves, que é título e também corpo, que é a mensagem de notificação real. Então, para o corpo, vamos ver mensagem pacificar que recebemos do objeto de dados dentro desta função de nuvem. Então vamos colocar a mensagem. E para o título, podemos derramar o nosso título personalizado, que vai ser intitulado que enviamos com pedidos e também nome do quarto. Ok, então vamos ser o título de quarto pobre. Então vamos colocar o título e, em seguida, do nome da porta de dados. Então, desta forma, teremos título e do nome ao lado dele. Mas vamos colocar talvez o nome do quarto em atenuações dos pais para que pareça mais estético. Está bem, vai lá. Agora vamos dar uma olhada em como somos capazes de enviar isso. Podemos usar mensagens ponto admin feito, disse multicast, e depois mensagem. Ok, bom. Então precisamos usar mensagens de ponto admin. Vamos criar disponível aqui chamado Messaging on. Vamos ligar para as mensagens do administrador. Ok. Perfeito. Agora podemos copiar esse código. Deixe-me copiar apenas a primeira linha porque não vamos usar as promessas no Texas. Vamos usar um pensar longe. Então deixe-me ligar para mensagens administrativas const. Eu vou substituí-lo por mensagens, então enviar multi cast e nós vamos enviar mensagem FC M, e nós vamos colocá-lo em um verdadeiro, que chamado Batch responde, e então vamos esperar este comando. Ok, bom. Agora, o problema é que os tokens podem ser inválidos ou os tokens podem expirar porque, como você se lembra, no token de recusa pode ser atualizado. Assim, quando o token é atualizado, o token anterior não é mais válido. Então este é o caso quando falhamos tokens. Então, podemos realmente usar esse trecho de código para detectar quais tokens estão falhando, e então podemos entregá-los do banco de dados. Deixe-me copiar este trecho de código, e eu posso chamá-lo assim, então teremos muitas respostas e verificamos se muito responde. Contagem de falhas é maior que zero do que para cada resposta scones amanteigados. Analisamos as respostas e verificamos se as nossas respostas não foram bem-sucedidas. Então este é o caso. Todos os tokens com falha foram enviados para essa taxa de tokens com falha. No entanto, queremos fazer alguma coisa com eles. Certo? Queremos limpar nosso banco de dados também. Para isso, vamos puxar esses tokens falhados aqui para o topo, e faremos a próxima coisa. Então, atualizaremos nossos tokens falhados. Com este empurrão dentro, removeremos esta fechadura do cônsul. E agora que todos nós temos tokens falhados, nós podemos realmente chamar nossos dados maneiras até que todos esses tokens aqui no final, nós vamos criar um novo array fora de promessas que vamos executar com o ponto de promessa tudo novamente porque nós podemos até que vários tokens do banco de dados. Para isso, podemos criar remover promessas valiosas. E vamos mapear cada token falhado para prometer assim fichas falhadas mapa ponto. Então teremos token, e vamos chamar o banco de dados Dot Rascunho. Então vamos chamar o FC M Jokinen do que Tokcan e depois a porta foi removida. Está bem, Perfeito. Assim, desta forma, vamos acabar com um raio fora, remover promessas, e no final fora de nossa função de nuvem, podemos chamar retorno promessa pensamento tudo e vamos derramá-lo de promessas e, em seguida, no caso fora de qualquer erro que podemos usar realmente ponto pegar Syntex aqui em vez de um pensar esperar. Porque esta é a nossa última operação e parece mais legível neste caso. Então, no caso de qualquer outro, vamos retornar mensagem de ponto de erro. Está bem, Perfeito. Então é isso. Esta é a nossa função, e é assim que vamos gerenciá-la. Acho que é isso para este vídeo. E no próximo vídeo, vamos começar a atualizar nosso cliente. Vamos testar essa função e o que eu propus fazer. Como você pode ver nos arquivos. Aqui, temos você I d.
Bach. Vamos adicionar este arquivo para ser ignorado. Você eu ou talvez vamos adicionar todos os arquivos de aparência para ser ignorado. Não precisamos deles. Está bem, fixe. E temos este aviso dizendo que se espera retornar ao valor. Ok, talvez nós possamos realmente atualizar o nosso fiapo sim para que possamos colocar um retorno
consistente e consistente seria zero. Ok. E parece que já temos um algures aqui. Vamos colocar em zero. E vamos entregá-lo aqui para evitar este tipo de aviso dentro do nosso arquivo e também para o Islã , Darcy, porque temos vários arquivos de criação dentro do nosso projeto. Um na pasta raiz e outro aqui. Também queremos ter certeza de que adicionamos opção rota é igual a dois. Verdadeiro. Então agora ele é reconhecido por decodificação. Certo, perfeito. Então, por enquanto, estamos acabados. Vamos cometer nossas mudanças. Então nunca vamos voltar para a pasta raiz. Em seguida, vamos chamar, obter tudo e, em seguida, obter commit e digamos editar função de nuvem para enviar mensagens
FC M. obter tudo e, em seguida, obter commit e digamos editar função de nuvem para enviar mensagens
FC M. Perfeito. Vejo você na próxima.
153. Correção de função na nuvem: Ei aí. No vídeo anterior, quando criamos enviou função FC M Cloud, Eu fiz alguns erros ortográficos que eu quero corrigir neste vídeo. O primeiro erro está subjacente aos dados da sala. Queremos obter os dados do valor do ponto de instantâneo da sala, então vamos corrigi-lo. Teoh quarto instantâneo valor ponto,
em seguida, o segundo erro está dentro de usuários de meio cm. Queremos transformar nossos dados de usuários do DAR FC M em vez de usuário do FC M. Em seguida, se nós rolar para baixo para FC um objeto mensagem aqui. Usamos tokens de registro, e esse erro vem do ritmo de cópia da documentação do firebase. Então vamos removê-lo e vamos colocar tokens e o mesmo celular fazer dentro tokens de falha Não empurre porque queremos ter certeza de que obtemos tokens de nossos tokens, um estupro. Então, se descermos, o último será. Você tem que ser registrado e é isso. Tudo o resto parece bom. Agora. Vamos salvar o arquivo e confirmar nossas alterações. Vamos esquecer tudo,
em seguida, obter commit e digamos corrigir erros ortográficos. CEO perfeito no próximo
154. Enviando e exibindo notificações usando funções de nuvem: Ei aí. Neste vídeo, vamos trabalhar com clientes e vamos criar uma janela modelo a partir da qual vamos enviar uma solicitação para nossa função de nuvem e, em seguida, enviar uma notificação para Absi. Usuários. Vamos, vamos voltar para o código B. E primeiro, vamos abrir fogo Base Duchy s e vamos importar pacote de funções. Então, no topo, eu vou derramar funções de barra de firebase de importação. Agora vamos saudar uma nova instância. Então exportar funções const app dar funções. E quando ele abriu, Parenti disse que você pode ver uma região aqui. A coisa com funções de nuvem que eles estão disponíveis em várias regiões por padrão. Eles estão disponíveis na região Leste
dos EUA. Para os usuários da Europa, isso não é ótimo. É por isso que precisamos mudar a região fora de nossa função. Para isso, vamos navegar para FC M Dodgy s no lugar onde criamos essa função. E dentro desta definição, vamos adicionar outra cadeia fora de uma região e dentro bolha especificado que esta função será executado na Europa Oeste três região. Você pode especificar qualquer região que você gosta. OK, então Europa Oeste 3 E agora, quando
inicializarmos esta instância, precisamos passar pela Europa Oeste 3 para que funcione. E também quando vamos usar esta instância de funções dentro do nosso cliente, ele vai tentar acessar a função de nuvem rial que já está implantada. Mas para o desenvolvimento local, isso não é bom. É por isso que precisamos aqui na verificação inferior Se estamos atualmente dentro do desenvolvimento local , então vamos usar funções. Amma mais tarde que executamos com MP Enron, iniciar dentro da pasta Funções. Então, aqui, se vamos verificar se é o host local e é o host local anteriormente em vídeos Nós
exportamos partir daqui nós extraímos Este é o host local valioso do arquivo de serviço criado pelo aplicativo
Creek React e agora vamos usá-lo. Certo, então é o anfitrião local. Vamos importá-lo. Então, se este for o caso, então vamos dizer funções, usar funções. EMLeader e precisamos de especificar a Europa para isso. Vamos para a pasta Funções dentro do nosso terminal. E aqui vamos brincar e o PM Ron começar e vamos ver a saída. Tudo bem. Como você pode ver, nosso emulador de funções está sendo executado no host local 5001. Então precisamos especificar aqui http do que host local e 5001. Tudo bem agora, estamos todos prontos com os nossos decaídos. Agora vamos criar o Moto real. Então vamos para a janela de bate-papo Top. E dentro desta pasta vamos criar qualquer arquivo que vamos nomear enviado FC M Bt em Moto Gs. E, na verdade, vamos copiar e colar o código de Vamos navegar para criar o quarto Beat e Moto, então vamos chamar de ser tudo isso e colocá-lo aqui. Agora vamos começar a substituir as coisas. Então, primeiro de tudo, vamos renomeá-lo para enviar FC M Bt e modelo e vamos realmente usar este componente dentro togs
índice dentro da pasta superior. Então aqui, em vez de fazer isso, vamos perguntar se nosso usuário é admin,
então, por favor, mostre-nos. Mande FC M Bt e Moto. Tudo bem, Bom. Agora vamos começar a substituir o componente. Primeiro, vamos verificar o nosso motile para o nosso formulário, para não termos nome e descrição. Teremos título e mensagem que enviaremos para a nossa função de nuvem para título e mensagem e é necessário. Vamos dizer que o título é obrigatório e o corpo da mensagem é necessário. Ok, bom. Agora vamos excluir esta importação do que o nosso formulário inicial vai ser intitulado e mensagem agora vamos importar usar estado motile novamente. Tudo bem, então temos formulário. O valor está carregando para ele. Rough em submeter. Certo, vamos mudar um pouco. Então, na verdade, vamos excluir essa parte e mantê-la assim. Agora, aqui, dentro do Js seis. Vamos remover isto, Steve completamente. Vamos remover este nome de classe, e vamos deixá-lo como um fragmento de reação. Então, para botão, vamos especificar aparência fora primário e tamanho vai ser extra pequeno do que
não vai ser um componente de bloco e cor. Vamos manter a cor padrão. Por isso, para que eu possa, vamos especificar que eu cumpri. Elenco e vamos dizer transmissão mensagem em vez de enviado FC M. Vamos ser um pouco mais criativo. Então, para modelo, tudo bem. Vamos alterar o título para enviar notificação aos usuários da sala Teoh do que para este formulário. Parece bom para o grupo de formulários. Vamos mudá-lo. Teoh Título nome de controle de formulário vai ser título e espaços reservados vai ser inserir título da
mensagem de quatro descrição. Vamos mudar para mensagem novamente. Vai ser um componente de área de texto do nosso nome vai ser mensagem. Este nome deve corresponder à nossa chave de estado, que é título e mensagem. Tudo bem,
então, por favor, Holder deve ser algo como e a mensagem de notificação. Ok, bom. E por este botão na parte inferior. Então aparência, primário no clique em enviar bloco. Está bem, parece bom. Agora, vamos apenas mudar o texto para publicar uma mensagem assim. Ok, bom. Agora vamos dar uma olhada no topo. Temos alerta desnecessário e também uma importação de firebase necessária. Vamos dizer com vamos voltar para o Chade. E agora temos essa janela moral, então digite um título e uma mensagem. Tudo bem, agora vamos definir a funcionalidade. Então, o que vai acontecer no Submeter? Precisamos enviar um pedido para a nossa função de nuvem. E como você se lembra, nossa função de nuvem é uma função chamável, e usamos funções como deterioradas. É por isso que vai ser tão fácil de fazer. Então vamos colocar o bloqueio kitsch aqui. Vamos colocar de lado está carregando para o topo assim dentro bloco kitsch banal, vamos fazer a próxima coisa Primeiro, vamos criar qualquer valioso enviado FC M e, em seguida, vamos chamar funções como deterioradas que importamos de Firebase Dodgy S. Então vamos chamar https ingênuo. E aqui precisamos especificar o nome da função que queremos chamar, então isso é muito importante. Então dentro togs índice que exportamos enviar função de nuvem FC M. Este é o seu nome. Tudo bem, então vamos copiá-lo. E aqui vamos especificar que vamos chamar enviado FC M função Nuvem. Este método https crédulo, devolve-nos e você função que precisamos chamar, a fim de realmente enviar uma solicitação para a função de
nuvem. Tudo bem, este não é o pedido em si. Então, agora precisamos chamar ou invocar comeu areia FC M com dados que queremos passar para a função de
nuvem. E então esses dados estarão disponíveis aqui sob esses dados disponíveis. Então o que vamos fazer, vamos chamar um peso do que enviado FC M. e dentro vamos passar chat I d. Como você se lembra, precisamos receber Chad I d título e mensagem. Então, ideia
Chet, precisamos primeiro pegá-la. Então vamos colocar aqui e os melhores programas Char i. D. D.
Hughes. OK, Bom. Então nós verificamos I d e também precisamos enviar título e mensagem, que é o nosso valor de formulário. Então podemos simplesmente espalhá-lo assim dentro deste objeto, e agora ele vai enviar o pedido. Então, no final, teremos dito está carregando tais bagatelas. Em seguida, vamos chamar valor de formulário sat para o valor inicial. Então inicial para e também vamos fechar esta janela do motor. Então, no caso de qualquer alerta ou em caso de qualquer outro, vamos chamar alerta do que na nossa e, em seguida, nunca encaixar mensagem com a idéia Não. Sete segundos. E também em caso de sucesso, vamos especificar informações de alerta e vamos dizer notificação. O feijão enviou bem? Parece bastante incrível. Agora vamos dar uma olhada, como eu posso ver aqui, eu devo movê-lo para o topo. Tudo bem, vamos navegar. Vamos para a mensagem de transmissão. Vamos especificar algo super e publicar. Mensagem e notificação foram enviadas. Agora vamos dar uma olhada. Se abrirmos o nosso terminal, podemos ver que dentro do nosso terminal direito onde executamos a função de nuvem, podemos ver que a execução inicial terminou a execução, então ele realmente funciona. Agora vamos dar uma olhada dentro do nosso conselho. Não vemos nada. E também talvez vamos tentar enviá-lo mais uma vez para ver o que vai acontecer. E vamos abrir a rede. Então eu disse a mensagem. Em seguida, você pode ver que o pedido está sendo enviado para o Host Chat local. Web up Europa foi três Sand FC um, eu
já vi que o resultado é falso. E isso ocorre porque, como você se lembra, dentro de nossa função de nuvem, verificamos os usuários do FC M de dados de sala. Mas neste momento, dentro do nosso banco de dados, se
abrirmos nossos quartos, não temos usuários FC M ainda. Precisamos mudá-lo. Então vamos navegar para criar sala Bt e Moto e ouvir o que vamos especificar. Então, para admite, vamos usar também o usuário atual seu i d. Mas também, nós vamos especificar FC um usuários. O primeiro administrador. O criador fora desta sala também receberá uma notificação por padrão. Então vamos copiá-lo assim. Digamos que estamos e agora precisamos modificar o grupo existente, mas que vamos realmente primeiro copiar nosso usuário i d.
daqui. Em seguida, vamos clicar neste sinal de mais e digamos que os usuários do FC M. Então, mais uma vez, sinal de adição. Vamos adicionar nosso próprio usuário. E depois para o valor. Vamos pela verdade. Em seguida, adicionamos esse valor. Agora, vamos tentar transmitir a mensagem mais uma vez, então vou dizer algo estúpido. Ok? A notificação foi enviada. Se eu abri meu cônsul agora eu posso ver que eu recebo um novo registro do cônsul, que vem do Firebase Dodgy s. e se eu abrir este arquivo, eu posso ver que ele vem desta mensagem na mensagem. Então eu tenho de notificação, eu tenho corpo e título. Agora, a única coisa que eu preciso fazer aqui é realmente exibir esta notificação de forma mais
amigável . Espere. Bem, isso vai ser muito fácil de fazer com brinde ou componente de notificação que vem do nosso terno. O que vamos fazer, vamos importar notificação como brinde do nosso terno. Por quê? Estou usando aqui. Notificação torrou em não notificação porque a notificação também está disponível como
valioso global dentro do objeto janela dentro do navegador. Então pode ser confuso e podemos fazer alguma coisa. Então, só para ter certeza de que usamos um componente personalizado, nós o nomeamos dosed. Então aqui dentro na mensagem. Nós vamos servir algo como, como você se lembra, nós temos notificação. Objeto dentro, para que possamos destruí-lo daqui. Notificação. E então vamos ligar novamente vamos destruir o chur desta vez do título da notificação e corpo. Agora temos essas duas chaves e vamos ligar para a porta torrada em quatro. Em seguida, vamos derramar descrição título e descrição vai ser corpo e velho, então duração zero. Então o que ele vai fazer, ele vai cortejar e você componente um componente de notificação do nosso queimado com este título com este corpo, que é a descrição. Mantenha que precisamos passar por esta informação e, em seguida, a duração é definida como zero, modo que nunca vai fechar por si só. Precisamos fechar manualmente esta notificação. Tudo bem, então agora vamos saborear e dar uma olhada. Então, se eu colocar algo como um baixo e, em seguida, este é o corpo e publicou nova mensagem Agora eu tenho esta notificação e é isso. No entanto, há mais uma coisa legal nisso. Se eu clicar em algo como esta mensagem publicada e quando eu clicar neste botão e , em seguida, alternar rapidamente entre toques. Agora vou receber esta notificação. Muito legal, certo? Então é isso. E é assim que vai funcionar. E todos os usuários inscritos nesta mensagem de transmissão os receberão em seus dispositivos. Ou é PC ou dispositivo móvel ou qualquer dispositivo para usar. Mas isso é o que vamos gerenciar no próximo vídeo. Por enquanto, terminamos aqui. Vamos cometer nossas mudanças. Vamos abrir o nosso terminal. Aqui está uma coisa boa. Ele nos dá aviso Firebase dizendo que usando um índice não especificado. Então vamos realmente adicionar, e você indexar para nossas regras de banco de dados. Então vamos abri-lo. E, como você pode ver, considere adicionar índice no valor em tokens FC M. Então vamos para tokens FC M. Então vamos adicionar índice. Então vamos copiar de algum lugar e colocá-lo aqui e Índice em vai ser valor de ponto. OK, então agora vamos publicar essas mudanças. Vamos copiar todos eles. Vamos navegar para as regras do banco de dados, Jason, e vamos substituí-las assim. Ok, olha, marcou. Agora vamos cometer nossas mudanças. Finalmente. Então deixe-me parar com tudo, então eu vou colocar pegar em tudo e então me comprometer. E então eu vou dizer, gerenciar FC M da planta chamada função nuvem e enviou FC M Perfeito. Vejo-te no próximo.
155. Gerenciando usuários da FCM: Olá. Neste vídeo, vamos criar uma nova janela modelo. Nunca perguntará aos usuários se eles querem receber notificações ou não. Vamos lá. Vamos navegar de volta para o código e em Bate-papo Window Top pasta. Vamos criar um novo arquivo. Pergunte FC M Bt e modelo. Vamos completar este componente. Será coberto com o ato Frackman. E como um gatilho, vamos servir o botão Aiken para Aiken. Nós vamos especificar que eu posso componente e para eu posso componente vai citar. Posso citar o podcast. Este I can Button também terá tamanho de colarinho azul vai ser pequeno e também vai ser um círculo. Vamos salvá-lo. Vamos navegar até Index Duchy Sim, dentro da pasta superior e vamos usar este componente dentro desta barra de botões logo antes de uma praia de
Detroit e Robert. Vamos perguntar ao FC M Beach em Moto. Vamos dizer esperar e vamos dar uma olhada Agora, Como você pode ver, Eu tenho esta marca quebrada no topo, e isso é porque se abrirmos edição quarto Beach introdução Burr foram para cima no elemento dif. Vamos removê-lo e vamos manter o fragmento de reagir. Agora, se dermos uma olhada. Tudo está bem alinhado. Perfeito. Agora vamos continuar a construir o nosso perguntar FC e batido e Moto. Então vamos definir uma janela de motel aqui. Dentro, teremos cabeça mortal do que corpo e rodapé. Deixe-me especificar todos eles. Então dentro da Heather, teremos o título dos pontos mortais e as pessoas dizem que não são férias de chá. Permissão. Ok, bom. Agora, a
fim de exibir algo dentro do corpo, precisamos saber se nosso usuário atual já está recebendo mensagens do FC M. Para isso, precisamos derramar algum outro valor dentro do nosso contexto. Vamos navegar até o Chad Togs. Então esta é Page onde passamos alguns dados de contexto sobre nossa sala atual. Aqui podemos obter nossos usuários FC M, Então vamos pobres usuários FC M valiosos. Em seguida, vamos chamar transformar para matriz do que os usuários atuais sala FC M. Agora precisamos pegar nosso Bullen. Então vamos criar está recebendo FC M e vamos perguntar se FC abusadores matriz inclui US
usuário atual . Seu passado condenável. Isto está recebendo FC e Bullen para a nossa corrente do contexto. Agora vamos salvá-lo e dentro perguntar FC M Entre Moto, vamos começar está recebendo FC M de usar gancho sala atual. Certo, perfeito. Mas para seletor, vamos especificar o valor está recebendo FC M Good. Agora, para modelo, precisamos usar o estado mortal. Então vamos usar este gancho de estado modelo e você vai ter, como sempre, está aberto, fechado e aberto. Então, para janela mortal, nós vamos especificar o show propriedade que vai ser aberto no esconderijo. Você vai estar perto. E também vamos especificar outros adereços que não usamos antes, como tamanho. Vamos especificar extra pequeno e também pano de fundo vai ser estático. Tudo bem, agora vamos realmente derramar nossa renderização condicional por dentro, mas antes deixe-me resolver rapidamente este assunto e aqui também, e nós não precisamos disso. Então, dentro do rodapé para evitar esta linha vermelha para um delicioso botão put com texto alto e dentro do corpo colocará renderização condicional. Então vamos perguntar se está recebendo FC M. Então vamos colocar um elemento diff com o nome da classe fora do centro de texto. E dentro deste Dave, vamos colocar eu vir com o nome da classe fora do texto verde e margem inferior três, então eu posso nomear vai ser círculo de verificação e tamanho vai ser cinco vezes grande. E ao lado disso, eu posso Nós forneceremos o título H seis com texto. Você está inscrito para transmitir mensagens enviadas por ad Mons fora desta sala. Tudo bem, Bom. Agora, se não estamos assinando mensagens,
em seguida, vamos exibir outro ao vivo novamente com o nome da classe fora do centro de texto desta vez irá exibir outro ícone com classe. Nome fora do texto Azul e margem inferior três também. Então eu posso nomear vai ser questionado. Círculo e tamanho novamente cinco vezes grande. Agora, ao lado deste Aiken novamente, h seis título. E você quer assinar minhas mensagens enviadas por ad mons fora desta sala? Ok, bom. Ao lado desta renderização condicional, vamos derramar outro texto. Então vamos colocar tag p e classe. Nome vai ser margem top dois, e vamos dizer para receber notificações, certifique-se de não permitir férias em seu navegador. Tudo bem, Bom. Vamos saborear e dar uma olhada. Então, antes de podermos fazer isso, vamos derramar no manipulador clique para o botão Aiken. Vamos abrir e dar uma olhada. Ok, então se eu clicar neste botão agora eu tenho notificações. Permissão? Você está inscrito para receber notificações. Certifique-se de permitir notificações no seu navegador. Além
disso, seria bom se tivéssemos algum tipo de valor que indica se temos a permissão ou não. Porque se abrirmos essa informação lateral aqui, restringimos permissões diferentes, como localização, microfone e notificações. Então, se isso estiver configurado para bloquear, não
seremos capazes de receber nada. É por isso que é bom exibir aqui. Mas que a permissão é concedida não foram para isso. Vamos colocá-lo ao lado deste indicador de permissão da tag P. Então, vamos dizer permissão. Em seguida, vamos embarcar cólon e, em seguida, colocar renderização condicional. Então vamos colocar notificação e notificação é o objeto global dentro da janela dentro do navegador. Se eu, no entanto, você pode ver que isso é notificações ap I Então, se a permissão de ponto de notificação é igual a dois grunhidos, então eu vou exibir um elemento girado que vai dizer grunhir e vamos colocar um nome de classe fora Texto verde. Caso contrário, se não tivermos a permissão, vamos exibir span com texto de noite e o nome da classe vai ser texto lido. Perfeito. Mas agora posso guardá-lo porque parece que tenho um lugar melhor. Tudo bem, vamos fazer este Pitak até o fim assim. Ok, parece bom. Agora vamos dar uma olhada. Se eu abrisse esta janela agora, eu tenho permissão na frente. Parece que vai agora precisamos definir nossa funcionalidade. Então, dentro do rodapé. Vamos primeiro colocar um botão de fechar. Então deixe-me fazer um recapitalizado e no clique vai ser perto. E logo antes deste botão, vamos colocar nossos botões principais para funcionalidade. Então vamos perguntar se nosso usuário está recebendo FC M. Então vamos colocar botão com texto. Mudei de ideia porque, como se lembra, temos uma pergunta. Deseja subscrever mensagens por cores? Vamos especificar verde e para unclipped vamos criar em cancelar função apenas em um momento . Caso contrário, se não recebermos nenhuma notificação, citaremos outro botão. Mas texto Sim, eu quero me inscrever. Tudo bem. Para unclip vamos derramar sobre, exceto e para uma cor. Trabalharemos verde também. Tudo bem, vamos salvá-lo. E agora vamos definir nossas funções primeiro. Vamos derramar. Cancele em. Cancele e aqui vamos fazer referência ao nosso banco de dados. Então vamos colocar banco de dados que importamos do arquivo firebase de referência. E as pessoas especificam quartos, sala de
corte I D ou chat I D que obtemos de usar Paramus Hook. Então, chat i d. Ele recebeu do uso permanente. Vamos mover esta importação para o topo do que estamos indo para referenciar usuários FC M e para filho, que está fora do usuário atual. Vamos importante fora do usuário atual que eu d Não remover. Vamos simplesmente remover este objeto do nosso banco de dados. Bom. Agora vamos definir a segunda função, que está em, exceto e nacionalidade diferente vai ser bastante semelhante licious. Entendido, Nipper. E em vez de remover esta criança, vamos definir isso para a verdade. Tudo bem? Perfeito. Agora vamos realmente testado. Então, vamos abrir o nosso motile e aqui vamos clicar em Eu mudei de idéia e agora você pode ver que a condicionalidade entrando funciona. E se olharmos dentro do banco de dados, vamos para os quartos agora não temos usuários do FC M. Se eu clicar em sim, eu faço. Agora temos usuários FC M com o meu usuário i d insight, Mas para torná-lo um pouco mais amigável. Vamos realmente definir outra cor para o nosso botão Aiken. Então, vamos dizer aparência. Se o nosso usuário estiver recebendo FC M, então vamos derramar aparência padrão. Caso contrário, vamos colocar fantasma e vamos dar uma olhada no que vai acontecer. Então, se eu disser o que agora eu tenho esta cor azul aqui com a aparência normal. Tudo bem, então se eu mudei de idéia agora eu tenho essa aparência fantasma sem a cor dentro do fundo. Ok, bom. Então é isso. É assim que podemos gerenciar nossos usuários, mas eles querem se inscrever ou não. Então, se eles não estão assinando, isso significa que eles não receberão qualquer notificação que são enviados por esta forma moral. Tudo bem, então eu acho que é isso para este vídeo. E esta é a hora de comprometermos nossas mudanças. Vamos abrir nosso terminal e então vamos pegar Dar e nos comprometer. Vamos um homem idade FC M usuários com o pedir FC M vtm Moto perfeito para terminar esta jornada. Vamos Bush tudo online para nos levantarmos. Consiga a reunião de origem de Bush depois de terminar. Vamos executar, firebase implantar e desfrutar do nosso aplicativo de bate-papo online. Fico feliz em dizer que estamos completamente terminados com este projeto. Implementamos tudo o que queríamos. As notificações em tempo real, funções
de administrador, presença
do usuário. Temos tudo no lugar. Haverá mais alguns vídeos sobre o conceito de reagir que não cobrimos o seu nestes
três projetos. Mas, no entanto, espero que tenha sido uma experiência valiosa para nós dois. E espero que este curso lhe dê o que veio buscar. Obrigado por isso. Tempo e paciência. Te vejo na próxima vez.
156. Características essenciais do React: Ei, nesta seção mais, vamos cobrir recursos de reação que quase todos os aplicativos de reação regular de produção têm . Mas não tivemos a chance de usá-los em nossos projetos. Tudo o que será abordado aqui será aplicado ao nosso
aplicativo final de chat do projeto para nos ajudar com o código de referência dupla oficial reagir documentação. Eu recomendo que você leia você mesmo para entender melhor como reagir funciona. Vejo você no próximo vídeo.
157. Portais de reato: Santificar. Nosso primeiro vídeo será sobre reagir. Portais e portais é apenas uma maneira Teoh. Renderizar algo com reagir fora def com fruta ideal. O que quero dizer, se abrirmos nosso aplicativo de bate-papo e se
inspecionarmos nossos elementos, sabemos que todos os nossos elementos, todos os nossos componentes, nosso aplicativo vai sob este dif com idéia escreveu direito, No entanto, vamos dar uma olhada quando abrimos uma janela modelo onde ele será renderizado. Então, se eu abri isso através de oito novas salas de bate-papo, você pode ver isso aqui na parte inferior. Eu tenho esse diálogo de função def, e se eu abri-lo e inspecionar, você pode ver que, na verdade, meu novo modelo Chatham está sendo processado fora desta rota. Então é para isso que os portais são usados. Isso é útil para algo como janelas de modelo ou dicas de ferramentas ou pairamentos. Eu não sei nada que deve ser locatário fora do tratamento principal componente. Isso é muito útil quando lidamos com propriedade CSS índice Z. Então, nunca vamos voltar à documentação e vamos olhar através de exemplos aqui você pode ler palavras que eu acabei de dizer alguma vez olhando para este exemplo, pode ser muito complicado entender o que está acontecendo. Então, em vez de copiar, passear, classe motile da documentação, vamos abrir nosso código. Eu já Irã o aplicativo e outros componentes. Vamos criar um novo modelo de arquivo. Vamos criar um novo componente. E aqui, em vez de devolver este Dave da documentação, podemos ver que somos capazes de usar reagir, não criar método portal. Então, em vez desta definição, vamos voltar. Crie portal e ele será importado automaticamente para nós. E se eu abrir festas, como eu posso ver que aqui eu tenho Crianças e, em seguida, elemento Tudo bem, recipiente. Então, para Crianças, vamos colocar Crianças que passarão para este componente mortal. Então aqui vou destruir seus filhos. E depois passarei para criar o Porto do que o nosso contentor. Deve ser outra div que o problema define dentro do índice html. Então aqui nós já temos este diferente com idéia Satu Road. Agora vamos criar outro dia se isso for um contêiner para nossas janelas modelo. Tudo bem, então aqui vamos criar Dave e eu serei a rota modelo. Vamos salvá-lo e dentro do modelo de togs. Se abrirmos documentação, podemos obtê-lo usando documento. Obter elemento por
I.D. I.D. então vamos copiar esse. Vamos colocá-lo aqui no topo e para criar portal como um segundo argumento, vamos passar rota moral. Certo, Perfeito. Agora vamos salvá-lo. E diz que reagir é declarado. Nunca usei. Tudo bem, então talvez vamos removê-lo. Agora vamos abrir. Talvez página de assinatura. E aqui, vamos dar as boas-vindas ao bate-papo. Vamos fazer a visita deles dentro da janela do modelo. Então aqui vamos colocar modelo importado do nosso arquivo que criamos, não do nosso terno. Então vamos remover essa importação, e eu quero importá-la do nosso arquivo. Tudo bem. Parece que importa do nosso terno. Vamos importá-lo manualmente do modelo de componentes. Perfeito. Então, dentro deste modelo, vamos colocar nossa def com centro de texto. Agora, se nunca voltarmos ao nosso aplicativo Se terminarmos a sessão agora, você poderá ver as boas-vindas. Chad está localizado no fundo e se eu for aos elementos e inspecionar minha árvore idiota aqui no fundo, posso ver a rota mortal. E dentro desta rota modelo, confinamos nossas boas-vindas à cadeira sob o centro de texto. Então este é um Este é usado em suas bibliotecas de olhos como o nosso CLR para janelas de modelo e para
dicas de ferramentas . Por exemplo, se tivéssemos que criar, eles reagem aplicação sem usar biblioteca lágrima I e tivemos que implementar janela móvel. Muito provavelmente usaríamos portais de reação porque eles são renderizados fora do nosso principal deleite
confiante. Você pode achá-lo mais prático Onley quando você entrar nele em um exemplo do mundo real. Tudo bem se você não entender completamente. Mas confie em mim, este é o conceito chave que você deve pelo menos conhecer. Ok. Obrigado. Vejo você na próxima.
158. Limites de erros: Ei aí. Neste vídeo, vamos falar sobre seus coqueiros. Vamos voltar para o tribunal e abrir a página de sinal aqui. O que vai acontecer se vamos dizer, lançar um erro dentro deste componente? Vamos pobre lançar novo erro. Algo ruim aconteceu. Agora vamos dizer o que e vamos dar uma olhada. Se eu refrescar a tinta, podemos ver que temos um nunca e algo ruim aconteceu. E a coisa é que estes entram está preso. Isso significa que ele é chamado por reagir, mas não por nós,
e, eventualmente, reagir será a quantidade de toda a árvore competente, que é realmente ruim se tivermos uma produção pronta por aplicação para evitar que temos melhores coqueiros que são limites são componentes que capturam todos esses tipos de letras e a exibição no fullback You I, por exemplo, uma mensagem que estes paginados falharam. Por favor, atualize-o. Então, se abrirmos a documentação, limitamos um exemplo oficial de como criar um componente de árvore de pão de resposta simples. E para a maioria dos casos isso é suficiente. A menos que você tenha um registro de erro realmente sofisticado ou eu não sei nada o que eu propus fazer eu quero ir para uma demonstração ao vivo? Então eu quero que você abra este exemplo e daqui eu vou copiar isso. Digite classe Bunge re. Então deixe-me copiar tudo isso. Então eu vou abrir a decodificação e, em seguida, dentro de componentes, eu vou criar um arquivo de sempre Bun gery. E dentro vou colocar este componente baseado em classe. E não seja assustador sobre este componente que é baseado em classe. Vou explicar tudo o que acontece aqui. Então deixe-me importar, reagir de reagir. E também temos um monte de sim avisos de comprimento. Vamos desativá-los todos. Vou apenas clicar na correção rápida e desativada para todo o arquivo. O mesmo que farei aqui. Agora vamos salvá-lo. E o que está acontecendo aqui dentro do construtor que definimos em seu estado, que é um objeto com sempre e informações de erro do que usar uma ação competente Catch, gancho de
ciclo de vida ou evento de ciclo de vida. Nós detectamos qualquer erro que está acontecendo dentro deste componente, ok? Ou aos seus Filhos. Quando temos qualquer erro, atualizamos esse estado e,
em seguida, dentro do método de renderização. Se tivermos algum erro dentro do nosso estado, que é jogado o fullback ey. E caso contrário, se tudo estiver bem, nós simplesmente renderizamos todos os seus Filhos. Ok, bem simples. Agora, a
fim de usar este editor, precisamos envolver toda a nossa árvore dentro desta carta. O Bunbury. Então vamos abrir Abdel Gs. E aqui eu vou para sempre grupo que nós componentes que criamos. Deixe-me salvar tudo isso. Em seguida, navegarei de volta para o meu aplicativo. Vou refrescar o amplificador e agora ainda tenho esse aviso de reação. Isso é porque estamos no barco de desenvolvimento. No entanto, se eu fechá-lo agora, em vez de assinar página, Eu tenho este algo uma mensagem errada com os detalhes dentro. E se eu abrir minha outra árvore de pão, eu posso ver que em caso de algum erro, isso é exatamente o que eu estou renderizando e pode ser um viés personalizado. É assim que conseguimos capturar qualquer outro dentro do Y em cada
aplicação pronta para produção . Isto é uma obrigação. A coisa legal sobre nossos limites é que podemos criar vários componentes. Por exemplo, agora colocamos a árvore Herman global. Se qualquer erro dentro da árvore competente será produzido do que ele será capturado por este limite de
letra e, em vez de fora de qualquer componente. Ele exibirá esta mensagem com algo quando bêbado. Digamos que temos um monte de componentes e botão ou esmagado, se não barra caiu. Não queremos remover tudo certo para essas situações. Podemos colocar vários outros limites, por exemplo, por componente ou por página. Então, para a página de assinatura, eu posso puxar sua própria árvore de pão entrar assim. Então eu posso criar outro componente com outro mercado para sempre. E então eu posso esfregar outra página em volta de outra na árvore de pão dela. Assim, desta forma, se o erro será produzido dentro da página inicial, ele será capturado por estes outros bun DRI e, em seguida, o U Y. Isso está listado dentro desta árvore de pão letra será exibido. A questão é por quê? E correu bem. Evers podem ser produzidos por qualquer coisa. Pode ser qualquer erro dentro do código que não controlamos ou simplesmente evitamos. Ou talvez possa ser uma rede de sempre, por exemplo, se algo precisa ser acessado online. Mas do nada, Internet caiu e o componente não conseguiu renderizar desta forma, ele será enjaulado por enter bun tree e é muito importante entender que esses tipos de erros não serão capturados por nunca. Bun árvores em seus coqueiros pegar outros Onley relacionado Teoh renderização. Agora eu acho que nós precisávamos disso algum tipo de Bunbury melhor dentro do nosso aplicativo de bate-papo. Então acho que é uma boa hora para cometermos nossas mudanças. Então vamos derramar este trono. Sua companhia aérea está assinando e vamos colocar uma árvore de pão global para o nosso aplicativo de bate-papo e vamos cometer nossas mudanças. Então eu vou servir. Tudo bem, deixe-me reiniciar o terminal. Eu vou colocar, obter em tudo e, em seguida, começar cometer e, em seguida, adicionar melhor árvore de pão. Perfeito. Espero que tenha sido abrangente e não muito complicado. Vejo-te no próximo.
159. Dividindo: Hey lá nesta bolha de vídeo, falar sobre a divisão de código no modo de reagir, divisão é firmemente acoplado com o carregamento preguiçoso em reagir, morto, divisão significa para componentes de carga preguiçoso, dependências ou talvez até mesmo CSS arquivos. Se lermos a documentação, podemos ver esta seção de agrupamento onde diz que sempre que construímos um aplicativo, temos o arquivo JavaScript final. E, de fato, se olharmos dentro do nosso projeto e formos para o mais recente script estático e ciumento construído aqui, limitaremos alguns trabalhos, ótimos arquivos. E como você pode ver, eles são ampliados e, ao mesmo tempo, eles são bastante grandes. Então é aqui que a nossa lógica vai. Mas com o carregamento a laser, somos capazes de criar mais pedaços de nossa aplicação. E desta forma, podemos colocar uma carga nossos pedaços JavaScript em Lee quando eles são necessários. Por exemplo, se você olhar dentro de nosso aplicativo, basicamente não precisamos fazer login na página agora. Precisamos de Onley quando não estamos autorizados, certo? Então, faria sentido para sinal de carga preguiçoso e componente de página. Então, se vamos para a documentação e se nós rolar para baixo para o exemplo real com reagir, preguiçoso reagir Lisi é uma técnica dentro reagir a componentes de carga preguiçoso. Podemos usar este exemplo para carregar preguiçoso nossa página de login. Vamos copiar esta linha de código do que eu vou navegar para Abla GS Place onde renderizamos o componente de assinatura aqui. Vou pagar este outro componente e vou substituí-lo pelo Sinan. E, em seguida, vou copiar o passe para entrar na página. E então eu vou realmente importar preguiçoso bem de reagir em vez de usar tinta como essa. E também eu preciso importar suspeitos como podemos ver na documentação, porque quando nós preguiçosos, baixos fracos Ojul, pode levar alguns segundos ou milissegundos para carregar este módulo. E enquanto ele está sendo carregado para evitar carne, podemos usar algum fullback. Você eu algo como carregar. É por isso que precisamos fornecer suspense sempre. Então deixe-me copiá-lo, e meu pregador está faltando. Então deixe-me cancelá-lo e realmente iniciou o aplicativo. Talvez funcione. Ok, então eu vou derramar suspeitos que eu iria assinar na página e eu vou colocá-lo assim agora eu posso almoçar meu aplicativo de volta e deixe-me salvá-lo e Agora nós devemos usar entrar
assim com suspeitos e vamos remover a importação antiga página de início de sessão desligado. Agora, se eu guardá-lo, também preciso importar suspense. Agora, se eu disser onde e se eu navegar de volta para o tribunal se eu atualizar o aplicativo se eu clicar em inspecionar e se eu abri o toque de rede, deixe-me sair e prestar atenção. Qual arquivo será carregado? Então, se eu clicar neste botão, você viu esta pequena cintilação com carga def que colocamos como uma volta completa aqui enquanto esta queda para trás você. Eu estava mostrando que nós realmente carregamos o pedaço do nosso casaco. E se abrirmos aqui, confinamos nossos EUA ou vemos páginas de assinatura. Então é isso que significa codificar dividir nosso aplicativo. Se você construir um aplicativo realmente grande, provavelmente quando alguém lança seu site pela primeira vez, a maioria de seus componentes provavelmente não são necessários. Esta técnica é realmente importante para entender. E um bom exemplo seria apenas abrir o lado do rap do Twitter e ver que em todos os lugares quando você apenas carrega o site, você pode ver spinners que eles usam preguiçoso carregamento muito para que eles preguiçosos carregam todos os componentes para reduzir o tamanho inicial do pacote porque realmente importa. Se eu atualizar o aplicativo, você pode ver que um monte de arquivos foram carregados aqui, como um bloco principal, e queremos manter o Chunk principal o menor possível porque o Senhor inicial fora do site importa. Tudo bem, então isso é sobre carregamento a laser? Espero que tenha sido abrangente. Agora vamos realmente confirmar nossas alterações para o aplicativo de bate-papo. Então vamos servir, pegar o Dar e depois nos internar. Adicionar preguiçoso e flutuante CEO perfeito no próximo.
160. Conclusão: Olá. Agora você sabe todas as coisas modernas necessárias para criar um grande aplicativo de reação pronto para produção. Dê um pouco mais de prática e você definitivamente reunirá tudo o que cobrimos . Aqui está uma tarefa para você. Percorra a documentação de reagir e confie em tópicos que você não ouviu durante o curso . Há muitos detalhes sutis que não são vistos no primeiro copo. Certifique-se de entender por que você está usando essa técnica. Quanto a agora, terminamos com esta seção. Vejo-te no próximo.
161. Resumo - Conhecimento que você ganhou: Olá, Você fez muito bem. Você constrói três projetos de reação separados de complexidade diferente. Você pode orgulhosamente dizer que você tem experiência de desenvolvimento reagir. Agora vamos resumir o que você aprendeu neste curso. Dividirei tudo em seu próprio contexto. Os tribunais começaram com coisas mais gerais onde você olhou para diferentes tipos de
renderização do site . Pode AP olhos dado os exemplos do mundo real sua engrenagem, sem cursos de acidente GS e JavaScript modernos e, em seguida, preparou-se para começar a trabalhar com reagir em nosso primeiro projeto. Tick tack para você conhecer primeiro componentes React, sondas,
estilos, estilos, ST Dynamic, você I e desenvolvimento de Flow. Em geral, você criou um projeto de reação simples que demonstra noções básicas fortes. Com bilheteria, você mudou para um aplicativo de reação mais complexo, trabalhando com um P I externo e gerenciando cenários
primitivos conhecidos . Usando três cozinheiros AC, você aprende o conceito de multidões dinâmicas e dados remotos trazendo você para como otimizar e analisar componentes de reação, CIA diz em GS ou componentes estilizados não são estrangeiros para você a partir de agora. Até o final deste projeto, você tem típico aplicativo reagir que requer re mais abrangente reconhecer No último aplicativo de bate-papo projeto. Você começa a conhecer a base de fogo em primeiro lugar. Você fez um ótimo trabalho na gestão do estado global com contexto. AP I Você experimenta situações confusas e não primitivas que exigem
compreensão avançada de reagir. Gerenciar estilos você mesmo nem sempre desejável. É por isso que agora você entende o significado de seus componentes Y, bibliotecas, usuário, estado e páginas privadas são coisas normais para você agora. E ganchos de reação é a sua arma principal. Vários s recuando fora do curso. Pague menos com o mínimo de esforço. No final do chat up, você cria um aplicativo Web pronto para produção com tecnologias atualizadas. Havia também uma pequena sala fora reagir conceitos onde olhamos para eles separadamente e aplicamos ao nosso projeto final. Depois de tudo isso, você deve estar confiante trabalhando com reagir e é eco sistema. Haverá sempre esse sentimento de que o seu conhecimento não é suficiente. E isso é bom. Todo desenvolvedor tem esse senso. Não há limite para a perfeição. Estas foram as coisas que você aprendeu neste curso. Vejo você na próxima vez
162. Movimentos do futuro: Olá. Vamos falar sobre seus próximos passos após o discurso. Não há um roteiro certo para desenvolvedores da Web, mas aqui estão minhas sugestões e recomendações. Primeiro de tudo, aprenda datilografia. É uma linguagem construída em cima do JavaScript. Ele traz sistema de tipo para o projeto, e no final do dia, ele vai aumentar a confiabilidade do código. Google quatro Reagir artigos datilografados e começar com estes integrados em um
projeto de reação simples para entender por que é incrível. Em seguida, dê uma olhada em patos re. Você já sabe o uso. Reducer Hook Read Acts é uma biblioteca de gerenciamento de estado global que usa a mesma abordagem como redutor
usado. Tem uma curva de aprendizagem, mas com ganchos reagem e redox para criança, Redox tornou-se mais abrangente. Muitos tutoriais e facilidade forçada Redox, mas na maioria das vezes você não precisa dele. Ao mesmo tempo, será realmente uma boa prática aumentar seu valor como desenvolvedor. Google para qualquer artigo sobre redução moderna com três patos toolkit. Se você quer crescer como um desenvolvedor reagir, você definitivamente deve começar a olhar para o próximo GS e Gatsby. Esses dois são frameworks construídos sobre reagir, e ambos destinados à renderização do lado do servidor. Sistema ecológico incrível, bons tutoriais. Eles têm tudo para lhe dar o mais confortável possível desenvolvimento e forçar-se a construir um A p I sem GS, nenhum conhecimento Jess é necessário em todos os lugares, seja um back-end JavaScript ou apenas script de fundo. Encontre qualquer artigo sobre como configurar o GS expresso e nenhum GS. Faça você mesmo que aumentou esse conhecimento fazendo mais prática no final do dia. Saiba mais sobre testes ao fazer alterações. Para decodificar é importante não quebrar nada. É por isso que os testes existem com ferramentas modernas. O teste é muito simplificado e agradável. O teste é importante, mas o mais importante, é testar em Lee o que realmente precisa ser testado. Google Para qualquer artigo relacionado a brincadeira ou teste de reação enzimática. Leia mais sobre segurança fora do aplicativo Web, especialmente sobre Jason Webb tokens, cookies e armazenamento local. Proteger backend também é uma coisa, mas para isso começar a baixar togs, nenhum banco de dados SQL como Mongo, DB ou firebase é fácil, mas eles gostam de consultas e estruturas poderosas ao construir. E não, ela voltou e sabiamente decidir sobre o DB. Pergunte aos seus bancos de dados são mais preferíveis em vestido pose de grande escala. Pergunte L e Mongo db são bastante populares hoje em dia. Mais atenção também é dada ao enxerto ul. Uma vez que você se sente confortável sem xadrez e descanso AP olhos começar a pensar em enxerto. Você vai É mais flexível quando há muita solicitação com a forma de dados dinâmicos Warren Cloud Computing e desenvolvimento off wraps usando serviços de nuvem, ele não vai mudar a pilha de desenvolvimento subjacente, por exemplo, Reagir e observar o GS, mas ele lhe dará serviços que permitem implantar e gerenciar o APP. Implantação sem servidor ou armazenamento em nuvem são exemplos de serviços em nuvem. Dê uma olhada em provedores de nuvem populares e escolha um. Torne tudo automatizado com integração contínua e continua a entrega. A entrega permite automatizar o processo de implantação. Por exemplo, quando você envia uma nova alteração e se levanta, o APP será implantado automaticamente continua. A integração vai antes de continuar a entrega. Ele basicamente define o modelo fora do novo código Push para o código principal. Este tópico não é tão fácil de entender. Então sinta-se livre para ler qualquer artigo e ter um monte de perguntas. Estas são as minhas recomendações. Sinta-se livre para escolher sua própria direção. Vejo você na próxima vez