# Guia da propriedade CSS pointer-events

> Como pointer-events decide qual elemento recebe cliques e hover, por que ela é herdada, e o que ela não faz: desabilitar elemento nem impedir seleção de texto.

URL: https://dpw.dev/css/pointer-events-css/  
Publicado em: 2026-09-03  
Categoria: css  
Tags: interface, usabilidade  
Autor: Tárcio Zemel

Overlay que bloqueia o clique no que está atrás, submenu invisível que continua interceptando o mouse: os dois problemas se resolvem com uma linha de **pointer-events**.

Só que a propriedade não desabilita eventos: ela muda qual elemento é escolhido como alvo. Entender essa diferença explica praticamente todo o comportamento dela.

> Artigo baseado em [pointer-events](https://css-tricks.com/almanac/properties/p/pointer-events/).

A propriedade `pointer-events` controla se um elemento pode se tornar o alvo de eventos de ponteiro, como cliques, estados de hover e outros eventos baseados em ponteiro. Em outras palavras, ela permite decidir se o navegador deve tratar um elemento como interativo quando o ponteiro está sobre ele.

```css
.no-pointer-events {
  pointer-events: none;
}
```

[Exemplo no CodePen](https://codepen.io/anon/pen/AoWEYg)

Para entender como a propriedade funciona, ajuda saber o que o navegador faz antes de disparar um evento de ponteiro. Primeiro, ele precisa determinar qual elemento está sob o ponteiro. Esse processo é conhecido como hit-testing.

Normalmente, o navegador escolhe o elemento mais ao topo sob o ponteiro. Mas, se esse elemento tiver `pointer-events` definido como `none`, o navegador o ignora e continua procurando o próximo elemento elegível abaixo dele.

Uma vez que se pensa em `pointer-events` dessa forma, a maior parte do comportamento dela começa a fazer sentido. Em vez de desabilitar eventos, ela simplesmente muda qual elemento (ou, no caso de SVG, qual parte de um elemento) se torna o alvo do evento.

## Sintaxe

```css
pointer-events: auto | bounding-box | visiblePainted | visibleFill | visibleStroke | visible | painted | fill | stroke | all | none;
```

- **Valor inicial:** auto
- **Aplica-se a:** todos os elementos. Em SVG, aplica-se a elementos container, elementos gráficos e ao próprio elemento.
- **Herdada:** sim
- **Valor computado:** a palavra-chave especificada
- **Tipo de animação:** discreto

## Valores

```css
pointer-events: auto;
pointer-events: none;

/* Valores de SVG */
pointer-events: visiblePainted;
pointer-events: visibleFill;
pointer-events: visibleStroke;
pointer-events: visible;
pointer-events: painted;
pointer-events: fill;
pointer-events: stroke;
pointer-events: bounding-box;
pointer-events: all;

/* Valores globais */
pointer-events: inherit;
pointer-events: initial;
pointer-events: revert;
pointer-events: revert-layer;
pointer-events: unset;
```

Além dos valores globais padrão de CSS mostrados acima, a `pointer-events` define onze palavras-chave.

Você vai usar `auto` e `none` tanto com elementos HTML quanto SVG. As outras nove são exclusivas de SVG e oferecem controle mais fino sobre quais partes de um gráfico podem receber eventos de ponteiro.

- **`auto`**: o valor padrão. O elemento se comporta normalmente e pode receber eventos de ponteiro. Em SVG, funciona igual a `visiblePainted`.
- **`none`**: o elemento em si não pode se tornar alvo de eventos de ponteiro, o que significa que ele não pode ser clicado nem receber hover. Em vez dele, o navegador mira no que estiver embaixo.

### Valores exclusivos de SVG

- **`visiblePainted`**: o elemento só recebe eventos de ponteiro quando está visível (`visibility: visible`) e o ponteiro está sobre uma parte pintada do gráfico. Ou seja, sobre uma área preenchida (`fill` diferente de `none`) ou sobre uma borda traçada (`stroke` diferente de `none`).
- **`visibleFill`**: o elemento só recebe eventos de ponteiro quando está visível e o ponteiro está sobre o preenchimento dele, independentemente do valor da propriedade `fill`, que pode até estar como `none`.
- **`visibleStroke`**: o elemento só recebe eventos de ponteiro quando está visível e o ponteiro está sobre o traço dele, independentemente do valor da propriedade `stroke`.
- **`visible`**: o elemento só recebe eventos de ponteiro quando está visível e o ponteiro está sobre o preenchimento ou o traço, independentemente dos valores das propriedades `fill` e `stroke`.
- **`painted`**: o elemento só recebe eventos de ponteiro quando o ponteiro está sobre uma parte pintada do gráfico (preenchimento ou traço), independentemente do valor da propriedade `visibility`.
- **`fill`**: o elemento só recebe eventos de ponteiro quando o ponteiro está sobre o preenchimento dele, independentemente dos valores das propriedades `fill` e `visibility`.
- **`stroke`**: o elemento só recebe eventos de ponteiro quando o ponteiro está sobre o traço dele, independentemente dos valores das propriedades `stroke` e `visibility`.
- **`bounding-box`**: o elemento recebe eventos de ponteiro em qualquer ponto dentro da bounding box dele (o menor retângulo que o cerca por completo), independentemente do formato, mesmo que partes dessa área não estejam pintadas.
- **`all`**: o elemento recebe eventos de ponteiro quando o ponteiro está sobre o preenchimento ou o traço dele, independentemente dos valores das propriedades `fill`, `stroke` ou `visibility`.

## Filhos podem voltar a participar

Algo fácil de deixar passar é que `pointer-events` é uma propriedade herdada. Definir `pointer-events` como `none` em um pai significa que os filhos também herdam esse valor.

Só que qualquer filho pode sobrescrever o valor herdado, voltando `pointer-events` para `auto` (ou outro valor válido).

```css
.parent {
  pointer-events: none;
}

.child {
  pointer-events: auto;
}
```

Neste exemplo, o pai ignora eventos de ponteiro, mas o filho ainda pode se tornar alvo deles.

Um caso de uso comum é um <a href="/css/usar-estilizar-dialog-html-css/" target="_blank">modal</a>. Você pode usar um container de página inteira para centralizar o modal, mas esse container também cobre toda a viewport. Sem mudar o valor de `pointer-events` dele, ele impede que eventos de ponteiro cheguem aos elementos abaixo.

Definir `pointer-events` como `none` no container resolve isso. Mas, como a propriedade é herdada, também é preciso restaurar o próprio modal com `pointer-events` em `auto`.

Na demonstração a seguir, quando a propriedade `pointer-events` está especificada como `none`, é possível interagir com os botões de fundo mesmo estando eles atrás do overlay.

[Exemplo no CodePen](https://codepen.io/anon/pen/LExmXwq)

## A propagação de eventos continua funcionando

A propriedade `pointer-events` só determina qual elemento se torna o alvo do evento. Ela não muda como o evento trafega pelo DOM depois disso.

Por exemplo: se um filho com `pointer-events: auto` é clicado dentro de um pai com `pointer-events: none`, o filho ainda se torna o `event.target`. A partir dali, o evento segue as fases normais de captura e bubbling, então os listeners anexados ao pai continuam rodando.

Em outras palavras, `pointer-events` afeta a seleção do alvo, não a propagação do evento.

Na demonstração a seguir, dá para ver como o pai com `pointer-events: none` ainda pode receber `click`, `pointerenter` e `pointerleave` quando você clica ou move o ponteiro para dentro ou para fora do filho interativo.

[Exemplo no CodePen](https://codepen.io/anon/pen/gbgegqr)

## Ela não desabilita um elemento

A propriedade `pointer-events` só impede que o elemento se torne alvo de eventos de ponteiro. Portanto, o elemento ainda pode receber foco de teclado com a tecla Tab, e o usuário pode continuar interagindo com ele pelo teclado, se ele for focável por outros meios.

Se você precisa desabilitar um controle de formulário nativo, use o atributo `disabled`. E, se o objetivo é tornar uma seção inteira da página completamente não interativa (incluindo entrada por ponteiro, foco de teclado e a árvore de acessibilidade), o atributo `inert` é a melhor escolha.

Essa distinção importa: esconder algo do mouse sem esconder do teclado é uma armadilha clássica de <a href="/acessibilidade/acessibilidade-css/" target="_blank">acessibilidade em CSS</a>.

## Ela não impede a seleção de texto

Definir a propriedade `pointer-events` como `none` não impede que o usuário selecione texto. Ele ainda pode selecioná-lo pressionando `Ctrl/Cmd + A` no teclado, por exemplo.

Isso acontece porque a seleção de texto não é determinada por um elemento poder ou não se tornar alvo de eventos de ponteiro.

Se o objetivo é impedir que o texto seja selecionado, use a propriedade <a href="https://css-tricks.com/almanac/properties/u/user-select/" target="_blank" rel="noopener noreferrer">`user-select`</a>.

```css
.avoid-user-selection {
  user-select: none;
}
```

Tente selecionar o texto de cada bloco abaixo:

[Exemplo no CodePen](https://codepen.io/anon/pen/YPNaNoX)

## Demonstração

Na construção de um menu de navegação, um padrão comum é esconder um submenu definindo a `opacity` dele em `0` e depois torná-lo visível quando o usuário passa o mouse sobre o item pai. O problema é que o submenu continua ali, então ele ainda pode receber eventos de ponteiro mesmo sem estar visível.

Abaixo, dá para ver dois menus idênticos. Um esconde o submenu usando apenas opacidade, e o outro usa também `pointer-events`. Passe o mouse sobre a área do submenu invisível e tente interagir com o conteúdo atrás dela, para ver como a `pointer-events` evita que elementos invisíveis fiquem no caminho.

[Exemplo no CodePen](https://codepen.io/anon/pen/PwWRppj)

Também para entender melhor como cada valor de SVG dessa propriedade funciona, escolha um deles no dropdown e mova o ponteiro pelo anel: sobre a faixa preenchida, dentro do centro vazado e sobre os cantos vazios da bounding box tracejada. Note como a área interativa muda a cada valor.

[Exemplo no CodePen](https://codepen.io/anon/pen/LExdWzp)

## Suporte dos navegadores

Os valores `auto` e `none` funcionam em todos os navegadores em uso, incluindo versões bem antigas. Os valores exclusivos de SVG têm suporte irregular, com o `bounding-box` sendo o mais recente e o menos difundido. Vale conferir a <a href="https://caniuse.com/pointer-events" target="_blank" rel="noopener noreferrer">tabela de suporte no Can I Use</a> antes de depender de um valor específico de SVG.

## Propriedades relacionadas

A parceira mais próxima é a <a href="https://css-tricks.com/almanac/properties/u/user-select/" target="_blank" rel="noopener noreferrer">`user-select`</a>, que resolve o problema que a `pointer-events` não resolve: controlar a seleção de texto. E, para casos de menu, vale ver as <a href="/ui-ux/10-dicas-menus-responsivos/" target="_blank">10 dicas para menus responsivos</a>.

---

Fonte: [dpw - desenvolvimento para web](https://dpw.dev/) (pt-BR).
Guia para agentes: https://dpw.dev/llms.txt
Índice completo: https://dpw.dev/sitemap-index.xml
Feed: https://dpw.dev/rss.xml
