← Fundamentos de HTML e CSS: estrutura, apresentação e diagnóstico
05 / 10 · 65 MIN

Cascata, herança e contratos dos seletores

Determinar que declaração fornece um valor e distinguir correspondência, precedência, herança e invalidade após substituição.

Começar pela correspondência

No exemplo, .card > .title exige uma relação de filho direto. Se um section passar a envolver o título, a regra deixa de corresponder, mesmo mantendo todas as classes. Aumentar especificidade ou acrescentar !important não resolve uma condição falsa.

Trocar > por um espaço alarga o âmbito a descendentes mais profundos e pode atingir cartões aninhados; decide se esse alargamento pertence ao contrato do componente.

Uma ordem de decisões

A cascata começa pelas regras relevantes, incluindo seletores e condições de media. Origem, importância e layers precedem a comparação de especificidade. Regras com scope podem ainda exigir comparação de proximidade antes da ordem de aparecimento.

Nos exercícios delimitamos estes fatores: regras de autor, sem animações ou transições, e com scope explicitamente ausente. Assim é possível justificar um resultado sem transformar uma simplificação numa regra universal.

Layers como contrato de integração

Com @layer vendor, app, declarações normais em app têm precedência sobre declarações normais em vendor. O ID do seletor vendor não muda esta relação. Porém, uma regra normal fora de layers tem precedência sobre ambas.

Reabrir vendor depois de app acrescenta regras, sem mover a layer. Para integrar CSS externo, decide onde entram essas regras e conserva a ordem inicial num ponto claro; evita acumular overrides que escondem a causa do conflito.

Peso sem perder o âmbito

A parte :where(#catalog) continua a exigir o contexto de #catalog, mas acrescenta zero à especificidade. Em :where(#catalog) .card > .title, as duas classes exteriores contam. Em contraste, :is(.note, #urgent) usa o peso do argumento de maior especificidade, mesmo num elemento que corresponde por .note.

Esta diferença ajuda a desenhar bibliotecas fáceis de adaptar e explica por que acrescentar uma alternativa com ID pode alterar conflitos existentes.

Importância e estilos inline

Um estilo inline normal vence as regras normais de autor em folhas, mesmo com seletores por ID. Isso não significa que vença todos os mecanismos da cascata. Entre declarações importantes das layers de autor, a ordem das layers inverte-se: a primeira ganha à seguinte, e as importantes agrupadas ganham às importantes fora de layers.

A folha de utilizador importante e as transições exigem outros critérios; os exemplos deste bloco não os simulam.

Herança e reposição

Sem uma declaração própria aplicável, color pode vir do pai; border e margin não são herdadas por omissão. O valor unset segue esta distinção: numa propriedade herdada comporta-se como inherit; nas restantes usa o valor inicial. Não significa remover uma regra e escolher a anterior.

No diagnóstico, regista se o valor vem de uma declaração no elemento, da herança ou da inicialização. A aparência semelhante não demonstra que duas caixas têm a mesma origem de estilo.

Seguir var até ao valor calculado

No label do exemplo, --tone contém 20px e não tem registo @property. Esse valor existe como custom property, mas não é uma cor. A declaração color: var(--tone, red) vence a cascata e só falha depois da substituição.

Não se recupera color: blue, nem se escolhe red por ser uma cor válida: color acaba por herdar green do cartão. Compara este caso com uma variável ausente, em que o fallback pode ser usado, e corrige o contrato do valor antes de multiplicar regras de substituição.

@layer vendor, app;
@layer vendor {
  #catalog .card > .title { color: navy; }
}
@layer app {
  :where(#catalog) .card > .title { color: teal; }
}
.card { color: green; }
.label { color: blue; }
.label { --tone: 20px; color: var(--tone, red); }
NA PRÁTICA

Considera um .card dentro de #catalog, com filhos diretos h2.title e span.label. Só existem estas regras de autor, sem estilos inline, scope, animações, transições ou regras importantes. O título fica teal pela ordem das layers.

O label herda green porque 20px não é uma cor válida após substituição. O fallback red não funciona como verificador de tipo.

Armadilhas comuns

Tratar !important como maior especificidade; aplicar a ordem normal às layers importantes; presumir que :where deixa de restringir a correspondência; usar var como validação de tipo; trocar a ordem das classes no HTML para resolver a cascata.

Tópicos relacionados: Estrutura do documento e semântica · Modelo de caixa, fluxo e overflow · Diagnóstico de estilos e entrega

Leva esta ideia contigo

Primeiro identifica regras aplicáveis e a precedência relevante. Depois compara especificidade e os restantes critérios de desempate. Se a declaração usa var, segue a substituição até ao valor calculado; herança e valor inicial podem explicar um resultado que a simples ordem das regras não explica.

Criar conta

Referência: Cascade order and bounded author-rule comparisons · HTML Living Standard; modular CSS