Mobile

Formularios no app: React Hook Form, Zod e teclado sem caos no React Native

Guia pratico para formularios mobile com React Hook Form, Zod, TextInput, teclado e tratamento de erro de API no React Native.

Guia de leitura

O que esta leitura cobre

Use os pontos abaixo como mapa para navegar pelo artigo, comparar sintomas, riscos e proximos passos antes de aplicar qualquer decisao tecnica.

  1. 011. Formulario mobile nao e apenas um conjunto de inputs
  2. 022. React Hook Form entra para organizar estado e submit
  3. 033. Zod ajuda quando a regra precisa ser legivel e tipada
  4. 044. Resolver liga o schema ao formulario sem cola manual
  5. 055. Campo mobile pede componente consistente, nao improviso por tela

Formulario ruim em app corporativo nao falha apenas na estetica. Ele falha na operacao. A pessoa perde texto ao trocar de tela, o teclado cobre o botao de enviar, a validacao muda entre campos, o backend devolve erro que some da interface e o codigo cresce em volta de useState, onChangeText e regras espalhadas. Em pouco tempo, cada tela tem seu proprio mini framework de formulario.

Esse e o tipo de area em que um app React Native amadurece muito quando escolhe uma estrategia clara. React Hook Form ajuda a organizar estado, submit e erro. Zod ajuda a transformar regra de entrada em schema legivel e tipado. E o proprio React Native lembra que teclado, autofill e comportamento de TextInput tambem fazem parte do desenho, nao apenas do visual.

Este guia organiza uma abordagem pratica para formularios mobile em app corporativo: campo, schema, erro local, erro de API, teclado, submit e ligacao com leitura e escrita do backend.

1. Formulario mobile nao e apenas um conjunto de inputs

Em produto real, formulario costuma envolver muito mais do que capturar texto. Ha mascara, valor inicial vindo da API, estado de carregamento, campo dependente, erro de negocio, anexos, confirmacao de envio, rascunho local e reabertura da tela depois de interrupcao. Quando tudo isso entra direto em estado local solto, a manutencao degrada rapido.

Por isso vale separar logo de inicio algumas responsabilidades:

  • estado e submit do formulario;
  • schema de validacao da entrada;
  • componente visual do campo;
  • persistencia e envio para API;
  • tratamento de erro local e remoto.

Essa separacao conversa muito bem com o artigo TanStack Query no app: query e mutation cuidam do fluxo remoto, enquanto o formulario cuida da edicao local antes do envio.

2. React Hook Form entra para organizar estado e submit

O repositorio oficial do React Hook Form descreve a biblioteca como focada em performance, UX e DX, com integracao pronta para bibliotecas de UI e suporte a validadores como Zod. Em outras palavras, ela foi desenhada justamente para evitar que a tela precise reinventar controle, submit e erros a cada formulario.

Na pratica, o ganho aparece quando o app deixa de espalhar:

  • um useState por campo;
  • um bloco de validacao por botao;
  • um loading paralelo fora do fluxo do submit;
  • erros soltos sem ligacao clara com o campo.

O formulario passa a ter uma fonte de verdade unica para valores, erros, dirty state e submissao.

3. Zod ajuda quando a regra precisa ser legivel e tipada

A documentacao do Zod o apresenta como uma biblioteca de validacao orientada a TypeScript, com inferencia estatica de tipos. O exemplo oficial mostra a ideia central: definir um schema e fazer parse do dado nao confiavel antes de usa-lo com seguranca.

Isso e especialmente util em app corporativo porque o formulario quase sempre representa um contrato de negocio. Nao e so saber se o texto esta vazio. E validar combinacoes de campos, formatos esperados, limites, obrigatoriedade condicional e regras que depois ainda vao conversar com a API.

Quando o schema fica explicito, o time ganha pelo menos tres coisas:

  • regra de entrada mais facil de revisar;
  • tipagem coerente entre tela e submit;
  • menos duplicacao entre validacao visual e payload final.

4. Resolver liga o schema ao formulario sem cola manual

O README oficial de @hookform/resolvers explica o objetivo com clareza: permitir uso transparente de bibliotecas de validacao externas, incluindo Zod, junto do React Hook Form. O mesmo material mostra que Zod participa da tabela de resolvers com inferencia de valores a partir do schema.

Na pratica, isso evita um anti-pattern comum: montar schema num lugar, validar manualmente em outro e ainda converter erros de forma artesanal antes de chegar na UI. Com resolver, o formulario e o schema passam a conversar no fluxo normal do submit.

Essa organizacao nao elimina a necessidade de regra de negocio no backend. Ela so impede que o app envie lixo obvio ou trate validacao como detalhe cosmetico.

5. Campo mobile pede componente consistente, nao improviso por tela

Em React Native, cada formulario tende a repetir os mesmos elementos: label, ajuda, erro, estado desabilitado, indicacao de obrigatoriedade, comportamento de foco e botao para avancar ao proximo campo. Quando isso fica solto em cada screen, o app vira uma colecao de campos parecidos, mas nunca iguais.

Vale muito mais criar um componente base de campo que receba valor, erro, descricao e props relevantes de TextInput. O objetivo nao e montar uma mega abstracao. E garantir consistencia minima de UX e legibilidade.

Esse tipo de componente base tambem ajuda a deixar o formulario pronto para acessibilidade, ajuste visual futuro e mudanca de regra sem retrabalho em dez telas diferentes.

6. TextInput tem detalhes que impactam conversao e conforto

A documentacao oficial de TextInput lembra que o componente aceita varias pistas para melhorar o uso real. Entre elas, autoComplete para autofill do sistema e enterKeyHint para orientar o texto exibido na tecla de retorno. A mesma documentacao mostra valores multiplataforma como done, next, search, send e go.

Isso parece detalhe, mas em formulario mobile muda bastante a experiencia:

  • campo de e-mail deve aproveitar autofill e teclado adequado;
  • sequencia de campos deve sugerir next quando houver proximo passo;
  • ultimo campo pode sugerir done ou send conforme o fluxo;
  • senha pede tratamento proprio, inclusive com secureTextEntry quando fizer sentido.

Campo bem configurado reduz erro silencioso e torna o formulario menos cansativo.

7. Teclado faz parte do problema de layout

A pagina oficial de KeyboardAvoidingView diz que o componente ajusta altura, posicao ou padding inferior com base na altura do teclado para manter o conteudo visivel. A mesma pagina recomenda configurar a prop behavior tanto em iOS quanto em Android e lembra que keyboardVerticalOffset pode precisar de ajuste conforme header e area segura.

Em tela de formulario, isso significa que o teclado nao deveria esconder CTA principal, feedback de erro ou o campo em foco. E tambem significa que formulario longo quase sempre pede teste real por plataforma, em vez de confiar apenas no simulador.

Outro detalhe importante vindo da documentacao de TextInput: no Android, selecao de texto pode alterar windowSoftInputMode para adjustResize, o que afeta telas com elementos em position: absolute enquanto o teclado esta ativo. Traduzindo para a vida real: rodape fixo bonito pode quebrar justo na tela que mais precisa funcionar.

8. Validacao local ajuda, mas erro de API continua sendo parte do fluxo

Mesmo com schema bom, a API ainda pode rejeitar o envio por regra de negocio, conflito, permissao ou dado desatualizado. Por isso, formulario maduro nao mistura tudo em uma mensagem generica de falha nem tenta fingir que o schema local conhece o dominio inteiro.

Uma divisao pratica costuma funcionar bem:

  • erro local para formato, obrigatoriedade e consistencia imediata;
  • erro de API para regra de negocio, conflito e validacao do servidor;
  • erro geral para indisponibilidade, timeout ou falha inesperada.

Esse desenho conversa diretamente com validacao e erros de API REST. Quando backend e app usam linguagens completamente diferentes para o mesmo problema, a UX vira loteria.

9. Mutation e formulario precisam ter fronteira clara

Depois que o submit acontece, o app sai do mundo da edicao local e entra no mundo da mutation remota. E aqui a disciplina do artigo sobre TanStack Query volta a importar: o formulario nao deveria assumir sozinho o papel de atualizar lista, detalhe e cache inteiro. Ele envia, recebe sucesso ou erro, e a mutation invalida o que precisa invalidar.

Isso deixa a tela mais previsivel:

  • o formulario cuida de valor, erro e submit;
  • a mutation cuida de comunicacao com a API;
  • a invalidacao cuida do reflexo nas telas de leitura.

Sem essa fronteira, o mesmo submit comeca a acumular side effects demais e vira um ponto fragil da tela.

10. Rascunho longo pede persistencia, nao so estado em memoria

Formulario curto pode morrer com a screen sem grande drama. Ja formulario operacional, vistoria, diagnostico, checklist ou cadastro longo costuma pedir rascunho real. Nesses casos, so manter estado em memoria nao basta. Fechar app, cair chamada, trocar de modulo ou perder foco prolongado pode virar retrabalho direto para a pessoa usuaria.

A resposta geralmente passa por persistencia local estruturada, como discutido em AsyncStorage, SecureStore e SQLite. O ponto importante aqui e nao misturar rascunho com cache de leitura nem com sessao.

Rascunho tem ciclo de vida proprio. E precisa ser tratado como tal.

11. Submit bom evita clique duplo e deixa o retorno honesto

Formulario mobile sofre muito quando o app nao deixa claro se esta enviando, se validou, se falhou ou se concluiu. O minimo saudavel envolve:

  • desabilitar reenvio concorrente enquanto a mutation esta em andamento;
  • mostrar erro em campo ou erro geral no ponto certo;
  • deixar explicito o sucesso real antes de sair da tela;
  • nao limpar tudo cedo demais se houver falha de API.

Em app corporativo, limpar formulario na primeira tentativa e uma forma eficiente de irritar quem acabou de preencher tudo no celular.

12. Multi-etapas e edicao de dados merecem cuidado extra

Outra armadilha comum e tratar formulario de edicao igual formulario vazio. Quando o dado inicial vem da API, a tela precisa decidir quando hidratar o valor, o que acontece se a pessoa ja editou algo e como preservar dirty state com honestidade. Em fluxo de varias etapas, tambem importa saber se o app valida por tela, por secao ou apenas no envio final.

Nao existe uma unica resposta universal, mas existe um principio forte: a regra de validacao e o comportamento de persistencia precisam estar definidos antes de a tela crescer. Fazer isso no susto, no meio da entrega, quase sempre produz formulario inconsistente.

13. Um desenho simples que costuma funcionar bem

  1. Defina schema de entrada com Zod.
  2. Ligue schema ao formulario com resolver.
  3. Crie componente base de campo para TextInput.
  4. Configure autoComplete, tipo de teclado e enterKeyHint conforme o contexto.
  5. Teste teclado com KeyboardAvoidingView e ajuste de offset real.
  6. Separe erro local, erro de API e erro geral.
  7. Deixe mutation e invalidacao fora do componente visual do campo.
  8. Quando houver rascunho longo, persista de forma intencional.

14. Quando vale um diagnostico tecnico

Se hoje o app sofre com formulario que perde valor, teclado cobrindo CTA, regra duplicada, erro remoto mal exibido, submit concorrente ou telas que reinventam validacao em cada fluxo, talvez o problema nao seja um campo isolado. Falta arquitetura de formulario. Nessa hora, um diagnostico tecnico ajuda a revisar componentes base, contrato de API, persistencia de rascunho e fronteira entre edicao local e mutation remota antes que o app acumule mais uma camada de improviso.

Formulario bom em mobile nao e o que parece bonito no Figma. E o que continua confiavel com teclado aberto, rede oscilando, regra de negocio apertando e gente real tentando terminar uma tarefa no celular.

Referencias editoriais: React Hook Form, React Hook Form Resolvers, Zod, React Native - KeyboardAvoidingView e React Native - TextInput.

Glossario conectado

Termos tecnicos desta leitura

Alguns conceitos aparecem com frequencia neste tema. Abrir o glossario ajuda a comparar definicoes, exemplos e leituras relacionadas sem sair do contexto do artigo.

APIsAPIInterface que permite que sistemas conversem por contratos definidos, normalmente usando requisicoes HTTP.MobileautoCompleteProp do TextInput que informa ao sistema o tipo de conteudo esperado para permitir autofill mais coerente.MobileenterKeyHintProp do TextInput usada para sugerir o texto da tecla de retorno, como next, done ou send, conforme o contexto do campo.MobileKeyboardAvoidingViewComponente do React Native que ajusta altura, posicao ou padding da tela para manter o conteudo visivel quando o teclado virtual aparece.MobileReact Hook FormBiblioteca usada para organizar estado, submit e erros de formularios com menos rerender e menos codigo repetido na tela.MobileResolverAdaptador que liga o schema de validacao ao formulario, permitindo que bibliotecas como Zod participem do fluxo normal de submit e erro.
Continue a análise

Próximos passos para aprofundar o tema.

Veja conteúdos próximos e materiais práticos para transformar a leitura em uma revisão mais objetiva.

Mobile

Contrato de API para app React Native: Spring Boot sem retrabalho no mobile

Guia pratico para desenhar APIs Spring Boot que funcionam bem com apps React Native, cobrindo erros, paginacao, retry, idempotencia e versao.

Ler artigo
Mobile

Seguranca em app React Native corporativo: tokens, dados sensiveis e API

Guia pratico para proteger tokens, dados locais, logs, deep links e chamadas de API em apps corporativos React Native.

Ler artigo
Mobile

Navegacao autenticada no app React Native: rotas por perfil sem bagunca

Guia pratico para organizar login, sessao, rotas protegidas, perfil de acesso e deep links em apps corporativos React Native.

Ler artigo

Converse sobre seu cenário técnico.

Envie sua dúvida ou contexto para avaliarmos o melhor caminho.

Prefere falar direto?

Tambem atendemos pelo WhatsApp em (12) 98855-9188.

Falar no WhatsApp

Ao enviar, você concorda que a RM Porto Tech utilize seus dados para responder ao contato solicitado.

WhatsApp(12) 98855-9188