Pseudoclasses

The CSS Podcast - 015: Pseudo-classes

Suponha que você tenha um formulário de inscrição por e-mail e queira que o campo de e-mail tenha uma borda vermelha se contiver um endereço de e-mail inválido. Como fazer isso? Você pode usar uma pseudoclasse CSS :invalid, que é uma das muitas pseudoclasses fornecidas pelo navegador.

Uma pseudoclasse permite aplicar estilos com base em mudanças de estado e fatores externos. Isso significa que seu design pode reagir à entrada do usuário, como um endereço de e-mail inválido. Eles são abordados no módulo seletores, e este módulo vai explicar cada um deles com mais detalhes.

Ao contrário dos pseudoelementos, que você pode conhecer melhor no módulo anterior, as pseudoclasses se conectam a estados específicos em que um elemento pode estar, em vez de estilizar partes desse elemento de maneira geral.

Estados interativos

As pseudoclasses a seguir são aplicadas devido a uma interação do usuário com sua página.

:hover

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 2.

Source

Se um usuário tiver um dispositivo apontador, como um mouse ou trackpad, e o colocar sobre um elemento, você poderá se conectar a esse estado com :hover para aplicar estilos. Essa é uma maneira útil de sugerir que um elemento pode ser interagido.

:active

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

Esse estado é acionado quando um elemento está sendo interagido ativamente, como um clique, antes que o clique seja liberado. Se um dispositivo apontador, como um mouse, for usado, esse estado será quando o clique começar e ainda não tiver sido liberado.

:focus, :focus-within e :focus-visible

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

Se um elemento puder receber foco, como um <button>, você poderá reagir a esse estado com a pseudoclasse :focus.

Você também pode reagir se um elemento filho do seu elemento receber foco com :focus-within.

Elementos focalizáveis, como botões, mostram um anel de foco quando estão em foco, mesmo quando clicados. Nesse tipo de situação, um desenvolvedor aplica o seguinte CSS:

button:focus {     outline: none; } 

Esse CSS remove o anel de foco padrão do navegador quando um elemento recebe foco, o que apresenta um problema de acessibilidade para usuários que navegam em uma página da Web com um teclado. Se não houver um estilo de foco, o usuário não conseguirá acompanhar onde o foco está no momento ao usar a tecla Tab. Com :focus-visible é possível apresentar um estilo de foco quando um elemento recebe foco usando o teclado, além de usar a regra outline: none para evitar isso quando um dispositivo de ponteiro interage com ele.

button:focus {     outline: none; }  button:focus-visible {     outline: 1px solid black; } 

:target

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.3.

Source

A pseudoclasse :target seleciona um elemento que tem um id correspondente a um fragmento de URL. Suponha que você tenha o seguinte HTML:

<article id="content">     <!-- ... --> </article> 

É possível anexar estilos a esse elemento quando o URL contém #content.

#content:target {     background: yellow; } 

Isso é útil para destacar áreas que podem ter sido vinculadas especificamente, como o conteúdo principal de um site, usando um link de navegação.

Estados históricos

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

A pseudoclasse :link pode ser aplicada a qualquer elemento <a> que tenha um valor href que ainda não foi visitado.

:visited

É possível estilizar um link que já foi visitado pelo usuário usando a pseudoclasse :visited. Esse é o estado oposto a :link, mas você tem menos propriedades de CSS para usar por motivos de segurança. Só é possível estilizar color, background-color, border-color, outline-color e a cor dos elementos SVG fill e stroke.

A ordem é importante

Se você definir um estilo :visited, ele poderá ser substituído por uma pseudoclasse de link com especificidade pelo menos igual. Por isso, recomendamos que você use a regra LVHA para estilizar links com pseudoclasses em uma ordem específica: :link, :visited, :hover, :active.

a:link {} a:visited {} a:hover {} a:active {} 

Estados do formulário

As pseudoclasses a seguir podem selecionar elementos de formulário nos vários estados em que esses elementos podem estar durante a interação.

:disabled e :enabled

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Se um elemento de formulário, como um <button>, for desativado pelo navegador, você poderá se conectar a esse estado com a pseudoclasse :disabled. A pseudoclasse :enabled está disponível para o estado oposto, embora os elementos de formulário também sejam :enabled por padrão, portanto, talvez você não precise usar essa pseudoclasse.

:checked e :indeterminate

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

A pseudoclasse :checked está disponível quando um elemento de formulário compatível, como uma caixa de seleção ou um botão de opção, está marcado.

O estado :checked é binário (verdadeiro ou falso), mas as caixas de seleção têm um estado intermediário quando não estão marcadas nem desmarcadas. Esse é o estado :indeterminate.

Um exemplo desse estado é quando você tem um controle "Selecionar tudo" que marca todas as caixas de seleção em um grupo. Se o usuário desmarcar uma dessas caixas de seleção, a caixa de seleção raiz não representará mais "tudo" marcado e, portanto, deverá ser colocada em um estado indeterminado.

O elemento <progress> também tem um estado indeterminado que pode ser estilizado. Um caso de uso comum é dar a ele uma aparência listrada para indicar que não se sabe quanto mais é necessário.

:placeholder-shown

Browser Support

  • Chrome: 47.
  • Edge: 79.
  • Firefox: 51.
  • Safari: 9.

Source

Se um campo de formulário tiver um atributo placeholder e nenhum valor, a pseudoclasse :placeholder-shown poderá ser usada para anexar estilos a esse estado. Assim que houver conteúdo no campo, com ou sem um placeholder, esse estado não será mais aplicado.

Estados de validação

Browser Support

  • Chrome: 10.
  • Edge: 12.
  • Firefox: 4.
  • Safari: 5.

Source

Você pode responder à validação de formulários HTML com pseudoclasses como :valid, :invalid e :in-range. As pseudoclasses :valid e :invalid são úteis em contextos como um campo de e-mail que tem um pattern que precisa ser correspondido para ser um campo válido. Esse estado de valor válido pode ser mostrado ao usuário, ajudando-o a entender que pode passar para o próximo campo com segurança.

A pseudoclasse :in-range está disponível se uma entrada tiver um min e um max, como uma entrada numérica e o valor estiver dentro desses limites.

Com formulários HTML, é possível determinar que um campo é obrigatório com o atributo required. A pseudoclasse :required estará disponível para campos obrigatórios. Os campos que não são obrigatórios podem ser selecionados com a pseudoclasse :optional.

Como selecionar elementos por índice, ordem e ocorrência

Há um grupo de pseudoclasses que selecionam itens com base em onde eles estão no documento.

:first-child e :last-child

Browser Support

  • Chrome: 4.
  • Edge: 12.
  • Firefox: 3.
  • Safari: 3.1.

Source

Se quiser encontrar o primeiro ou o último item, use :first-child e :last-child. Essas pseudoclasses retornam o primeiro ou o último elemento em um grupo de elementos irmãos.

:only-child

Browser Support

  • Chrome: 2.
  • Edge: 12.
  • Firefox: 1.5.
  • Safari: 3.1.

Source

Também é possível selecionar elementos que não têm irmãos com a pseudoclasse :only-child.

:first-of-type e :last-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Você pode selecionar :first-of-type e :last-of-type, que, a princípio, parecem fazer a mesma coisa que :first-child e :last-child, mas considere este HTML:

<div class="my-parent">     <p>A paragraph</p>     <div>A div</div>     <div>Another div</div> </div> 

E este CSS:

.my-parent div:first-child {     color: red; } 

Nenhum elemento seria colorido de vermelho porque o primeiro filho é um parágrafo e não uma div. A pseudoclasse :first-of-type é útil nesse contexto.

.my-parent div:first-of-type {     color: red; } 

Mesmo que o primeiro <div> seja o segundo filho, ele ainda é o primeiro do tipo dentro do elemento .my-parent, portanto, com essa regra, ele será colorido de vermelho.

:nth-child e :nth-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Você não está limitado a primeiro e último filhos e tipos. As pseudoclasses :nth-child e :nth-of-type permitem especificar um elemento que está em um determinado índice. A indexação em seletores CSS começa em 1.

As pseudoclasses :nth-last-child() e :nth-last-of-type() contam do final, e não do início.

Você também pode transmitir mais de um índice para essas pseudoclasses. Se você quiser selecionar todos os elementos pares, use :nth-child(even).

Também é possível criar seletores mais complexos que encontram itens em intervalos regularmente espaçados usando a microssintaxe An+B.

li:nth-child(3n+3) {     background: yellow; } 

Esse seletor seleciona todos os itens a cada três, começando pelo item 3. O n nessa expressão é o índice, que começa em zero, e o 3 (3n) é o valor pelo qual você multiplica esse índice.

Digamos que você tenha sete itens <li>. O primeiro item selecionado é 3 porque 3n+3 é traduzido como (3 * 0) + 3. A próxima iteração escolheria o item 6 porque n agora foi incrementado para 1, então (3 * 1) + 3). Essa expressão funciona para :nth-child e :nth-of-type.

:nth-child() e :nth-last-child() também oferecem suporte a uma sintaxe "de S" que permite filtrar as correspondências com um seletor, semelhante a :nth-of-type(). li:nth-of-type(even) é equivalente a :nth-child(even of li). Enquanto :nth-of-type permite filtrar apenas com base no tipo de elemento (como li ou p), a sintaxe "de S" permite filtrar qualquer seletor.

Se você tiver uma tabela, talvez queira adicionar listras a cada outra linha. Embora seja possível segmentar todas as outras linhas com tr:nth-child(even), isso não funciona se você estiver filtrando algumas linhas. Se você implementar a filtragem aplicando o atributo hidden, adicione of :not([hidden]) ao seletor para pré-filtrar os itens ocultos antes de selecionar as linhas pares.

tr:nth-child(even of :not([hidden])){   background: lightgrey; } 

Você pode testar esse tipo de seletor neste teste de nth-child ou nesta ferramenta de seletor de quantidade.

:only-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Por fim, é possível encontrar o único elemento de um determinado tipo em um grupo de irmãos com :only-of-type. Isso é útil se você quiser selecionar listas com apenas um item ou encontrar o único elemento em negrito em um parágrafo.

Encontrar elementos vazios

Às vezes, é útil identificar elementos completamente vazios, e há uma pseudoclasse para isso também.

:empty

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Se um elemento não tiver filhos, a pseudoclasse :empty será aplicada a ele. No entanto, os filhos não são apenas elementos HTML ou nós de texto: eles também podem ser espaços em branco, o que pode ser confuso ao depurar o seguinte HTML e se perguntar por que ele não está funcionando com :empty:

<div> </div> 

O motivo é que há um espaço em branco entre as tags de abertura e fechamento <div>. Por isso, :empty não vai funcionar.

A pseudoclasse :empty pode ser útil se você tiver pouco controle sobre o HTML e quiser ocultar elementos vazios, como um editor de conteúdo WYSIWYG. Aqui, um editor adicionou um parágrafo vazio perdido.

<article class="post">  <p>Donec ullamcorper nulla non metus auctor fringilla.</p>  <p></p>  <p>Curabitur blandit tempus porttitor.</p> </article> 

Com o :empty, você pode encontrar e ocultar esse conteúdo.

.post :empty {     display: none; } 

Encontrar e excluir vários elementos

Algumas pseudoclasses ajudam você a escrever CSS mais compacto.

:is()

Browser Support

  • Chrome: 88.
  • Edge: 88.
  • Firefox: 78.
  • Safari: 14.

Source

Se você quiser encontrar todos os elementos filhos h2, li e img em um elemento .post, pode pensar em escrever uma lista de seletores assim:

.post h2, .post li, .post img {      } 

Com a pseudoclasse :is(), é possível escrever uma versão mais compacta:

.post :is(h2, li, img) {     /* ... */ } 

A pseudoclasse :is não é apenas mais compacta do que uma lista de seletores, mas também mais tolerante. Na maioria dos casos, se houver um erro ou um seletor não compatível em uma lista de seletores, toda a lista deixará de funcionar. Se houver um erro nos seletores transmitidos em uma pseudoclasse :is, o seletor inválido será ignorado, mas os válidos serão usados.

:not()

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Também é possível excluir itens com a pseudoclasse :not(). Por exemplo, você pode usar esse seletor para estilizar todos os links que não têm um atributo class.

a:not([class]) {     color: blue; } 

Uma pseudoclasse :not também pode ajudar a melhorar a acessibilidade. Por exemplo, um <img> precisa ter um alt, mesmo que seja um valor vazio. Assim, você pode escrever uma regra CSS que adicione um contorno vermelho grosso a imagens inválidas:

img:not([alt]) {     outline: 10px red; } 

:has()

E se você quiser estilizar elementos com base no que está contido neles? Para isso, use a pseudoclasse :has(). Por exemplo, talvez você queira aplicar estilos a botões que incluem ícones.

 button:has(svg) {   /* ... */ } 

Na configuração mais básica, como no exemplo anterior, é possível pensar em :has() como um seletor principal. Você também pode usar o seletor de correspondência de elemento pai combinado com outros seletores para segmentar outros elementos.

form:has(input:valid) label {   font-weight: bold; }  form:has(input:valid) label::after {   content: "✅"; } 

Neste exemplo, estamos aplicando estilos ao elemento de rótulo e ao pseudoelemento label::after quando a entrada do formulário tem uma pseudoclasse valid.

A pseudoclasse :has() não pode ser aninhada em outra :has(), mas pode ser combinada com outras pseudoclasses.

:is(h1, h2, h3):has(a) {    /* ... */ } 

A lista de seletores é implacável. Se algum seletor na lista for inválido, todas as regras de estilo serão ignoradas.

.my-element:has(img, ::before) {   /* any styles here will be discarded since pseudo elements can't be included in the :has() selector list */ } 

Teste seu conhecimento

Teste seus conhecimentos sobre pseudoclasses

As pseudoclasses agem como se uma classe tivesse sido aplicada dinamicamente a um elemento, enquanto os pseudoelementos agem no próprio elemento.

Verdadeiro
Observe o uso de um único ou duplo : como um caractere de distinção principal no seletor.
Falso
Pseudoelementos são para partes, pseudoclasses são para estado.

Qual das opções a seguir é uma pseudoclasse funcional?

:is()
🎉
:target
As pseudoclasses funcionais têm () depois delas para indicar que aceitam parâmetros.
:empty
As pseudoclasses funcionais têm () depois delas para indicar que aceitam parâmetros.
:not()
🎉

Qual das seguintes pseudoclasses é resultado de uma interação do usuário?

:hover
🎉
:press
Tente novamente.
:squeeze
Tente novamente.
:target
🎉
:focus-within
🎉

Quais das seguintes opções são pseudoclasses de estado <form>?

:enabled
🎉
:fresh
Tente novamente.
:indeterminate
🎉
:checked
🎉
:in-range
🎉
:loading
Tente novamente.
:valid
🎉