Monstera

Monstera é uma webapp implementada com React e Firebase que permite aos utilizadores pesquisarem acerca das suas plantas favoritas.

Conceito

O conceito da aplicação é uma plataforma interativa direcionada a amantes de plantas, que permita aos seus utilizadores efetuar pesquisas relacionadas com o assunto por forma a obter informações úteis e interessantes sobre as mesmas. Seria disponibilizada aos utilizadores a possibilidade de se registarem na aplicação, criando um perfil personalizável ao qual poderia ser associada uma “coleção” que armazenaria os dados das plantas nesta incluídas. No decorrer da implementação do projeto optámos ainda por criar a funcionalidade de pesquisa através de imagem, visto que encontrámos uma API que nos possibilitaria fazê-lo.

Design

Cores

cores-monstera

Tipografia

tipografia-monstera

Logo

logo-monstera

Tecnologias e ferramentas

No decorrer do projeto tiramos partido de um conjunto de tecnologias e ferramentas de modo a desenvolver a aplicação acima descrita. Assim, utilizamos React como base do nosso trabalho. De seguida, associamos ao projeto duas APIs relacionadas com as funcionalidades de pesquisa da aplicação. Em primeiro lugar, utilizámos a Trefle que está relacionada com o tratamento e a demonstração de informações sobre cada planta pesquisada. Por sua vez, a Pl@ntNet desempenhava as funções relacionadas com a pesquisa por imagens, sendo que se encontrava também ligada à Trefle. Por fim, tiramos proveito de vários módulos da API Firebase, nomeadamente a base de dados, que utilizámos para armazenar informações sobre cada um dos utilizadores a longo termo, a storage, onde, por exemplo, foram guardadas imagens relativas aos perfis dos utilizadores, e a autenticação, que nos permitiu implementar o sistema de registo e login

Implementação

Diagrama de classes UML

diagrama-uml-monstera

Estrutura da base de dados

estrutura-bd-monstera

Login e registo

Para a implementação do sistema de login e de registo da aplicação utilizamos o módulo de autenticação do Firebase, tanto para controlar se algum utilizador está autenticado como para efetuar e guardar informações relativas aos registos dos utilizadores.

login-registo-monstera

Caso exista algum erro, tanto na operação de login como de registo, é chamada a função showAlert que está declarada no componente App.js e é passada como prop para todos os componentes em que seja necessária a sua utilização. Esta função cria uma div com uma mensagem de erro/sucesso e insere-a no DOM.

route-register-monstera

Quando um utilizador faz login com sucesso uma função listener no componente App.js altera o objeto user no state desse mesmo componente. É esse objeto que determina o que o componente App.js vai renderizar. Caso o objeto esteja definido, significa que um utilizador fez login com sucesso e deve ser renderizado o perfil do utilizador relativo ao componente Profile.js e respetivas Routes, caso contrário deve ser renderizada a página inicial da aplicação e respetivas Routes.

authListener-monstera

Editar perfil

A página onde o utilizador pode efetuar alterações ao seu perfil, nomeadamente o nome, imagem de perfil e a password pode ser acessada através de uma route renderizada no componente Profile.js.

route-edit-profile-monstera

Para que possa ser identificado o utilizador que está a fazer as alterações ao perfil é passado através de um handle dinâmico o ID relativo ao documento da base de dados com as informações do respetivo utilizador. É depois possível aceder a este ID no componente EditProfile.js através das match props.

handle-dinamico-monstera

Quando o componente é renderizado é executada uma função que procura o url da imagem de perfil e o username do utilizador autenticado na base de dados, guarda no state do componente e substitui nos devidos espaços. Caso o utilizador não tenha definido uma imagem é renderizada uma imagem default.

getPrevImg-monstera

Quando o utilizador guarda as alterações que quer realizar, caso tenha sido alterada a imagem a mesma é guardada na firebase storage e o url é guardado no state do componente. Após isso, os dados que tenham sido alterados (nome, password ou url da imagem de perfil) são alterados na base de dados. Durante este processo, de maneira a dar feedback ao utilizador de que a ação que quer realizar está a acontecer inserimos um ecrã de loading.

Pesquisar plantas

A principal função da aplicação é a possibilidade dos utilizadores pesquisarem plantas, essa pode ser realizada pesquisando através do seu nome, inserindo-o na barra de pesquisa ou fazendo o upload de uma imagem na aplicação.

Quando o utilizador pesquisa uma planta através da barra de pesquisa é realizado um GET Request à Trefle API no componente Search.js. Após o pedido ter sido realizado e ter devolvido um array de resultados é chamada uma função callback que guarda os resultados no state do componente pai Profile.js e ativa o loading screen, como o pedido não devolve as imagens relativas às plantas, após os resultados serem guardados no state do componente Profile.js é executado um loop que faz um GET Request para cada resultado recebido e guarda as imagens relativas aos resultados num array no state do componente.

fetch-imagens-monstera

Após os pedidos das imagens serem efetuados e os respetivos resultados serem guardados no state do componente são renderizados os componentes relativos aos resultados obtidos. Caso não sejam encontrados resultados é apresentada uma mensagem de erro.

iteracao-resultados-monsteraaparencia-resultados-monstera

É possível clicar em qualquer um dos resultados e aceder a uma página que mostra informações acerca da respectiva planta. Para isso utilizamos um handler dinâmico que passa para o componente PlantInfo.js várias informações relevantes (id da planta e token de autenticação) que permitem que, quando o componente renderizar, seja efetuado um pedido à Trefle API e sejam mostradas nessa página um conjunto de informações relativas à planta selecionada.

handle-dinamico-2-monsteraredirect-com-params-monsteraaparencia-plant-info

É também possível realizar pesquisas por imagem. Para isso o utilizador insere uma imagem na aplicação que é guardada na storage do firebase. É depois gerado um url dessa imagem que é encoded, sendo depois usado para fazer um pedido à Pl@ntNet API que reconhece a planta e devolve o nome científico da mesma. Por sua vez, esse nome é utilizado para fazer um pedido à Trefle API que irá devolver os resultados relativos à planta.

upload-imagem-monsteraget-request-trefle-monstera

Coleção

Decidimos implementar também a possibilidade de os utilizadores adicionarem plantas a uma “coleção” para que possam verificar sempre que necessitarem informações acerca das suas plantas favoritas sem ser necessário pesquisar novamente.

collection-monstera

Quando a página Profile.js mount é executada uma função que verifica na base de dados se o utilizador tem uma coleção e, caso tenha, que plantas é que estão associadas. Esta função guarda em três arrays distintos localizados no state do componente os ID’s, nomes e imagens relativas às plantas presentes na coleção.

retrieve-collection-monstera

Após isso, como todos os arrays têm o mesmo número de itens, um deles é iterado. Assim, para cada iteração é renderizada a respetiva planta com a devida imagem e nome na página designada. Clicando nas plantas da coleção é possível aceder novamente à informação da planta.

render-plantas-collection

É possível adicionar e remover plantas da coleção a partir do componente PlantInfo.js. Quando este componente renderiza é executada uma função para verificar se a planta pesquisada já está presente na coleção. Caso ainda não esteja é renderizado o botão de “Adicionar à coleção” relativo ao componente AddCollectionBtn.js, no cenário contrário é renderizado o botão de “Remover da coleção” relativo ao componente RemoveFromCollection.js.

checkIfInCollection-monsterarender-btn-collectionbtn-collection-aparencia

Resultado

result-monstera