/* ---------------------------------------------------------------------------
   Ascom Suite — folha do hub. Consome tokens.css; nenhum hexadecimal aqui.
   Sem framework e sem CDN: a tela de login é onde menos se aceita terceiro.
--------------------------------------------------------------------------- */

* { box-sizing: border-box; }

html, body { height: 100%; }

body {
  margin: 0;
  font-family: var(--fonte);
  color: var(--texto);
  -webkit-font-smoothing: antialiased;

  /* O FUNDO DA SUSi, copiado de SUSi AI/dist/assets/styles.css:16.
     Duas camadas, e é o par `scroll, fixed` que faz o efeito: os pontinhos
     acompanham a rolagem e o banho de Tiffany fica preso na base da tela.
     Trocar por um valor só achata isso num degradê comum. */
  background-color: var(--fundo);
  background-image:
    radial-gradient(circle, rgba(10, 186, 181, .18) 1.1px, transparent 1.1px),
    linear-gradient(to top, rgba(10, 186, 181, .2), transparent 52%);
  background-size: 24px 24px, 100% 100%;
  background-repeat: repeat, no-repeat;
  background-attachment: scroll, fixed;
}

/* No tema escuro os pontinhos e o banho precisam de menos força, senão viram
   ruído sobre superfície escura. */
:root[data-tema="escuro"] body {
  background-image:
    radial-gradient(circle, rgba(10, 186, 181, .10) 1.1px, transparent 1.1px),
    linear-gradient(to top, rgba(10, 186, 181, .12), transparent 52%);
}

.sr-so-leitor {
  position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
  overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* --- Tela de entrada ------------------------------------------------------ */

.entrada {
  min-height: 100dvh;
  display: grid;
  place-items: center;
  padding: 1.5rem;
}

.cartao-entrada {
  width: min(380px, 100%);
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-xl);
  box-shadow: var(--sombra-painel);
  padding: 2.25rem 1.75rem 1.75rem;
}

.marca {
  text-align: center;
  margin-bottom: 1.75rem;
}

.marca h1 {
  margin: 0 0 .35rem;
  font-size: 1.9rem;
  font-weight: 700;
  letter-spacing: -.02em;
}

/* O "Suite" ganha a cor viva da marca; o resto fica no texto normal. Mesma ideia
   do nome SUSi em Tiffany no cabeçalho dela. */
.marca h1 b { color: var(--destaque-vivo); font-weight: 700; }
:root[data-tema="escuro"] .marca h1 b { color: var(--destaque); }

.marca p {
  margin: 0;
  color: var(--texto-suave);
  font-size: .92rem;
  line-height: 1.5;
}

.campo { margin-bottom: .85rem; }

.campo label {
  display: block;
  font-size: 11px;
  letter-spacing: .06em;
  text-transform: uppercase;
  font-weight: 700;
  color: var(--apagado);
  margin-bottom: .35rem;
}

/* Campo no padrão da SUSi: pill achatado, sem borda, com o foco marcado por
   box-shadow interno em vez de outline — assim o campo não "pula" 1px ao focar. */
.campo input[type="text"],
.campo input[type="password"] {
  width: 100%;
  font: inherit;
  font-size: 1rem;
  color: var(--texto);
  background: var(--painel-3);
  border: 0;
  border-radius: var(--raio-md);
  padding: .8rem .9rem;
  transition: background var(--dur) var(--ease), box-shadow var(--dur) var(--ease);
}

.campo input::placeholder { color: var(--apagado); opacity: .8; }
.campo input:hover { background: var(--painel-2); }
.campo input:focus {
  outline: none;
  box-shadow: inset 0 0 0 2px var(--destaque);
}

/* Senha + botão de ver. O padding à direita abre espaço para o olho não cobrir
   o texto digitado. */
.campo-senha { position: relative; }
.campo-senha input { padding-right: 3rem; }

.olho {
  position: absolute;
  right: .4rem;
  top: 50%;
  transform: translateY(-50%);
  width: 2.2rem; height: 2.2rem;
  display: grid; place-items: center;
  background: transparent;
  border: 0;
  border-radius: var(--raio-sm);
  color: var(--apagado);
  cursor: pointer;
}
.olho:hover { color: var(--texto-suave); background: var(--neutro-fundo); }
.olho svg { width: 18px; height: 18px; fill: none; stroke: currentColor; stroke-width: 2; }

.lembrar {
  display: flex;
  align-items: center;
  gap: .55rem;
  margin: .9rem 0 1.1rem;
  font-size: .88rem;
  color: var(--texto-suave);
  cursor: pointer;
  user-select: none;
}

.lembrar input {
  appearance: none; -webkit-appearance: none;
  width: 18px; height: 18px; margin: 0;
  border: 1.5px solid var(--apagado);
  border-radius: var(--raio-xs);
  background: transparent;
  cursor: pointer;
  display: grid; place-items: center;
  transition: background var(--dur) var(--ease), border-color var(--dur) var(--ease);
}
.lembrar input:checked {
  background: var(--destaque);
  border-color: var(--destaque);
}
.lembrar input:checked::after {
  content: "";
  width: 10px; height: 6px;
  border-left: 2px solid var(--painel);
  border-bottom: 2px solid var(--painel);
  transform: rotate(-45deg) translate(1px, -1px);
}

.botao {
  width: 100%;
  font: inherit;
  font-size: .98rem;
  font-weight: 600;
  color: var(--sobre-destaque);
  background: var(--destaque);
  border: 0;
  border-radius: var(--raio-total);
  padding: .85rem 1rem;
  cursor: pointer;
  transition: filter var(--dur) var(--ease), opacity var(--dur) var(--ease);
}
.botao:hover:not(:disabled) { filter: brightness(1.08); }
.botao:disabled { opacity: .6; cursor: default; }

/* ÁREA DE AVISO COM ALTURA RESERVADA.
   Regra do DESIGN-SYSTEM §5.1: mensagem que muda a altura do cartão desloca o
   botão e faz a pessoa clicar no lugar errado. (O aviso vem DEPOIS do botão,
   então ele não empurra para baixo — mas o cartão é centrado na vertical, e
   crescer move tudo para cima. Dá no mesmo.)

   3,25rem = 52px NÃO É CHUTE: medido em navegador real, a mensagem mais alta
   ("Muitas tentativas. Tente de novo em 14 min e 59 s." e a de falha de rede)
   ocupa 49,9px em DUAS linhas, e continua em duas linhas de 320px até desktop —
   o cartão encolhe junto com a tela, então a quebra não muda. A versão anterior
   reservava 2,6rem (41,6px) e deslocava o botão em 4px.
   Ao mexer nas mensagens, MEDIR DE NOVO: test/f1b.navegador.mjs prova isso. */
.aviso {
  min-height: 3.25rem;
  margin-top: .9rem;
  display: flex;
  align-items: center;
  justify-content: center;
  text-align: center;
  font-size: .86rem;
  line-height: 1.35;
  border-radius: var(--raio-md);
  padding: .4rem .6rem;
  transition: background var(--dur) var(--ease);
}
.aviso:empty { padding: 0; }
.aviso[data-tom="erro"] { color: var(--perigo); background: var(--perigo-fundo); }
.aviso[data-tom="espera"]{ color: var(--aviso); background: var(--aviso-fundo); }
.aviso[data-tom="ok"] { color: var(--ok); background: var(--ok-fundo); }

/* --- Aviso que faz alguma coisa (FU.0) -----------------------------------

   O aviso de senha inicial deixou de ser um parágrafo e virou dois controles:
   o texto ABRE a tela de troca, e o X fecha o aviso. O aviso de rede segue o
   mesmo desenho, com "Tentar de novo" no lugar do X.

   `:empty` não alcança estes: eles têm filhos. Por isso a largura vem do
   conteúdo e não há `min-height` a zerar. */
.aviso--acao {
  gap: .5rem;
  justify-content: space-between;
  text-align: left;
  padding: .5rem .5rem .5rem .9rem;
}

/* O texto é um botão de verdade — é ele que abre a troca de senha. Sem cara de
   botão: a cara de botão está no aviso inteiro, e dois retângulos aninhados
   leriam como dois alvos diferentes. */
.aviso-texto {
  flex: 1;
  font: inherit;
  color: inherit;
  text-align: left;
  background: transparent;
  border: 0;
  padding: .15rem 0;
  cursor: pointer;
  text-decoration: underline;
  text-underline-offset: 3px;
  text-decoration-thickness: 1px;
  text-decoration-color: rgba(var(--destaque-rgb), .45);
}
/* O do aviso de rede é <span>: não abre nada, quem age é o botão ao lado. */
.aviso-texto--parado { cursor: default; text-decoration: none; }

.aviso-fechar {
  flex: none;
  display: grid;
  place-items: center;
  width: 1.9rem;
  height: 1.9rem;
  color: inherit;
  background: transparent;
  border: 0;
  border-radius: var(--raio-total);
  cursor: pointer;
  opacity: .75;
  transition: background var(--dur) var(--ease), opacity var(--dur) var(--ease);
}
.aviso-fechar:hover { opacity: 1; background: rgba(0, 0, 0, .07); }
:root[data-tema="escuro"] .aviso-fechar:hover { background: rgba(255, 255, 255, .1); }
.aviso-fechar svg {
  width: 1rem; height: 1rem; fill: none;
  stroke: currentColor; stroke-width: 2; stroke-linecap: round;
}

/* A linha do "esqueceu a senha?". Discreta de propósito: é saída de emergência,
   não convite — quem sabe a senha não precisa nem reparar nela. */
.rodape-entrada--ajuda { margin-top: .75rem; }

.rodape-entrada {
  margin-top: 1.25rem;
  text-align: center;
  font-size: .78rem;
  color: var(--apagado);
}

/* ===========================================================================
   PAINEL — a grade de aplicações (F1c)
   =========================================================================== */

.topo {
  position: sticky;
  top: 0;
  z-index: 10;
  background: color-mix(in srgb, var(--fundo) 88%, transparent);
  backdrop-filter: blur(10px);
  border-bottom: 1px solid var(--linha);
}

.topo-interno {
  max-width: var(--largura-max);
  margin-inline: auto;
  padding: .8rem 1.25rem;
  display: flex;
  align-items: center;
  gap: 1rem;
}

.topo-marca { font-weight: 700; font-size: 1.05rem; white-space: nowrap; }
.topo-marca b { color: var(--destaque-vivo); }
:root[data-tema="escuro"] .topo-marca b { color: var(--destaque); }

.topo-busca { flex: 1; min-width: 0; display: flex; justify-content: center; }

/* Campo de busca no padrão da SUSi: pill achatado, sem borda, foco por sombra
   interna — o campo não "pula" 1px ao focar. */
.campo-busca {
  width: min(420px, 100%);
  font: inherit;
  font-size: .92rem;
  color: var(--texto);
  background: var(--painel-3);
  border: 0;
  border-radius: var(--raio-total);
  padding: .55rem 1rem;
  transition: background var(--dur) var(--ease), box-shadow var(--dur) var(--ease);
}
.campo-busca::placeholder { color: var(--apagado); opacity: .85; }
.campo-busca:hover { background: var(--painel-2); }
.campo-busca:focus { outline: none; box-shadow: inset 0 0 0 2px var(--destaque); }
.campo-busca::-webkit-search-cancel-button { -webkit-appearance: none; appearance: none; display: none; }

.topo-pessoa { display: flex; align-items: center; gap: .6rem; white-space: nowrap; }
.pessoa-nome { font-size: .9rem; font-weight: 600; }

.botao-texto {
  font: inherit;
  font-size: .85rem;
  color: var(--texto-suave);
  background: transparent;
  border: 1px solid var(--linha);
  border-radius: var(--raio-total);
  padding: .35rem .85rem;
  cursor: pointer;
}
.botao-texto:hover { background: var(--neutro-fundo); color: var(--texto); }

.tag {
  display: inline-block;
  font-size: .7rem;
  font-weight: 700;
  letter-spacing: .03em;
  text-transform: uppercase;
  padding: .2rem .5rem;
  border-radius: var(--raio-total);
  background: var(--neutro-fundo);
  color: var(--neutro-texto);
}
.tag-papel { background: rgba(var(--destaque-rgb), .12); color: var(--destaque); }

.painel {
  max-width: var(--largura-max);
  margin-inline: auto;
  padding: 1.75rem 1.25rem 4rem;
}

.painel .aviso { max-width: 640px; margin-inline: auto; margin-bottom: 1.5rem; }

.titulo-secao {
  font-size: 11px;
  letter-spacing: .06em;
  text-transform: uppercase;
  font-weight: 700;
  color: var(--apagado);
  margin: 0 0 .25rem;
}
.meta-secao { margin: 0 0 1rem; font-size: .85rem; color: var(--apagado); }
.titulo-secao + .grade { margin-top: 1rem; }

.grade {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(260px, 1fr));
  gap: 20px;
  margin-bottom: 2.5rem;
}

.vazio {
  color: var(--apagado);
  font-size: .9rem;
  padding: 1rem 0 2.5rem;
}

/* --- Cartão de aplicação -------------------------------------------------- */

/* É um <a> de verdade, não uma div com onclick: abrir em nova aba com o meio do
   mouse tem de funcionar, e leitor de tela precisa anunciar "link".

   O cartão mostra SÓ A IMAGEM. O texto (nome, descrição, nível, selo) fica num
   painel que se abre POR CIMA, para baixo, no hover — decisão do dono. Por isso
   o `overflow: hidden` saiu daqui e foi para a .miniatura: é ela que precisa
   recortar a imagem nos cantos; o cartão precisa deixar o painel escapar. */
.cartao-app {
  --cor-app: var(--destaque-rgb); /* sem cor no catálogo, herda o destaque */
  position: relative;
  display: block;
  text-decoration: none;
  color: inherit;
  border-radius: var(--raio-xl);
  transition: transform var(--dur) var(--ease), box-shadow var(--dur) var(--ease);
}

/* O cartão aberto passa por cima dos vizinhos — e sobe no z-index, senão o
   painel apareceria ATRÁS do cartão da linha de baixo. */
.cartao-app:hover,
.cartao-app:focus-within { z-index: 5; }

.miniatura {
  position: relative;
  display: grid;
  place-items: center;
  aspect-ratio: 16 / 10;
  overflow: hidden;
  border: 1px solid var(--linha);
  border-radius: var(--raio-xl);
  background: linear-gradient(135deg, rgba(var(--cor-app), .16), rgba(var(--cor-app), .04));
  box-shadow: var(--elev-1);
  /* `transform` aqui é o CAMINHO DE VOLTA da pegada do arrasto: a escala e o
     giro entram pela regra de `.arrastando` (em --dur-curta, resposta tátil) e
     saem por esta, quando a classe é removida no fim do encaixe. Sem ela a
     miniatura voltaria seca ao pousar. */
  transition: border-color var(--dur) var(--ease), box-shadow var(--dur) var(--ease),
              transform var(--dur) var(--ease);
}
/* Sem contorno colorido no hover — decisão do dono. Quem sinaliza que o cartão
   respondeu é a ELEVAÇÃO; a borda muda de cor a cada passagem do mouse e a grade
   inteira pisca. A cor da aplicação segue viva no fundo da miniatura e na
   etiqueta de nível. */
.cartao-app:hover .miniatura,
.cartao-app:focus-within .miniatura {
  box-shadow: var(--elev-3);
}

/* Placeholder que NUNCA quebra: a inicial em CSS mora embaixo, e a imagem só
   aparece quando carrega de verdade. Regra do DESIGN-SYSTEM §7 — nem imagem
   quebrada, nem espaço vazio. */
.miniatura-inicial {
  font-size: 2.6rem;
  font-weight: 700;
  color: rgb(var(--cor-app));
  opacity: .55;
  user-select: none;
}

.miniatura img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: top center;
}

/* O painel de texto: some do fluxo e aparece por cima, ancorado no rodapé da
   imagem. `position: absolute` de propósito — crescer no fluxo empurraria a
   grade inteira a cada passagem do mouse.

   NÃO usa `display:none` nem `visibility:hidden`: os dois tiram o texto da
   árvore de acessibilidade, e quem usa leitor de tela ficaria só com a imagem.
   Com `opacity` o conteúdo continua lá para ser lido. */
.cartao-corpo {
  position: absolute;
  top: calc(100% - var(--raio-xl));
  left: 0;
  right: 0;
  z-index: 2;
  display: flex;
  flex-direction: column;
  gap: .35rem;
  padding: calc(var(--raio-xl) - .4rem) 1rem 1rem;
  background: var(--painel);
  border: 1px solid var(--linha);
  border-top: 0;
  border-radius: 0 0 var(--raio-xl) var(--raio-xl);
  box-shadow: var(--elev-3);
  opacity: 0;
  pointer-events: none;
  transform: translateY(-8px);
  transition: opacity var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.cartao-app:hover .cartao-corpo,
.cartao-app:focus-within .cartao-corpo {
  opacity: 1;
  pointer-events: auto;
  transform: none;
}

/* ATENCAO: EM TELA DE TOQUE NÃO EXISTE HOVER. Sem isto, no celular o texto NUNCA
   apareceria — tocar no cartão navega. Em ponteiro grosso o painel volta a ser
   parte do cartão, sempre visível. */
@media (hover: none) {
  .cartao-corpo {
    position: static;
    opacity: 1;
    pointer-events: auto;
    transform: none;
    border: 1px solid var(--linha);
    border-top: 0;
    box-shadow: none;
    padding: .95rem 1rem 1rem;
  }
  .miniatura { border-radius: var(--raio-xl) var(--raio-xl) 0 0; }
}

.cartao-titulo { font-size: 1.02rem; font-weight: 700; }

.cartao-descricao {
  font-size: .84rem;
  line-height: 1.45;
  color: var(--texto-suave);
  flex: 1;
}

.cartao-rodape {
  display: flex;
  align-items: center;
  gap: .5rem;
  flex-wrap: wrap;
  margin-top: .55rem;
}

.tag-nivel { background: rgba(var(--cor-app), .12); color: rgb(var(--cor-app)); }

/* O selo é a regra §2.5 da filosofia virando pixel: enquanto o SSO não existe
   para aquele app, o cartão diz que ele vai pedir senha própria. */
.selo {
  font-size: .74rem;
  color: var(--apagado);
  display: inline-flex;
  align-items: center;
  gap: .25rem;
}
.selo--sso { color: var(--ok); }

/* F2.C.4 — o selo que é um caminho, não só um recado. Sublinhado e não só
   colorido: cor sozinha não é sinal suficiente (DESIGN-SYSTEM §6), e aqui ela
   precisaria competir com a cor de destaque do próprio cartão. */
.selo--acao {
  color: var(--aviso);
  text-decoration: underline;
  text-underline-offset: 2px;
  cursor: pointer;
}
.selo--acao:hover { color: var(--texto); }

/* Sem acesso: aparece, apagado. Esconder faria a pessoa não saber que a
   ferramenta existe — e o hub existe justamente para isso. */
.grade--apagada .cartao-app {
  opacity: .55;
  filter: saturate(.4);
  cursor: default;
  box-shadow: none;
}
.grade--apagada .cartao-app:hover .miniatura { border-color: var(--linha); box-shadow: var(--elev-1); }

/* Sem acesso = sem miniatura (o servidor não manda). Um cartão só de imagem
   viraria um quadrado vazio, então aqui o texto fica sempre à vista. */
.grade--apagada .cartao-corpo {
  position: static;
  opacity: 1;
  transform: none;
  border: 1px solid var(--linha);
  border-top: 0;
  box-shadow: none;
  padding: .95rem 1rem 1rem;
}
.grade--apagada .miniatura { border-radius: var(--raio-xl) var(--raio-xl) 0 0; }

@media (max-width: 640px) {
  .topo-interno { flex-wrap: wrap; gap: .6rem; }
  .topo-busca { order: 3; flex-basis: 100%; }
  .topo-busca .campo-busca { width: 100%; }
  .grade { grid-template-columns: 1fr; }
}

[hidden] { display: none !important; }

/* ===========================================================================
   APARÊNCIA — tema e cor por pessoa (F1d)
   Mecânica herdada do Lupagram (interruptor + bolinhas de cor). O que muda é o
   escopo: lá era por MODO, aqui é por PESSOA, e fica guardado na conta.
   =========================================================================== */

.ajustes-wrap { position: relative; }

.botao-icone {
  width: 2.1rem; height: 2.1rem;
  display: grid; place-items: center;
  background: transparent;
  border: 1px solid var(--linha);
  border-radius: var(--raio-total);
  color: var(--texto-suave);
  cursor: pointer;
  padding: 0;
}
.botao-icone:hover { background: var(--neutro-fundo); color: var(--texto); }
.botao-icone svg { width: 16px; height: 16px; fill: none; stroke: currentColor; stroke-width: 2; stroke-linecap: round; }
.botao-icone[aria-expanded="true"] { background: rgba(var(--destaque-rgb), .12); color: var(--destaque); border-color: var(--destaque); }

.ajustes {
  position: absolute;
  top: calc(100% + 10px);
  right: 0;
  z-index: 20;
  width: 268px;
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-lg);
  box-shadow: var(--sombra-painel);
  padding: .9rem 1rem 1rem;
}

.ajustes-titulo {
  margin: 0 0 .75rem;
  font-size: 11px; letter-spacing: .06em; text-transform: uppercase;
  font-weight: 700; color: var(--apagado);
}

.controle {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: .75rem;
  font-size: .88rem;
  color: var(--texto-suave);
  padding: .45rem 0;
  cursor: pointer;
}

.ajustes-nota {
  margin: .6rem 0 0;
  font-size: .74rem;
  line-height: 1.4;
  color: var(--apagado);
  border-top: 1px solid var(--linha);
  padding-top: .6rem;
}

/* Interruptor — do Lupagram. */
.chave { position: relative; display: inline-block; width: 38px; height: 21px; flex: none; }
.chave input { position: absolute; opacity: 0; width: 100%; height: 100%; margin: 0; cursor: pointer; }
.chave-trilho {
  position: absolute; inset: 0;
  background: var(--painel-3);
  border-radius: var(--raio-total);
  transition: background var(--dur) var(--ease);
  pointer-events: none;
}
.chave-trilho::after {
  content: "";
  position: absolute; top: 3px; left: 3px;
  width: 15px; height: 15px;
  background: var(--painel);
  border-radius: 50%;
  box-shadow: var(--elev-1);
  transition: transform var(--dur) var(--ease);
}
.chave input:checked + .chave-trilho { background: var(--destaque); }
.chave input:checked + .chave-trilho::after { transform: translateX(17px); }
.chave input:focus-visible + .chave-trilho { outline: 2px solid rgba(var(--destaque-rgb), .7); outline-offset: 2px; }

/* Bolinhas de cor — do Lupagram (.hi-dot).

   ATENCAO: A cor de cada bolinha mora AQUI, não num style="--ponto:…" no HTML.
   `style-src 'self'` bloqueia atributo style vindo do markup — as bolinhas
   ficavam sem cor nenhuma, e só o teste de navegador mostrou (o de API não vê
   CSP). Definir por JS funcionaria (CSSOM não é bloqueado), mas cor fixa e
   conhecida é folha de estilo, não script. */
.ponto[data-destaque="tiffany"] { --ponto: 10, 186, 181; }
.ponto[data-destaque="verde"] { --ponto: 69, 208, 162; }
.ponto[data-destaque="rosa"] { --ponto: 245, 120, 205; }
.ponto[data-destaque="azul"] { --ponto: 110, 180, 255; }

.pontos { display: flex; gap: 9px; }
.ponto {
  width: 20px; height: 20px;
  border-radius: 50%;
  background: rgb(var(--ponto));
  border: 2px solid transparent;
  padding: 0;
  cursor: pointer;
  box-shadow: var(--elev-1);
  transition: box-shadow var(--dur) var(--ease), border-color var(--dur) var(--ease);
}
.ponto[aria-checked="true"] {
  border-color: var(--texto);
  box-shadow: 0 0 0 3px rgba(var(--ponto), .3);
}

/* ===========================================================================
   ADMINISTRAÇÃO — pessoas, acessos e catálogo (F1e)
   =========================================================================== */

.titulo-tela { font-size: .92rem; font-weight: 600; color: var(--texto-suave); }

.botao--curto { width: auto; padding: .55rem 1.1rem; font-size: .88rem; }

/* ATENCAO: `.botao--discreto` era usado em TRÊS diálogos e no botão de visitante SEM
   REGRA NENHUMA: "Cancelar" saía pintado igualzinho a "Salvar". Duas ações com o
   mesmo peso visual, e a que desfaz do lado da que confirma — o olho escolhe
   pela posição, que é como se aperta o botão errado.
   Silencioso, mas com contorno: continua parecendo botão, e não texto solto. */
.botao--discreto {
  background: transparent;
  color: var(--texto-suave);
  border: 1px solid var(--linha);
}
.botao--discreto:hover { background: var(--painel-2); color: var(--texto); }
:root[data-forma="poligonal"] .botao--discreto {
  border: 0;
  background: var(--painel-3);
  border-radius: 0;
  clip-path: polygon(
    var(--chanfro) 0, 100% 0,
    100% calc(100% - var(--chanfro)), calc(100% - var(--chanfro)) 100%,
    0 100%, 0 var(--chanfro));
}
.botao-largo { width: 100%; margin-top: .7rem; }

.admin-cabeca {
  display: flex; align-items: center; justify-content: space-between;
  gap: 1rem; margin-bottom: 1rem; flex-wrap: wrap;
}
.admin-cabeca .titulo-secao { margin: 0; }

.lista-pessoas { display: flex; flex-direction: column; gap: 8px; margin-bottom: 2rem; }

.pessoa-linha {
  display: flex; align-items: center; gap: .85rem;
  width: 100%; text-align: left;
  font: inherit; color: inherit;
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-lg);
  padding: .7rem .9rem;
  cursor: pointer;
  transition: border-color var(--dur) var(--ease), background var(--dur) var(--ease);
}
.pessoa-linha:hover { border-color: var(--destaque); }
.pessoa-linha[aria-current="true"] { border-color: var(--destaque); background: rgba(var(--destaque-rgb), .06); }

.pessoa-avatar {
  width: 34px; height: 34px; flex: none;
  display: grid; place-items: center;
  border-radius: 50%;
  background: rgba(var(--destaque-rgb), .14);
  color: var(--destaque);
  font-weight: 700; font-size: .9rem;
}
.pessoa-dados { display: flex; flex-direction: column; gap: 1px; flex: 1; min-width: 0; }
.pessoa-titulo { font-weight: 600; font-size: .95rem; }
.pessoa-sub { font-size: .78rem; color: var(--apagado); }
.pessoa-papel { background: rgba(var(--destaque-rgb), .12); color: var(--destaque); }
.pessoa-estado[data-ativo="nao"] { background: var(--perigo-fundo); color: var(--perigo); }
.pessoa-estado[data-ativo="sim"] { background: var(--ok-fundo); color: var(--ok); }

/* --- Ficha da pessoa ------------------------------------------------------ */

.ficha {
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-xl);
  box-shadow: var(--sombra-painel);
  padding: 1.25rem 1.4rem 1.4rem;
  max-width: 640px;
}
.ficha-topo { display: flex; align-items: flex-start; justify-content: space-between; gap: 1rem; margin-bottom: 1rem; }
.ficha-nome { margin: 0 0 .15rem; font-size: 1.15rem; }
.ficha-meta { margin: 0; font-size: .8rem; color: var(--apagado); }
.ficha-linha { padding: .7rem 0; border-top: 1px solid var(--linha); }
.ficha-linha > label { display: block; font-size: 11px; letter-spacing: .06em; text-transform: uppercase; font-weight: 700; color: var(--apagado); margin-bottom: .4rem; }
.ficha-linha.controle { flex-direction: row; align-items: center; }
.ficha-linha.controle > span:first-child { font-size: .9rem; color: var(--texto); }
.ficha-dica { margin: .35rem 0 0; font-size: .76rem; color: var(--apagado); }
.ficha-subtitulo { margin: 1.2rem 0 .6rem; }

select, .linha-botao input[type="text"] {
  font: inherit; font-size: .92rem;
  color: var(--texto);
  background: var(--painel-3);
  border: 0; border-radius: var(--raio-md);
  padding: .6rem .75rem;
  width: 100%;
}
select:focus, .linha-botao input:focus { outline: none; box-shadow: inset 0 0 0 2px var(--destaque); }

.linha-botao { display: flex; gap: .6rem; align-items: center; }
.linha-botao .botao { flex: none; }

.permissoes { display: flex; flex-direction: column; gap: 6px; }
.permissao {
  display: flex; align-items: center; gap: .75rem;
  padding: .4rem .6rem;
  border-radius: var(--raio-md);
  background: var(--fundo-2);
}
.permissao-nome { flex: 1; font-size: .9rem; }
.permissao-nivel { width: auto; min-width: 170px; flex: none; }

/* --- F2.C.1: a ponte de identidade ---------------------------------------- */

.vinculos { display: flex; flex-direction: column; gap: 6px; }

/* Grade e não flex: a nota ocupa a linha inteira embaixo, e com flex-wrap ela
   ficaria pendurada na coluna do botão. */
.vinculo {
  display: grid;
  grid-template-columns: minmax(6rem, auto) 1fr auto;
  align-items: center;
  gap: .5rem .75rem;
  padding: .5rem .6rem;
  border-radius: var(--raio-md);
  background: var(--fundo-2);
}
.vinculo-app { font-size: .9rem; font-weight: 600; }

/* O NOME em tamanho de leitura, o identificador menor e apagado. Mostrar só o
   codigo foi o que quase deu a uma pessoa a identidade de outra. */
.vinculo-quem { font-size: .9rem; display: flex; flex-direction: column; gap: .1rem; min-width: 0; }
.vinculo-id {
  font-size: .72rem; color: var(--apagado);
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  overflow-wrap: anywhere;
}
.vinculo-escolha { min-width: 0; width: 100%; }
.vinculo-nota {
  grid-column: 1 / -1;
  margin: 0; font-size: .76rem; color: var(--apagado);
}
.vinculo-nota[data-tom="espera"] { color: var(--aviso); }

@media (max-width: 640px) {
  /* Em coluna: com 380px, "nome | escolha | botao" espreme os tres. */
  .vinculo { grid-template-columns: 1fr; }
}

/* --- Diálogos ------------------------------------------------------------- */

.cortina {
  position: fixed; inset: 0; z-index: 50;
  display: grid; place-items: center;
  padding: 1.5rem;
  background: rgba(0, 0, 0, .45);
  overflow-y: auto;
}
.dialogo-titulo { margin: 0 0 1.25rem; font-size: 1.25rem; text-align: center; }
.cortina .aviso { margin-top: .7rem; }
.cortina .linha-botao { margin-top: 1rem; }
.cortina .linha-botao .botao { flex: 1; }

@media (max-width: 640px) {
  .permissao { flex-direction: column; align-items: stretch; gap: .35rem; }
  .permissao-nivel { width: 100%; }
}

/* --- Marca: triângulo com um olho ---------------------------------------- */

/* `currentColor` no símbolo faz a marca acompanhar a cor de destaque da pessoa
   e funcionar nos dois temas — sem uma segunda arte para o escuro. */
.marca-simbolo {
  width: 1.15em;
  height: 1.15em;
  vertical-align: -.18em;
  margin-right: .4em;
  color: var(--destaque-vivo);
  flex: none;
}
:root[data-tema="escuro"] .marca-simbolo { color: var(--destaque); }

.marca-simbolo--grande {
  display: block;
  width: 3.1rem;
  height: 3.1rem;
  margin: 0 auto .6rem;
}

/* Separador "ou" entre entrar com senha e entrar como visitante. */
.ou {
  display: flex; align-items: center; gap: .8rem;
  margin: 1.1rem 0 .9rem;
  color: var(--apagado); font-size: .78rem;
}
.ou::before, .ou::after {
  content: ""; flex: 1; height: 1px; background: var(--linha);
}

/* ===========================================================================
   FORMA POLIGONAL — terceiro eixo da personalização (data-forma)
   ===========================================================================
   Tudo abaixo só vale sob :root[data-forma="poligonal"]. O padrão
   ("arredondada") continua exatamente como estava — nada aqui o altera.

   TRÊS COISAS QUE O clip-path QUEBRA, e como cada uma é resolvida:

   1. Ele COME A SOMBRA. `box-shadow` é pintado fora do recorte e some. A
      elevação passa a vir de `filter: drop-shadow()`, que acompanha o contorno.
   2. Ele COME O ANEL DE FOCO. `outline` é cortado nos cantos e some. O foco
      passa a ser `box-shadow: inset`, que é pintado por dentro.
   3. NÃO EXISTE BORDA em clip-path. O contorno se faz com duas camadas: a de
      baixo na cor da linha, a de cima recuada na cor do painel.

   E a regra que impede virar bagunça: os cantos desviam SÓ PARA DENTRO. Assim
   os blocos continuam alinhados na grade, por mais tortos que fiquem.
   =========================================================================== */

:root[data-forma="poligonal"] {
  --torto: 9px; /* desvio máximo de canto — o único número a mexer */
  --chanfro: 11px; /* corte reto dos controles */
}

/* --- Blocos grandes: cartão de entrada, ficha, diálogos ------------------- */

:root[data-forma="poligonal"] .cartao-entrada,
:root[data-forma="poligonal"] .ficha {
  border: 0;
  border-radius: 0;
  box-shadow: none;
  filter: drop-shadow(0 14px 34px rgba(20, 45, 50, .16));
  /* Recorte mais forte aqui de propósito: o cartão de entrada é o herói da
     tela, e é onde a estética se apresenta. */
  clip-path: polygon(
    0 calc(var(--torto) * 1.4),
    calc(100% - var(--torto) * 1.8) 0,
    100% calc(var(--torto) * .6),
    100% calc(100% - var(--torto) * 1.2),
    calc(var(--torto) * 1.6) 100%,
    0 calc(100% - var(--torto) * .5)
  );
  /* O recorte come o preenchimento nos cantos: sem folga a mais, o texto
     encosta na diagonal. */
  padding: 2.6rem 2.1rem 2.1rem;
}

:root[data-tema="escuro"][data-forma="poligonal"] .cartao-entrada,
:root[data-tema="escuro"][data-forma="poligonal"] .ficha {
  filter: drop-shadow(0 18px 44px rgba(0, 0, 0, .5));
}

/* --- Cartões de aplicação ------------------------------------------------- */

/* A sombra sobe para o cartão inteiro: dentro da .miniatura ela seria cortada. */
:root[data-forma="poligonal"] .cartao-app {
  filter: drop-shadow(0 3px 8px rgba(20, 45, 50, .14));
  transition: filter var(--dur) var(--ease), transform var(--dur) var(--ease);
}
:root[data-forma="poligonal"] .cartao-app:hover,
:root[data-forma="poligonal"] .cartao-app:focus-within {
  filter: drop-shadow(0 10px 22px rgba(20, 45, 50, .22));
}
:root[data-tema="escuro"][data-forma="poligonal"] .cartao-app {
  filter: drop-shadow(0 3px 10px rgba(0, 0, 0, .45));
}

:root[data-forma="poligonal"] .miniatura {
  border: 0;
  border-radius: 0;
  box-shadow: none;
}
:root[data-forma="poligonal"] .cartao-app:hover .miniatura,
:root[data-forma="poligonal"] .cartao-app:focus-within .miniatura { box-shadow: none; }

:root[data-forma="poligonal"] .cartao-corpo {
  border: 0;
  border-radius: 0;
  box-shadow: none;
  /* Topo RETO: é a costura com a miniatura, que fica logo acima. Torto dos dois
     lados deixaria uma fresta. */
  clip-path: polygon(
    0 0, 100% 0,
    100% calc(100% - var(--torto) * .8),
    calc(var(--torto) * 1.2) 100%,
    0 calc(100% - var(--torto) * .3)
  );
  padding: calc(var(--raio-xl) - .4rem) 1.1rem 1.4rem;
}

/* SEIS silhuetas, escolhidas pelo IDENTIFICADOR da aplicação (hub.js). Não é
   sorteio: o SUSi tem sempre a mesma forma, e você aprende a reconhecer de
   longe. Sorteio a cada carregamento faria a grade parecer instável. */
:root[data-forma="poligonal"] .cartao-app[data-forma-i="0"] .miniatura {
  clip-path: polygon(0 var(--torto), calc(100% - var(--torto)) 0, 100% calc(100% - var(--torto) * .4), var(--torto) 100%);
}
:root[data-forma="poligonal"] .cartao-app[data-forma-i="1"] .miniatura {
  clip-path: polygon(var(--torto) 0, 100% calc(var(--torto) * .5), calc(100% - var(--torto) * .8) 100%, 0 calc(100% - var(--torto) * .6));
}
:root[data-forma="poligonal"] .cartao-app[data-forma-i="2"] .miniatura {
  clip-path: polygon(0 calc(var(--torto) * .4), calc(100% - var(--torto) * .6) 0, 100% 100%, calc(var(--torto) * .9) calc(100% - var(--torto) * .3));
}
:root[data-forma="poligonal"] .cartao-app[data-forma-i="3"] .miniatura {
  clip-path: polygon(calc(var(--torto) * .7) 0, calc(100% - var(--torto) * .3) calc(var(--torto) * .6), 100% calc(100% - var(--torto)), 0 100%);
}
:root[data-forma="poligonal"] .cartao-app[data-forma-i="4"] .miniatura {
  clip-path: polygon(0 0, 100% calc(var(--torto) * .8), calc(100% - var(--torto) * .5) calc(100% - var(--torto) * .5), var(--torto) 100%);
}
:root[data-forma="poligonal"] .cartao-app[data-forma-i="5"] .miniatura {
  clip-path: polygon(calc(var(--torto) * .5) calc(var(--torto) * .6), 100% 0, 100% 100%, 0 calc(100% - var(--torto) * .9));
}

/* Grade um pouco mais folgada: silhuetas irregulares se atropelam com o mesmo
   espaçamento das arredondadas. */
:root[data-forma="poligonal"] .grade { gap: 26px; }

/* --- Controles: CHANFRO, não torto ---------------------------------------- */

/* Botão torto lê como erro de renderização; chanfro lê como decisão. O corte é
   sempre nos mesmos dois cantos opostos — previsível, porque é um controle. */
:root[data-forma="poligonal"] .botao,
:root[data-forma="poligonal"] .botao-texto,
:root[data-forma="poligonal"] .botao-icone,
:root[data-forma="poligonal"] .campo input[type="text"],
:root[data-forma="poligonal"] .campo input[type="password"],
:root[data-forma="poligonal"] .campo-busca,
:root[data-forma="poligonal"] select,
:root[data-forma="poligonal"] .linha-botao input[type="text"] {
  border-radius: 0;
  clip-path: polygon(
    var(--chanfro) 0, 100% 0,
    100% calc(100% - var(--chanfro)), calc(100% - var(--chanfro)) 100%,
    0 100%, 0 var(--chanfro)
  );
}

:root[data-forma="poligonal"] .botao-icone { border: 0; background: var(--painel-3); }
:root[data-forma="poligonal"] .botao-texto { border: 0; background: var(--painel-3); }

/* O `outline` é cortado pelo recorte e some. `box-shadow: inset` é pintado por
   dentro e sobrevive — sem isso, o tema poligonal quebra o uso por teclado. */
:root[data-forma="poligonal"] :where(a, button, input, select, textarea, [tabindex]):focus-visible {
  outline: none;
  box-shadow: inset 0 0 0 2px var(--painel), inset 0 0 0 4px rgb(var(--destaque-rgb));
}

/* Etiquetas: a pílula vira hexágono achatado, cortado nas duas pontas. */
:root[data-forma="poligonal"] .tag,
:root[data-forma="poligonal"] .pessoa-avatar {
  border-radius: 0;
  clip-path: polygon(6px 0, 100% 0, calc(100% - 6px) 100%, 0 100%);
  padding-inline: .7rem;
}

:root[data-forma="poligonal"] .ponto { border-radius: 0; clip-path: polygon(50% 0, 100% 50%, 50% 100%, 0 50%); }
:root[data-forma="poligonal"] .chave-trilho { border-radius: 0; }
:root[data-forma="poligonal"] .chave-trilho::after { border-radius: 0; }
:root[data-forma="poligonal"] .lembrar input { border-radius: 0; }
:root[data-forma="poligonal"] .aviso { border-radius: 0; clip-path: polygon(8px 0, 100% 0, calc(100% - 8px) 100%, 0 100%); }
:root[data-forma="poligonal"] .pessoa-linha { border-radius: 0; }
:root[data-forma="poligonal"] .permissao { border-radius: 0; }

/* Em tela de toque o painel de texto volta ao fluxo (ver @media hover:none):
   ali ele precisa do topo reto e do fundo torto, encaixando na miniatura. */
@media (hover: none) {
  :root[data-forma="poligonal"] .cartao-corpo { padding: 1.1rem 1.1rem 1.4rem; }
}

/* O <svg> que só define o <symbol> da marca. Fora do fluxo, invisível.
   ATENCAO: Estava como style="position:absolute" no HTML e a CSP bloqueava — mesmo
   erro das bolinhas de cor. Atributo style vindo do markup é sempre recusado
   por `style-src 'self'`; o teste de navegador é o único que enxerga isso. */
.defs-marca { position: absolute; }

/* ===========================================================================
   MODO DE EDIÇÃO (F1g) — engrenagem flutuante, seções e arrastar
   =========================================================================== */

/* Botão de ação flutuante — CÍRCULO, só o ícone (F1k). Fundo na COR DE DESTAQUE,
   não no branco do painel: branco sobre o fundo claro da SUSi some no canto — e
   sumiu mesmo.

   O rótulo "Organizar" saiu da pílula. Ele existia por um motivo registrado (o
   dono não achou o modo de edição quando era só ícone), então a descoberta foi
   devolvida em dois lugares: a etiqueta no hover/foco, e a revelação de uma vez
   só na primeira visita (.flutuante--revelando, ligada pelo hub.js). */
.flutuante {
  position: fixed;
  right: 1.5rem;
  bottom: 1.5rem;
  z-index: 30;
  /* Botão primeiro no DOM (para o `+` alcançar a etiqueta), etiqueta à esquerda
     na tela. Quem inverte é aqui. */
  display: flex;
  flex-direction: row-reverse;
  align-items: center;
  gap: .6rem;
}

.engrenagem {
  width: 3.4rem; height: 3.4rem;
  flex: none;
  display: grid; place-items: center;
  padding: 0;
  border: 0; border-radius: 50%;
  background: var(--destaque);
  color: var(--sobre-destaque);
  box-shadow: var(--sombra-painel);
  cursor: pointer;
  transition: transform var(--dur) var(--ease), filter var(--dur) var(--ease),
              background var(--dur) var(--ease), color var(--dur) var(--ease);
}
.engrenagem:hover { filter: brightness(1.08); transform: scale(1.06); }
/* Afundar sob o dedo é a única confirmação tátil possível numa tela — e é o que
   responde ao "responsivo" do pedido. Curta de propósito: 180ms aqui já atrasa. */
.engrenagem:active { transform: scale(.94); transition-duration: var(--dur-curta); }

/* Ligado: inverte para o painel, com o ícone na cor de destaque — fica óbvio que
   é o mesmo botão em outro estado, e não um segundo botão. */
.engrenagem[aria-pressed="true"] {
  background: var(--painel);
  color: var(--destaque);
  animation: pulso-ligado 460ms var(--ease);
}
/* Pulso de escala, não anel de sombra: no tema poligonal o `clip-path` comeria
   qualquer anel, e escala funciona igual nas duas formas — um comportamento só. */
@keyframes pulso-ligado {
  0% { transform: scale(1); }
  45% { transform: scale(1.12); }
  100% { transform: scale(1); }
}

/* Os dois ícones ocupam a MESMA célula de grade e se cruzam. */
.engrenagem-icones { display: grid; place-items: center; width: 21px; height: 21px; }
.engrenagem-icones svg {
  grid-area: 1 / 1;
  width: 21px; height: 21px;
  fill: none; stroke: currentColor; stroke-width: 2;
  stroke-linecap: round; stroke-linejoin: round;
  transition: opacity var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.icone-tique { opacity: 0; transform: rotate(-90deg) scale(.6); }
.engrenagem[aria-pressed="true"] .icone-lapis { opacity: 0; transform: rotate(90deg) scale(.6); }
.engrenagem[aria-pressed="true"] .icone-tique { opacity: 1; transform: none; }

/* A etiqueta. Irmã do botão, nunca ::after dele — clip-path recorta pseudo-
   elemento junto, e no tema poligonal ela sairia cortada pela metade. */
.flutuante-etiqueta {
  pointer-events: none;
  white-space: nowrap;
  font-size: .85rem; font-weight: 600;
  color: var(--texto);
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-total);
  padding: .4rem .8rem;
  box-shadow: var(--elev-2);
  opacity: 0;
  transform: translateX(8px);
  transition: opacity var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.engrenagem:hover + .flutuante-etiqueta,
.engrenagem:focus-visible + .flutuante-etiqueta,
.flutuante--revelando .flutuante-etiqueta {
  opacity: 1;
  transform: none;
}

/* No poligonal o botão pega o MESMO chanfro de dois cantos dos outros controles
   — é a língua do tema, e botão torto leria como erro de renderização
   (DESIGN-SYSTEM §8). O corte é maior que o dos campos porque `--chanfro` foi
   calibrado para controles de ~40px: num quadrado de 54px ele fica tímido e o
   botão parece um círculo mal-acabado.

   ATENCAO: `box-shadow` é pintado FORA do recorte e some: a elevação vira drop-shadow,
   que acompanha o contorno. É a armadilha nº 1 do §8. */
:root[data-forma="poligonal"] { --chanfro-flutuante: 16px; }
:root[data-forma="poligonal"] .engrenagem {
  border-radius: 0;
  box-shadow: none;
  filter: drop-shadow(0 10px 22px rgba(20, 45, 50, .28));
  clip-path: polygon(
    var(--chanfro-flutuante) 0, 100% 0,
    100% calc(100% - var(--chanfro-flutuante)), calc(100% - var(--chanfro-flutuante)) 100%,
    0 100%, 0 var(--chanfro-flutuante)
  );
}
:root[data-tema="escuro"][data-forma="poligonal"] .engrenagem {
  filter: drop-shadow(0 12px 26px rgba(0, 0, 0, .55));
}
/* ATENCAO: O `box-shadow: none` da regra acima é MAIS TARDIO, na folha, que a regra
   genérica de foco do tema poligonal (a de `box-shadow: inset`) e tem a MESMA
   especificidade — então apagava o anel e o botão ficava sem rastro nenhum para
   quem usa teclado. Só o teste de navegador enxerga isto.
   Os dois anéis servem aos dois estados: com a edição desligada o fundo é o
   destaque e quem aparece é o anel de painel; com ela ligada o fundo é o painel
   e quem aparece é o de destaque. */
:root[data-forma="poligonal"] .engrenagem:focus-visible {
  box-shadow: inset 0 0 0 2px var(--painel), inset 0 0 0 5px rgb(var(--destaque-rgb));
}
/* A etiqueta é elemento próprio, então aqui o clip-path não atrapalha nada. */
:root[data-forma="poligonal"] .flutuante-etiqueta {
  border: 0;
  border-radius: 0;
  background: var(--painel-3);
  clip-path: polygon(8px 0, 100% 0, calc(100% - 8px) 100%, 0 100%);
  padding-inline: 1rem;
}

.barra-edicao {
  position: sticky;
  top: 0;
  z-index: 20;
  display: flex; align-items: center; gap: .8rem; flex-wrap: wrap;
  padding: .7rem 1.25rem;
  background: var(--destaque);
  color: var(--sobre-destaque);
  font-size: .88rem;
}
.barra-edicao-texto { flex: 1; min-width: 12rem; }

/* O estado de salvar. Reserva altura nenhuma porque está numa barra em linha —
   mas reserva a COR, para "Ordem salva" não repintar a barra inteira. */
.barra-edicao-estado {
  font-size: .82rem; font-weight: 600;
  padding: .2rem .6rem;
  border-radius: var(--raio-total);
  background: rgba(var(--sobre-destaque-rgb), .18);
  opacity: 0;
  transition: opacity var(--dur) var(--ease);
}
.barra-edicao-estado:not(:empty) { opacity: 1; }
.barra-edicao-estado[data-tom="erro"] { background: var(--perigo); color: var(--sobre-perigo); }
:root[data-forma="poligonal"] .barra-edicao-estado {
  border-radius: 0;
  clip-path: polygon(6px 0, 100% 0, calc(100% - 6px) 100%, 0 100%);
}
.barra-edicao .botao-texto { color: var(--sobre-destaque); border-color: rgba(var(--sobre-destaque-rgb), .5); background: transparent; }
.barra-edicao .botao-texto:hover { background: rgba(var(--sobre-destaque-rgb), .16); color: var(--sobre-destaque); }
.barra-edicao .botao { background: var(--painel); color: var(--destaque); }

.secao-cabeca { display: flex; align-items: center; gap: .8rem; }
.secao-acoes { display: none; gap: .4rem; }
.secao-vazia { display: none; color: var(--apagado); font-size: .85rem; padding: 1.2rem 0 2rem; }

/* Só o modo de edição revela os controles das seções e o alvo de largar. */
body.editando .secao-acoes { display: inline-flex; }
body.editando .secao-vazia:only-child,
body.editando .grade:empty + .secao-vazia { display: block; }

/* Em edição o cartão vira peça, não link: cursor de mover e nada de navegar.

   ATENCAO: `touch-action: none` NÃO É DETALHE. Sem ele o navegador entende o dedo como
   rolagem, começa a rolar e dispara `pointercancel` — o arrasto morre antes de
   começar, e o painel é usado no celular. O `preventDefault()` do pointermove
   chega tarde: a decisão de rolar já foi tomada. Isto é o que faz o caminho de
   toque (a razão de ter escolhido Pointer Events) existir de verdade.

   Só em edição: fora dela, arrastar por cima de um cartão tem de rolar a página. */
body.editando .cartao-app { cursor: grab; touch-action: none; }
body.editando .cartao-app .cartao-corpo { display: none; }
body.editando .grade {
  outline: 1.5px dashed var(--linha);
  outline-offset: 10px;
  border-radius: var(--raio-md);
  min-height: 60px;
  transition: outline-color var(--dur) var(--ease), background var(--dur) var(--ease);
}
/* A seção que vai receber se acende. Sem isto não se sabe onde o cartão cai —
   o tracejado era sempre igual em todas as seções. */
body.editando .grade.grade--alvo {
  outline-color: var(--destaque);
  background: rgba(var(--destaque-rgb), .05);
}
/* O botão flutuante não pode cobrir a última linha de cartões. */
body.editando .painel { padding-bottom: 7rem; }

/* --- O cartão erguido ------------------------------------------------------
   Antes ele ENCOLHIA e APAGAVA (opacity .55, scale .96) — esse é o vocabulário
   de "desabilitado". Pegar um objeto o traz PARA FRENTE, não para trás.

   Divisão de trabalho, e ela importa: o JS escreve só o `translate` no CARTÃO
   (para seguir o ponteiro sem atraso nenhum), e o CSS cuida da pegada — escala,
   giro e sombra — na MINIATURA, com transição própria. Se a escala estivesse no
   mesmo transform do JS, ou o seguir ficaria travado pela transição, ou a
   pegada entraria seca. */
.cartao-app.arrastando {
  /* Sair do teste de acerto do ponteiro, senão `elementFromPoint` devolve ele
     mesmo e nunca se acha o destino. */
  pointer-events: none;
  opacity: 1;
  z-index: 40;
  cursor: grabbing;
  will-change: transform; /* só durante o arrasto: permanente custa memória */
}
.cartao-app.arrastando .miniatura {
  /* O giro de -1,5° é o que separa "arrastando" de "só maior": objeto erguido
     por uma mão nunca fica alinhado, e o olho lê isso antes de qualquer pista. */
  transform: scale(1.04) rotate(-1.5deg);
  box-shadow: var(--elev-3), 0 18px 34px rgba(20, 45, 50, .28);
  transition: transform var(--dur-curta) var(--ease), box-shadow var(--dur-curta) var(--ease);
}
:root[data-tema="escuro"] .cartao-app.arrastando .miniatura {
  box-shadow: var(--elev-3), 0 18px 34px rgba(0, 0, 0, .55);
}
/* No poligonal a sombra da miniatura é recortada; quem a carrega é o cartão. */
:root[data-forma="poligonal"] .cartao-app.arrastando { filter: drop-shadow(0 16px 28px rgba(20, 45, 50, .3)); }
:root[data-forma="poligonal"] .cartao-app.arrastando .miniatura { box-shadow: none; }

body.arrastando-algo { cursor: grabbing; user-select: none; }
/* Fica: existe para a transição de CSS não brigar com o FLIP. Quem anima os
   vizinhos durante o arrasto é a API de animações, não a folha de estilo. */
body.arrastando-algo .cartao-app { transition: none; }

/* --- Ficha do cartão (F1i) ------------------------------------------------ */

/* O diálogo de aplicação tem mais campo que o de pessoa e fica apertado no
   mesmo tamanho. É a única diferença. */
.cartao-entrada--largo { max-width: 34rem; }

.cartao-entrada--largo textarea {
  width: 100%;
  font: inherit;
  color: var(--texto);
  background: var(--painel-2);
  border: 1px solid var(--linha);
  border-radius: var(--raio-md);
  padding: .7rem .9rem;
  resize: vertical;
}
:root[data-forma="poligonal"] .cartao-entrada--largo textarea {
  border-radius: 0;
  clip-path: polygon(
    var(--chanfro) 0, 100% 0,
    100% calc(100% - var(--chanfro)), calc(100% - var(--chanfro)) 100%,
    0 100%, 0 var(--chanfro));
}

/* As bolinhas de cor da ficha são as mesmas do painel de aparência, com a cor
   vindo do JS (CSSOM — a única via que a CSP aceita para valor de runtime). */
.pontos--app { margin-bottom: .6rem; }
.ponto--app { background: rgb(var(--ponto)); }

.miniatura-ficha { display: flex; gap: 1rem; align-items: center; }
.miniatura-previa {
  flex: none;
  width: 132px;
  aspect-ratio: 16 / 10;
  display: grid; place-items: center;
  overflow: hidden;
  border: 1px solid var(--linha);
  border-radius: var(--raio-md);
  background: var(--painel-2);
}
.miniatura-previa img { width: 100%; height: 100%; object-fit: cover; object-position: top center; }

/* --- Cartão oculto (F1i) --------------------------------------------------
   Aplicação com `estado = oculto` some de /api/apps para todo mundo, inclusive
   para quem administra. Ela reaparece AQUI, como fantasma, só no modo de edição
   — senão esconder pela tela seria perder, e desfazer só por SQL. */
.cartao-app[data-oculto] { opacity: .55; }
.cartao-app[data-oculto] .miniatura {
  border-style: dashed;
  filter: grayscale(1);
}
body.editando .cartao-app[data-oculto] .miniatura { border-color: var(--apagado); }

/* ===========================================================================
   TAMBOR (F1m) — as aplicações na face de um cilindro
   ===========================================================================
   A escala NÃO é um `scale` inventado: os itens distantes recuam no eixo Z e
   quem os encolhe é a divisão de perspectiva do navegador. É a diferença entre
   um tambor e um desenho de tambor. A conta está no hub.js.
   =========================================================================== */

/* Respiro de peça principal: o tambor abre o painel e a grade vem DEPOIS dele,
   com folga suficiente para não disputar a atenção. */
.tambor { margin: .5rem 0 3rem; }

.tambor-palco {
  position: relative;
  display: flex;
  align-items: center;
  gap: .25rem;
  /* O conjunto inteiro — setas e pista — centralizado como um bloco. Sem o
     teto, as setas iam parar nas bordas da tela, a centenas de pixels do
     tambor que elas comandam. */
  max-width: var(--tambor-palco);
  margin-inline: auto;
}

.tambor-pista {
  flex: 1; min-width: 0;
  display: flex;
  align-items: center;
  overflow-x: auto;
  overflow-y: hidden;
  /* O encaixe é nativo: nada de física reimplementada em JS. */
  scroll-snap-type: x mandatory;
  /* pan-x e não `none`: a faixa recebe o deslize horizontal e a PÁGINA continua
     rolando na vertical. Com `none` o dedo ficaria preso na faixa. */
  touch-action: pan-x;
  scrollbar-width: none;
  perspective: var(--tambor-perspectiva);
  padding-block: 1.4rem;
  padding-inline: 0;
  gap: var(--tambor-vao);
}
.tambor-pista::-webkit-scrollbar { display: none; }

/* Os vãos que deixam o PRIMEIRO e o ÚLTIMO item alcançarem o centro.
   ---------------------------------------------------------------------------
   ATENCAO: Aqui morava um erro de centralização que nenhuma prova pegava. Isto era
   `padding-inline: calc(50% - largura/2)` na própria pista — e porcentagem de
   PADDING mede o bloco que contém, que é o PALCO, não a pista. Como as setas
   comem largura do palco (2,2rem cada, mais o vão), o vão saía ~39px maior que
   o necessário: o item em foco parava à DIREITA do centro, e o `scrollLeft` que
   o JS divide por passo virava um número quebrado — nenhum item chegava a
   encarar a pessoa de frente, todos ficavam ~4° tortos.

   O headless não pegava porque relata `hover: none`, e aí as setas somem
   (@media abaixo) e palco e pista dão a mesma largura. Só aparecia no PC de
   quem tem mouse — que é onde o dono estava olhando.

   Porcentagem de LARGURA de um filho, sim, mede o pai: 50% aqui é metade da
   pista, que é exatamente o que "centro da pista" quer dizer. O `--tambor-vao`
   sai da conta porque o `gap` entra depois, entre o vão e o primeiro item. */
.tambor-pista::before,
.tambor-pista::after {
  content: "";
  flex: none;
  width: calc(50% - var(--tambor-largura) / 2 - var(--tambor-vao));
}

/* A VAGA — o lugar na fila, que não se move nunca.
   ---------------------------------------------------------------------------
   ATENCAO: É ela que carrega o `scroll-snap-align`, e isso não é detalhe: o ponto de
   encaixe de um elemento é a caixa DEPOIS do transform. Com o encaixe no item
   que gira, cada quadro movia os pontos de encaixe, e o encaixe obrigatório
   brigava com a rolagem — a rolagem suave da seta do teclado morria a ~100px do
   destino, e o tambor "andava um terço de passo e travava".

   `position` fica ESTÁTICO de propósito: assim o `offsetParent` do item segue
   sendo o palco, e `item.offsetLeft` continua medindo o passo real da pista.

   `preserve-3d` porque a perspectiva está na PISTA, e ela só alcança os filhos
   diretos. Sem isto o item vira um `scale` chapado e o cilindro some. */
.tambor-vaga {
  flex: none;
  width: var(--tambor-largura);
  scroll-snap-align: center;
  transform-style: preserve-3d;
}

.tambor-item {
  display: block;
  width: 100%;
  /* Âncora do ::before do alvo de toque: sem isto ele se prenderia à PISTA e o
     alvo de 44px sairia por baixo de todos os itens de uma vez. */
  position: relative;
  text-decoration: none;
  color: inherit;
  /* O transform vem do JS (CSSOM — valor calculado em runtime é a única coisa
     que pode não estar na folha; ver DESIGN-SYSTEM §8). Sem transição: quem
     manda no tempo é a rolagem, e transição aqui viraria borracha. */
  transform-style: preserve-3d;
}

.tambor-face {
  --cor-app: var(--destaque-rgb);
  position: relative;
  display: grid; place-items: center;
  aspect-ratio: 16 / 10;
  overflow: hidden;
  border-radius: var(--raio-lg);
  border: 1px solid var(--linha);
  background: linear-gradient(135deg, rgba(var(--cor-app), .16), rgba(var(--cor-app), .04));
  box-shadow: var(--elev-2);
}
.tambor-face img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; object-position: top center; }
.tambor-face .miniatura-inicial { font-size: 1.9rem; }

/* Alvo de toque mínimo: o item distante fica pequeno, e 44px é o piso. O padding
   invisível cresce por fora sem mexer no desenho. */
.tambor-item::before {
  content: "";
  position: absolute;
  inset: -8px;
  z-index: -1;
}

/* O nome cresce junto com a faixa: sendo o tambor o elemento principal, um
   rótulo de 0,92rem embaixo de um cartaz de 400px ficaria órfão. Ele é o título
   do que está em foco, e o texto é o que a pessoa lê antes de clicar. */
.tambor-nome {
  margin: .5rem 0 0;
  text-align: center;
  font-size: 1.35rem;
  font-weight: 700;
  letter-spacing: -.01em;
  color: var(--texto);
  min-height: 1.4em; /* altura reservada: nome vazio não pode encolher a faixa */
}

.tambor-seta {
  flex: none;
  width: 2.2rem; height: 2.2rem;
  display: grid; place-items: center;
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: 50%;
  color: var(--texto-suave);
  cursor: pointer;
  padding: 0;
  box-shadow: var(--elev-1);
  transition: background var(--dur) var(--ease), color var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.tambor-seta svg { width: 17px; height: 17px; fill: none; stroke: currentColor; stroke-width: 2.2; stroke-linecap: round; stroke-linejoin: round; }
.tambor-seta:hover { background: var(--painel-2); color: var(--texto); }
.tambor-seta:active { transform: scale(.9); transition-duration: var(--dur-curta); }
.tambor-seta:disabled { opacity: .3; cursor: default; }

/* As setas existem para o MOUSE: a roda vertical não é sequestrada, então sem
   elas quem usa mouse não teria como girar o tambor. Em tela de toque o dedo já
   resolve, e elas só ocupariam largura. */
@media (hover: none) { .tambor-seta { display: none; } }

/* O tambor é DERIVADO da ordem do painel, não arranjado: não há o que arrastar
   nele. Some na edição — uma coisa a menos para explicar, e zero interação
   entre o arrastar e a faixa. */
body.editando .tambor { display: none; }

/* No poligonal a face pega as MESMAS seis silhuetas do cartão (data-forma-i,
   escolhida pelo identificador do app — o SUSi tem sempre a mesma forma).

   ATENCAO: O `drop-shadow` sai aqui de propósito: recorte + transform 3D + sombra
   filtrada em 10 elementos, animando junto com a rolagem, é a combinação mais
   cara do projeto. A profundidade já vem da perspectiva; a sombra seria custo
   sem leitura. */
:root[data-forma="poligonal"] .tambor-face {
  border: 0;
  border-radius: 0;
  box-shadow: none;
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="0"] .tambor-face {
  clip-path: polygon(0 var(--torto), calc(100% - var(--torto)) 0, 100% calc(100% - var(--torto) * .4), var(--torto) 100%);
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="1"] .tambor-face {
  clip-path: polygon(var(--torto) 0, 100% calc(var(--torto) * .5), calc(100% - var(--torto) * .8) 100%, 0 calc(100% - var(--torto) * .6));
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="2"] .tambor-face {
  clip-path: polygon(0 calc(var(--torto) * .4), calc(100% - var(--torto) * .6) 0, 100% 100%, calc(var(--torto) * .9) calc(100% - var(--torto) * .3));
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="3"] .tambor-face {
  clip-path: polygon(calc(var(--torto) * .7) 0, calc(100% - var(--torto) * .3) calc(var(--torto) * .6), 100% calc(100% - var(--torto)), 0 100%);
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="4"] .tambor-face {
  clip-path: polygon(0 0, 100% calc(var(--torto) * .8), calc(100% - var(--torto) * .5) calc(100% - var(--torto) * .5), var(--torto) 100%);
}
:root[data-forma="poligonal"] .tambor-item[data-forma-i="5"] .tambor-face {
  clip-path: polygon(calc(var(--torto) * .5) calc(var(--torto) * .6), 100% 0, 100% 100%, 0 calc(100% - var(--torto) * .9));
}
:root[data-forma="poligonal"] .tambor-seta {
  border: 0; border-radius: 0;
  background: var(--painel-3);
  clip-path: polygon(var(--chanfro) 0, 100% 0, 100% calc(100% - var(--chanfro)), calc(100% - var(--chanfro)) 100%, 0 100%, 0 var(--chanfro));
}

@media (max-width: 640px) {
  /* No celular o tambor também é o elemento principal: 190px de item num
     aparelho de 390 é a peça que domina a tela.

     Consequência aceita: as PONTAS (±2) nascem fora da viewport. Elas são
     cenário — pequenas demais para serem alvo de toque de qualquer jeito, e o
     hub.js já as tira do caminho do ponteiro pela regra dos 44px. O que precisa
     caber, e cabe, é o do meio mais os dois vizinhos. */
  :root { --tambor-largura: 190px; --tambor-vao: 10px; }
  .tambor-nome { font-size: 1rem; }
}

/* ===========================================================================
   TRILHA FU — experiência de uso (05/08/2026)
   =========================================================================== */

/* --- Fita "nova" e estrela: sobre a MINIATURA ------------------------------

   As duas moram sobre a imagem, e não no corpo do cartão, porque o cartão em
   repouso é só imagem (DESIGN-SYSTEM §10) — o texto abre no hover. Selo que só
   aparece ao passar o mouse não avisa ninguém de nada, e estrela que só aparece
   no hover não existe em tela de toque. */

.fita-nova {
  position: absolute;
  top: .55rem;
  left: .55rem;
  z-index: 2;
  font-size: .66rem;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ok-texto);
  background: var(--ok-fundo);
  border: 1px solid rgba(var(--destaque-rgb), .25);
  border-radius: var(--raio-total);
  padding: .18rem .5rem;
  /* A miniatura tem `overflow: hidden` e, no poligonal, `clip-path`: a fita fica
     dentro dela de propósito, para ser recortada junto com a silhueta em vez de
     escapar por cima do canto cortado. */
  backdrop-filter: blur(2px);
}

.estrela {
  position: absolute;
  top: .4rem;
  right: .4rem;
  z-index: 2;
  display: grid;
  place-items: center;
  width: 2rem;
  height: 2rem;
  border-radius: var(--raio-total);
  cursor: pointer;
  /* Em repouso é discreta; marcada, acende. Nunca some por completo: uma
     estrela que só aparece no hover não é achável no celular. */
  opacity: .55;
  transition: opacity var(--dur) var(--ease), background var(--dur) var(--ease);
}
.estrela svg {
  width: 1.15rem;
  height: 1.15rem;
  fill: none;
  /* ATENCAO: este branco FICA, e e a unica excecao da F3.5. Os outros oito
     estavam sobre um TOKEN que muda de tema; este esta sobre a MINIATURA — uma
     foto arbitraria. Nao ha token que descreva o fundo dela, e quem garante o
     contraste aqui e o drop-shadow abaixo, nao a paleta. */
  stroke: #fff;
  stroke-width: 1.8;
  stroke-linejoin: round;
  filter: drop-shadow(0 1px 2px rgba(0, 0, 0, .55));
}
.estrela:hover { opacity: 1; background: rgba(0, 0, 0, .28); }
.estrela--marcada { opacity: 1; }
.estrela--marcada svg { fill: var(--aviso); stroke: var(--aviso); }

/* Sem miniatura, o fundo é claro e o contorno branco da estrela some. */
.miniatura:has(img[hidden]) .estrela svg,
.miniatura:not(:has(img)) .estrela svg { stroke: var(--texto-suave); }

/* --- Faixas pessoais: favoritas e recentes ---------------------------------

   Faixa é ATALHO, não catálogo: os cartões vêm menores para caber numa linha e
   não empurrarem a grade real para baixo da dobra. */
.secao--faixa .secao-cabeca { margin-bottom: .5rem; }
.grade--faixa {
  grid-template-columns: repeat(auto-fill, minmax(190px, 1fr));
  gap: 14px;
  margin-bottom: 2rem;
}

/* --- Cartão-fantasma do carregamento (FU.6) --------------------------------

   NÃO é a coreografia de entrada que o PROPOSTA-PAINEL-VIVO §7 recusou: aquilo
   somava movimento a uma espera que já existia. Isto diz que a espera é uma
   espera. A pulsação é lenta de propósito — rápida vira nervosismo. */
.cartao-fantasma {
  display: block;
  aspect-ratio: 16 / 10;
  border: 1px solid var(--linha);
  border-radius: var(--raio-xl);
  background: linear-gradient(135deg, rgba(var(--destaque-rgb), .10), rgba(var(--destaque-rgb), .03));
  animation: fantasma-respira 1.6s var(--ease) infinite;
}
@keyframes fantasma-respira {
  0%, 100% { opacity: .45; }
  50% { opacity: .85; }
}

/* --- Pedir acesso (FU.5) --------------------------------------------------- */

.pedir-acesso { margin-top: .55rem; align-self: flex-start; }

/* Contador na aba "Pessoas": só aparece quando há alguém esperando. */
.conta-pedidos {
  display: inline-grid;
  place-items: center;
  min-width: 1.25rem;
  height: 1.25rem;
  margin-left: .4rem;
  padding: 0 .3rem;
  font-size: .7rem;
  font-weight: 700;
  color: var(--sobre-perigo);
  background: var(--perigo);
  border-radius: var(--raio-total);
}

.pedidos-fila { margin-bottom: 2rem; }
.lista-pedidos { display: flex; flex-direction: column; gap: .5rem; margin-top: .75rem; }

.pedido-linha {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: .4rem;
  width: 100%;
  font: inherit;
  text-align: left;
  color: var(--texto);
  background: var(--painel);
  border: 1px solid var(--linha);
  border-left: 3px solid var(--aviso);
  border-radius: var(--raio-md);
  padding: .6rem .8rem;
  cursor: pointer;
  transition: background var(--dur) var(--ease);
}
.pedido-linha:hover { background: var(--painel-2); }
.pedido-quem { font-weight: 700; }
.pedido-oque { font-size: .85rem; color: var(--apagado); }

/* Movimento reduzido: o fantasma para de pulsar e vira uma caixa parada. Ele
   continua dizendo "está carregando" pela presença, não pelo movimento. */
@media (prefers-reduced-motion: reduce) {
  .cartao-fantasma { animation: none; opacity: .6; }
}

/* ---------------------------------------------------------------------------
   Trilha FA — o painel de administração (tela-gestao, gestao.js).
   Só tokens: nenhuma cor nova. O vermelho, o amarelo e o verde são os mesmos
   --perigo, --aviso e --ok que já passaram pela medição de contraste da F3.
   --------------------------------------------------------------------------- */
.abas {
  display: flex; flex-wrap: wrap; gap: 4px;
  border-bottom: 1px solid var(--linha);
  margin-bottom: 1.25rem;
}
.aba {
  font: inherit; font-size: .9rem; font-weight: 600;
  color: var(--texto-suave);
  background: none; border: 0;
  border-bottom: 2px solid transparent;
  padding: .6rem .9rem;
  margin-bottom: -1px;
  cursor: pointer;
}
.aba:hover { color: var(--texto); }
.aba[aria-selected="true"] { color: var(--destaque); border-bottom-color: var(--destaque); }
.aba:focus-visible { outline: 2px solid var(--destaque); outline-offset: 2px; }
.aba-painel > .titulo-secao { margin-top: 1.75rem; }
/* O `.aviso` reserva altura de propósito (a tela de entrada não pode pular
   quando a mensagem chega). Aqui, aviso vazio ou escondido não ocupa nada — e
   `[hidden]` precisa ser dito, porque o `display: flex` do .aviso vence o do
   navegador. */
#tela-gestao .aviso:empty, #tela-gestao .aviso[hidden] { display: none; }
#tela-gestao .aviso { margin: 0 auto 1rem; }

.numeros {
  display: grid; gap: 10px;
  grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
  margin-bottom: 1.25rem;
}
.numero {
  background: var(--painel);
  border: 1px solid var(--linha);
  border-radius: var(--raio-lg);
  padding: .75rem .9rem;
  display: flex; flex-direction: column; gap: 2px;
}
.numero b { font-size: 1.35rem; line-height: 1.2; }
.numero span { font-size: .78rem; color: var(--apagado); }
.numero[data-tom="perigo"] { background: var(--perigo-fundo); border-color: transparent; }
.numero[data-tom="perigo"] b { color: var(--perigo); }
.numero[data-tom="aviso"] { background: var(--aviso-fundo); border-color: transparent; }
.numero[data-tom="aviso"] b { color: var(--aviso); }
.numero[data-tom="ok"] b { color: var(--ok); }
.numeros--miudo { grid-template-columns: repeat(auto-fill, minmax(130px, 1fr)); }
.numeros--miudo .numero b { font-size: 1.05rem; }

.lista-pendencias, .lista-eventos, .lista-simples { list-style: none; margin: 0 0 1rem; padding: 0; display: flex; flex-direction: column; gap: 6px; }
.pendencia {
  background: var(--painel);
  border: 1px solid var(--linha);
  border-left: 4px solid var(--linha);
  border-radius: var(--raio-md);
  padding: .6rem .8rem;
  display: flex; flex-direction: column; gap: 4px;
}
.pendencia[data-gravidade="alta"] { border-left-color: var(--perigo); }
.pendencia[data-gravidade="media"] { border-left-color: var(--aviso); }
.pendencia-titulo { font-size: .9rem; }
.pendencia-comando, .mono, .ficha-dica code {
  font-family: ui-monospace, "SFMono-Regular", Menlo, Consolas, monospace;
  font-size: .8rem;
}
.pendencia-comando { color: var(--texto-suave); background: var(--neutro-fundo); border-radius: var(--raio-sm); padding: 2px 6px; align-self: flex-start; overflow-wrap: anywhere; }

.lista-datas { display: grid; grid-template-columns: max-content 1fr; gap: 6px 1rem; margin: 0; font-size: .88rem; }
.lista-datas dt { color: var(--apagado); }
.lista-datas dd { margin: 0; }

/* A tabela rola DENTRO da caixa: em tela de celular a página não ganha rolagem
   lateral, que é a regra de layout do projeto. */
.tabela-rolagem { overflow-x: auto; margin-bottom: 1.25rem; border: 1px solid var(--linha); border-radius: var(--raio-lg); background: var(--painel); }
.tabela { border-collapse: collapse; width: 100%; font-size: .85rem; }
.tabela th, .tabela td { text-align: left; vertical-align: top; padding: .5rem .7rem; border-bottom: 1px solid var(--linha); }
.tabela th { font-size: 11px; letter-spacing: .05em; text-transform: uppercase; color: var(--apagado); font-weight: 700; white-space: nowrap; }
.tabela tbody tr:last-child td { border-bottom: 0; }
.tabela tr[data-tom="aviso"] td, .tabela td[data-tom="aviso"] { background: var(--aviso-fundo); }
.tabela .num { text-align: right; white-space: nowrap; }
.tabela .nowrap { white-space: nowrap; }
.tabela .quebra { overflow-wrap: anywhere; }
.tabela .vazio, .lista-simples .vazio { color: var(--apagado); font-style: italic; }
.tabela-sub { display: block; font-size: .76rem; color: var(--apagado); overflow-wrap: anywhere; }

.sinal {
  display: inline-flex; align-items: center; gap: 6px;
  font-size: .8rem; font-weight: 700;
  padding: 2px 8px; border-radius: var(--raio-total);
  background: var(--neutro-fundo); color: var(--neutro-texto);
}
.sinal[data-sinal="verde"] { background: var(--ok-fundo); color: var(--ok); }
.sinal[data-sinal="amarelo"] { background: var(--aviso-fundo); color: var(--aviso); }
.sinal[data-sinal="vermelho"] { background: var(--perigo-fundo); color: var(--perigo); }

.marca-sim-nao { font-size: .8rem; font-weight: 600; }
.marca-sim-nao[data-v="sim"] { color: var(--ok); }
.marca-sim-nao[data-v="nao"] { color: var(--aviso); }
.marca-sim-nao[data-v="na"] { color: var(--apagado); font-weight: 400; }
.select-curto { width: auto; padding: .35rem .5rem; font-size: .82rem; }

.lista-eventos li { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; font-size: .85rem; padding: .4rem 0; border-bottom: 1px solid var(--linha); }
.evento-quando { color: var(--apagado); font-size: .78rem; min-width: 8.5rem; }
.lista-eventos .tabela-sub { flex-basis: 100%; }

.colunas { display: grid; gap: 1rem; grid-template-columns: repeat(auto-fit, minmax(280px, 1fr)); margin-bottom: 1rem; }
.colunas .ficha { max-width: none; }
.ficha--larga { max-width: none; margin-bottom: 1rem; }
.lista-simples { margin-top: .75rem; }
.lista-simples li { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; font-size: .86rem; padding: .35rem 0; border-top: 1px solid var(--linha); }
.lista-simples li span { color: var(--apagado); font-size: .8rem; flex: 1; min-width: 12rem; }

.form-acao, .filtros { display: flex; flex-wrap: wrap; gap: .6rem; align-items: center; margin-top: .9rem; }
.form-acao select { width: auto; min-width: 220px; flex: 1; }
.campo-acao {
  font: inherit; font-size: .92rem;
  color: var(--texto); background: var(--painel-3);
  border: 0; border-radius: var(--raio-md);
  padding: .55rem .75rem;
}
.campo-acao:focus { outline: none; box-shadow: inset 0 0 0 2px var(--destaque); }
.form-acao .botao, .filtros .botao { width: auto; }
a.botao { display: inline-block; text-decoration: none; text-align: center; }
.botao--perigo { background: var(--perigo); color: var(--sobre-perigo); }

.filtros { background: var(--painel); border: 1px solid var(--linha); border-radius: var(--raio-lg); padding: .8rem .9rem; margin-bottom: 1rem; }
.filtros label { display: flex; flex-direction: column; gap: 3px; font-size: 11px; letter-spacing: .05em; text-transform: uppercase; font-weight: 700; color: var(--apagado); }
.filtros select { width: auto; min-width: 150px; text-transform: none; letter-spacing: 0; font-weight: 400; }
.filtros .campo-acao { text-transform: none; letter-spacing: 0; font-weight: 400; }

.paginacao { display: flex; align-items: center; justify-content: center; gap: 1rem; font-size: .85rem; color: var(--apagado); }
.paginacao .botao-texto:disabled { opacity: .4; cursor: default; }

@media (max-width: 640px) {
  .form-acao select, .form-acao .campo-acao, .form-acao .botao { width: 100%; flex: 1 1 100%; }
  .filtros label, .filtros select { width: 100%; }
  .lista-datas { grid-template-columns: 1fr; }
  .lista-datas dd { margin-bottom: .5rem; }
}

/* ---------------------------------------------------------------------------
   UX (21/10/2026) — ícones e cor de situação. Ver DESIGN-SYSTEM §12.
   O ícone é traço em `currentColor`: ele pinta da cor do texto ao lado, então o
   tom de estado (--ok, --aviso, --perigo, --info) cobre os dois de uma vez, e os
   dois temas funcionam sem uma linha a mais. Nenhuma cor nova aqui.
   --------------------------------------------------------------------------- */
.icone {
  width: 1.1em; height: 1.1em;
  flex: none;
  fill: none; stroke: currentColor;
  stroke-width: 2; stroke-linecap: round; stroke-linejoin: round;
  vertical-align: -.2em;
}
.botao-com-icone { display: inline-flex; align-items: center; justify-content: center; gap: .4rem; }
.aba { display: inline-flex; align-items: center; gap: .4rem; }
.aba .conta-pedidos { margin-left: .1rem; }
.aviso-texto { display: inline-flex; align-items: center; gap: .5rem; }
.aviso--acao > .icone { margin-right: .35rem; }

/* Selos de cartão: cada situação com a sua cor. Cinza (o .selo puro) continua
   sendo "nada a fazer, só saiba"; cor é para o que muda o que a pessoa faz. */
.selo .icone { width: 1em; height: 1em; }
.selo--aviso { color: var(--aviso); }
.selo--info { color: var(--info); }
.selo--perigo { color: var(--perigo); }

/* Etiquetas da tela de Pessoas e do painel com ícone e tom. */
.tag { display: inline-flex; align-items: center; gap: .3rem; }
.tag .icone { width: 1em; height: 1em; }
.tag--aviso { background: var(--aviso-fundo); color: var(--aviso); }

/* A contagem do botão Pessoas é gente esperando resposta, não erro: amarelo.
   O vermelho fica para a Administração, onde a contagem é de problema. */
.conta-pedidos--aviso { background: var(--aviso-fundo); color: var(--aviso); }

/* Painel de administração com ícones e gravidade (UX, 21/10/2026). */
.numero b { display: inline-flex; align-items: center; gap: .45rem; }
.numero b .icone { width: .85em; height: .85em; opacity: .8; }

.pendencia-cabeca { display: flex; flex-wrap: wrap; align-items: center; gap: .35rem .6rem; }
.pendencia-gravidade {
  display: inline-flex; align-items: center; gap: .3rem;
  font-size: 11px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase;
  padding: 2px 8px; border-radius: var(--raio-total);
  background: var(--neutro-fundo); color: var(--neutro-texto);
}
.pendencia[data-gravidade="alta"] { background: var(--perigo-fundo); border-color: transparent; }
.pendencia[data-gravidade="alta"] .pendencia-gravidade { background: var(--perigo); color: var(--sobre-perigo); }
.pendencia[data-gravidade="media"] .pendencia-gravidade { background: var(--aviso-fundo); color: var(--aviso); }
.pendencia[data-gravidade="baixa"] .pendencia-gravidade { background: var(--info-fundo); color: var(--info); }

.lista-datas dt { display: inline-flex; align-items: center; gap: .4rem; }
.lista-datas .dd--aviso { color: var(--aviso); font-weight: 600; }

.tabela tr[data-tom="perigo"] td { background: var(--perigo-fundo); }
.tabela-sub.sub--perigo { color: var(--perigo); font-weight: 600; }
.tabela-sub .icone, .tabela td > span > .icone { width: 1em; height: 1em; margin-right: .3rem; }
.marca-sim-nao { display: inline-flex; align-items: center; gap: .2rem; }

.girando .icone { animation: girar 1s linear infinite; }
@keyframes girar { to { transform: rotate(360deg); } }
@media (prefers-reduced-motion: reduce) {
  .girando .icone { animation: none; }
}

/* ---------------------------------------------------------------------------
   FT.3 — funções. O chip reaproveita a .tag-nivel (cor por --cor-app, como o
   cartão de aplicação); o botão de ligar/desligar segue o mesmo desenho, com
   aria-pressed dizendo o estado — e o ícone de check, porque cor sozinha não é
   sinal (DESIGN-SYSTEM §6).
   --------------------------------------------------------------------------- */
.tag-funcao { font-weight: 600; }
.pessoa-linha .tag-funcao { font-size: .72rem; }
.funcoes-chips { display: flex; flex-wrap: wrap; gap: 6px; margin-top: .35rem; }
.chip-funcao {
  display: inline-flex; align-items: center; gap: .3rem;
  font: inherit; font-size: .82rem; padding: .3rem .7rem; border-radius: 999px; cursor: pointer;
  border: 1px solid rgba(var(--cor-app, var(--destaque-rgb)), .45);
  background: transparent; color: var(--texto);
}
.chip-funcao[aria-pressed="true"] { background: rgba(var(--cor-app, var(--destaque-rgb)), .14); color: rgb(var(--cor-app, var(--destaque-rgb))); font-weight: 600; }
.chip-funcao:disabled { opacity: .55; cursor: default; }
.chip-funcao:focus-visible { outline: 2px solid var(--destaque); outline-offset: 2px; }
.chip-funcao .icone { width: 1em; height: 1em; }
:root[data-forma="poligonal"] .chip-funcao { border-radius: 0; }
.permissao-origem { display: block; font-size: .74rem; color: var(--apagado); margin-top: 2px; }
.lista-funcoes .botao-texto[aria-current="true"] .tag-funcao { outline: 2px solid rgb(var(--cor-app)); outline-offset: 1px; }

/* ---------------------------------------------------------------------------
   Trilha FV — mais visual em Funções e na ficha da pessoa. Só tokens; a cor
   por dado (função, aplicação) chega por CSSOM em --cor-app.
   --------------------------------------------------------------------------- */

/* FV.8 — o contador sobre a capa do cartão de Checklists. Mesmo lugar e mesma
   lógica da fita "nova": dentro da miniatura, recortado junto com ela. */
.contador-capa {
  position: absolute; left: .55rem; bottom: .55rem; z-index: 2;
  font-size: .74rem; font-weight: 700;
  color: var(--aviso); background: var(--painel);
  border: 1px solid var(--aviso); border-radius: var(--raio-total);
  padding: .2rem .55rem; box-shadow: var(--elev-1);
}
:root[data-forma="poligonal"] .contador-capa { border-radius: 0; }

/* FV.6 — a matriz funções x aplicações. A intensidade da célula é a força do
   nível; a palavra está sempre escrita no seletor (cor nunca sozinha). */
.matriz-legenda { list-style: none; margin: .4rem 0 .8rem; padding: 0; display: flex; flex-wrap: wrap; gap: .3rem 1rem; font-size: .78rem; color: var(--texto-suave); }
.matriz-legenda li { display: inline-flex; align-items: center; gap: .35rem; }
.matriz-amostra { width: .9rem; height: .9rem; border-radius: var(--raio-xs); border: 1px solid var(--linha); }
.matriz-rolagem { overflow-x: auto; }
.matriz { border-collapse: separate; border-spacing: 3px; font-size: .82rem; min-width: 100%; }
.matriz-canto { text-align: left; font-size: .72rem; text-transform: uppercase; letter-spacing: .05em; color: var(--apagado); vertical-align: bottom; padding: 0 .4rem .3rem 0; }
.matriz-funcao { vertical-align: bottom; padding: 0 0 .3rem; min-width: 6.5rem; }
.matriz-funcao-botao { padding: 0; }
.matriz-gente { display: flex; align-items: center; gap: 2px; margin-top: .3rem; }
.mini-avatar {
  display: inline-grid; place-items: center; width: 1.3rem; height: 1.3rem; border-radius: var(--raio-total);
  font-size: .52rem; font-weight: 700; color: var(--texto); background: var(--painel-2);
  border: 1.5px solid rgb(var(--cor-app, var(--destaque-rgb)));
}
.matriz-gente-conta { font-size: .7rem; font-weight: 500; color: var(--apagado); margin-left: .25rem; }
.matriz-app { text-align: left; font-weight: 600; white-space: nowrap; padding-right: .6rem; }
.matriz-celula, .matriz-amostra, .matriz-peca { background: var(--neutro-fundo); }
.matriz-celula { border-radius: var(--raio-sm); padding: 0; }
.matriz-celula[data-nivel="leitor"], .matriz-amostra[data-nivel="leitor"], .matriz-peca[data-nivel="leitor"] { background: rgba(var(--destaque-rgb), .18); }
.matriz-celula[data-nivel="editor"], .matriz-amostra[data-nivel="editor"], .matriz-peca[data-nivel="editor"] { background: rgba(var(--destaque-rgb), .38); }
/* Administra é a cor cheia, com o texto "sobre destaque": o par que o tema já
   mede, em vez de um meio-tom que ninguém mediu. */
.matriz-celula[data-nivel="admin"], .matriz-amostra[data-nivel="admin"], .matriz-peca[data-nivel="admin"] { background: var(--destaque); }
.matriz-celula[data-nivel="admin"] .matriz-nivel, .matriz-peca[data-nivel="admin"] span { color: var(--sobre-destaque); }
.matriz-nivel {
  appearance: none; -webkit-appearance: none; width: 100%; min-width: 0;
  font: inherit; font-size: .78rem; font-weight: 600; color: var(--texto); text-align: center; text-align-last: center;
  background: transparent; border: 0; padding: .45rem .3rem; cursor: pointer; border-radius: inherit;
}
.matriz-celula[data-padrao="sim"] .matriz-nivel { font-weight: 400; color: var(--texto-suave); font-style: italic; }
.matriz-celula:hover { box-shadow: inset 0 0 0 2px rgba(var(--destaque-rgb), .6); }
.matriz-cartoes { display: none; }

/* O diff do ensaio, em setas. */
.ensaio-linha { display: flex; flex-wrap: wrap; align-items: center; gap: .3rem .6rem; }
.lista-simples li.ensaio-linha span { flex: none; min-width: 0; font-size: .82rem; color: inherit; }
.ensaio-linha[data-tom="perigo"] > .icone { color: var(--perigo); }
.ensaio-linha[data-tom="ok"] > .icone { color: var(--ok); }
.ensaio-seta { display: inline-flex; align-items: center; gap: .35rem; }
.lista-simples li .ensaio-de { text-decoration: line-through; color: var(--apagado); }
.lista-simples li .ensaio-para { font-weight: 700; padding: .05rem .45rem; border-radius: var(--raio-total); }
.ensaio-linha[data-tom="perigo"] .ensaio-para, .ensaio-linha[data-tom="perigo"] .ensaio-tipo { color: var(--perigo); }
.ensaio-linha[data-tom="perigo"] .ensaio-para { background: var(--perigo-fundo); }
.ensaio-linha[data-tom="ok"] .ensaio-para, .ensaio-linha[data-tom="ok"] .ensaio-tipo { color: var(--ok); }
.ensaio-linha[data-tom="ok"] .ensaio-para { background: var(--ok-fundo); }
.lista-simples li .ensaio-tipo { font-size: .72rem; text-transform: uppercase; letter-spacing: .05em; font-weight: 700; }

/* FV.7 — o mapa de acesso da pessoa: um mosaico de capas com o nível em cima. */
.mapa-acesso { display: grid; grid-template-columns: repeat(auto-fill, minmax(180px, 1fr)); gap: 10px; }
.mapa-acesso .permissao { flex-direction: column; align-items: stretch; gap: .45rem; padding: .5rem; background: var(--painel); border: 1px solid var(--linha); }
.mapa-acesso .permissao-nome { font-weight: 600; }
.mapa-acesso .permissao-nivel { min-width: 0; width: 100%; }
.permissao-capa {
  position: relative; display: grid; place-items: center; aspect-ratio: 16 / 10; overflow: hidden;
  border-radius: var(--raio-sm); --cor-app: var(--destaque-rgb);
  background: linear-gradient(135deg, rgba(var(--cor-app), .22), rgba(var(--cor-app), .05));
}
.permissao-capa img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; object-position: top; }
.permissao-inicial { font-size: 1.8rem; font-weight: 800; color: rgb(var(--cor-app)); }
.selo-nivel {
  position: absolute; left: .4rem; bottom: .4rem; z-index: 1;
  font-size: .7rem; font-weight: 700; padding: .12rem .5rem; border-radius: var(--raio-total);
  color: var(--texto); background: var(--painel); box-shadow: var(--elev-1);
}
.selo-nivel[data-nivel="admin"] { color: var(--sobre-destaque); background: var(--destaque); }
.selo-nivel[data-nivel="editor"] { color: var(--info); background: var(--painel); box-shadow: inset 0 0 0 1.5px var(--info), var(--elev-1); }
.selo-nivel[data-nivel="negado"] { color: var(--apagado); }
.mapa-acesso .permissao[data-nivel="negado"] .permissao-capa > :not(.selo-nivel) { filter: grayscale(1); opacity: .35; }
.mapa-acesso .permissao[data-nivel="negado"] .permissao-nome { color: var(--apagado); }

@media (max-width: 760px) {
  .matriz-legenda, .matriz-rolagem { display: none; }
  .matriz-cartoes { display: flex; flex-direction: column; gap: 10px; }
  .matriz-cartao { border: 1px solid var(--linha); border-radius: var(--raio-md); padding: .6rem; border-top: 3px solid rgb(var(--cor-app, var(--destaque-rgb))); }
  .matriz-cartao-cab { display: flex; flex-wrap: wrap; align-items: center; gap: .3rem .5rem; padding: 0; text-align: left; }
  .matriz-mosaico { list-style: none; margin: .5rem 0 0; padding: 0; display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 4px; }
  .matriz-peca { display: flex; flex-direction: column; padding: .35rem .45rem; border-radius: var(--raio-sm); min-width: 0; }
  .matriz-peca-nome { font-size: .78rem; font-weight: 600; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
  .matriz-peca-nivel { font-size: .7rem; color: var(--texto-suave); }
  .mapa-acesso { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
:root[data-forma="poligonal"] :is(.matriz-celula, .matriz-amostra, .mini-avatar, .selo-nivel, .permissao-capa, .matriz-peca, .matriz-cartao, .lista-simples li .ensaio-para) { border-radius: 0; }

/* FV — o chip de função leva a cor do dado como TEXTO, e várias cores da paleta
   (verde, laranja, mostarda) não chegam a 4,5:1 sobre a própria tinta. A mistura
   com --texto escurece no claro e clareia no escuro; a cor continua lá. */
.tag-funcao { color: color-mix(in srgb, rgb(var(--cor-app, var(--destaque-rgb))) 58%, var(--texto)); }
:root[data-tema="escuro"] .tag-funcao { color: color-mix(in srgb, rgb(var(--cor-app, var(--destaque-rgb))) 50%, var(--texto)); }

/* ===== FR — o quadro de Atribuições ==========================================
   Um componente (public/assets/atribuicoes.js) montado em duas páginas: a aba
   Atribuições das Checklists e a da Administração. Por isso mora aqui, e não no
   checklists.css: as duas páginas carregam o hub.css. Cor da função por
   --cor-app (CSSOM), como nos chips de função. */
.atr-aviso { margin: 0 0 .75rem; }
.atr-aviso:empty { display: none; }
.atr-resumo { display: grid; gap: 10px; grid-template-columns: repeat(4, minmax(0, 1fr)); margin: 0 0 1rem; }
.atr-numero { display: flex; flex-direction: column; gap: .1rem; padding: .7rem .9rem; border: 1px solid var(--linha); border-radius: var(--raio-lg); background: var(--painel); }
.atr-numero-valor { font-size: 1.6rem; font-weight: 700; font-variant-numeric: tabular-nums; line-height: 1.1; }
.atr-numero-rotulo { font-size: .78rem; color: var(--texto-suave); }
.atr-numero[data-tom="aviso"] .atr-numero-valor { color: var(--aviso); }
.atr-numero[data-tom="ok"] .atr-numero-valor { color: var(--ok); }
.atr-barra { display: flex; flex-wrap: wrap; align-items: center; gap: .6rem; margin: 0 0 1rem; }
.atr-vistas { display: inline-flex; flex-wrap: wrap; gap: 2px; padding: 3px; border-radius: var(--raio-md); background: var(--neutro-fundo); }
.atr-vista {
  display: inline-flex; align-items: center; gap: .35rem;
  font: inherit; font-size: .84rem; color: var(--texto-suave); cursor: pointer;
  padding: .4rem .7rem; border: 0; border-radius: var(--raio-sm); background: transparent;
  transition: background var(--dur) var(--ease), color var(--dur) var(--ease);
}
.atr-vista:hover { color: var(--texto); }
.atr-vista[aria-pressed="true"] { background: var(--painel); color: var(--texto); font-weight: 600; box-shadow: var(--elev-1); }
.atr-busca { flex: 1; min-width: 12rem; }
.atr-form { margin-bottom: 1rem; }
.atr-campos { display: grid; gap: .75rem; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); margin: .75rem 0; }
.atr-campo { display: flex; flex-direction: column; gap: .3rem; font-size: .82rem; color: var(--texto-suave); }
.atr-campo select, .atr-campo input { width: 100%; font: inherit; color: var(--texto); }

.atr-grade { display: grid; gap: 14px; grid-template-columns: repeat(auto-fill, minmax(290px, 1fr)); align-items: start; }
.atr-coluna {
  --cor-app: var(--destaque-rgb);
  border: 1px solid var(--linha); border-top: 3px solid rgb(var(--cor-app)); border-radius: var(--raio-lg);
  background: linear-gradient(180deg, rgba(var(--cor-app), .06), transparent 7rem), var(--painel);
  padding: .75rem;
}
.atr-coluna-cab { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: .4rem; margin: 0 0 .6rem; font-size: 1rem; }
.atr-coluna-conta { font-size: .76rem; font-weight: 400; color: var(--texto-suave); }
.atr-lista, .atr-subs, .atr-pessoas, .atr-por-pessoa { list-style: none; margin: 0; padding: 0; }
.atr-lista { display: flex; flex-direction: column; gap: 8px; }
.atr-cartao { border: 1px solid var(--linha); border-radius: var(--raio-md); background: var(--painel); padding: .6rem .7rem; }
.atr-cartao[data-estado="lacuna"] { border-style: dashed; border-color: var(--aviso); }
.atr-cartao[data-estado="inativa"] { opacity: .6; }
.atr-cartao--sub { border: 0; border-left: 2px solid rgba(var(--cor-app), .45); border-radius: 0; padding: .35rem 0 .35rem .65rem; background: transparent; }
.atr-cartao--sub[data-estado="lacuna"] { border-left: 2px dashed var(--aviso); }
.atr-subs { display: flex; flex-direction: column; gap: 4px; margin-top: .5rem; }
.atr-cartao-topo { display: flex; flex-wrap: wrap; align-items: flex-start; gap: .3rem .4rem; }
/* O nome pede pelo menos 9rem antes de dividir a linha: sem isso, numa coluna
   estreita, ele quebrava palavra por palavra e o "Editar" vazava a borda. */
.atr-nome { margin: 0; font-size: .92rem; line-height: 1.3; flex: 1 1 9rem; min-width: 0; overflow-wrap: anywhere; }
.atr-cartao--sub .atr-nome { font-size: .86rem; }
.atr-selo { display: inline-flex; align-items: center; gap: .25rem; flex: none; }
.atr-selo .icone { width: 12px; height: 12px; }
.atr-editar { flex: none; margin-left: auto; font-size: .78rem; padding: .15rem .4rem; }
.atr-descricao { margin: .25rem 0 0; font-size: .78rem; color: var(--texto-suave); line-height: 1.4; }
.atr-pessoas { display: flex; flex-wrap: wrap; gap: 4px 6px; margin-top: .45rem; }
.atr-pessoa { display: inline-flex; flex-wrap: wrap; align-items: center; gap: .3rem; font-size: .8rem; padding: .15rem .45rem .15rem .15rem; border-radius: var(--raio-total); background: var(--neutro-fundo); }
.atr-pessoa--titular { background: rgba(var(--cor-app), .14); font-weight: 600; }
.atr-pessoa[data-estado="fora"] { text-decoration: line-through; color: var(--apagado); }
.atr-avatar {
  display: inline-grid; place-items: center; flex: none;
  width: 22px; height: 22px; border-radius: 50%;
  font-size: .62rem; font-weight: 700; letter-spacing: .02em;
  background: rgba(var(--cor-app, var(--destaque-rgb)), .22); color: var(--texto);
}
.atr-papel { font-size: .66rem; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; color: var(--texto-suave); }
.atr-papel--fora { color: var(--perigo); }
.atr-sem-funcao { display: inline-flex; align-items: center; gap: .2rem; font-size: .7rem; color: var(--aviso); }
.atr-sem-funcao .icone { width: 12px; height: 12px; }
.atr-ninguem { font-size: .78rem; color: var(--apagado); font-style: italic; }
.atr-acao { font-size: .74rem; padding: .05rem .35rem; }
.atr-tirar .icone { width: 12px; height: 12px; }
.atr-editor { margin-top: .6rem; padding-top: .6rem; border-top: 1px solid var(--linha); }
.atr-editor .atr-campos { grid-template-columns: 1fr; margin: .5rem 0 0; }
.atr-por { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }
.atr-por select { flex: 1; min-width: 10rem; }
.atr-titular { display: inline-flex; align-items: center; gap: .3rem; font-size: .8rem; color: var(--texto-suave); }
.atr-apagar { color: var(--perigo); }

.atr-por-pessoa { display: flex; flex-direction: column; gap: 8px; }
.atr-linha-pessoa { border: 1px solid var(--linha); border-radius: var(--raio-md); background: var(--painel); padding: .6rem .75rem; }
.atr-linha-cab { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }
.atr-linha-cab .atr-pessoa-nome { font-weight: 600; }
.atr-linha-cab .atr-avatar { width: 28px; height: 28px; font-size: .72rem; }
.atr-chips { display: flex; flex-wrap: wrap; gap: 4px; margin-top: .45rem; }
.atr-chip { text-transform: none; letter-spacing: 0; font-weight: 600; }
.atr-chip--titular { box-shadow: inset 0 0 0 1px rgba(var(--cor-app), .5); }

/* As atribuições na identificação: ficha de Pessoas, lista e o menu da pessoa. */
.atr-identidade { display: flex; flex-wrap: wrap; gap: 4px; }
.atr-identidade .tag { text-transform: none; letter-spacing: 0; }
.atr-alerta-funcao { display: flex; flex-wrap: wrap; align-items: center; gap: .4rem; margin-top: .45rem; font-size: .78rem; color: var(--aviso); }
.ajustes-atribuicoes { margin: 0 0 .75rem; padding-bottom: .75rem; border-bottom: 1px solid var(--linha); }
.ajustes-atribuicoes .ajustes-titulo { margin-bottom: .4rem; }

@media (max-width: 760px) {
  .atr-resumo { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .atr-grade { grid-template-columns: 1fr; }
}
:root[data-forma="poligonal"] :is(.atr-numero, .atr-coluna, .atr-cartao, .atr-linha-pessoa, .atr-pessoa, .atr-avatar, .atr-vista, .atr-vistas) { border-radius: 0; }
