:root {
  --tinta: #1a1a1a;
  --tinta-suave: #5c5c5c;
  --linha: #e0ddd8;
  --papel: #fbfaf8;
  --cartao: #ffffff;
  --destaque: #1F3A5F;
  --alerta: #8c2f2f;
}
* { box-sizing: border-box; }
/* Desvio do brief da Task 8 (documentado no relatorio): sem esta regra,
   qualquer classe abaixo que declare display (.cartao, .acoes, .linha, .topo)
   apaga o "display: none" do atributo hidden nativo -- author style de
   prioridade normal sempre vence sobre o user-agent style, mesmo com
   especificidade igual. O !important e necessario porque, sem ele, uma regra
   [hidden] normal empata em especificidade com .cartao e perde por ordem no
   arquivo (.cartao vem depois). Efeito real observado antes do fix: o
   formulario de motivo da rejeicao (#form-motivo, class="cartao" hidden) em
   rdo.mjs aparecia visivel assim que um RDO pendente era aberto, antes mesmo
   do fiscal clicar em "Rejeitar". */
[hidden] { display: none !important; }
body {
  margin: 0;
  background: var(--papel);
  color: var(--tinta);
  font: 16px/1.55 system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
}
.raiz { max-width: 56rem; margin: 0 auto; padding: 2rem 1.25rem 4rem; }

h1 { font-size: 1.5rem; font-weight: 600; letter-spacing: -0.01em; margin: 0 0 .25rem; }
h2 { font-size: .8rem; font-weight: 600; text-transform: uppercase;
     letter-spacing: .08em; color: var(--tinta-suave);
     margin: 2.5rem 0 .75rem; }
.marca { text-align: center; margin-bottom: 2rem; }
/* MESMA declaracao do `.menu img` la embaixo, de proposito: o pedido era "o
   mesmo tamanho da do menu", e casar por `width` faz isso ser verdade por
   construcao. Com `height: 44px`, que era o valor antigo, manter os dois
   iguais dependeria de alguem refazer a conta 362x132 a cada mudanca -- e
   errar essa conta nao quebra nada, so faz as duas divergirem em silencio.
   Se um dia mudar aqui, mude la tambem. */
.marca img { width: 10rem; margin-bottom: 1rem; }
.marca-nome { font-size: 1.125rem; font-weight: 600; margin: 0 0 1rem; }
/* Marca da organizacao no topo das telas do fiscal e no menu do admin: so o
   logo quando ha logo, o nome quando nao ha (lib/marca.mjs). O logo da
   organizacao e arbitrario (largo, 362x132, ou quadrado):
   teto nas DUAS medidas, sem ampliar logo pequeno. No menu, 10rem e a largura
   do logo embarcado antigo e cabe na coluna de 12rem; a altura de 5rem segura
   um logo quadrado. */
.marca-topo, .marca-menu { display: flex; align-items: center; gap: .5rem;
                           font-weight: 600; margin: 0 0 .5rem; }
.marca-topo img, .marca-menu img { width: auto; height: auto; margin: 0; }
.marca-menu img { max-width: 10rem; max-height: 5rem; }
.marca-topo img { max-width: 12rem; max-height: 3.5rem; }
.marca-sub { color: var(--tinta-suave); font-size: .875rem; margin: 0; }
.topo { display: flex; justify-content: space-between; align-items: flex-start;
        gap: 1rem; padding-bottom: 1.25rem; border-bottom: 1px solid var(--linha); }

/* Abas dos catalogos. Sem estas regras os tres botoes saem com o verde
   primario e ficam identicos: depois do clique nada diz em qual catalogo voce
   esta, e gravar um cargo dentro de equipamentos vira erro silencioso. A ativa
   e' a unica com tinta e sublinhado; o estado real esta no aria-current, a
   classe so pinta. */
.abas { display: flex; gap: .25rem; margin: 1.5rem 0;
        border-bottom: 1px solid var(--linha); }
.abas button, .abas a { background: transparent; color: var(--tinta-suave);
               border: 0; border-bottom: 2px solid transparent; border-radius: 0;
               padding: .55rem .9rem; margin-bottom: -1px; text-decoration: none; }
.abas button:hover, .abas a:hover { color: var(--tinta); }
.abas button.ativa, .abas a.ativa { color: var(--destaque); font-weight: 600;
                     border-bottom-color: var(--destaque); }

.cartao { background: var(--cartao); border: 1px solid var(--linha);
          border-radius: 6px; padding: 1.5rem; display: grid; gap: 1rem;
          max-width: 24rem; margin: 0 auto; }
label { display: grid; gap: .35rem; font-size: .875rem; color: var(--tinta-suave); }
input, textarea { font: inherit; color: var(--tinta); padding: .6rem .7rem;
                  border: 1px solid var(--linha); border-radius: 4px;
                  background: var(--cartao); width: 100%; }
input:focus, textarea:focus { outline: 2px solid var(--destaque); outline-offset: 1px; }

button { font: inherit; font-weight: 500; padding: .65rem 1.1rem; border-radius: 4px;
         border: 1px solid var(--destaque); background: var(--destaque);
         color: #fff; cursor: pointer; }
button:disabled { opacity: .55; cursor: default; }
button.secundario { background: transparent; color: var(--tinta-suave);
                    border-color: var(--linha); }
button.perigo { background: transparent; color: var(--alerta); border-color: var(--alerta); }
.acoes { display: flex; gap: .75rem; margin: 1.5rem 0; }

.linha { display: flex; align-items: center; gap: 1rem; width: 100%; text-align: left;
         background: var(--cartao); color: var(--tinta); border: 1px solid var(--linha);
         border-radius: 4px; padding: .9rem 1rem; margin-bottom: .5rem; font-weight: 400; }
.linha:hover { border-color: var(--tinta-suave); }
.linha-num { font-weight: 600; min-width: 6rem; }
.linha-data { color: var(--tinta-suave); }
.linha-obra { color: var(--tinta-suave); flex: 1; }
.selo { margin-left: auto; font-size: .75rem; text-transform: uppercase;
        letter-spacing: .06em; padding: .2rem .5rem; border-radius: 3px; }
.selo-aprovado { color: var(--destaque); background: #E8EEF5; }
.selo-rejeitado { color: var(--alerta); background: #f8eded; }
/* Revisao e recusa, mas nao e rejeicao: ambar, nem o verde da aprovacao
   nem o vermelho da recusa. Sem cor propria a distincao morre na lista. */
.selo-revisao { color: #92400e; background: #fdf4e3; }

/* Lista dos catalogos. Sem list-style o item deixa de nascer com marcador e
   recuo do navegador. A moldura fica so na linha de item de verdade
   (li[data-id]): "Carregando…" e a linha de vazio sao texto solto, e uma
   moldura em volta deles pareceria um item cadastrado. */
.lista { list-style: none; margin: 1.5rem 0 0; padding: 0; }
.lista li[data-id] { display: flex; align-items: center; gap: .75rem;
                     background: var(--cartao); border: 1px solid var(--linha);
                     border-radius: 4px; padding: .7rem 1rem; margin-bottom: .5rem; }
.lista li[data-id] span { flex: 1; }
.lista li[data-id] button { background: transparent; color: var(--tinta-suave);
                            border-color: var(--linha); padding: .35rem .7rem;
                            font-size: .875rem; }
.lista li[data-id] button:hover { color: var(--tinta); border-color: var(--tinta-suave); }
/* Item de RDO: mesma moldura, mas empilhado -- o motivo da rejeicao e o nome
   de quem decidiu sao linhas abaixo do titulo, nao colunas ao lado dele. */
.lista li.item-rdo { flex-direction: column; align-items: flex-start; gap: .2rem; }
.lista li.item-rdo small { color: var(--tinta-suave); font-size: .8rem; }

.visor { margin: 1.5rem 0; border: 1px solid var(--linha); border-radius: 4px;
         overflow: hidden; background: var(--cartao); }
.pdf { width: 100%; height: 70vh; border: 0; display: block; }
.nota { background: #f3f1ec; border-left: 3px solid var(--tinta-suave);
        padding: .8rem 1rem; margin: 1.25rem 0; font-size: .9rem; }
.vazio { color: var(--tinta-suave); font-size: .9rem; padding: .75rem 0; }
.erro { color: var(--alerta); font-size: .875rem; margin: .75rem 0 0; }

/* Mensagem de sucesso. So existia .erro; sem isto o "Papel atualizado."
   apareceria sem estilo nenhum. */
.aviso { color: var(--destaque); font-size: .875rem; margin: .75rem 0 0; }

/* Linha de usuario: nome e e-mail a esquerda, seletor de papel a direita. */
.linha-usuario {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
}
.linha-usuario small {
  display: block;
  color: var(--tinta-suave);
}

/* Linha bloqueada, na LISTA (a matriz tem a regra irma dela mais abaixo,
   .matriz-obras tr.linha-bloqueada). Ate a revisao final desta fatia, a
   classe `linha-bloqueada` era posta no <li> (telas/usuarios.mjs) mas NAO
   existia regra nenhuma pra ela aqui -- so' a da matriz. A spec (§A.4) pede
   "linha bloqueada aparece visualmente distinta"; sem esta regra, so' o
   ROTULO do botao trocava para "Desbloquear", e a linha inteira continuava
   com a mesma cor de uma linha ativa. */
.lista li.linha-bloqueada { color: var(--tinta-suave); }

/* ------------------------------------------------- linha da tela Usuarios
   A linha de usuario deixa de ser fila unica e passa a EMPILHAR: identidade
   em cima, acoes embaixo, confirmacao em faixa cheia.

   POR QUE: `.lista li[data-id]` e' `display: flex` de uma fila so, e a linha
   de usuario tem sete filhos (identidade, papel, quatro botoes e quatro
   faixas de confirmacao escondidas). O flex espremia todos na mesma fila --
   "Resetar 2o fator" quebrava em TRES linhas, o "Excluir" saia pela borda
   do cartao, e, ao abrir a confirmacao de exclusao, o texto do "nao ha como
   desfazer" virava uma coluna estreita transbordando o cartao. Medido na
   producao de 19/08, em dois prints do Alan. Ilegivel ali nao e' questao de
   gosto: e' o unico texto que a pessoa le antes de apagar alguem para
   sempre.

   ESCOPADO em `.linha-usuario` de proposito. Cinco telas dividem `.lista`
   (cadastros, obras, RDOs da obra, pessoas e usuarios); mexer na regra
   generica consertaria uma e quebraria quatro. */
.lista li.linha-usuario { display: block; }

.usuario-identidade { display: flex; align-items: flex-start; gap: .75rem;
                      justify-content: space-between; }
/* O `flex: 1` do `.lista li[data-id] span` nao alcanca este bloco (e' div),
   entao o empurrao do seletor de papel para a direita vem do
   space-between -- e o `min-width: 0` deixa nome e e-mail longos quebrarem
   dentro do proprio bloco em vez de esticar a linha. */
.usuario-identidade > div { min-width: 0; }
.usuario-identidade select { width: auto; flex: none; }

/* `flex-wrap` e' o que impede o vazamento: em janela estreita os botoes
   descem de linha em vez de estourar a borda. E `nowrap` no botao mata a
   quebra de "Resetar 2o fator" em tres linhas -- o rotulo e' curto, quem
   estava quebrando era o aperto do flex, nao o texto. */
.usuario-acoes { display: flex; flex-wrap: wrap; gap: .5rem; margin-top: .75rem; }
.linha-usuario .usuario-acoes:empty { display: none; }
.linha-usuario button { white-space: nowrap; }

/* Faixa de largura INTEIRA, separada por um fio: e' o conserto do texto que
   transbordava. `display: block` nao briga com o `hidden`, porque a regra
   `[hidden] { display: none !important }` (linha 21) vence -- a mesma
   armadilha que `.cartao` ja tinha pago. */
.linha-usuario .confirma-acao { display: block; margin-top: .75rem;
                                padding-top: .75rem; border-top: 1px solid var(--linha);
                                line-height: 1.5; }

/* Rotulo do checkbox "Exibir bloqueados" (telas/usuarios.mjs). Sem regra
   propria ele herdava o `label` generico da linha 59 (display: grid, gap:
   .35rem -- pensado pra rotulo EM CIMA de campo de texto) e a caixa nascia
   empilhada acima do texto, em vez de lado a lado como um checkbox se le.
   Achado (minor) da revisao final: a classe existia no HTML sem nenhum CSS a
   alcancar. `input { width: auto }` desfaz o `input { width: 100% }` da
   linha 60 -- sem isto o quadradinho do checkbox esticaria pra ocupar a
   largura inteira do rotulo. */
.filtro-bloqueados { display: flex; align-items: center; gap: .5rem;
                      color: var(--tinta-suave); font-size: .875rem; margin: 0; }
.filtro-bloqueados input { width: auto; }

/* Os dois filtros da tela de Usuarios na mesma fileira -- os dois filtram
   EXIBICAO, sem buscar nada, e ficar em linhas separadas sugeriria que sao
   coisas de naturezas diferentes.

   `flex-wrap` porque em janela estreita o seletor de obra (que carrega nome de
   obra, e nome de obra e' longo) empurraria a caixa para fora do cartao -- a
   mesma licao que a linha de usuario ja pagou em 19/08.

   A margem de topo saiu do .filtro-bloqueados e veio para ca: com dois filhos,
   quem deve espacar do bloco de cima e' a fileira, senao os dois controles
   nascem desalinhados na vertical. */
.filtros-usuarios { display: flex; align-items: center; gap: 1.5rem;
                    flex-wrap: wrap; margin: 1.25rem 0 0; }

/* `display: flex` desfaz o `display: grid` que todo <label> desta folha tem --
   sem isto o rotulo "Obra" ficaria EM CIMA do seletor e a fileira ganharia o
   dobro da altura, desalinhando a caixa ao lado. Quem faz esse trabalho e' o
   `flex`, e nao um `flex-direction: row`: `row` ja e o padrao, e a revisao
   mediu que declara-lo nao muda um pixel. O irmao `.filtro-bloqueados` acima
   e' `display: flex` puro pelo mesmo motivo.

   E NAO ha `width: auto` aqui, de proposito: a folha nao tem regra
   `select { width: 100% }` para desfazer (a da linha 60 e `input, textarea`),
   entao a declaracao seria no-op com cara de load-bearing. O
   `.filtro-bloqueados input { width: auto }` do bloco acima, esse sim, e
   necessario -- medido: sem ele o checkbox estica de 21px para 50px. */
.filtro-obra { display: flex; align-items: center;
               gap: .5rem; color: var(--tinta-suave); font-size: .875rem; }
.filtro-obra select { padding: .35rem .5rem; font-size: .875rem;
                      border: 1px solid var(--linha); border-radius: 4px;
                      background: var(--cartao); color: var(--tinta); }

/* Confirmacao de reset do 2o fator OU de gerar nova senha, dentro da linha
   do usuario -- mesma classe para as duas, so o texto interno muda (fixo no
   HTML de cada bloco, ver telas/usuarios.mjs). SEM `display` aqui: o
   atributo `hidden` nativo e' uma regra do navegador, e qualquer display de
   autor neste elemento venceria e deixaria a confirmacao visivel o tempo
   todo. Mesma armadilha registrada na §9 do HANDOFF. */
.confirma-acao { font-size: .875rem; color: var(--tinta-suave); }
.confirma-acao button { margin-left: .5rem; }

/* Trilha: onde voce esta dentro da obra. */
.trilha { color: var(--tinta-suave); font-size: .875rem; margin: 0 0 .75rem; }
.trilha a { color: var(--tinta-suave); }

/* Titulo de grupo (Em aprovacao / Aprovados / Rejeitados). Sem regra propria o
   h3 herdava o tamanho do navegador e saia MAIOR que o h2 da pagina, invertendo
   a hierarquia. Fica um degrau abaixo do h2, que e' .8rem em caixa alta.
   Escopado em .grupo-rdos e nao no elemento: a 28c traz quatro secoes, e o
   primeiro h3 novo herdaria caixa alta e cinza sem ninguem pedir. */
.grupo-rdos h3 { font-size: .75rem; font-weight: 600; text-transform: uppercase;
                 letter-spacing: .06em; color: var(--tinta-suave); margin: 1.75rem 0 0; }

/* Area de admin: menu lateral fixo + conteudo. Em tela estreita o menu vira
   uma faixa no topo, porque coluna de 12rem num celular come metade da tela. */
.admin { display: flex; gap: 1.5rem; align-items: flex-start; }
.menu {
  display: flex; flex-direction: column; gap: .25rem;
  width: 12rem; flex-shrink: 0; padding: 1rem 0;
}
/* 10rem = 160px de largura, 58px de altura (o arquivo e 362x132, entao a
   proporcao e ~2,74:1). Era 5rem, que rendia 29px de altura e sumia ao lado
   dos rotulos do menu. Nao borra: 160px continua ABAIXO dos 362px nativos --
   so acima de ~22rem o navegador passaria a ampliar. A coluna tem 12rem
   (192px) e a margem esquerda come .75rem, entao 10rem cabe com folga. */
.menu .marca-menu { margin: 0 0 1rem .75rem; }
.menu a {
  padding: .5rem .75rem; border-radius: .375rem;
  color: var(--tinta); text-decoration: none;
}
.menu a.ativo { background: var(--destaque); color: #fff; }
.menu button { margin-top: 1rem; }
.conteudo { flex: 1; min-width: 0; }

@media (max-width: 40rem) {
  .admin { flex-direction: column; }
  .menu { width: auto; flex-direction: row; flex-wrap: wrap; align-items: center; }
  .menu .marca-menu { margin: 0 .75rem 0 0; }
  .menu button { margin-top: 0; }
}

/* Formulario de obra: rotulo em cima do campo, e a mensagem de erro do campo
   logo abaixo dele. Erro por campo, e nao um so no topo, porque sao sete
   campos e "preencha os obrigatorios" faz a pessoa cacar qual falta. */
.form-obra .campo { display: block; margin-bottom: .9rem; }
.form-obra .campo > span { display: block; font-size: .8rem; color: var(--tinta-suave);
                           margin-bottom: .25rem; }
.form-obra .campo input { width: 100%; box-sizing: border-box; }
.form-obra .erro-campo { display: block; color: var(--alerta); font-size: .8rem;
                         margin-top: .25rem; }
.form-obra .acoes, .situacao-obra .acoes { display: flex; gap: .5rem; margin-top: 1rem; }
.situacao-obra { margin-top: 1.5rem; }
.situacao-obra h3 { font-size: .8rem; font-weight: 600; text-transform: uppercase;
                    letter-spacing: .06em; color: var(--tinta-suave); margin: 0 0 .5rem; }

/* Selo de situacao na lista de obras. Obra inativa CONTINUA na lista -- o admin
   precisa acha-la para reativar --, entao ela precisa se distinguir a olho. */
.selo-inativa { background: #eceae4; color: var(--tinta-suave); border-radius: 3px;
                padding: .1rem .4rem; font-size: .7rem; text-transform: uppercase;
                letter-spacing: .04em; }
.lista li.item-obra { flex-direction: column; align-items: flex-start; gap: .2rem; }
.lista li.item-obra small { color: var(--tinta-suave); font-size: .8rem; }
/* .selo tem margin-left: auto para empurrar para a direita numa linha (flex-
   direction: row). Aqui a coluna e' vertical, e essa margem vence o
   align-items: flex-start e joga o selo para a borda direita do item, longe
   do texto que ele qualifica. Neutraliza so dentro de .item-obra -- .selo
   continua servindo outras telas em linha. */
.lista li.item-obra .selo { margin-left: 0; }

/* Detalhe da pessoa (cargo/e-mail do aprovador, e-mail do destinatario) AO
   LADO do nome, na mesma cor apagada que as outras listas usam para
   informacao secundaria. Compartilhada porque as duas telas listam pessoas
   no mesmo formato. (Ao lado, e nao embaixo: .item-pessoa nao declara
   flex-direction: column, ao contrario de .item-obra acima. O comentario
   dizia "embaixo" e discordava do proprio CSS.) */
.lista li.item-pessoa small { color: var(--tinta-suave); font-size: .8rem; }
/* A linha que o formulario do topo esta editando. O formulario e' o mesmo
   para criar e editar, entao sem este realce nada na LISTA indicava qual
   linha estava aberta -- e quem voltasse ao computador depois de uma
   interrupcao podia digitar por cima achando que cadastrava alguem novo,
   renomeando outra pessoa. Par visual do titulo "Editando «Fulano»". */
.lista li.em-edicao { border-left: 3px solid var(--destaque); padding-left: .6rem; }
/* Sem esta regra, o botao "Apagar" da confirmacao de exclusao (dentro de
   li[data-id]) herdava a cor apagada de `.lista li[data-id] button` -- essa
   regra tem mais especificidade que `button.perigo` sozinha (duas classes/
   atributo contra uma classe) e vencia, deixando a acao destrutiva com a
   mesma cor neutra dos botoes Editar/Apagar, sem nenhum sinal visual de que
   e' irreversivel. */
.lista li[data-id] button.perigo { color: var(--alerta); border-color: var(--alerta); }

/* Matriz de obras (Task 8): usuarios nas linhas, obras nas colunas. O
   contêiner com overflow-x: auto e' o pedido explicito do brief -- producao
   tem uma obra hoje, mas uma tabela mais larga que a tela empurraria o resto
   da pagina e sumiria com a rolagem vertical, e isso aconteceria na PRIMEIRA
   obra nova cadastrada, nao numa hipotese distante. Sem isto a tabela vaza
   por baixo do .raiz (max-width: 56rem) e cobre o rodape. */
.matriz-obras-wrap { overflow-x: auto; margin: 1.5rem 0 0; }
.matriz-obras { border-collapse: collapse; width: 100%; font-size: .875rem; }
.matriz-obras th, .matriz-obras td { border: 1px solid var(--linha); padding: .5rem .75rem;
                                      text-align: center; white-space: nowrap; }
.matriz-obras thead th { background: var(--cartao); text-align: left; }
/* A COLUNA DO NOME NAO ROLA JUNTO.
   O contêiner acima ja resolvia o espaco -- a tabela larga rola em vez de
   empurrar a pagina. O que ele nao resolve e' a IDENTIDADE: rolando ate a
   quinta obra, o nome sai da tela e quem esta marcando nao sabe mais de quem
   e' a linha. Numa matriz cuja escrita e' vincular/desvincular no clique,
   marcar a caixa da pessoa errada e' o dano, e ele e' silencioso.

   `background` opaco e' obrigatorio, nao enfeite: sem ele as celulas passam
   por baixo e os dois textos se sobrepoem enquanto rola.

   O divisor e' `box-shadow`, e NAO `border-right`: com `border-collapse:
   collapse` a borda pertence a TABELA, nao a celula, e por isso nao acompanha
   o elemento posicionado -- a coluna fixa ficaria sem divisor exatamente
   quando ele mais importa, que e' com conteudo passando por baixo. */
.matriz-obras th[scope="row"] { text-align: left; font-weight: 500;
                                position: sticky; left: 0; z-index: 1;
                                background: var(--cartao);
                                box-shadow: 1px 0 0 var(--linha); }
/* O canto (o "Usuário" do cabecalho) precisa do MESMO `left: 0` das celulas de
   baixo, senao ele rola e a coluna fixa fica sem titulo.

   SO O EIXO HORIZONTAL e' fixo -- nao ha `top` em lugar nenhum desta folha, e
   o `.matriz-obras-wrap` nao rola na vertical (nao tem `max-height`). Uma
   versao anterior deste comentario afirmava "fixo nos DOIS eixos"; a revisao
   mediu `getComputedStyle(canto).top === "auto"` e derrubou. O `z-index: 2`
   fica de qualquer forma, barato, para o dia em que o `thead` virar sticky --
   mas hoje ele nao esta vencendo ninguem. */
.matriz-obras thead th:first-child { position: sticky; left: 0; z-index: 2;
                                     background: var(--cartao);
                                     box-shadow: 1px 0 0 var(--linha); }
/* Mesma classe, e a mesma ideia, da linha bloqueada em .lista (acima) --
   apaga o usuario para reforcar visualmente por que a caixa "Exibir
   bloqueados" precisou estar ligada para ele aparecer. */
.matriz-obras tr.linha-bloqueada th, .matriz-obras tr.linha-bloqueada td { color: var(--tinta-suave); }
.topo-lista { display: flex; align-items: center; justify-content: space-between; gap: 1rem; }
/* Link que se comporta como botao: a navegacao e por href para o Voltar do
   navegador continuar funcionando, mas o alvo tem de parecer clicavel. */
.botao { display: inline-block; background: var(--destaque); color: #fff;
         border-radius: 4px; padding: .45rem .9rem; font-size: .875rem;
         text-decoration: none; }
.botao:hover { opacity: .9; }
