# Mobile first: como otimizar campos de CPF para telas pequenas

> Boas práticas para otimizar campos de CPF em dispositivos móveis, melhorando a experiência do usuário e reduzindo abandono de formulários.

**Publicado:** 12/05/2024
**Autor:** Redação CPFHub.io
**URL:** https://cpfhub.io/blog/mobile-first-como-otimizar-campos-de-cpf-para-telas-pequenas

---


Para otimizar campos de CPF em mobile, use `type="text"` com `inputmode="numeric"` (exibe teclado numérico sem remover zeros à esquerda), aplique máscara de formatação em tempo real (000.000.000-00), garanta fonte mínima de 16px (evita zoom automático no iOS) e altura mínima de 44px para o campo. A validação algorítmica deve acontecer em tempo real; a consulta à API, no evento `blur` — após o preenchimento completo dos 11 dígitos.

## Introdução

No Brasil, a maioria dos acessos à internet acontece por dispositivos móveis. Dados recentes mostram que mais de 60% das transações digitais no país são realizadas via smartphones. Para aplicações que solicitam CPF -- e-commerces, fintechs, plataformas de cadastro, aplicativos de serviços -- otimizar o campo de CPF para telas pequenas é uma questão de sobrevivência comercial.

Um campo de CPF mal implementado em mobile pode resultar em taxas de abandono significativamente maiores do que em desktop. Teclados inadequados, campos que não se adaptam à tela, ausência de máscara de formatação e feedback visual insuficiente são erros que transformam uma tarefa simples em uma experiência frustrante.

---
## O teclado certo faz toda a diferença

O erro mais comum em campos de CPF mobile é exibir o teclado alfanumérico completo quando o usuário precisa digitar apenas números. Isso força o usuário a procurar os dígitos entre letras, aumentando o tempo de preenchimento e a chance de erros.

### A solução com inputmode

O atributo `inputmode="numeric"` instrui o navegador a exibir o teclado numérico, enquanto `type="text"` permite o uso de máscara com caracteres não numéricos (pontos e traço):

```html
<input
 type="text"
 inputmode="numeric"
 pattern="[0-9]*"
 id="cpf"
 name="cpf"
 placeholder="000.000.000-00"
 maxlength="14"
 autocomplete="off"
 aria-label="Número do CPF"
/>
```

### Por que não usar type="number"

Embora pareça a escolha óbvia, `type="number"` apresenta problemas em campos de CPF:

* **Remove zeros à esquerda** -- CPFs que começam com zero perdem esse dígito.
* **Não aceita formatação** -- Pontos e traços são caracteres não numéricos.
* **Setas de incremento** -- Navegadores podem exibir botões de incrementar/decrementar desnecessários.
* **Comportamento inconsistente** -- Diferentes navegadores tratam `type="number"` de formas distintas.

---

## Máscara de formatação adaptada ao mobile

A máscara de CPF deve funcionar de forma fluida em mobile, sem causar travamentos ou comportamentos inesperados ao digitar ou apagar caracteres.

### Implementação otimizada para mobile

```javascript
function mascaraCPFMobile(input) {
 input.addEventListener('input', function(e) {
 var valor = e.target.value.replace(/\D/g, '');
 var tamanho = valor.length;
 var formatado = '';

 if (tamanho > 0) formatado = valor.substring(0, Math.min(3, tamanho));
 if (tamanho > 3) formatado += '.' + valor.substring(3, Math.min(6, tamanho));
 if (tamanho > 6) formatado += '.' + valor.substring(6, Math.min(9, tamanho));
 if (tamanho > 9) formatado += '-' + valor.substring(9, Math.min(11, tamanho));

 e.target.value = formatado;
 });

 // Prevenir colagem de valores não numéricos
 input.addEventListener('paste', function(e) {
 e.preventDefault();
 var texto = (e.clipboardData || window.clipboardData).getData('text');
 var numeros = texto.replace(/\D/g, '').substring(0, 11);
 input.value = numeros;
 input.dispatchEvent(new Event('input'));
 });
}

// Inicializar
document.addEventListener('DOMContentLoaded', function() {
 var campoCpf = document.getElementById('cpf');
 if (campoCpf) mascaraCPFMobile(campoCpf);
});
```

---

## Tamanho e espaçamento do campo

Em telas pequenas, cada pixel conta. O campo de CPF precisa ser grande o suficiente para ser facilmente tocado e lido, mas sem ocupar espaço excessivo.

### CSS otimizado para mobile

```css
.campo-cpf {
 width: 100%;
 max-width: 320px;
 padding: 16px 14px;
 font-size: 18px;
 line-height: 1.4;
 border: 2px solid #ccc;
 border-radius: 8px;
 box-sizing: border-box;
 -webkit-appearance: none;
 appearance: none;
 transition: border-color 0.2s ease;
}

.campo-cpf:focus {
 border-color: #0066cc;
 outline: none;
 box-shadow: 0 0 0 3px rgba(0, 102, 204, 0.15);
}

.campo-cpf.valido {
 border-color: #28a745;
}

.campo-cpf.invalido {
 border-color: #dc3545;
}

/* Garantir tamanho mínimo de toque (44x44px recomendado) */
@media (max-width: 480px) {
 .campo-cpf {
 font-size: 20px;
 padding: 18px 14px;
 min-height: 56px;
 }
}
```

### Diretrizes de tamanho

* **Altura mínima do campo**: 44px (recomendação Apple Human Interface Guidelines e Material Design).
* **Fonte mínima**: 16px (evita zoom automático no iOS quando o campo recebe foco).
* **Padding**: pelo menos 12px horizontal e vertical para conforto de toque.
* **Largura**: 100% do container, com max-width para evitar esticamento em tablets.

---

## Validação em tempo real com feedback visual

Em mobile, o espaço para mensagens de erro é limitado. O feedback visual (cores, ícones) é mais eficiente do que textos longos.

### Implementação com validação e feedback

```javascript
function validarCPFComFeedback(input) {
 var container = input.parentElement;
 var feedback = container.querySelector('.feedback-cpf');

 input.addEventListener('input', function() {
 var cpf = input.value.replace(/\D/g, '');

 input.classList.remove('valido', 'invalido');
 feedback.textContent = '';

 if (cpf.length < 11) {
 feedback.textContent = cpf.length + '/11 dígitos';
 feedback.className = 'feedback-cpf neutro';
 return;
 }

 if (validarDigitosCPF(cpf)) {
 input.classList.add('valido');
 feedback.textContent = 'CPF válido';
 feedback.className = 'feedback-cpf sucesso';
 } else {
 input.classList.add('invalido');
 feedback.textContent = 'CPF inválido';
 feedback.className = 'feedback-cpf erro';
 }
 });
}
```

### HTML do componente

```html
<div class="container-cpf">
 <label for="cpf">CPF</label>
 <input
 type="text"
 inputmode="numeric"
 id="cpf"
 class="campo-cpf"
 placeholder="000.000.000-00"
 maxlength="14"
 autocomplete="off"
 />
 <span class="feedback-cpf"></span>
</div>
```

---

## Validação completa via API no evento blur

Quando o usuário termina de digitar o CPF (evento `blur`), realize a consulta à API para validação completa. No mobile, essa etapa deve ser rápida e não bloquear a interação:

```javascript
document.getElementById('cpf').addEventListener('blur', async function() {
 var cpf = this.value.replace(/\D/g, '');
 if (cpf.length !== 11 || !validarDigitosCPF(cpf)) return;

 var feedback = document.querySelector('.feedback-cpf');
 feedback.textContent = 'Verificando...';
 feedback.className = 'feedback-cpf neutro';

 try {
 var response = await fetch('https://api.cpfhub.io/cpf/' + cpf, {
 method: 'GET',
 headers: {
 'x-api-key': 'SUA_CHAVE_DE_API',
 'Accept': 'application/json'
 }
 });
 var data = await response.json();

 if (data.success) {
 feedback.textContent = 'CPF verificado';
 feedback.className = 'feedback-cpf sucesso';
 document.getElementById('cpf').classList.add('valido');
 } else {
 feedback.textContent = 'CPF não encontrado';
 feedback.className = 'feedback-cpf erro';
 }
 } catch (error) {
 feedback.textContent = '';
 }
});
```

A API da [**CPFHub.io**](https://www.cpfhub.io/) responde em aproximadamente 900ms — rápido o suficiente para exibir o resultado antes que o usuário avance para o próximo campo do formulário.

---

## Acessibilidade em mobile

Campos de CPF acessíveis beneficiam todos os usuários, não apenas aqueles com deficiência. Em mobile, onde a interação é limitada ao toque, a acessibilidade é ainda mais importante.

### Boas práticas de acessibilidade

* **Associar label ao input** -- Usar `for` e `id` para que leitores de tela identifiquem o campo.
* **Usar aria-describedby** -- Para conectar instruções ou mensagens de erro ao campo.
* **Contraste adequado** -- Texto e bordas devem ter contraste suficiente com o fundo (mínimo 4.5:1).
* **Mensagens de erro claras** -- Não depender apenas de cor para indicar erro; incluir texto descritivo.

```html
<label for="cpf">CPF</label>
<input
 type="text"
 inputmode="numeric"
 id="cpf"
 aria-describedby="cpf-instrucao cpf-erro"
 aria-invalid="false"
 class="campo-cpf"
/>
<span id="cpf-instrucao" class="instrucao">Informe os 11 dígitos do seu CPF</span>
<span id="cpf-erro" class="erro" role="alert" aria-live="polite"></span>
```

---

## Evitando problemas comuns em mobile

### Zoom automático no iOS

O Safari no iOS aplica zoom automático quando o usuário foca em um campo com fonte menor que 16px. Para evitar isso, garanta que a fonte do campo seja de pelo menos 16px.

### Scroll indesejado

Quando o teclado virtual aparece, a viewport é reduzida. Certifique-se de que o campo de CPF esteja visível acima do teclado, utilizando `scrollIntoView` se necessário.

### Autocomplete indesejado

Navegadores podem tentar autocompletar o campo de CPF com dados salvos. Use `autocomplete="off"` para desativar esse comportamento.

### Duplo toque acidental

Em mobile, toques rápidos podem ser interpretados como duplo toque (zoom). Desabilite o zoom em campos de formulário com CSS apropriado.

---

## Perguntas frequentes

### Por que `type="number"` não funciona bem para campos de CPF em mobile?
O `type="number"` remove zeros à esquerda (CPFs como 012.345.678-90 perdem o primeiro dígito), não aceita pontos e traços da máscara de formatação e pode exibir botões de incremento/decremento desnecessários. Use `type="text"` com `inputmode="numeric"` para exibir o teclado numérico sem essas limitações.

### Como evitar o zoom automático no iOS ao focar no campo de CPF?
Garanta que a fonte do campo seja de pelo menos 16px. O Safari no iOS aplica zoom automático quando o campo focado tem fonte menor que isso — comportamento que quebra o layout e frustra o usuário. Defina `font-size: 16px` ou superior no CSS do campo, não apenas no placeholder.

### Quando fazer a consulta à API de CPF — durante a digitação ou após o preenchimento?
Após o preenchimento completo, no evento `blur` (quando o usuário sai do campo). Consultar a API a cada digitação é ineficiente e gasta créditos desnecessariamente. A sequência ideal: validação algorítmica em tempo real (durante a digitação) → feedback visual imediato → consulta à API no blur, quando o CPF tiver 11 dígitos e passar na validação local.

### Como garantir que o campo de CPF seja acessível em mobile para usuários com deficiência?
Associe sempre um `<label>` ao campo via atributo `for`, use `aria-describedby` para conectar instruções e mensagens de erro ao campo, garanta contraste mínimo de 4.5:1 entre texto e fundo, e adicione `role="alert"` com `aria-live="polite"` às mensagens de erro para que leitores de tela anunciem as mudanças sem interromper o fluxo do usuário.

### Leia também

- [Diferença entre validação de CPF e consulta de CPF: quando usar cada uma](https://cpfhub.io/blog/diferenca-entre-validacao-de-cpf-e-consulta-de-cpf-quando-usar-cada-uma)
- [API de CPF grátis para desenvolvedores: como começar em 5 minutos](https://cpfhub.io/blog/api-cpf-gratis-desenvolvedores-comecar-5-minutos)
- [Onboarding digital em fintechs: como validar CPF em menos de 30 segundos](https://cpfhub.io/blog/onboarding-digital-em-fintechs-como-validar-cpf-em-menos-de-30-segundos)
- [KYC no Brasil: quais setores são obrigados a validar CPF por lei](https://cpfhub.io/blog/kyc-no-brasil-quais-setores-sao-obrigados-a-validar-cpf-por-lei)

---

## Conclusão

Otimizar o campo de CPF para mobile não é um luxo -- é uma necessidade em um país onde a maioria dos acessos digitais acontece pelo smartphone. Cada detalhe conta: o tipo de teclado exibido, o tamanho do campo, a máscara de formatação, o feedback visual e a acessibilidade. Juntos, esses elementos determinam se o usuário vai completar o formulário ou abandoná-lo.

Ao combinar um campo bem implementado com uma API de validação rápida, como a da CPFHub.io, que responde em aproximadamente 900ms, a experiência mobile se torna fluida, segura e eficiente.

Cadastre-se em [cpfhub.io](https://www.cpfhub.io/) — 50 consultas mensais gratuitas, sem cartão de crédito — e adicione validação de CPF em tempo real ao seu formulário mobile hoje mesmo.

