:root{
  /* A propriedade sobrepõe-se ao <meta>, por isso tem de dizer o mesmo: a
     página sabe apresentar-se clara e escura. Quem escolhe é o applyTheme(),
     que estreita isto para um dos dois com um estilo em linha. */
  color-scheme:light dark;
  /* A linguagem de 2026-10 (o canvas do Claude Design): fundo frio, cartões
     brancos com contorno, cobalto para a ação, azul-noite na barra lateral, e
     três cores para o dinheiro que diferem também em luminosidade — receita
     verde, despesa laranja, prestação roxa. O vermelho fica só para o perigo:
     atraso, erro, o que destrói. */
  --bg:#f2f3f6; --card:#ffffff; --field:#ffffff; --chip:#f6f7f9; --tint:#f6f7f9; --press:#e9ecf2;
  --ink:#121826; --muted:#4f586b; --faint:#687083; --line:#e2e5eb; --line2:#cdd2db;
  --accent:#2952d9; --accent-ink:#ffffff; --accent-soft:#e9eefc; --accent-text:#1d3fb0; --accent-press:#1d3fb0; --accent-fundo:#16318a; --accent-relevo:#1d3fb0;
  --in:#16775a; --in-soft:#e2f3eb; --out:#bd420c; --out-soft:#fceadf; --loan:#6845c2; --loan-soft:#efeafb;
  --danger:#b42318; --danger-soft:#fde8e6; --danger-ink:#ffffff; --danger-press:#912018; --warn:#8f5600; --warn-soft:#fff1d1;
  --side:#0e1830; --side-ink:#ffffff; --side-text:#c2cbe0; --side-muted:#8e9bb8; --side-hover:rgba(255,255,255,.07); --side-on:rgba(255,255,255,.12); --side-line:#22305a;
  --cnt:#ffb27a; --cnt-ink:#3a1a05;
  /* a marca não muda com o tema: é o cobalto do claro nos dois */
  --marca:#2952d9;
  /* o aviso de baixo é escuro no claro e claro no escuro: tem de se destacar
     do fundo nos dois */
  --toast:#121826; --toast-ink:#ffffff; --toast-btn:#2a3348;
  --track:#e2e5eb; --blur:rgba(242,243,246,.94); --shadow:0 16px 40px rgba(16,24,40,.16);
  --veu:rgba(9,14,28,.55);
  /* as duas letras, auto-alojadas em web/fonts/ (a CSP só deixa font-src
     'self'): a Geist no texto, a Bricolage Grotesque nos títulos e nos
     valores grandes */
  --letra:'Geist',system-ui,-apple-system,"Segoe UI",Roboto,sans-serif;
  --letra-titulo:'Bricolage Grotesque','Geist',system-ui,-apple-system,"Segoe UI",sans-serif;
  --rail:264px;
  /* Movimento: uma só escala de durações e duas curvas, citadas por toda a
     folha, para nada aqui ser um número escolhido à sorte. --curva arranca
     depressa e chega devagar — é a de quem entra em cena; --curva-sai faz o
     inverso, e serve o que se fecha ou desaparece. */
  /* O --lento é o degrau de quem atravessa distância — a folha da janela. A
     .26s não chegava: com a curva certa, uma folha que sobe o ecrã inteiro
     precisa de tempo para se ver subir. */
  --rapido:.12s; --medio:.2s; --lento:.34s;
  /* fora da escala porque não são reações: --desenho é um gráfico a
     desenhar-se e --pulso é um crachá a saltar */
  --desenho:.5s; --pulso:.18s;
  /* e --volta é a roda da espera a girar: uma volta que se vê, contínua */
  --volta:.9s;
  /* o tempo que o toque longo espera antes de disparar (componentes.js): a
     animação da espera tem de durar exatamente o mesmo, senão promete uma
     coisa e faz outra */
  --espera:.48s;
  /* TRÊS curvas de entrada, e a diferença é a distância percorrida.
     A --curva é um estalido: medida, faz 83% do caminho em 30% do tempo. É o
     que se quer num botão que encolhe 3% — a reação tem de parecer imediata.
     Numa folha que atravessa o ecrã, quer dizer 83% da altura em 78 ms: a
     janela teleporta-se e passa o resto do tempo a assentar os últimos 4%.
     A --curva-entra faz 64% em 30% e é a de quem ATRAVESSA distância: a folha
     da janela, a gaveta, as barras de um gráfico a crescer, o conteúdo de uma
     dobra. Quem estiver na dúvida: se o que se move percorre mais do que uns
     poucos pixeis, é a --curva-entra.
     A --curva-fita é para o que atravessa EM BLOCO: as duas fitas — a dos
     separadores e a das listas — em que o que sai e o que entra viajam
     agarrados. Ali a --curva-entra estava errada por ser a de quem CHEGA:
     arranca à velocidade máxima, e uma fita que estava parada não pode ter o
     primeiro fotograma já a toda a brida — lê-se como um empurrão. Esta sai
     das outras duas: o arranque da --curva-sai (.4,0) com a chegada da
     --curva-entra (.2,1). Parte do sítio, ganha velocidade, chega devagar. E
     é uma só para os dois painéis de propósito: com curvas diferentes
     abria-se uma fenda entre eles a meio do caminho. */
  --curva:cubic-bezier(.22,1,.36,1); --curva-entra:cubic-bezier(0,0,.2,1);
  --curva-sai:cubic-bezier(.4,0,1,1); --curva-fita:cubic-bezier(.4,0,.2,1);
  --safe:env(safe-area-inset-top,0px);
  --inset-top:var(--safe); --inset-bottom:env(safe-area-inset-bottom,0px);
  --inset-left:env(safe-area-inset-left,0px); --inset-right:env(safe-area-inset-right,0px);
}
:root.dark{
  color-scheme:dark;
  --bg:#0b111e; --card:#141c2c; --field:#141c2c; --chip:#1a2335; --tint:#1a2335; --press:#253049;
  --ink:#e9edf5; --muted:#aeb7c9; --faint:#8c96ab; --line:#253049; --line2:#33405c;
  --accent:#7c9bff; --accent-ink:#0b111e; --accent-soft:#1e2a4d; --accent-text:#b5c6ff; --accent-press:#9db3ff; --accent-fundo:#b5c6ff; --accent-relevo:#5a78e0;
  --in:#4cc79a; --in-soft:#123327; --out:#ff9a62; --out-soft:#3a2216; --loan:#b49bff; --loan-soft:#2a2247;
  --danger:#ff8a80; --danger-soft:#3d1a1a; --danger-ink:#1a0605; --danger-press:#ffb1aa; --warn:#f2c25a; --warn-soft:#352a12;
  --side:#070c17; --side-ink:#ffffff; --side-text:#9aa6c0; --side-muted:#7b88a6; --side-hover:rgba(255,255,255,.07); --side-on:rgba(255,255,255,.12); --side-line:#1a2440;
  --cnt:#ffb27a; --cnt-ink:#3a1a05;
  --toast:#e9edf5; --toast-ink:#121826; --toast-btn:#c9d0de;
  --track:#253049; --blur:rgba(11,17,30,.92); --shadow:0 24px 60px rgba(0,0,0,.6);
  --veu:rgba(2,5,12,.66);
}
/* As letras da app (web/fonts/, OFL — as licenças ao lado). Variáveis: um
   ficheiro dá todos os pesos, e a Bricolage traz também o eixo ótico, que
   abre o desenho nos tamanhos grandes. Só o latino: o português cabe todo
   nele (com o espaço fino U+202F do dinheiro e o − tipográfico), e o resto cai
   na letra do sistema pelo unicode-range. O swap mostra o texto logo na letra
   do sistema e troca quando a nossa chega: nunca há texto invisível. */
@font-face{font-family:'Geist';font-style:normal;font-weight:100 900;font-display:swap;
  src:url(/fonts/geist.woff2) format('woff2');
  unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}
@font-face{font-family:'Bricolage Grotesque';font-style:normal;font-weight:200 800;font-display:swap;
  src:url(/fonts/bricolage-grotesque.woff2) format('woff2');
  unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}
*{box-sizing:border-box}
html,body{height:100%}
/* A Geist no texto, a 15px com entrelinha de 1.45; o antialiasing de tons de
   cinzento porque o subpixel engrossa a letra clara sobre fundo escuro. */
body{margin:0;background:var(--bg);color:var(--ink);font-family:var(--letra);font-size:15px;line-height:1.45;-webkit-text-size-adjust:100%;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}
button,input,select,textarea{font:inherit;color:inherit}
/* A Bricolage Grotesque nos títulos e nos valores grandes, a 650 e um pouco
   apertada; o eixo ótico (font-optical-sizing) desenha-a mais aberta quanto
   maior. A .disp é a mesma letra para o que não é um título (um valor de KPI,
   o total de uma lista). */
h1,h2,h3,.disp{font-family:var(--letra-titulo);font-weight:650;letter-spacing:-.015em;font-optical-sizing:auto}
.value,.table td,.table th,.stat b,.num{font-variant-numeric:tabular-nums}

.app{display:flex;min-height:100%}
aside{width:var(--rail);flex:0 0 var(--rail);background:var(--side);color:var(--side-text);display:flex;flex-direction:column;position:sticky;top:0;height:100vh;height:100dvh;transition:width var(--medio) var(--curva-entra),flex-basis var(--medio) var(--curva-entra),transform var(--medio) var(--curva-sai);z-index:62}
/* A barra lateral de 2026-10: azul-noite, a marca e o nome na Bricolage, o
   «Criar» a toda a largura, os grupos com títulos pequenos em maiúsculas e os
   itens de 40px (44 no dedo) com o ativo num fundo translúcido — sem o traço
   à esquerda, que o canvas não tem. O texto inativo é o --side-text; o ativo,
   branco. */
.brand{display:flex;align-items:center;gap:10px;padding:calc(20px + var(--inset-top)) 22px 10px;min-height:60px}
.brand .txt{flex:1;min-width:0}
.brand b{font-family:var(--letra-titulo);font-size:20px;font-weight:650;letter-spacing:-.015em;color:var(--side-ink);display:block;white-space:nowrap}
nav{display:grid;gap:2px;padding:10px 14px calc(16px + var(--inset-bottom));flex:1;align-content:start;overflow:auto}
nav a{display:flex;align-items:center;gap:12px;min-height:40px;padding:0 12px;border-radius:10px;color:var(--side-text);cursor:pointer;white-space:nowrap;position:relative;font-size:14.5px;font-weight:500;text-decoration:none}
nav a svg{flex:0 0 20px}
/* o realce de passar por cima só onde há rato: no telemóvel um toque deixava-o
   preso (a regra da casa) */
@media(hover:hover) and (pointer:fine){nav a:hover{background:var(--side-hover);color:var(--side-ink)}}
nav a.on{background:var(--side-on);color:var(--side-ink);font-weight:600}
.railfoot{padding:10px 10px calc(10px + var(--inset-bottom));border-top:1px solid rgba(255,255,255,.09)}
.railbtn{width:100%;display:flex;align-items:center;gap:12px;background:transparent;border:0;color:var(--side-muted);padding:10px 12px;border-radius:11px;cursor:pointer;text-align:left}
@media(hover:hover) and (pointer:fine){.railbtn:hover{background:var(--side-hover);color:var(--side-ink)}}
/* O véu acompanha a gaveta em vez de chegar inteiro no primeiro frame: a
   mesma duração e a mesma curva do aside, aqui em cima. O display fica de fora
   de propósito — com opacity:0 e display:block o véu continuava a apanhar os
   toques com a gaveta fechada; é o visibility que o tira da frente, e o atraso
   de --medio só o esconde depois de ele ter acabado de desvanecer. */
.scrim{position:fixed;inset:0;background:var(--veu);z-index:61;opacity:0;visibility:hidden;
  transition:opacity var(--medio) var(--curva-sai),visibility 0s var(--medio)}
main{flex:1;min-width:0;display:flex;flex-direction:column}
/* Vidro à Apple: o blur com saturação deixa as cores de baixo atravessar
   vivas em vez de acinzentadas; o prefixo -webkit- é o que o iOS antigo lê.
   E a risca de baixo nasce transparente — no topo da página não há conteúdo
   por baixo dela para separar; é o ouvinte de scroll do toTop
   (componentes.js) que a acende com body.rolada. */
header.top{position:sticky;top:0;z-index:20;background:var(--blur);-webkit-backdrop-filter:blur(12px) saturate(140%);backdrop-filter:blur(12px) saturate(140%);border-bottom:1px solid transparent;
  transition:border-bottom-color var(--rapido) var(--curva);
  padding:calc(13px + var(--inset-top)) calc(clamp(16px,3vw,36px) + var(--inset-right)) 13px calc(clamp(16px,3vw,36px) + var(--inset-left));
  display:flex;align-items:center;gap:12px}
body.rolada header.top{border-bottom-color:var(--line)}
/* o título da página na Bricolage: 32px no computador, 22 no telemóvel
   (a @media de baixo), com o subtítulo só no computador */
header.top h1{font-size:32px;line-height:1.1;margin:0}
header.top .sub{color:var(--muted);font-size:14px;margin-top:4px}
.burger{display:none;border:0;background:transparent;border-radius:12px;padding:0;width:44px;height:44px;cursor:pointer;color:var(--ink);margin-left:-8px}
.spacer{flex:1}
/* a página no computador: 24px em cima, clamp(16px,3vw,36px) aos lados e no
   máximo 1240px (o contrato); no telemóvel, 16px aos lados (a @media de baixo) */
.wrap{padding:24px calc(clamp(16px,3vw,36px) + var(--inset-right)) calc(44px + var(--inset-bottom)) calc(clamp(16px,3vw,36px) + var(--inset-left));max-width:1240px;width:100%}
@media(max-width:900px){
  aside{position:fixed;left:0;top:0;transform:translateX(-100%);width:var(--rail);flex-basis:var(--rail)}
  body.open aside{transform:none;box-shadow:8px 0 32px rgba(0,0,0,.3);
    transition:width var(--medio) var(--curva-entra),flex-basis var(--medio) var(--curva-entra),transform var(--medio) var(--curva-entra)}
  body.open .scrim{opacity:1;visibility:visible;transition:opacity var(--medio) var(--curva-entra),visibility 0s}
  .burger{display:inline-flex;align-items:center;justify-content:center}
  .wrap{padding:4px calc(16px + var(--inset-right)) calc(44px + var(--inset-bottom)) calc(16px + var(--inset-left))}
  header.top{padding:calc(10px + var(--inset-top)) calc(8px + var(--inset-right)) 6px calc(8px + var(--inset-left));gap:4px}
  header.top h1{font-size:22px}
  header.top .sub{display:none}
  .burger{margin-left:0}
}
@media(max-width:520px){.hideS{display:none}}

/* O cartão tem contorno e não tem sombra: só flutua o que sobe (janelas e
   menus). 18px de enchimento no computador, 14 no telemóvel (a @media de
   baixo), como no canvas. */
.card{background:var(--card);border:1px solid var(--line);border-radius:16px;padding:18px;min-width:0;max-width:100%}
@media(max-width:520px){.card{padding:14px}}
.cols>*{min-width:0}
/* clicável: reage ao toque e ao rato; informativo fica liso. O risco de
   acento à esquerda saiu com a linguagem de 2026-10 — o que se toca diz-se
   pela seta, pelo hover e pelo premido, e não por uma borda colorida. */
.card.tap{cursor:pointer;position:relative;overflow:hidden;transition:border-color var(--rapido) var(--curva),transform var(--rapido) var(--curva),background var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.card.tap:hover{border-color:var(--line2);background:var(--tint)}}
/* 1% não se vê: era a queixa de «não reage ao toque, só muda de cor». As
   linhas de lista são a superfície que mais se toca na app. */
.card.tap:active{transform:scale(.98);background:var(--press)}
.card.kpi::before{display:none}
[data-lp]{-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
*{-webkit-tap-highlight-color:transparent}
button,.tap,.selbtn,.selopt,.fold-head{-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
/* Segurar o dedo sobre uma superfície que reage ao toque não é selecionar
   texto. A lista dos movimentos MEXE-SE por baixo do dedo ao entrar em modo
   de seleção — nasce a barra acima de tudo, o título do mês cresce e cola-se
   ao topo —, e o dedo acaba sobre o cabeçalho do mês, que não tem data-lp e
   escapava às duas regras de cima. Casa pelo comportamento e não pelo
   elemento: o tornarFocavel carimba role="button" em tudo o que tem onclick,
   e é por aí que se apanha também o que ainda não existe. O que se copia — o
   IBAN, as notas, os valores das fichas — não tem onclick nenhum. */
[role="button"],.section-title,.selbox,.sel-cab{-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
.grid{display:grid;gap:14px;grid-template-columns:repeat(auto-fit,minmax(158px,1fr))}
.cols{display:grid;gap:14px;grid-template-columns:repeat(auto-fit,minmax(290px,1fr));margin-top:14px}
@media(max-width:520px){.grid{gap:10px}}
/* O indicador: o rótulo em letra de texto, sem maiúsculas (o canvas escreve
   «Receita» com a bolinha da cor ao lado), e o valor na Bricolage, grande. */
.kpi .label{font-size:13.5px;color:var(--muted);font-weight:600;display:flex;align-items:center;gap:7px}
.kpi .value{font-family:var(--letra-titulo);font-size:28px;font-weight:650;margin-top:4px;letter-spacing:-.015em;line-height:1.15;font-optical-sizing:auto}
@media(max-width:520px){.kpi .value{font-size:21px}}
/* A faixa da série de um indicador: a silhueta dos doze meses e a variação
   face ao ano anterior. A ALTURA E FIXA de propósito — a caixa nasce vazia
   com o render e só depois é enchida (vistas.js:pintarSeriesKpi), e sem altura
   reservada tudo o que está por baixo saltava quando ela aparecesse. */
/* Duas linhas: a silhueta e a variação em cima, o ano e o valor em baixo.
   Numa linha só, «2025: 8 500 €» era o terceiro a caber e o primeiro a ser
   cortado pelas reticências — desaparecia, e sem ele a percentagem não diz de
   que números fala. A altura é dada (e não a do conteúdo) porque a caixa
   nasce vazia e é enchida depois: sem ela, tudo o que está por baixo saltava
   quando a variação aparecesse. */
.kserie{min-height:38px;margin:5px 0 1px;display:flex;flex-wrap:wrap;align-items:center;gap:2px 6px;min-width:0}
.kserie .ksilhueta{width:46px;height:16px;flex:0 0 46px;color:var(--line2);opacity:.9}
.kserie .kvar{font-size:11.5px;font-weight:700;white-space:nowrap;color:var(--muted)}
.kserie .kvar.pos{color:var(--in)}
.kserie .kvar.neg{color:var(--out)}
.kserie .kvsub{font-size:10.5px;color:var(--muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;
  flex:1 0 100%;min-width:0}
.kpi .foot{font-size:11.5px;color:var(--muted);margin-top:3px}
.kpi.why{cursor:pointer}
.kpi .expl{display:none;margin-top:10px;padding-top:10px;border-top:1px solid var(--line);font-size:12px;color:var(--muted);line-height:1.5}
.kpi.open .expl{display:block}
.kpi.why::after{content:"?";position:absolute;top:12px;right:13px;width:16px;height:16px;border-radius:50%;
  background:var(--chip);color:var(--muted);font-size:10.5px;font-weight:700;display:grid;place-items:center}
.kpi.open::after{content:"×"}
.card.kpi{position:relative}

/* dica dos gráficos */
.tip{position:fixed;z-index:95;background:var(--toast);color:var(--toast-ink);padding:7px 11px;border-radius:10px;
  font-size:12.5px;font-weight:600;pointer-events:none;opacity:0;transition:opacity var(--rapido) var(--curva);max-width:calc(100vw - 16px);text-align:center;line-height:1.35}
.tip.on{opacity:1}
/* O dinheiro tem três cores: o que entra é verde (--in), o que sai é laranja
   (--out) e o aviso é âmbar. O vermelho não é dinheiro negativo — é perigo
   (atraso, erro, destrutivo), e escreve-se .perigo. */
.pos{color:var(--in)}.neg{color:var(--out)}.amber{color:var(--warn)}.perigo{color:var(--danger)}.prest{color:var(--loan)}
/* o rótulo de secção do canvas: 12px, maiúsculas só por estilo, espaçado */
.section-title{font-size:12px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--muted);margin:24px 0 10px}
.toolbar{display:flex;gap:10px;align-items:center;flex-wrap:wrap;margin-bottom:12px}
/* O botão diz o verbo. 44px de altura em todo o lado (o canvas não tem
   tamanho compacto para o rato), raio 12, contorno --line2; o primário é
   cobalto; o que destrói é VERMELHO CHEIO e nunca igual ao Guardar; o
   fantasma não tem fundo nem contorno. */
.btn{border:1px solid var(--line2);background:var(--card);color:var(--ink);min-height:44px;padding:0 16px;border-radius:12px;cursor:pointer;display:inline-flex;align-items:center;justify-content:center;gap:8px;font-weight:600;font-size:15px;line-height:1.2;text-decoration:none}
@media(hover:hover) and (pointer:fine){.btn:hover{background:var(--tint)}}
.btn.primary{background:var(--accent);color:var(--accent-ink);border-color:var(--accent)}
@media(hover:hover) and (pointer:fine){.btn.primary:hover{background:var(--accent-press);border-color:var(--accent-press)}}
.btn.ghost{background:transparent;border-color:transparent;color:var(--ink)}
@media(hover:hover) and (pointer:fine){.btn.ghost:hover{background:var(--chip)}}
.btn.sm{min-height:36px;padding:0 12px;font-size:14px;border-radius:10px}
.btn.danger{color:var(--danger-ink);border-color:var(--danger);background:var(--danger)}
@media(hover:hover) and (pointer:fine){.btn.danger:hover{background:var(--danger-press);border-color:var(--danger-press)}}
/* o botão só de ícone: um quadrado com o lado do botão (aria-label sempre) */
.btn.so-icone{width:44px;padding:0}
.btn.sm.so-icone{width:36px}
.btn:disabled,.btn[aria-disabled="true"]{opacity:.5;cursor:not-allowed}
.list{display:grid;gap:11px}
/* O selo de estado: retangular de cantos pequenos (raio 6), 22px, e a cor
   diz o estado — cobalto por omissão (por confirmar, por começar), verde o
   que está bem (.in: em vigor, em dia, arrendado), cinzento o neutro
   (terminado, uso próprio, silenciado), âmbar o que está para breve (vago,
   faltam até 30 dias), vermelho o que passou (em atraso, faltam até 7 dias),
   laranja a despesa e roxo o que vem de um crédito ou é automático. Os pares
   passam 4,5:1 a 12px nos dois temas (medido na prova da fundação). */
.badge{display:inline-flex;align-items:center;gap:5px;min-height:22px;padding:2px 8px;border-radius:6px;background:var(--accent-soft);color:var(--accent-text);font-size:12px;font-weight:600;line-height:1.3;white-space:nowrap}
.badge.grey{background:var(--chip);color:var(--muted)}
.badge.amber{background:var(--warn-soft);color:var(--warn)}
.badge.red{background:var(--danger-soft);color:var(--danger)}
.badge.in{background:var(--in-soft);color:var(--in)}
.badge.out{background:var(--out-soft);color:var(--out)}
.badge.loan{background:var(--loan-soft);color:var(--loan)}
.title{font-weight:600;letter-spacing:-.005em}
/* Um título que divide a linha com um valor e com a porta das opções tem de
   cortar: a coluna dele encolhe, e o que sobra sai da caixa. Três cartões
   escreviam isto à mão no style de cada um — passou a ser a regra do padrão.
   Só neste padrão: um .title que é o cabeçalho de uma folha pode embrulhar. */
.card .row-between>div:first-child{min-width:0}
.card .row-between>div:first-child>.title{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.small{font-size:13px;color:var(--muted)}
/* Um vazio não é um beco: diz o que falta e oferece a ação certa. Tracejado,
   alinhado à esquerda, o título a 600 e o botão por baixo (vistas.js:saida). */
.empty{padding:18px;text-align:left;color:var(--muted);border:1px dashed var(--line2);border-radius:14px;background:transparent;display:flex;flex-direction:column;align-items:flex-start;gap:8px;font-size:14px}
.empty>div{display:flex;flex-wrap:wrap;gap:8px}
/* o calendário (o canvas M-Agenda): sete colunas, cada dia um botão sem
   contorno com o número e os pontos por baixo; hoje a cheio em cobalto, o dia
   escolhido com um anel, os dias dos meses vizinhos esbatidos e sem toque */
.calgrid{display:grid;grid-template-columns:repeat(7,minmax(0,1fr));gap:2px}
.calhead{margin-bottom:4px}
.calhead span{text-align:center;font-size:12px;color:var(--muted);font-weight:600}
.calday{height:50px;min-width:0;border:0;border-radius:12px;padding:6px 0 0;margin:0;
  display:flex;flex-direction:column;align-items:center;justify-content:flex-start;gap:4px;
  background:transparent;color:var(--ink);font:inherit;font-size:15px;font-weight:500;cursor:pointer}
.calday.fora{color:var(--faint);cursor:default}
.calday.hoje{background:var(--accent);color:var(--accent-ink);font-weight:700}
.calday .n{font-size:15px;line-height:1.2;color:inherit;font-variant-numeric:tabular-nums}
.calday.on{background:var(--accent-soft);color:var(--accent-text);font-weight:700;box-shadow:inset 0 0 0 2px var(--accent)}
.calday.hoje.on{background:var(--accent);color:var(--accent-ink);box-shadow:none}
@media(hover:hover) and (pointer:fine){.calday.tap:not(.on):not(.hoje):hover{background:var(--tint)}}
.calday.tap:focus-visible{outline:2px solid var(--accent);outline-offset:1px}
.calday .pts{display:flex;gap:3px;height:6px}
/* a grelha dos dias arrasta-se para os lados (calendario.js:calArrastar): a
   vertical continua a ser da página, a horizontal passa a ser do calendário */
#calDias{touch-action:pan-y;user-select:none;-webkit-user-select:none}
/* durante o arrasto os vizinhos espreitam dos lados, recortados pelo cartão;
   em altura, pelo mês de agora: um vizinho de seis semanas tem mais uma fila
   que um mês de cinco, e ela ficava por cima da legenda. A fila a mais só
   aparece depois de largar, quando a fita abre o espaço (continuidade.js:
   aFitaAbreEspaco). O clip, e não o hidden, deixa os lados à vista. */
#calDias.arrasta{position:relative;overflow-y:clip}
#calCard.arrasta{overflow:hidden}
.calvizinho{position:absolute;top:0;width:100%;pointer-events:none}
/* o ponto das visitas é cobalto e o dos planeados laranja (o dinheiro que sai,
   como no canvas); em cima do dia de hoje, que é cobalto, trocam para cores
   que se leem sobre ele */
.pt{width:6px;height:6px;border-radius:50%;display:inline-block}
.pt.vis{background:var(--accent)}
.pt.pla{background:var(--out)}
.pt.mais{background:var(--muted)}
.calday.hoje .pt.vis{background:var(--accent-ink)}
.calday.hoje .pt.pla{background:var(--cnt)}
:root.dark .calday.hoje .pt.pla{background:var(--out-soft)}
.empty b{display:block;color:var(--ink);font-weight:600;font-size:15px}
/* Uma boa notícia no lugar de um gráfico vazio (projecoes.js:livreDeDividas):
   não é um vazio a pedir ação, por isso não leva o tracejado do .empty — um
   selo com o visto na cor da app, e a frase. */
.livre{display:flex;flex-direction:column;align-items:center;gap:4px;padding:22px 12px 14px;text-align:center;color:var(--muted);font-size:13.5px}
.livre b{color:var(--ink);font-size:16px}
.livre-selo{width:52px;height:52px;border-radius:50%;display:grid;place-items:center;margin-bottom:8px;background:var(--in-soft);color:var(--in)}
.row-between{display:flex;justify-content:space-between;gap:14px;align-items:flex-start;min-width:0}
.row-between>*{min-width:0}
.txrow .title,.txrow .small{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.txrow{overflow:hidden}
.table{width:100%;border-collapse:collapse;font-size:14px}
.table th,.table td{padding:10px 10px;border-bottom:1px solid var(--line);text-align:right;white-space:nowrap}
/* o cabeçalho da tabela em letra de texto, 12px a 600, sem maiúsculas (as
   tabelas do canvas: B-Operacao, D-Avaliacao, D-Declaracao) */
.table th{font-size:12px;color:var(--muted);font-weight:600}
.table th:first-child,.table td:first-child{text-align:left}
.table tr:last-child td{border-bottom:0}
.tablewrap{overflow-x:auto;margin:0 -4px}
.hint{font-size:13px;color:var(--muted);line-height:1.5}
.rich{white-space:normal;line-height:1.55}
.rich div,.rich p{margin:0}
.rich pre{white-space:pre-wrap;background:var(--chip);padding:6px 8px;border-radius:7px;font:12px ui-monospace,Menlo,monospace;margin:4px 0}
.rich ul,.rich ol{margin:4px 0;padding-left:22px}
.rich code{background:var(--chip);padding:1px 5px;border-radius:5px;font:12px ui-monospace,Menlo,monospace}
.rich b{font-weight:700}.rich s{opacity:.7}
.divider{height:1px;background:var(--line);margin:14px 0}
.stat{display:flex;justify-content:space-between;gap:12px;padding:10px 0;border-bottom:1px solid var(--line);font-size:14.5px}
.stat:last-child{border-bottom:0}
.stat b{font-weight:600}
/* as pessoas são redondas; as iniciais em cobalto sobre o suave */
.avatar{width:36px;height:36px;border-radius:50%;background:var(--accent-soft);color:var(--accent-text);display:grid;place-items:center;font-weight:700;font-size:13px;flex:0 0 36px}
.chips{display:flex;gap:6px;flex-wrap:wrap;margin-top:9px}
.thumbs{display:grid;grid-template-columns:repeat(auto-fill,minmax(96px,1fr));gap:9px}
.thumb{border:1px solid var(--line);border-radius:12px;overflow:hidden;background:var(--chip);cursor:pointer}
.thumb img{width:100%;height:76px;object-fit:cover;display:block}
.thumb .nm{font-size:11px;padding:6px 7px;color:var(--muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.thumb input.nm{color:var(--ink);font-weight:500;background:var(--field)}
.prow{display:flex;align-items:center;gap:8px;min-width:0}
.prow .pth{width:64px;height:52px;border-radius:10px;background:var(--chip);overflow:hidden;flex:0 0 64px;cursor:pointer;position:relative}
.prow .capa{position:absolute;left:4px;bottom:4px;z-index:2;background:rgba(0,0,0,.55);color:#fff;font-size:11px;font-weight:700;padding:1px 6px;border-radius:999px;letter-spacing:.03em}
.prow .pnm{flex:1;min-width:0}
.pgrab{width:34px;height:40px;border:1px solid var(--line);background:var(--field);border-radius:9px;display:grid;place-items:center;color:var(--muted);cursor:grab;flex:0 0 34px;touch-action:none}
.prow.drag{position:relative;z-index:5;box-shadow:0 10px 26px rgba(0,0,0,.25);background:var(--card);border-radius:12px}
.prow{transition:transform var(--rapido) var(--curva)}
.prow.drag{transition:none}
.pcover img{width:100%;height:100%;object-fit:cover;display:block}
.thumb input.nm:focus{outline:2px solid var(--accent-soft);outline-offset:-2px}
.ownrow{display:flex;align-items:center;gap:8px;padding:7px 9px;border:1px solid var(--line);border-radius:12px;background:var(--field)}
.ownrow .nm{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-weight:600;font-size:13.5px;color:var(--ink)}
.ownrow input{width:66px;padding:7px 8px;text-align:right;flex:0 0 66px}
.ownrow .pc{color:var(--muted);font-size:12px}

.chartbox svg{width:100%;height:auto;display:block;overflow:visible}
/* Ler um gráfico com o dedo (graficos.js). A guia é SOBREPOSTA ao desenho; a
   leitura não: vive na cabeça, por cima do desenho, no canto superior direito
   — a faixa que ficava sobreposta ao topo do desenho tapava as barras mais
   altas e o eixo, e o pé debaixo do eixo ficava tapado pela mão, que no
   telemóvel vem de baixo. O lugar dela existe sempre, invisível, com a altura
   e a largura que o molde lhe dá: um gráfico não pode mudar de altura só por
   alguém lhe tocar. */
/* Sem seleção nem callout: os rótulos do eixo são <text> a sério dentro do
   SVG, e segurar o dedo caía no gesto de selecionar palavra do browser — que
   escolhia o mês e, ao começar, roubava o ponteiro e cancelava a leitura. É a
   mesma proteção que a app já dá a [data-lp], o outro gesto de segurar. */
.chartbox{position:relative;touch-action:pan-y;-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
.chartguia,.chartlido{opacity:0;pointer-events:none;transition:opacity var(--rapido) var(--curva)}
.chartbox.a-ler .chartguia,.chartler:has(>.chartbox.a-ler) .chartlido{opacity:1}
.chartguia{position:absolute;top:0;bottom:13px;width:1.5px;margin-left:-.75px;background:var(--line2);border-radius:2px}
/* A cabeça: a legenda à esquerda e o lugar da leitura à direita, numa grelha
   — a legenda nunca fica por baixo da leitura. A coluna da leitura tem a
   largura do molde (fit-content) e nunca passa de 58%: num telemóvel a
   legenda precisa do resto. O lugar desce ao fundo da cabeça, colado ao
   desenho. Sem legenda (.so), o lugar fica sozinho no canto. */
.chartcab{display:grid;grid-template-columns:minmax(0,1fr) fit-content(58%);gap:10px 12px;align-items:start;margin-bottom:10px}
.chartcab>.legend{margin-top:0;grid-column:1;grid-row:1}
.chartlugar{grid-column:2;grid-row:1;align-self:end;position:relative;min-width:0}
/* Empilhado (graficos.js:cabecaEmpilha — nomes compridos ou mais de quatro
   séries): a legenda toma a largura toda e parte os nomes em linhas, que é
   onde o nome inteiro se lê; a leitura vai para baixo dela, no mesmo canto,
   logo acima do desenho. */
.chartcab.empilhado{grid-template-columns:minmax(0,1fr)}
.chartcab.empilhado .chartlugar{grid-column:1;grid-row:2;justify-self:end;max-width:100%}
.chartcab.empilhado>.legend{grid-template-columns:repeat(auto-fill,minmax(220px,1fr))}
.chartcab.empilhado>.legend .nm{white-space:normal;overflow-wrap:anywhere}
/* A leitura: uma grelha de três colunas — bolinha, nome, valor — com o
   rótulo a negrito por cima, a toda a largura. Os valores alinham pela
   direita, em algarismos de largura igual, e nunca se cortam; o nome corta
   com reticências. Uma série sem nome (.uma) é uma linha: rótulo, bolinha,
   valor. */
.chartlido{display:grid;grid-template-columns:8px minmax(0,1fr) auto;align-items:center;gap:3px 6px;
  padding:6px 9px;border-radius:10px;background:var(--chip);color:var(--ink);
  font-size:11.5px;line-height:1.35;white-space:nowrap;font-variant-numeric:tabular-nums}
.chartlido.uma{grid-template-columns:minmax(0,1fr) 8px auto}
.chartlido b{grid-column:1/-1;font-weight:700;min-width:0;overflow:hidden;text-overflow:ellipsis}
.chartlido.uma b{grid-column:auto}
.chartlido i{width:8px;height:8px;border-radius:3px}
.chartlido .lnm{min-width:0;overflow:hidden;text-overflow:ellipsis;color:var(--muted)}
.chartlido .lvl{font-weight:650;text-align:right}
/* O molde dá o tamanho e não se vê; a leitura que se vê fica por cima dele,
   em absoluto, e por isso o texto de cada mês não mexe na largura. O rótulo
   e o valor do molde levam TODOS os textos possíveis, empilhados na mesma
   célula (graficos.js:pilha): a largura é a do mais largo, e não a do que
   tem mais letras — «mai» não cabia no lugar do «jan». */
.chartmolde{visibility:hidden}
.chartmolde>b,.chartmolde>.lvl{display:grid}
.chartmolde>b>span,.chartmolde>.lvl>span{grid-area:1/1}
.chartlugar>.chartlido:not(.chartmolde){position:absolute;inset:0}
/* A página trancada por baixo de uma janela. Quem tranca é o overflow do
   html e o position:fixed do body — o body NÃO leva overflow:hidden.

   Levava, e o body tem uma altura de ecrã (html,body{height:100%}): trancado
   em position:fixed com top:-scrollY, passava a recortar o próprio conteúdo a
   uma caixa de um ecrã ancorada no INÍCIO do documento, e essa caixa está
   empurrada para fora da vista pelo valor do scroll. Com a página rolada, não
   se pintava nada por trás da janela — um retângulo escuro parado, que parecia
   um véu descolado do scroll e era a página a desaparecer. O .modal escapava
   ao recorte por ser fixed, e por isso a folha e o véu ficavam certos. */
html.noscroll{overflow:hidden}
html.noscroll body{position:fixed;left:0;right:0;width:100%}
.navh{font-size:10.5px;letter-spacing:.07em;text-transform:uppercase;color:var(--side-muted);padding:14px 12px 4px;opacity:.85;white-space:nowrap}
/* o crachá da barra lateral é quente (--cnt) sobre o azul-noite; o de
   aviso (nada passou ainda do prazo) é o azul claro informativo */
nav a .cnt{margin-left:auto;min-width:22px;height:20px;display:inline-flex;align-items:center;justify-content:center;background:var(--cnt);color:var(--cnt-ink);font-size:12px;font-weight:700;padding:0 6px;border-radius:999px;font-variant-numeric:tabular-nums}
nav .cnt.u-bg-v-warn{background:#9fb4ff!important;color:#0e1830} /* o azul informativo do canvas (a Ajuda), que se lê no azul-noite */
/* As secções da gaveta recolhem-se (navegacao.js:gavetaHtml,
   navegacao.js:gavetaAlternar). O título é um botão com classe própria, e não
   o .navh: o .navh é também o título pequeno de listas fora da gaveta (os
   pedidos por responder, as visitas do dia) e esse não muda. Tem a letra do
   .navh e o alvo de toque de um botão.
   A altura anima por grid-template-rows, de 1fr a 0fr com os dois valores
   escritos — a dobra (.fold-body) tentou a partir de uma linha medida pelo
   conteúdo e não interpolava; entre dois fr interpola. O overflow:hidden que
   isto pede fica no .navsec-itens, alargado 10px para cada lado para não
   cortar o traço do ativo (nav a.on::before, a -10px); o anel de foco dos
   itens passa para dentro pela mesma razão. Recolhida, o visibility tira os
   itens do Tab e do leitor de ecrã — só no FIM da transição, para se verem a
   encolher; a abrir, logo no início. Sem movimento (prefers-reduced-motion)
   a regra geral desliga as transições, e tudo acontece de uma vez. */
.navsec{display:grid;min-width:0}
/* o espaço que separa a secção da de cima é MARGEM e não enchimento: com os
   14px do .navh por dentro do botão, o realce do toque e o anel de foco
   ficavam com o texto colado ao fundo de uma caixa meio vazia */
.navsec-tit{display:flex;align-items:center;gap:8px;width:100%;min-height:32px;margin:14px 0 2px;padding:6px 12px;border:0;border-radius:9px;
  background:transparent;color:var(--side-muted);cursor:pointer;text-align:left;font-size:11.5px;font-weight:600;letter-spacing:.08em;text-transform:uppercase;white-space:nowrap;
  transition:background-color var(--rapido) var(--curva),color var(--rapido) var(--curva)}
.navsec-tit .txt{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;opacity:.85}
.navsec-tit .chev{display:flex;opacity:.85;transition:transform var(--medio) var(--curva)}
.navsec.fechada>.navsec-tit .chev{transform:rotate(-90deg)}
.navsec-tit .cnt{display:none;background:var(--cnt);color:var(--cnt-ink);font-size:11.5px;font-weight:700;letter-spacing:0;padding:2px 7px;border-radius:999px}
.navsec.fechada>.navsec-tit .cnt{display:inline-block}
@media(hover:hover) and (pointer:fine){.navsec-tit:hover{background:var(--side-hover);color:var(--side-ink)}}
.navsec-tit:active{background:var(--side-on);color:var(--side-ink)}
.navsec-tit:focus-visible{outline:2px solid var(--side-ink);outline-offset:-2px}
.navsec-corpo{display:grid;grid-template-rows:1fr;transition:grid-template-rows var(--medio) var(--curva-entra)}
.navsec.fechada>.navsec-corpo{grid-template-rows:0fr;transition-timing-function:var(--curva-sai)}
.navsec-itens{display:grid;gap:2px;min-height:0;overflow:hidden;margin:0 -10px;padding:0 10px;visibility:visible;transition:visibility 0s}
.navsec.fechada .navsec-itens{visibility:hidden;transition:visibility 0s var(--medio)}
.navsec-itens a:focus-visible{outline-offset:-2px}
@media(pointer:coarse){.navsec-tit{min-height:44px}}
.kpi.evo{cursor:pointer}
.kpi .kic{position:absolute;top:11px;right:12px;width:18px;height:18px;border-radius:50%;background:var(--chip);color:var(--muted);display:grid;place-items:center}
/* secções que abrem e fecham */
.sect.fold{padding:0;gap:0}
.fold-head{display:flex;align-items:center;gap:10px;width:100%;max-width:100%;min-width:0;overflow:hidden;padding:12px 14px;border:0;background:transparent;cursor:pointer;text-align:left;font-size:15px;color:var(--ink);border-radius:14px}
@media(hover:hover) and (pointer:fine){.fold-head:hover{background:var(--tint)}}
.fold-head .ic{width:34px;height:34px;border-radius:10px;display:grid;place-items:center;background:var(--accent-soft);color:var(--accent-text);flex:0 0 34px}
.fold-head b{white-space:nowrap;overflow:hidden;text-overflow:ellipsis;min-width:0;flex:0 1 auto;font-weight:600}
.form>*{min-width:0}.sect{min-width:0}
.fold-head .fsum{margin-left:auto;color:var(--muted);font-size:13px;font-weight:500;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;text-align:right}
.fold-head .chev{flex:0 0 auto;color:var(--muted);transition:transform var(--medio) var(--curva)}
.fold.open>.fold-head .chev{transform:rotate(180deg)}
/* A dobra abre e fecha com o display, como sempre; o que é novo é o conteúdo
   entrar. Tem de ser @keyframes e não transition: um elemento que acaba de sair
   do display:none não tem valor antigo de onde partir.
   Animar a ALTURA (grid-template-rows 0fr→1fr) foi tentado e desfeito: medida
   no browser, a linha dimensionada por max-content não interpolava — a dobra
   ficava presa na altura do conteúdo e não chegava a fechar — e o
   overflow:hidden que a técnica obriga recortava os menus dos sel() lá dentro.
   Uma dobra que abre de golpe custa menos do que uma dobra que não fecha.
   A entrada é de quem ABRE: a classe .entra só o toggleFold a põe. Sem ela,
   re-renderizar a janela com a dobra já aberta (escolher uma categoria
   reconstrói tudo) fazia o conteúdo piscar a cada escolha. */
.fold-body{display:none;padding:2px 14px 14px;gap:13px}
.fold.open>.fold-body{display:grid}
.fold.entra.open>.fold-body{animation:foldEntra var(--medio) var(--curva-entra)}
@keyframes foldEntra{from{opacity:0;transform:translateY(-6px)}}
/* os por confirmar no cartão de um contrato (cloud/painel.js:pendBlock): as
   linhas do cartão dos Planeados (.plan-pend-linha), sem borda colorida */
.cw-pend{margin-top:12px}
.cw-pend-tit{margin:0;font-weight:600;color:var(--ink)}
.legend{display:grid;gap:7px;margin-top:12px;grid-template-columns:minmax(0,1fr)}
.legend>*{min-width:0}
.legend .li{display:flex;align-items:center;gap:8px;font-size:13px;min-width:0}
.legend .li.tap{cursor:pointer;border-radius:8px;margin:0 -4px;padding:2px 4px}
@media(hover:hover) and (pointer:fine){.legend .li.tap:hover{background:var(--chip)}}
.legend .dot{width:10px;height:10px;border-radius:3px;flex:0 0 10px}
.legend .nm{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;color:var(--muted)}
/* Em ecrã de dedo, nada abaixo do mínimo de toque. Só em pointer:coarse:
   no rato os tamanhos compactos continuam certos. */
@media(pointer:coarse){
  .btn{min-height:44px}
  .btn.sm{min-height:40px}
  .iconbtn{min-width:44px;min-height:44px;display:inline-flex;align-items:center;justify-content:center}
  /* o hambúrguer leva a MEDIDA do toque, mas não o display: quem decide se ele
     existe é a largura (abaixo de 900px), não o dedo. Levava, e isso
     ressuscitava-o em qualquer ecrã tátil — num telemóvel em «modo PC» ficava
     um botão à vista que não abria gaveta nenhuma (acima de 900px o aside é
     uma coluna, não uma gaveta) e que trancava o scroll ao ser tocado. */
  .burger{min-width:44px;min-height:44px}
  #nav a{min-height:44px}
  .legend .li.tap{min-height:40px;padding:8px 6px;margin:0 -6px}
  .tag button{min-width:28px;min-height:28px;display:inline-flex;align-items:center;justify-content:center}
  .qclear{min-width:36px;min-height:36px}
  .fold-head{min-height:44px}
  /* o «Anular» de um aviso é a única saída de uma ação já feita, e o aviso
     sai do ecrã ao fim de segundos: não é sítio para falhar a pontaria */
  .toast .toastbtn{min-height:44px}
}
/* um campo com erro aponta para si próprio, em vez de só um toast longe dele */
/* O erro de um campo: contorno de 2px no vermelho (o segundo pixel é a
   sombra, para o campo não saltar) e a frase por baixo a dizer o que fazer
   (componentes.js:falhaCampo escreve-a num .erro-campo). */
.err{border-color:var(--danger)!important;box-shadow:0 0 0 1px var(--danger)}
.erro-campo{color:var(--danger);font-size:13px;font-weight:600;margin:0}
.req{color:var(--danger);font-weight:700;margin-left:3px}
/* quem pediu menos movimento ao sistema recebe menos movimento */
@media(prefers-reduced-motion:reduce){*,*::before,*::after{animation:none!important;transition:none!important;scroll-behavior:auto!important}}
/* O FAB respeita o recorte lateral em landscape */
body .fab,body .fabmenu{right:calc(18px + var(--inset-right,0px))}
/* A barra de baixo: os quatro destinos quentes a um toque, no telemóvel.
   A gaveta fica para o resto — deixou de ser a única porta. */
/* A barra de baixo de 2026-10: Início, Casas, + (Criar), Dinheiro, Agenda.
   Ícones de 22 com o rótulo de 11.5px; o destino aceso só muda de cor (o
   cobalto), sem fundo; os outros ficam no --faint. */
.tabbar{display:none;position:fixed;left:0;right:0;bottom:0;z-index:40;background:var(--blur);-webkit-backdrop-filter:blur(12px) saturate(140%);backdrop-filter:blur(12px) saturate(140%);border-top:1px solid var(--line);
  grid-template-columns:repeat(4,1fr);gap:2px;padding:9px calc(8px + var(--inset-right)) calc(14px + var(--inset-bottom)) calc(8px + var(--inset-left))}
.tabbar a{display:flex;flex-direction:column;align-items:center;justify-content:center;gap:3px;padding:4px 2px;min-height:52px;
  font-size:11.5px;font-weight:600;color:var(--faint);border-radius:12px;position:relative;cursor:pointer;text-decoration:none}
.tabbar a.on{color:var(--accent)}
/* a barra lateral marca o ativo com um traço à esquerda (nav a.on::before);
   na barra de baixo esse traço aparecia como um risco sem sentido */
.tabbar a.on::before{display:none}
/* a barra de baixo é um <nav>: o fundo do ativo, do hover e do premido da
   barra lateral (nav a.on, nav a:hover, nav a:active) apanhava-a e, no
   escuro, o destino aceso ganhava uma pílula; o premido dela é o --press */
.tabbar a.on{background:none}
@media(hover:hover) and (pointer:fine){.tabbar a:hover{background:none;color:var(--accent)}}
.tabbar a:active{color:var(--accent)}
/* os crachás da barra de baixo e do sino: laranja (--out, o canvas) com a
   tinta das cores cheias (--accent-ink: branca no claro, escura no escuro —
   branco sobre o laranja claro do tema escuro não se lia em 10px); o de aviso
   (.u-bg-v-warn, fundo --warn) leva a mesma tinta */
.tabbar a .cnt{position:absolute;top:1px;left:calc(50% + 7px);background:var(--out);color:var(--accent-ink);font-size:10px;font-weight:700;min-width:15px;height:15px;border-radius:99px;display:grid;place-items:center;padding:0 3px}
#hdrBell .cnt{position:absolute;top:1px;right:1px;background:var(--out);color:var(--accent-ink);font-size:10px;font-weight:700;min-width:15px;height:15px;border-radius:99px;display:grid;place-items:center;padding:0 3px}
/* O + a meio da barra: no telemóvel é ele o botão de criar, e o FAB com o
   leque somem (na @media de baixo). A coluna dele é auto e os destinos
   repartem o resto; com menos de quatro destinos — quem colabora, um serviço
   desligado — a barra diz quantos são (d0…d3, navegacao.js:buildTabbar) e
   a grelha mantém o botão no CENTRO DO ECRÃ: com três, o terceiro destino
   toma a metade direita inteira e centra-se nela com a largura dos outros;
   com um, sobra uma coluna vazia à direita. */
.tabbar.mais{grid-template-columns:1fr 1fr auto 1fr 1fr}
.tabbar.mais.d3{grid-template-columns:1fr 1fr auto 2fr}
.tabbar.mais.d3 a:last-child{width:50%;justify-self:center}
.tabbar.mais.d2,.tabbar.mais.d1{grid-template-columns:1fr auto 1fr}
.tabbar.mais.d0{grid-template-columns:auto;justify-content:center}
/* Um botão, não um quinto destino: uma tecla em relevo, retangular de cantos
   arredondados, sólida na cor da marca, 50px contra os 48 dos destinos — e
   INTEIRA dentro da barra. A primeira versão era um círculo a subir 12px
   acima da borda, e no telemóvel saía cortado: o que ultrapassa a barra
   fica à mercê de quem recorta. O relevo é uma aresta de 3px por baixo
   (--accent-relevo, mais escura nos dois temas) mais a sombra difusa, e um
   fio de luz no topo; carregar afunda a tecla — desce 3px e a aresta some.
   Centrada na linha dos destinos, com margem de -1px em cima e em baixo: a
   caixa de margem fica nos 48 da linha, os 2px a mais pintam-se no padding
   da barra, e nem a barra nem os destinos crescem (sem a margem, a linha da
   grelha subia para 50 e esticava os destinos com ela). Sem :hover de
   propósito — no telemóvel não há. */
/* O «+» de 2026-10: um quadrado cobalto de 52px com raio 16, liso como no
   canvas, INTEIRO dentro da barra (a regra que ficou da tecla em relevo: o que
   ultrapassa a barra fica à mercê de quem recorta). Carregar afunda-o um
   pouco, pela escala. */
.tabmais{width:52px;height:52px;margin:0 6px;padding:0;border:0;border-radius:16px;align-self:center;justify-self:center;
  background:var(--accent);color:var(--accent-ink);display:flex;align-items:center;justify-content:center;
  box-shadow:0 4px 12px color-mix(in srgb,var(--accent) 28%,transparent);
  cursor:pointer;transition:transform var(--rapido) var(--curva),box-shadow var(--rapido) var(--curva)}
.tabmais:active{transform:scale(.94);box-shadow:0 1px 4px color-mix(in srgb,var(--accent) 20%,transparent)}
.tabmais:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
/* nos ecrãs mais estreitos os quatro rótulos precisam da largura: a tecla encolhe */
@media(max-width:340px){.tabmais{width:48px;height:48px;margin:0 2px}}
/* body à frente: estas regras vivem ANTES das de base do .fab/.totop na
   folha, e sem mais especificidade perdiam — o FAB voltava a aparecer */
@media(max-width:900px){
  .tabbar{display:grid}
  .wrap{padding-bottom:calc(96px + var(--inset-bottom))}
  /* o + da barra toma o lugar do FAB: o botão, o leque (aberto ou não) e o
     espaço que o render lhe deixava no fundo somem todos */
  body .fabmenu.on{display:none}
  /* o «topo» é um círculo ao centro, como o +: a 76px ficava a 6px dele */
  body .totop{bottom:calc(92px + var(--inset-bottom))}
  body.open .tabbar{display:none}
  /* o menu do telemóvel: o mapa completo numa gaveta de 328px, com o
     fecho; o cabeçalho perde os contornos dos botões e a
     ação do ecrã (o + da barra de baixo faz as vezes dela) */
  aside{width:min(328px,88vw);flex-basis:min(328px,88vw)}
  aside .brand .fecha-gaveta{display:inline-flex}
  /* o menu do telemóvel não tem o «Criar» (o M-Menu): lá o + vive na barra de baixo */
  aside .nav-criar{display:none}
  #hdrAcao,#hdrSec{display:none}
  header.top #hdrBell,header.top #hdrFilt{border-color:transparent;background:transparent;width:44px;min-width:44px;padding:0}
  /* aceso (o painel dos filtros aberto, ou o «Concluir» da edição dos
     cartões): o .btn.primary sem o fundo deixava o ícone na --accent-ink —
     branco no cabeçalho claro, escuro no escuro —, e o botão sumia justamente
     quando era a maneira de fechar o painel. Aceso é o par suave da escolha
     feita, o mesmo do .selopt.on, em claro e em escuro (vistas.js:pintarBotaoFiltros) */
  header.top #hdrFilt.primary{background:var(--accent-soft);color:var(--accent-text)}
  header.top .sync{background:transparent!important;width:44px;height:44px;padding:0;justify-content:center}
  header.top .sync span{display:none}
  /* com algo por enviar ou sem ligação, a frase desce para uma faixa fina por
     baixo do cabeçalho, a toda a largura (o contrato: «uma faixa quando há
     algo por enviar»); o ícone fica. O cabeçalho cresce o que ela ocupa, e
     ela pinta-se no fundo dele (o header é pegajoso: é ele a caixa dela). O
     «Guardado» fica só o ícone, e o «A ligar» da abertura também — a faixa a
     entrar e a sair em cada abertura fazia o cabeçalho saltar; a nova
     tentativa depois de uma falha (.liga.tenta) fica com a faixa que lá
     estava, agora laranja, e o cabeçalho não mexe de 30 em 30 segundos. */
  header.top:has(>.sync.pend),header.top:has(>.sync.fora),header.top:has(>.sync.tenta){padding-bottom:40px}
  header.top .sync.pend span,header.top .sync.fora span,header.top .sync.tenta span{display:flex;align-items:center;position:absolute;left:0;right:0;bottom:0;min-height:34px;padding:0 calc(16px + var(--inset-right)) 0 calc(16px + var(--inset-left));font-size:13px;font-weight:600;white-space:normal;line-height:1.25}
  header.top .sync.pend span{background:var(--accent-soft);color:var(--accent-text)}
  header.top .sync.fora span{background:var(--danger-soft);color:var(--danger)}
  header.top .sync.tenta span{background:var(--out-soft);color:var(--out)}
  /* no telemóvel o título é o da área (Casas, Dinheiro): os separadores logo
     por baixo já dizem onde se está (navegacao.js:tituloDoEcraHtml) */
  header.top #pageTitle .tit-sep{display:none}
  header.top #pageTitle .tit-area{display:inline}
  /* em edição dos cartões, o «Concluir» do cabeçalho fica só o visto
     (cloud/painel.js:patchHdr); a barra da edição tem o texto */
  header.top .hdr-concluir{display:none}
}
/* ======================= A CASCA DE 2026-10 =======================
   (navegacao.js, index.html) O que veste a barra lateral nova, o cabeçalho, as
   áreas e as janelas da navegação. */
/* «Criar», ao cimo da barra lateral */
.nav-criar{width:100%;justify-content:flex-start;margin:4px 0 10px}
/* a barra é uma coluna: os grupos rolam e o fundo (as Definições, a Ajuda e
   a conta, navegacao.js:gavetaHtml) encosta-se ao fundo e fica pegado lá,
   sempre à vista, com a divisória do canvas por cima — a 1440×900 a Ajuda e
   a conta só apareciam depois de rolar.
   O fundo vai rente ao fundo e de lado a lado: o espaço de baixo do #nav (e a
   área segura) passa para dentro dele, e as margens negativas cobrem as
   laterais. Com o espaço no #nav, o sticky parava acima dele, e os grupos
   viam-se a passar por baixo e pelos lados do fundo. */
#nav{display:flex;flex-direction:column;padding-bottom:0}
#nav>*{flex-shrink:0}
.nav-fundo{display:grid;gap:2px;margin:auto -14px 0;position:sticky;bottom:0;z-index:1;padding:8px 14px calc(16px + var(--inset-bottom));border-top:1px solid var(--side-line);background:var(--side)}
/* os títulos vazios das secções sem nome (as portas de cima e o fundo) não
   ocupam lugar: o HTML conta com eles como fronteira (gavetaHtml), o ecrã não */
#nav .navh:empty{padding:0}
/* o cartão da conta, no fundo */
.nav-conta{display:flex;align-items:center;gap:10px;width:100%;margin-top:8px;padding:10px 12px;border:0;border-radius:12px;background:var(--side-hover);color:var(--side-ink);text-align:left;cursor:pointer}
@media(hover:hover) and (pointer:fine){.nav-conta:hover{background:var(--side-on)}}
.nav-conta .avatar{background:#2a3a63;color:#fff;width:34px;height:34px;flex-basis:34px} /* o avatar do canvas na barra azul-noite */
.nav-conta b{display:block;font-size:14px;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.nav-conta small{display:block;color:var(--side-text);font-size:12.5px}
/* o fecho do menu só existe onde ele é uma gaveta */
aside .fecha-gaveta{display:none;color:var(--side-ink)}
@media(hover:hover) and (pointer:fine){aside .fecha-gaveta:hover{background:var(--side-hover);color:var(--side-ink)}}
/* o estado da sincronização, no cabeçalho (cloud/entrada.js:setSyncBadge):
   um selo de 30px com a nuvem e a frase; o «Guardado» recolhe ao ícone.
   «A ligar» é laranja (o --out: o --warn é âmbar acastanhado, e era a cor do
   «Sem ligação» de antes — as duas a meias confundiam-se), «Sem ligação» é
   vermelho (o --danger); os pares dão 4,5:1 ou mais em claro e em escuro */
#hdrSync:empty{display:none}
.sync{display:inline-flex;align-items:center;gap:6px;flex:0 0 auto;min-height:30px;padding:0 10px;border-radius:6px;font-size:13px;font-weight:600;white-space:nowrap}
.sync.liga{background:var(--out-soft);color:var(--out)}
.sync.ok{background:var(--in-soft);color:var(--in)}
.sync.pend{background:var(--accent-soft);color:var(--accent-text)}
.sync.fora{background:var(--danger-soft);color:var(--danger)}
.sync.recibo{padding:0 7px}
.sync.recibo span{display:none}
/* a ação principal do ecrã, no cabeçalho do computador, e a secundária à
   esquerda dela (navegacao.js:pintarAcaoDoCabecalho) */
#hdrAcao:empty{display:none}
#hdrSec:empty{display:none}
body.sel-on #hdrSec{display:none}
/* o título do cabeçalho numa área leva dois nomes (navegacao.js:tituloDoEcraHtml):
   no computador vê-se o do separador; no telemóvel, o da área (a @media de cima) */
#pageTitle .tit-area{display:none}
/* as áreas: os separadores no topo do ecrã (só no telemóvel) e o das
   Pessoas, sublinhado, em todos os ecrãs */
.abas{display:grid;gap:12px;margin:0 0 14px}
.abas-area>a .n{display:inline-flex;align-items:center;justify-content:center;min-width:20px;height:20px;padding:0 6px;border-radius:999px;background:var(--accent-soft);color:var(--accent-text);font-size:12px;font-weight:600}
.segm.abas-pessoas{display:flex;gap:18px;padding:0;border:0;border-bottom:1px solid var(--line);border-radius:0;background:transparent}
.segm.abas-pessoas>a{flex:0 1 auto;min-height:44px;padding:0 2px;border-radius:0;border-bottom:2.5px solid transparent;margin-bottom:-1px;font-size:15px;color:var(--muted)}
.segm.abas-pessoas>.on{background:transparent;box-shadow:none;color:var(--ink);font-weight:650;border-bottom-color:var(--accent)}
/* três no telemóvel (Inquilinos, Proprietários, Colaboradores — navegacao.js:PESSOAS):
   aos 375px, com os 18px e os 15px, o terceiro passava da margem. Abaixo dos
   420px o intervalo e a letra encolhem um pouco; e, num ecrã ainda mais
   estreito, cada um pode encolher (flex:0 1 auto: corta-se o fim, nunca rola de lado) */
@media(max-width:420px){.segm.abas-pessoas{gap:14px}.segm.abas-pessoas>a{font-size:14px}}
@media(min-width:901px){#abasArea,.abas>.abas-area{display:none}}
/* A casa das abas da área (index.html:#abasArea, navegacao.js:abasAssentar):
   por cima do #view e fora dele, para ficar parada enquanto o painel desliza.
   O espaçamento é o que o .wrap do telemóvel dava às abas quando viviam lá
   dentro: 16px aos lados, 4px em cima, e 14px até ao conteúdo (10 daqui e os
   4 do topo do #view). Quando as abas não cabem, a casa rola de lado, sem
   barra, e o polegar rola com elas (vive dentro da fila); o fim da rolagem
   não puxa o voltar do sistema. Cada aba tem a largura do seu texto (e do
   número) e a fila enche a linha, com a sobra repartida por igual (flex:1 0
   auto); nunca encolhe abaixo do texto — quando não cabem, rola. Colunas
   iguais (as de antes) tinham todas a largura de «Contratos», e as cinco das
   Casas já não cabiam aos 390px. A .abas-saida é a fila velha a sair numa travessia entre
   áreas (continuidade.js:abasNaFita), com o mesmo espaçamento. A moldura
   .abas que fica vazia no #view (navegacao.js:abasTirarDaVista) esconde-se
   no telemóvel; no computador continua a dar os 14px de sempre. */
#abasArea:empty{display:none}
@media(max-width:900px){.abas:empty{display:none}}
#abasArea,.abas-saida{padding:4px calc(16px + var(--inset-right)) 10px calc(16px + var(--inset-left))}
#abasArea{overflow-x:auto;overscroll-behavior-x:contain;scrollbar-width:none}
#abasArea::-webkit-scrollbar{display:none}
#abasArea>.segm.abas-area,.abas-saida>.segm.abas-area{display:flex;width:max-content;min-width:100%}
#abasArea>.segm.abas-area>a,.abas-saida>.segm.abas-area>a{flex:1 0 auto}
/* apertada só quando não cabe (navegacao.js:abasApertar): um ponto a menos na
   letra e 4px de enchimento — as cinco das Casas com um número cabem aos 375px */
.segm.abas-area.aperta>a{font-size:13px;padding-left:4px;padding-right:4px}
/* O realce da aba acesa é uma peça que corre por baixo das abas (o
   .segm-polegar do segmentado que desliza, imovel.js:imvSegmentado). As
   abas têm larguras diferentes, por isso o realce mede a aba: a posição
   (--pol-x) e a largura (--pol-w) são as da aba acesa, escritas no próprio
   realce (navegacao.js:abasPolegarEm), e a meio de um arrasto o dedo
   interpola-as entre as duas abas vizinhas. Desliza de uma aba para a outra no --medio e
   na --curva-fita, a de quem atravessa em bloco; ao largar um arrasto que
   vira, na duração da fita (.viaja: chega com o painel); ao voltar, na curva
   do regresso da página (.volta); com o dedo, sem transição (.arrasta). Sem
   movimento pedido, a regra geral do reduced-motion tira-lhe a transição. */
.segm.abas-area>.segm-polegar{left:0;width:var(--pol-w,0px);transform:translateX(var(--pol-x,0px))}
.abas-area>.segm-polegar.fora{visibility:hidden}
.abas-area>.segm-polegar{transition:transform var(--medio) var(--curva-fita),width var(--medio) var(--curva-fita)}
.abas-area.viaja>.segm-polegar{transition-duration:var(--lento)}
.abas-area.volta>.segm-polegar{transition-timing-function:var(--curva-entra)}
.abas-area.arrasta>.segm-polegar{transition:none}
/* deslizar entre separadores (navegacao.js:sepArrastar): no telemóvel, numa
   área com separadores, o arrasto de lado é da app e o vertical continua do
   browser, com o pinch-zoom. Enquanto o dedo leva a página, o pai corta o que
   lhe passa da margem — clip, e não hidden, para o cabeçalho pegajoso colar.
   O vizinho entra no palco (navegacao.js:sepPalco, sepVizinho): uma caixa
   fixa na camada de saída, recortada à largura do #view, com o vizinho
   pintado numa caixa com as classes do #view, posta à mão onde vai ficar.
   Sem movimento pedido, só o nome do vizinho espreita à beira do ecrã
   (navegacao.js:sepEspreita). */
@media(max-width:900px){#abasArea:not(:empty)~#view,#view:has(>.abas>.abas-area){touch-action:pan-y pinch-zoom}}
/* Uma lista curta ou vazia acabava a meio do ecrã, e o vazio por baixo era
   do main: um dedo pousado ali não virava o separador. Numa área com abas o
   #view cresce até ao fundo do main (que é flex em coluna), e o vazio passa
   a ser dele — o gesto e o touch-action valem no ecrã inteiro. */
@media(max-width:900px){#abasArea:not(:empty)~#view{flex:1 0 auto}}
main.sep-arrasto{overflow-x:clip}
.sep-palco{position:absolute;top:0;overflow:hidden;pointer-events:none}
.sep-vizinho{position:absolute;left:0;box-sizing:border-box;max-width:none;margin:0}
.sep-espreita{position:absolute;left:0;top:0;display:flex;align-items:center;gap:4px;max-width:45vw;padding:8px 12px;border-radius:999px;border:1px solid var(--line);background:var(--card);color:var(--muted);font-size:14px;font-weight:600;white-space:nowrap;opacity:0;transition:opacity var(--rapido),color var(--rapido),background-color var(--rapido),border-color var(--rapido)}
.sep-espreita span{overflow:hidden;text-overflow:ellipsis}
.sep-espreita svg{flex:0 0 auto}
.sep-espreita.on{opacity:1}
.sep-espreita.pronto{color:var(--accent-text);background:var(--accent-soft);border-color:var(--accent-soft)}
/* a folha «Criar» (navegacao.js:abrirAdicionar) */
.criar{display:flex;flex-direction:column;gap:10px}
.criar-tit{margin:6px 0 0}
/* os cinco tipos em três colunas (o canvas, M-Criar): a transferência, a
   última, toma duas; assim a folha cabe num telemóvel de 844px */
.criar-tipos{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:8px}
.criar-tipos>:last-child:nth-child(odd){grid-column:span 2}
.criar-tipo{display:flex;flex-direction:column;align-items:flex-start;gap:8px;min-height:84px;padding:12px;border-radius:14px;border:1px solid var(--line);background:var(--card);color:var(--ink);font-weight:600;font-size:14px;text-align:left;cursor:pointer}
.criar-tipo .ic{width:34px;height:34px;border-radius:10px;display:grid;place-items:center;background:var(--accent-soft);color:var(--accent-text)}
.criar-tipo .ic.in{background:var(--in-soft);color:var(--in)}
.criar-tipo .ic.out{background:var(--out-soft);color:var(--out)}
.criar-tipo .ic.loan{background:var(--loan-soft);color:var(--loan)}
.criar-tipo .ic.amber{background:var(--warn-soft);color:var(--warn)}
.criar-outros{display:grid;grid-template-columns:1fr 1fr;gap:8px}
.criar-outro{display:flex;align-items:center;gap:10px;min-height:52px;padding:6px 12px;border-radius:12px;border:1px solid var(--line);background:var(--card);color:var(--ink);font-size:14.5px;font-weight:500;text-align:left;cursor:pointer}
.criar-outro svg{color:var(--muted);flex:0 0 auto}
.criar-outro small{display:block;color:var(--accent-text);font-size:12px;font-weight:600}
@media(hover:hover) and (pointer:fine){.criar-tipo:hover,.criar-outro:hover{border-color:var(--line2);background:var(--tint)}}
/* o «Pede atenção» (notificacoes.js:notifModal) */
.atencao{display:flex;flex-direction:column;gap:10px}
/* uma fila só, que rola de lado: com as duas classes, para ganhar ao
   .chips-fila{flex-wrap:wrap}, que vem depois na folha */
.chips-fila.atencao-chips{margin-bottom:4px;flex-wrap:nowrap;overflow-x:auto;scrollbar-width:none;margin-left:-2px;padding:2px}
.atencao-cab{display:flex;align-items:baseline;gap:8px;padding:8px 2px 0}
.atencao-cab h3{margin:0;font-size:16px}
.atencao-lista{padding:0;overflow:hidden}
.atencao-linha{display:flex;flex-wrap:wrap;align-items:center;gap:8px 12px;width:100%;padding:14px;border:0;background:transparent;color:inherit;text-align:left}
.atencao-linha+.atencao-linha{border-top:1px solid var(--line)}
.atencao-linha.tap{cursor:pointer}
.atencao-txt{flex:1 1 180px;min-width:0}
.atencao-txt p{margin:0}
.atencao-valor{display:flex;flex-direction:column;align-items:flex-end;gap:4px;flex:0 0 auto}
.atencao-acoes{flex:1 0 100%}
.atencao-pedido{display:flex;flex-direction:column;gap:8px}
.atencao-pedido p{margin:0}
/* sem o FAB: no computador cria-se no «Criar» da barra lateral e na ação
   do cabeçalho, no telemóvel no + da barra de baixo */
body .fab,body .fabmenu,body .fabpad{display:none}
.donut{display:flex;gap:14px;align-items:center;flex-wrap:wrap;min-width:0}
.donut .pie{flex:0 0 132px;max-width:132px}
.donut .leg{flex:1 1 160px;min-width:0}
.legend .vl{font-weight:650;font-variant-numeric:tabular-nums}
.xlab{display:flex;gap:4px;margin-top:6px}
.xlab span{flex:1;text-align:center;font-size:11px;color:var(--muted);min-width:0;overflow:hidden}

.form{display:grid;gap:13px}
.row{display:grid;grid-template-columns:1fr 1fr;gap:11px}
.row3{display:grid;grid-template-columns:repeat(3,1fr);gap:11px}
@media(max-width:520px){.row,.row3{grid-template-columns:1fr}}
/* um intervalo De/Até lê-se lado a lado; empilhado parecia dois filtros */
.row.lado-a-lado{grid-template-columns:1fr 1fr}
/* um estado vazio não se cola aos indicadores que o antecedem */
.grid+.empty,.grid+.list{margin-top:14px}
/* O rótulo do campo é tinta a 14px e 600, por cima do campo (o canvas); o
   obrigatório leva o asterisco vermelho (.req) e o opcional di-lo no
   placeholder. */
label{font-size:14px;color:var(--ink);display:grid;gap:6px;font-weight:600}
.flabel{font-size:14px;color:var(--ink);font-weight:600;margin-bottom:7px}
/* O campo: 46px, raio 12, contorno --line2, a 15px e peso normal. */
input,textarea{width:100%;min-height:46px;padding:11px 14px;border:1px solid var(--line2);border-radius:12px;background:var(--field);font-weight:400;line-height:1.35}
input,textarea,.selbtn{font-size:15px;color:var(--ink)}
input::placeholder,textarea::placeholder{color:var(--faint);opacity:1}
input:disabled{opacity:.6}
.statin{width:120px;flex:0 0 auto;text-align:right;padding:8px 11px;border:1px solid var(--line2);border-radius:12px;background:var(--field);font-weight:600;font-size:14px;min-height:40px}
/* o foco: o contorno passa a cobalto e ganha um anel suave por fora */
input:focus,textarea:focus{outline:3px solid var(--accent-soft);outline-offset:0;border-color:var(--accent)}
/* a caixa cresce com o texto (o resto do suporte em componentes.js:ajustarCaixas);
   a partir de 60% do ecrã desliza, para um texto enorme não empurrar o «Guardar» para longe */
textarea{min-height:90px;max-height:60vh;max-height:60dvh;resize:vertical;field-sizing:content}
/* ---- os campos de data vazios no iPhone (componentes.js:marcarDatasVazias) ----
   Um <input type="date"> ignora o placeholder. O Chrome e o Android escrevem
   «dd/mm/aaaa» sozinhos; o Safari do iPhone deixa o campo em branco, e quem
   o vê pela primeira vez não sabe o que ele espera. Só nesse WebKit — o
   -webkit-touch-callout só existe no iOS —, e só com a marca data-vazio, que
   o marcarDatasVazias põe e tira: o texto vive num ::before que nunca empurra
   um valor, porque só existe enquanto o campo está vazio. Sem pointer-events,
   para o toque cair no campo e abrir o seletor, e não no texto. */
@supports (-webkit-touch-callout:none){
  input[type=date][data-vazio]::before{content:'dd/mm/aaaa';color:var(--muted);pointer-events:none}
}
/* as notas guardadas com o HTML do antigo editor rico (formato.js:rich) */
.rich b,.rich strong{font-weight:700}
.rich i,.rich em{font-style:italic}
.rich s,.rich strike,.rich del{text-decoration:line-through}
.rich u{text-decoration:underline}
.check{display:flex;align-items:center;gap:10px;font-weight:500;color:var(--ink);font-size:15px;cursor:pointer}
.check input{width:auto;min-height:0;margin:0;flex:0 0 auto;accent-color:var(--accent)}
input[type=checkbox],input[type=radio]{width:18px;height:18px;min-height:0;padding:0;accent-color:var(--accent)}

/* menu de escolha próprio, em vez do <select> do sistema */
.sel{position:relative;width:100%;max-width:100%;min-width:0}.form>label,.row>label,.row3>label{min-width:0}.selbtn{box-sizing:border-box;max-width:100%}
.selbtn{width:100%;display:flex;align-items:center;gap:8px;min-height:46px;padding:0 14px;border:1px solid var(--line2);
  border-radius:12px;background:var(--field);cursor:pointer;text-align:left;font-weight:400}
.selbtn span{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
@media(hover:hover) and (pointer:fine){.selbtn:hover{border-color:var(--faint)}}
.selbtn svg{color:var(--faint);flex:0 0 auto}
.selpop{display:none;position:absolute;left:0;right:0;top:calc(100% + 5px);z-index:15;background:var(--card);
  border:1px solid var(--line);border-radius:14px;box-shadow:var(--shadow);padding:6px;max-height:260px;overflow:auto}
.selpop.on{display:block}
.selopt{width:100%;display:flex;align-items:center;gap:9px;min-height:40px;padding:8px 12px;border:0;background:transparent;
  border-radius:10px;cursor:pointer;text-align:left;font-size:15px}
.selopt span{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
@media(hover:hover) and (pointer:fine){.selopt:hover{background:var(--chip)}}
.selopt.on{color:var(--accent-text);font-weight:600;background:var(--accent-soft)}
.sdiv{height:1px;background:var(--line);margin:5px 6px}
.selopt svg{color:var(--accent);flex:0 0 auto}

/* menu de ações (⋯) */
.menuwrap{position:relative}
.menupop{display:none;position:absolute;right:0;top:calc(100% + 6px);z-index:30;background:var(--card);
  border:1px solid var(--line);border-radius:14px;box-shadow:var(--shadow);padding:6px;min-width:200px}
.menupop.on{display:block}
.menupop button{width:100%;display:flex;align-items:center;gap:10px;min-height:42px;padding:8px 12px;border:0;background:transparent;
  border-radius:10px;cursor:pointer;text-align:left;font-size:15px;color:var(--ink)}
@media(hover:hover) and (pointer:fine){.menupop button:hover{background:var(--chip)}}
.menupop button.danger{color:var(--danger)}
.menupop.wide{min-width:250px;padding:12px}
.menupop.wide label{margin-bottom:9px}
.toolbar.stick{position:sticky;top:calc(57px + var(--inset-top));z-index:25;background:var(--bg);padding:9px 0;margin:-9px 0 4px;box-shadow:0 8px 10px -10px rgba(0,0,0,.25)}
@media(min-width:901px){.toolbar.stick{top:calc(62px + var(--inset-top))}}
.txq{flex:1 1 150px;min-width:130px;width:auto;padding:10px 12px}
.filtbtn{position:relative}
.filtbtn .dot{position:absolute;top:5px;right:5px;width:7px;height:7px;border-radius:50%;background:var(--accent)}
.fab{position:fixed;right:18px;bottom:calc(20px + var(--inset-bottom));z-index:58;width:56px;height:56px;border-radius:16px;
  background:var(--accent);color:var(--accent-ink);border:0;display:flex;align-items:center;justify-content:center;
  box-shadow:0 10px 24px rgba(16,24,40,.24);cursor:pointer}
.fab:active{transform:scale(.96)}
.fabmenu{position:fixed;right:18px;bottom:calc(86px + var(--inset-bottom));z-index:58;display:none;flex-direction:column;gap:9px;align-items:flex-end}
.fabmenu.on{display:flex}
.fabmenu .btn{box-shadow:0 6px 18px rgba(0,0,0,.22)}
/* O painel de filtros ancora aqui. Pegajoso, e não só relativo: estava preso
   ao topo do conteúdo e desaparecia ao primeiro scroll — abria-se o filtro,
   rolava-se para ver o efeito, e o painel ficava para trás. Assim acompanha,
   e o painel lá dentro continua a alinhar-se sozinho com o conteúdo. */
.fwrap{position:relative;position:sticky;top:calc(57px + var(--inset-top));z-index:46}
.fpanel{display:none;position:absolute;top:calc(100% + 6px);left:0;right:0;z-index:45;margin:0}
.fpanel.on{display:block}
.fpanel>.card{box-shadow:0 16px 38px rgba(0,0,0,.30);max-height:min(72vh,560px);max-height:min(72dvh,560px);overflow:auto;overscroll-behavior:contain}
/* «Limpar» e «Fechar» presos ao fundo (vistas.js:fpanelPe, no painel do
   vistas.js:anaPanel, o das análises), na forma do .sheet .foot: o resto
   rola por trás, o pé fica, com a divisória e o fundo do cartão. A caixa
   continua a ser quem rola (o cloud/filtros.js segue as listas abertas pelo
   scroll dela), e o pé é o último filho, pegajoso em baixo: num painel curto
   fica logo a seguir aos filtros. Sem padding em baixo na caixa, para o pé
   assentar no fundo; as margens negativas levam-no de lado a lado. O
   scroll-padding é a altura do pé: o Tab não deixa um campo escondido por
   trás dele. Os Movimentos têm o painel deles (.mov-fwrap), com o Limpar e o
   Fechar no topo. */
.fpanel>.card.fp-caixa{padding:12px 12px 0;scroll-padding-bottom:80px}
.fp-caixa>.fp-pe{position:sticky;bottom:0;z-index:1;display:flex;align-items:center;gap:10px;margin:12px -12px 0;padding:10px 12px 12px;background:var(--card);border-top:1px solid var(--line)}
/* no dedo, os dois a meias e com os 48px do rodapé das janelas */
@media(max-width:900px){.fp-caixa>.fp-pe .btn{flex:1;min-height:48px}}
.fabpad{height:84px}
.totop{position:fixed;left:50%;transform:translateX(-50%) scale(.9);bottom:calc(20px + var(--inset-bottom));z-index:57;width:44px;height:44px;
  border-radius:50%;border:1px solid var(--line);background:var(--card);color:var(--ink);display:flex;align-items:center;justify-content:center;
  box-shadow:0 8px 22px rgba(0,0,0,.24);cursor:pointer;opacity:0;visibility:hidden}
.totop.on{opacity:1;visibility:visible;transform:translateX(-50%)}
.qwrap{position:relative;width:100%}
.qwrap .txq{width:100%;padding-right:36px}
.qclear{position:absolute;right:8px;top:50%;transform:translateY(-50%);width:28px;height:28px;border:0;border-radius:50%;
  background:var(--chip);color:var(--muted);display:flex;align-items:center;justify-content:center;cursor:pointer;font-size:15px;line-height:1}

/* etiquetas removíveis */
/* As etiquetas de um registo são pílulas neutras com o × para as remover (o
   canvas: «Dedutível ×» no formulário do movimento); acrescentar é uma pílula
   tracejada em cobalto. */
.tagbox{display:flex;flex-wrap:wrap;gap:8px;align-items:center;border:1px solid var(--line2);border-radius:12px;padding:8px;background:var(--field);min-height:46px}
.tag{display:inline-flex;align-items:center;gap:4px;min-height:32px;padding:0 6px 0 12px;border-radius:999px;border:1px solid var(--line2);background:var(--card);color:var(--ink);font-size:14px;font-weight:500}
.tag.grey{background:var(--chip);border-color:var(--line)}
.tag button{border:0;background:transparent;padding:3px;border-radius:50%;cursor:pointer;color:var(--muted);display:grid;place-items:center}
@media(hover:hover) and (pointer:fine){.tag button:hover{color:var(--ink);background:var(--chip)}}
.tagadd{display:inline-flex;align-items:center;gap:6px;min-height:32px;border:1px dashed var(--line2);background:transparent;color:var(--accent-text);padding:0 12px;border-radius:999px;cursor:pointer;font-size:14px;font-weight:600}
@media(hover:hover) and (pointer:fine){.tagadd:hover{border-color:var(--accent);background:var(--accent-soft)}}

.addbox{display:flex;align-items:center;gap:12px;width:100%;text-align:left;padding:14px 16px;border:1px dashed var(--line2);
  border-radius:14px;background:transparent;cursor:pointer;color:var(--ink)}
@media(hover:hover) and (pointer:fine){.addbox:hover{border-color:var(--accent);background:var(--tint)}}
.addbox .ic{width:36px;height:36px;border-radius:10px;display:grid;place-items:center;background:var(--accent-soft);color:var(--accent-text);flex:0 0 36px}
.addbox b{display:block;font-size:15px;font-weight:600}
.addbox small{display:block;color:var(--muted);font-size:13px;margin-top:2px}
.addbox .plus{margin-left:auto;color:var(--muted);flex:0 0 auto}
/* a secção de um formulário longo é um cartão (o .grp do canvas): gap 16 */
.sect{border:1px solid var(--line);border-radius:16px;padding:16px;display:grid;gap:16px;background:var(--card)}
.sect-head{display:flex;align-items:center;gap:10px;font-size:16px;font-weight:600}
.sect-head .ic{width:34px;height:34px;border-radius:10px;display:grid;place-items:center;background:var(--accent-soft);color:var(--accent-text);flex:0 0 34px}
.seg{display:grid;gap:8px}.seg.c3{grid-template-columns:repeat(3,1fr)}.seg.c2{grid-template-columns:repeat(2,1fr)}.seg.c4{grid-template-columns:repeat(4,1fr)}
@media(max-width:520px){.seg.c4{grid-template-columns:repeat(2,1fr)}}
/* As opções em cartão (.seg com .opt): um tipo com ícone e frase. A
   escolhida tem o contorno cobalto e o fundo suave. Para duas a cinco opções
   curtas sem ícone, o componente é o segmentado (.segm, mais abaixo). */
.opt{border:1px solid var(--line2);background:var(--card);border-radius:12px;padding:12px 9px;cursor:pointer;display:grid;gap:6px;justify-items:center;text-align:center;transition:border-color var(--rapido) var(--curva),background-color var(--rapido) var(--curva),transform var(--rapido) var(--curva)}
.opt .ic{width:36px;height:36px;border-radius:10px;display:grid;place-items:center;background:var(--chip);color:var(--muted)}
.opt b{font-size:14px;font-weight:600}
.opt small{font-size:12px;color:var(--muted);line-height:1.3}
@media(hover:hover) and (pointer:fine){.opt:hover{border-color:var(--faint)}}
.opt.on{border-color:var(--accent);background:var(--accent-soft);color:var(--accent-text)}
.opt.on .ic{background:var(--card);color:var(--accent-text)}
.roomrow{display:flex;gap:8px;align-items:center}
.roomrow input{flex:1}
.invrow{display:grid;grid-template-columns:auto 1fr 62px 104px auto;gap:7px;align-items:center}
.invrow input{padding:9px 10px}
@media(max-width:520px){.invrow{grid-template-columns:auto 1fr auto;grid-template-areas:"c n x" "c q s"}
  .invrow .i-n{grid-area:n}.invrow .i-q{grid-area:q}.invrow .i-s{grid-area:s}}

/* height em dvh: com as barras do browser à mostra, o inset:0 dava a altura
   do ecrã SEM elas, e o modal ficava centrado num espaço maior do que o
   visível — o topo saía por cima e não havia como lá chegar. */
/* A ESCADA: o modal está acima de TUDO o que é navegação — do menu lateral
   (aside, 62) e do véu da gaveta (scrim, 61). Esteve abaixo, em 60, e em ecrã
   largo, onde o menu é permanente, isso cortava os modais ao meio: o título
   não se lia. Pior, o véu do modal (inset:0) ficava por baixo do menu, que
   assim não escurecia e continuava clicável — dava para navegar para outro
   ecrã com um formulário aberto.
   Um modal é um MODO: enquanto está aberto, o resto da app está suspenso, e
   tem de o parecer. Acima ficam só o toast (90) e o balão (95), que são avisos
   e leituras — nunca escondem nada com que se possa interagir. */
.modal{position:fixed;inset:0;height:100dvh;z-index:70;display:none}
.modal.open{display:block}
.modal.under .sheet{pointer-events:none}
.modal.under .bg{background:rgba(9,14,28,.3)} /* metade do --veu: a janela de baixo já tem o seu */
.modal .bg{position:absolute;inset:0;touch-action:none;background:var(--veu)}
/* A janela: raio 20, a cabeça com o título na Bricolage, o corpo que rola e o
   rodapé com os botões a toda a largura (48px, os do ecrã inteiro). */
.sheet{position:absolute;left:50%;top:50%;transform:translate(-50%,-50%);width:min(580px,calc(100vw - 28px));max-height:min(88vh,880px);max-height:min(88dvh,880px);background:var(--card);border-radius:20px;display:flex;flex-direction:column;overflow:hidden;box-shadow:var(--shadow)}
.sheet .head{padding:16px 20px;display:flex;align-items:center;gap:10px;border-bottom:1px solid var(--line)}
.sheet .head h2{margin:0;font-size:20px;line-height:1.2}
.sheet .body{overscroll-behavior:contain;padding:18px 20px;overflow:auto;scroll-padding-bottom:180px}
.sheet.kb .body{padding-bottom:300px}
.sheet .foot{padding:14px 20px calc(14px + var(--inset-bottom));border-top:1px solid var(--line);display:flex;gap:10px}
.sheet .foot .btn{flex:1;justify-content:center;min-height:48px}
.iconbtn{border:0;background:transparent;padding:7px;border-radius:10px;cursor:pointer;color:var(--muted);display:inline-flex;align-items:center;justify-content:center}
@media(hover:hover) and (pointer:fine){.iconbtn:hover{background:var(--chip);color:var(--ink)}}
/* A porta das opções de um registo, e é a mesma em toda a app: o kebab das
   listas (vistas.js), o dos movimentos (cloud/selecao.js) e o do menu de ações
   (componentes.js). Eram três desenhos, três tamanhos e três nomes — o mais
   usado tinha 37px de largura, abaixo do mínimo de alvo, e nenhum rótulo. Quem
   aprende a reconhecer a porta numa lista tem de a reconhecer na seguinte,
   senão o toque longo continua a parecer a única maneira de lá chegar.
   O alinhamento vem para aqui porque era um style= repetido em cada linha.
   A caixa é dada, não calculada: com padding, o alvo saía do tamanho do ícone
   mais a entrelinha do texto à volta, e dava 36x40 — abaixo do mínimo — sem
   ninguém ter pedido nada disso. */
.opcoes{display:inline-flex;align-items:center;justify-content:center;
  width:44px;height:44px;padding:0;color:var(--muted);flex:0 0 auto;align-self:flex-start}
/* A folha de baixo, no telemovel. O max-height tem de vir em dvh como o de
   cima: esta regra vem depois e, so com vh, desfazia-o. E vh e a altura com
   as barras do browser recolhidas — com a barra de endereco e a de comandos
   a mostra, a folha crescia para alem do que se ve e o topo ficava cortado,
   fora de alcance, porque esta encostada em baixo. */
@media(max-width:520px){.sheet{top:auto;bottom:0;left:0;transform:none;width:100%;max-height:93vh;max-height:93dvh;border-radius:20px 20px 0 0}
  /* a pega da folha de baixo: diz que é uma folha que sobe e desce */
  .sheet::before{content:"";display:block;flex:0 0 auto;width:36px;height:4px;border-radius:2px;background:var(--line2);margin:8px auto 0}
  .sheet .head{padding-top:10px}}
.toast{position:fixed;left:50%;bottom:calc(22px + var(--inset-bottom) + var(--acima,0px));transform:translateX(-50%) translateY(80px);background:var(--toast);color:var(--toast-ink);padding:10px 16px;border-radius:14px;z-index:90;font-size:14.5px;font-weight:500;box-shadow:0 10px 30px rgba(16,24,40,.22);width:max-content;opacity:0;transition:opacity var(--medio) var(--curva-sai),transform var(--medio) var(--curva-sai);pointer-events:none;max-width:90vw;text-align:center;
  display:flex;align-items:center;justify-content:center;gap:12px}
.toast.on{opacity:1;transform:translateX(-50%);pointer-events:auto;
  transition:opacity var(--medio) var(--curva),transform var(--medio) var(--curva)}
/* O aviso com botão (o «Anular») puxa-se para baixo com o dedo
   (componentes.js:avisoPousar). O touch-action entrega o gesto vertical à
   app em vez de rolar a página por trás, e o texto não se seleciona ao
   segurar. Durante o arrasto o transform é o do dedo, sem transição; só a
   opacidade anda: desce quando largar já fecha (.pronto) — é o que diz «vai
   sair», e sem movimento é o único sinal que fica. */
.toast.arrasta{touch-action:none;-webkit-user-select:none;user-select:none}
.toast.arrastar{transition:opacity var(--rapido) var(--curva)}
.toast.arrastar.pronto{opacity:.72}
/* O que desfaz o que acabou de acontecer não pode parecer texto: estava
   sublinhado, com cor de link, deitado sobre a barra escura do aviso. É a
   única saída de uma ação já feita, e uma saída quer-se com caixa e com um
   alvo que se acerta sem pontaria. */
.toast .toastbtn{margin:0 -6px 0 0;background:var(--toast-btn);border:0;color:var(--toast-ink);font:inherit;font-weight:600;font-size:14px;
  cursor:pointer;padding:0 14px;border-radius:10px;min-height:36px;flex:0 0 auto}
/* só com rato: num ecrã tátil o :hover ficava agarrado ao botão depois do toque */
@media(hover:hover) and (pointer:fine){.toast .toastbtn:hover{filter:brightness(1.12)}}

/* ---- componentes da linguagem de 2026-10 que a casa ainda não tinha ---- */
/* O chip: filtros e ações rápidas. Pílula de 36px; ligado leva o fundo suave,
   o contorno e o texto cobalto, e um × para o tirar. Os filtros aplicam-se ao
   mexer — não há «Aplicar» (vistas.js:lfMudar). O «Limpar» é um chip sem
   contorno, em cobalto. */
.chip{display:inline-flex;align-items:center;gap:6px;min-height:36px;padding:0 12px;border-radius:999px;border:1px solid var(--line2);background:var(--card);color:var(--ink);font-size:14px;font-weight:500;white-space:nowrap;cursor:pointer;text-decoration:none}
@media(hover:hover) and (pointer:fine){.chip:hover{background:var(--tint)}}
.chip.on{background:var(--accent-soft);border-color:var(--accent);color:var(--accent-text)}
.chip.limpar{border-color:transparent;background:transparent;color:var(--accent-text);font-weight:600}
.chip .n{color:var(--muted);font-variant-numeric:tabular-nums}
.chip.on .n{color:inherit}
.chip svg{flex:0 0 auto}
.chips-fila{display:flex;gap:8px;flex-wrap:wrap;align-items:center}
/* O segmentado: duas a cinco escolhas curtas, uma ligada (tipo de movimento,
   tema, pago por, imóvel inteiro ou por quartos, e os separadores das áreas no
   telemóvel). Um trilho cinzento e a escolhida em relevo branco. */
.segm{display:flex;gap:2px;padding:4px;border-radius:12px;background:var(--chip);border:1px solid var(--line);min-width:0}
.segm>button,.segm>a{flex:1 1 0;min-width:0;display:inline-flex;align-items:center;justify-content:center;gap:6px;min-height:38px;padding:0 8px;border:0;border-radius:9px;background:transparent;color:var(--muted);font-size:14px;font-weight:500;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;cursor:pointer;text-decoration:none}
.segm>.on,.segm>[aria-checked="true"],.segm>[aria-current="page"],.segm>[aria-selected="true"]{background:var(--card);color:var(--ink);font-weight:600;box-shadow:0 1px 2px rgba(16,24,40,.14)}
.segm .n{color:var(--muted);font-weight:500;font-variant-numeric:tabular-nums}
/* O segmentado que desliza (imovel.js:imvSegmentado, imovel.js:imvSegDeslizar):
   o realce da escolha é uma peça à parte, por baixo dos botões, com a largura
   de um deles (duas escolhas: o que sobra do enchimento e do espaço, a meias)
   e posta na escolha pela classe; desliza de uma para a outra por transform.
   O botão aceso fica só com a cor e o peso do texto. */
.segm.desliza{position:relative;isolation:isolate}
.segm-polegar{position:absolute;z-index:-1;top:4px;bottom:4px;left:4px;width:calc((100% - 10px) / 2);border-radius:9px;background:var(--card);box-shadow:0 1px 2px rgba(16,24,40,.14);pointer-events:none}
.segm-polegar.i1{transform:translateX(calc(100% + 2px))}
.segm.desliza>.on,.segm.desliza>[aria-checked="true"]{background:transparent;box-shadow:none}
.segm.desliza>button{transition:color var(--medio) var(--curva-fita)}
/* O interruptor: um botão role="switch" com aria-checked. 46×28; o botão
   branco corre para a direita quando liga. */
.interruptor{position:relative;flex:0 0 46px;width:46px;height:28px;padding:0;border:0;border-radius:999px;background:var(--line2);cursor:pointer;transition:background-color var(--rapido) var(--curva)}
.interruptor::after{content:"";position:absolute;top:3px;left:3px;width:22px;height:22px;border-radius:50%;background:var(--card);box-shadow:0 1px 2px rgba(16,24,40,.2);transition:transform var(--rapido) var(--curva)}
.interruptor[aria-checked="true"]{background:var(--accent)}
.interruptor[aria-checked="true"]::after{transform:translateX(18px)}
.interruptor:disabled{opacity:.45;cursor:not-allowed}
/* A roda da espera (À espera do servidor): 18px, o topo em cobalto. */
@keyframes roda{to{transform:rotate(1turn)}}
.roda{display:inline-block;flex:0 0 18px;width:18px;height:18px;border-radius:50%;border:2.5px solid var(--line2);border-top-color:var(--accent);animation:roda var(--volta) linear infinite}
.espera{display:flex;align-items:center;gap:14px;padding:14px 16px;border-radius:14px;background:var(--chip);font-size:14px;color:var(--muted)}
.espera b{color:var(--ink);font-weight:600}
/* o rótulo de secção, para quem não é um .section-title com margens */
.lbl{font-size:12px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--muted)}
/* a linha de uma lista que abre uma ficha: ícone em quadrado, texto, valor e
   a seta (o .ar do canvas) */
.linha{display:flex;align-items:center;gap:12px;min-height:60px;padding:10px 14px;color:inherit;text-decoration:none;cursor:pointer}
.linha+.linha{border-top:1px solid var(--line)}
.linha .ic{width:36px;height:36px;border-radius:10px;display:grid;place-items:center;flex:0 0 36px;background:var(--accent-soft);color:var(--accent-text)}
.linha .ic.in{background:var(--in-soft);color:var(--in)}
.linha .ic.out{background:var(--out-soft);color:var(--out)}
.linha .ic.loan{background:var(--loan-soft);color:var(--loan)}
.linha .ic.amber{background:var(--warn-soft);color:var(--warn)}
.linha .ic.red{background:var(--danger-soft);color:var(--danger)}
.linha .txt{flex:1;min-width:0}
.linha .seta{color:var(--faint);flex:0 0 auto}
/* a marca: a casa do ícone da app (o telhado com beirais e a porta pequena,
   icones.js:ic 'home'), em branco num quadrado cobalto arredondado. Branco
   escrito à mão de propósito: é a marca, não muda com o tema. */
.marca{width:30px;height:30px;border-radius:8px;flex:0 0 auto;display:grid;place-items:center;color:#fff;background:var(--marca)}
.marca svg{display:block}

/* ======================= MOVIMENTO =======================
   Fundações. Tudo o que se mexe cita os tokens do :root (--rapido, --medio,
   --lento, --curva, --curva-sai). O bloco fica no fim da folha de propósito:
   assim os :active e os :focus-visible ganham os empates com os :hover
   declarados acima, sem precisarem de especificidade a mais.

   --- O que se toca reage ao dedo ---
   A app desliga o realce nativo do toque em tudo (o -webkit-tap-highlight-color
   transparente, lá em cima) e até aqui só o .card.tap e o .fab o devolviam. No
   telemóvel não há :hover: sem isto, tocar em «Guardar», numa opção de menu ou
   num separador da barra de baixo não dá sinal nenhum entre o dedo e o
   resultado — lê-se como app parada, e é o que provoca o segundo toque.
   Sempre :active e nunca :hover, que no iOS fica preso depois do toque. */
.btn,.iconbtn,.selbtn,.selopt,.menupop button,.tabbar a,.addbox,.fold-head,
.tagadd,.tag button,.railbtn,nav a,.legend .li.tap,.card.kpi.why,.card.kpi.evo,
.qclear,.burger,.thumb,.chip,.segm>button,.segm>a,.linha{
  transition:background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva),
    color var(--rapido) var(--curva),transform var(--rapido) var(--curva)}
.btn:active,.iconbtn:active,.selbtn:active,.selopt:active,.menupop button:active,
.tabbar a:active,.tagadd:active,.tag button:active,.railbtn:active,nav a:active,
.burger:active,.opt:active,.chip:active,.segm>button:active,.segm>a:active{transform:scale(.97)}
/* as superfícies grandes afundam menos — a .99 do .card.tap é a régua */
.addbox:active,.fold-head:active,.legend .li.tap:active,.calday.tap:active,
.card.kpi.why:active,.card.kpi.evo:active,.linha:active{transform:scale(.98)}
/* O botão do topo aparece e some a meio de um scroll: entra e sai a
   desvanecer com um resto de escala, como o véu da gaveta — o display já
   não entra nisto, e a visibility só se esconde no fim. Transição, e não
   keyframes: o vaivém à volta dos 420px retarga a meio em vez de piscar. */
.totop{transition:opacity var(--medio) var(--curva-sai),transform var(--medio) var(--curva-sai),
  background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva),color var(--rapido) var(--curva),
  visibility 0s var(--medio)}
.totop.on{transition:opacity var(--medio) var(--curva),transform var(--medio) var(--curva),
  background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva),color var(--rapido) var(--curva),
  visibility 0s}
/* estes dois já usam o transform para se posicionarem: o scale entra a seguir
   ao que lá está, senão saltavam do sítio ao serem premidos */
.totop:active{transform:translateX(-50%) scale(.94)}
.qclear:active{transform:translateY(-50%) scale(.9)}
/* O fundo premido é o --press, e nunca o --chip: medido, cinco pares
   :hover/:active pintavam-se da mesma cor (.iconbtn, .selopt, .menupop
   button, .legend .li.tap e .btn.primary). Com rato, o ponteiro fica em cima
   depois do clique, o :hover mantém a cor, e o toque seguinte não muda nada —
   a app parecia deixar de responder ao segundo toque. Com uma cor própria,
   premido nunca pode ser igual a passar por cima.
   Só onde há fundo neutro para escurecer: quem já está ativo (.on) fica com o
   seu, e a gaveta tem paleta própria. */
.btn:active,.iconbtn:active,.selbtn:active,.selopt:active,.menupop button:active,
.addbox:active,.fold-head:active,.tagadd:active,.legend .li.tap:active,
.burger:active,.totop:active,.qclear:active,.linha:active,
.tabbar a:not(.on):active,.calday.tap:not(.on):active,.opt:not(.on):active,.chip:not(.on):active,.segm>button:not(.on):active{background:var(--press)}
/* o :hover já usava o --accent-press: sem uma cor mais funda, premir um
   botão primário com o rato em cima não mudava nada */
.btn.primary:active{background:var(--accent-fundo);border-color:var(--accent-fundo)}
.btn.danger:active{background:var(--danger);filter:brightness(.82)}
nav a:active,.railbtn:active{background:var(--side-on);color:#fff}
/* o FAB tinha o scale(.96) declarado e nenhuma transição para o executar:
   descia e subia em zero frames, na peça mais tocada da app */
.fab{transition:transform var(--rapido) var(--curva)}

/* A espera de um toque longo, que se vê encher. Sem isto ficava meio segundo
   uma laje cinzenta parada — o estado premido foi feito para um toque, que
   dura um instante — e a cor da seleção chegava como um salto. */
@keyframes lpEspera{from{background:var(--card)}to{background:var(--press)}}
.lp-espera{animation:lpEspera var(--espera) linear both}

/* Rede do premido, a par da do foco: o tornarFocavel dá role=button a tudo o
   que tem onclick, e medi cinco sítios só na visão geral que reagiam ao toque
   com nada. Fica por baixo das regras de cima na especificidade, por isso
   quem já tem o seu (o .card.tap, por exemplo) mantém-no. */
[role="button"]:active,.tap:active{transform:scale(.98)}
/* Uma forma de gráfico não é um botão que se afunda. O tornarFocavel dá-lhes
   role=button para o teclado lá chegar, e a regra de cima apanhava-as: num
   SVG, um transform não é uma reação — é o desenho a mudar de sítio. E a
   origem não é o centro da forma: a barra encolhe a partir do eixo e a ponta
   livre anda; o ponto de uma linha tem a origem em 0,0 do desenho inteiro e
   afasta-se na proporção da distância a que está dela. Medido: as barras
   saltavam ao serem tocadas, e a dica que aparece a seguir ficava ancorada à
   forma já deslocada, a assentar só quando o dedo saía. */
svg [role="button"]:active,svg .tap:active{transform:none}
[role="button"]:not(.on):active,.tap:not(.card):not(.on):active{background:var(--press)}

/* --- O foco desenha-se ---
   O tornarFocavel() dá tabindex e role=button a todos os cartões com onclick, e
   até aqui só os campos e os dias do calendário tinham anel. :focus-visible e
   nunca :focus: quem chega de rato não pode deixar anéis por onde passa. */
.btn:focus-visible,.iconbtn:focus-visible,.selbtn:focus-visible,.selopt:focus-visible,
.menupop button:focus-visible,.tabbar a:focus-visible,nav a:focus-visible,
.railbtn:focus-visible,.opt:focus-visible,.fold-head:focus-visible,
.addbox:focus-visible,.tagadd:focus-visible,.tag button:focus-visible,
.card.tap:focus-visible,.card.kpi.why:focus-visible,.card.kpi.evo:focus-visible,
.legend .li.tap:focus-visible,.thumb:focus-visible,.fab:focus-visible,
.chip:focus-visible,.segm>button:focus-visible,.segm>a:focus-visible,.interruptor:focus-visible,.linha:focus-visible,
.burger:focus-visible,.totop:focus-visible,.qclear:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
/* Rede de segurança, e não repetição: o tornarFocavel (vistas.js:tornarFocavel)
   põe tabindex e role=button em TUDO o que tem onclick — cartões, linhas de
   lista, e até as formas dos gráficos. Medido na visão geral: dezanove dos
   trinta e nove sítios que o Tab alcança não tinham anel nenhum, por não
   caberem em nenhuma das classes acima. */
[role="button"]:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
/* A gaveta tem fundo próprio e escuro: medido, o --accent (#244c3b) sobre o
   --side (#1a3a2c) dá 1.29:1 — o anel existia e não se via. Aqui o contraste
   vem da paleta da própria gaveta. */
nav a:focus-visible,.railbtn:focus-visible{outline-color:var(--side-ink)}

/* --- Janelas, folhas e menus entram ---
   O modal é criado e recebe .open no mesmo instante (componentes.js:modalLayer
   escreve className='modal open' e só depois é que o openModal faz o
   appendChild): uma transition não tem valor antigo de onde partir num nó
   acabado de inserir, e por isso a entrada escreve-se em @keyframes. Só a
   entrada — animar a saída obriga a adiar o M.el.remove() do closeModal e a
   mexer na pilha de janelas, e isso é outra conversa. */
@keyframes veuEntra{from{opacity:0}}
@keyframes folhaEntra{from{opacity:0;transform:translate(-50%,-50%) translateY(14px) scale(.98)}}
@keyframes folhaSobe{from{transform:translateY(100%)}}
@keyframes popEntra{from{opacity:0;transform:scale(.96)}}
.modal.open .bg{animation:veuEntra var(--lento) var(--curva-entra)}
.modal.open .sheet{animation:folhaEntra var(--lento) var(--curva-entra)}
/* abaixo dos 520px a janela é uma folha encostada em baixo: o gesto que o
   sistema ensina é subir, e até aqui ela materializava-se feita */
@media(max-width:520px){.modal.open .sheet{animation:folhaSobe var(--lento) var(--curva-entra)}}
/* a origem é o lado por onde o menu nasce: o do sel() cai do botão, o das
   ações abre do canto direito e o do FAB sobe do canto de baixo */
.selpop.on{transform-origin:top center;animation:popEntra var(--rapido) var(--curva)}
.menupop.on{transform-origin:top right;animation:popEntra var(--rapido) var(--curva)}
.fabmenu.on{transform-origin:bottom right;animation:popEntra var(--rapido) var(--curva)}
/* o painel de filtros é da família dos menus e entra como eles; a marca
   .entra é posta por quem o abre (vistas.js:fpanelEntra) e não sobrevive
   ao render seguinte — o painel já aberto não pisca a cada filtro mexido,
   que é o mesmo desenho da dobra (.fold.entra).
   Mas NÃO leva o tempo nem a curva dos outros menus, e a diferença é o
   tamanho: o sel() e o kebab são caixas de umas centenas de pixeis, este
   painel ocupa a largura do conteúdo — 1132px medidos em ecrã de 1440. Os
   4% do popEntra são ali 10px e aqui 45px, e a régua das curvas lá em cima
   é a distância percorrida, não a família do componente: com a --curva em
   --rapido, 83% do caminho fazia-se em 36ms e o painel aparecia feito.
   Daí o --medio com a curva de quem atravessa distância. */
.fpanel.on.entra{transform-origin:top center;animation:popEntra var(--medio) var(--curva-entra)}
/* --- E saem ---
   Mais curta do que a entrada (--medio contra --lento): o que se fecha já
   foi decidido e não pode prender a mão. O closeModal TROCA .open por .sai:
   as consultas a .modal.open (o aviso, o guia, a selecao-listas) deixam de
   ver a janela que sai sem mudarem, e o display vem por isso repetido aqui. */
@keyframes veuSai{to{opacity:0}}
@keyframes folhaSai{to{opacity:0;transform:translate(-50%,-50%) translateY(10px) scale(.98)}}
@keyframes folhaDesce{to{transform:translateY(100%)}}
.modal.sai{display:block;pointer-events:none}
.modal.sai .bg{animation:veuSai var(--medio) var(--curva-sai) both}
.modal.sai .sheet{animation:folhaSai var(--medio) var(--curva-sai) both}
@media(max-width:520px){.modal.sai .sheet{animation:folhaDesce var(--medio) var(--curva-sai) both}}

/* --- O que muda num nó vivo ---
   Os casos raros em que a classe troca sem o nó ser recriado, e portanto os
   únicos em que uma transition dispara mesmo: o dia escolhido do calendário
   (calendario.js:calSel troca o .on sem redesenhar a grelha) e o separador
   ativo da barra de baixo. */
.calday{transition:background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva),
  color var(--rapido) var(--curva),transform var(--rapido) var(--curva)}
.calday .n{transition:color var(--rapido) var(--curva)}
/* o selo do planeado que passa a em atraso: hoje o nó é sempre outro (o
   render recria a lista), mas a regra fica escrita para quando não for */
.badge{transition:background-color var(--medio) var(--curva),color var(--medio) var(--curva)}
/* o «porquê» do KPI é display:none→block e o texto vem solto dentro do .expl,
   sem elemento onde pendurar o 0fr→1fr da grelha (o vistas.js:kpi escreve-o
   assim); a alternativa era um max-height adivinhado, e o WHY mais longo já
   passa das doze linhas num cartão de 158px. Daí uma entrada em @keyframes,
   que num display a acender dispara à mesma. */
@keyframes explEntra{from{opacity:0;transform:translateY(-4px)}}
.kpi.open .expl{animation:explEntra var(--medio) var(--curva)}

/* --- Crachás que aparecem com um pulso ---
   O .cnt é recriado a cada buildNav/buildTabbar/notifSino, portanto uma
   transition nunca chegaria a disparar — um @keyframes de entrada dispara
   sempre, que é precisamente quando a contagem muda. */
@keyframes selo{from{transform:scale(.6);opacity:0}60%{transform:scale(1.06);opacity:1}}
/* só quando o número MUDA. O buildNav corre a cada render, e o render corre
   também na sincronização de fundo (cloud/nucleo.js:applyState, de 3 em 3
   minutos): sem o .novo, a app dava um pulso sozinha sem nada ter acontecido.
   Quem decide é o navegacao.js:cntNovo, que guarda a contagem anterior. */
.cnt.novo{animation:selo var(--pulso) var(--curva) both}

/* --- Os gráficos desenham-se ---
   As classes são postas pelo graficos.js; aqui ficam só as regras. O
   transform-box:fill-box é o que faz o transform-origin de um <rect> em SVG
   valer sobre a própria forma, e não sobre o sistema de coordenadas todo; sem
   ele a barra crescia a partir do canto do viewBox. O .gdonut conta com
   pathLength="1" nos paths, que é o que torna o dashoffset independente do
   comprimento real do arco. */
@keyframes gbar{from{transform:scaleY(0)}}
@keyframes ghbar{from{transform:scaleX(0)}}
@keyframes gdonut{from{stroke-dashoffset:1}}
/* Só quem CHEGA ao ecrã vê os gráficos desenharem-se: a marca .entra é posta
   pelo vistas.js:render e só quando foi uma navegação a pedir a repintura.
   Sem este portão, a sincronização de fundo (cloud/nucleo.js:applyState) e
   qualquer gesto que repinte a vista — fechar o cartão dos prazos, mudar um
   filtro — mandavam os gráficos redesenharem-se a meio de uma leitura.
   O escalonamento é escrito pelo graficos.js em cada barra: em SVG as barras
   são irmãs dos onze elementos do eixo, e um nth-child contava-os a todos (a
   primeira barra ficava com o último degrau); nas horizontais o .ghbar é
   sempre filho único, e nenhuma regra chegava a casar. */
#view.entra .gbar{transform-box:fill-box;transform-origin:bottom;animation:gbar var(--desenho) var(--curva-entra) both}
#view.entra .ghbar{transform-origin:left;animation:ghbar var(--desenho) var(--curva-entra) both}
/* A barra que desce cresce a partir do eixo, e o eixo é o topo da caixa dela.
   Medido: a linha do zero a y=90.9, uma barra de despesa de 90.9 a 141.5 — com
   a origem no fundo, ela nascia em baixo, longe do eixo, e subia até lá. */
#view.entra .gbar.desce{transform-origin:top}
/* o .redesenha é para quando é a própria roda a mudar de reparto (o donutDrill)
   e não a vista a chegar: os arcos traçam-se outra vez sem passar pelo render */
#view.entra .gdonut,#donutCard.redesenha .gdonut{stroke-dasharray:1;animation:gdonut var(--desenho) var(--curva-entra) both}
/* O selo de «sem dívidas» chega como os gráficos que substitui, e pelo mesmo
   portão: cresce do centro, com um pequeno passo além do tamanho (a festa é
   esse passo), só para quem chega ao ecrã. */
@keyframes livreSelo{0%{transform:scale(.4);opacity:0}70%{transform:scale(1.08);opacity:1}100%{transform:scale(1)}}
#view.entra .livre-selo{animation:livreSelo var(--desenho) var(--curva-entra) both}

/* --- Os recuos do sistema, no FIM da folha de propósito ---
   Estiveram antes da regra base da .tabbar e perderam o empate: à mesma
   especificidade ganha quem vem depois, e o vidro voltava por cima do
   sólido. Aqui em baixo ganham sempre. */
/* quem pediu menos transparência recebe o vidro sólido: o cabeçalho com o
   fundo da página, a barra de baixo com o do cartão — as cores que cada um
   fingia ter por trás do blur */
@media(prefers-reduced-transparency:reduce){
  header.top{background:var(--bg);-webkit-backdrop-filter:none;backdrop-filter:none}
  .tabbar{background:var(--card);-webkit-backdrop-filter:none;backdrop-filter:none}
}
/* e quem pediu mais contraste recebe contornos que se veem: só os tokens
   das linhas mudam, e tudo o que os cita muda com eles */
@media(prefers-contrast:more){
  :root{--line:#a3aab8;--line2:#6e7686}
  :root.dark{--line:#46506a;--line2:#5e6a86}
}
/* ====================== CLASSES DOS MÓDULOS ======================
   O que era um style="…" com declarações que se sobrepõem (margin com
   margin-top, padding com padding-left, e afins) ou que só faz sentido junto
   passa a uma classe do módulo que o escrevia, com o mesmo seletor #raiz#raiz
   dos utilitários e pela mesma razão. Uma secção por módulo, com o ficheiro
   que a escreve em cima. Também vieram para aqui, tal e qual, as folhas que
   alguns módulos criavam por JavaScript e penduravam na cabeça do documento:
   isso é CSS em linha, que a CSP sem 'unsafe-inline' recusa como recusa um
   atributo de estilo. */
/* ---- web/index.html ---- */
/* Os dois botões do cabeçalho (index.html:#hdrBell e #hdrFilt) nasciam com um
   style="display:none", e quem os mostra escreve el.style.display='' — o que
   tira um estilo em linha mas NÃO tira uma classe. Uma classe utilitária no
   lugar do style deixava-os escondidos para sempre, e quem os mostra vive em
   quatro ficheiros de quatro grupos (vistas.js:pintarBotaoFiltros,
   notificacoes.js:notifSino, cloud/painel.js:patchHdr e
   cloud/selecao.js:patchHdrSel).
   O que esses quatro têm em comum é que mostrar é sempre ENCHER: o botão nasce
   vazio no HTML e só ganha conteúdo — o ícone, o crachá, o «Concluir» — na
   mesma linha em que aparece; e esconder continua a ser um display:none
   escrito no el.style, que ganha a esta regra como ganhava ao style=. Por isso
   o que esconde aqui é o :empty, com o mesmo resultado no ecrã e sem tocar no
   el.style de ninguém.
   O seletor leva o #raiz#raiz dos módulos, como manda o contrato: com os três
   ids e a pseudo-classe fica em (3,1,0) e ganha aos utilitários (2,1,0) que os
   dois botões carregam, para que um u-d-… que alguém lhes venha a pôr não os
   desesconda. Continua abaixo de qualquer el.style, que é o que esconde e
   mostra estes dois. */
#raiz#raiz #hdrBell:empty,#raiz#raiz #hdrFilt:empty{display:none}
/* ---- web/app/componentes.js ---- */
/* O emblema de uma opção do pickModal (componentes.js): o fundo e a cor
   andam sempre aos pares — o vermelho no que apaga, a cor de destaque no
   resto —, e vinham de dois condicionais do mesmo o.icon dentro de um
   style=. Uma classe por ramo, com o par inteiro, em vez de dois
   utilitários: o background:var(--danger-soft) não está na tabela gerada
   (o ramo do condicional é um valor, e não uma declaração, e o gerador só
   aproveita declarações inteiras), e partir o par deixava metade de um
   estado escrita e a outra metade por escrever. */
#raiz#raiz .comp-pick-ic-destroi{background:var(--danger-soft);color:var(--danger)}
#raiz#raiz .comp-pick-ic-normal{background:var(--accent-soft);color:var(--accent)}
/* ---- web/cloud/painel.js ---- */
/* O emblema de uma opção do menu de toque longo (painel.js:menuOption): o
   fundo e a cor andam sempre aos pares — o vermelho no que destrói, a cor de
   destaque no resto — e vinham de um condicional dentro do style=. Uma classe
   por ramo, com o par inteiro, como no .comp-pick-ic-… do g07: o
   background:var(--danger-soft) não está na tabela dos utilitários (o ramo do
   condicional é um valor, e não uma declaração inteira), e partir o par
   deixava metade de um estado escrita e a outra metade por escrever. */
#raiz#raiz .painel-ic-destroi{background:var(--danger-soft);color:var(--danger)}
#raiz#raiz .painel-ic-normal{background:var(--accent-soft);color:var(--accent)}
/* A grelha dos cartões da visão geral (cloud/painel.js). Vivia numa folha que
   o JavaScript criava e pendurava na cabeça do documento (var cssPainel +
   document.head.appendChild) — CSS em linha, que a CSP sem 'unsafe-inline'
   recusa tal como recusa um style=. As regras vêm para aqui tal e qual, pela
   mesma ordem e sem o #raiz#raiz dos utilitários, para manterem a
   especificidade que tinham: nenhum destes nomes .cw-… aparece noutra regra
   da folha, e o «.cw-dash .grid» (0,2,0) continua a ganhar ao «.grid» (0,1,0)
   por especificidade, como ganhava antes por vir numa folha posterior. */
/* Doze colunas — número fixo, não auto-fit: com colunas a aparecer e a
   desaparecer conforme a largura, os cartões nunca caíam onde se esperava.
   Doze porque o canvas tem filas de dois (metades, .cw-wide) e de três
   (terços, .cw-terco); no telemóvel todos atravessam a grelha, e os
   indicadores repartem-se lá dentro em duas colunas (.cw-dash .grid).
   stretch, não start: cartões da mesma fila com alturas diferentes eram
   metade da desarrumação da vista. Sem margem por cima: o que vem antes (o
   «Pede atenção», os primeiros passos, os pedidos) traz a sua por baixo. */
.cw-dash{display:grid;grid-template-columns:repeat(12,minmax(0,1fr));gap:11px;margin-top:0;align-items:stretch}
.cw-dash>.cw-blk{grid-column:1/-1}
.cw-blk>.card{flex:1}
/* Reserva, para quem não tem container queries: corte pela largura do ecrã.
   Erra em paisagem no telemóvel, onde a barra lateral aparece e leva 264px
   sem a media query saber. */
@media(min-width:1000px){.cw-dash{gap:14px}.cw-dash>.cw-wide{grid-column:span 6}}
@media(min-width:1180px){.cw-dash>.cw-terco{grid-column:span 4}}
.cw-dash .grid{grid-template-columns:repeat(2,1fr)}
@media(min-width:1000px){.cw-dash .grid{grid-template-columns:repeat(4,1fr)}}
/* O que vale de verdade: a grelha responde à largura que tem, não à do ecrã.
   É a única forma de o telemóvel deitado dar quatro colunas — e acompanha a
   rotação sem recarregar, porque é CSS e não uma decisão tomada no arranque.
   560px é o telemóvel deitado: com a barra lateral a ocupar 264px sobram
   ~592px de conteúdo, e quatro colunas dão ~137px a cada indicador. É abaixo
   dos 158px que a app usava como mínimo — folga trocada de propósito por ver
   os oito indicadores de uma vez em paisagem. */
@supports (container-type:inline-size){
  .cw-cont{container-type:inline-size;container-name:vista}
  @container vista (max-width:559px){.cw-dash{gap:11px}.cw-dash>.cw-wide,.cw-dash>.cw-terco{grid-column:1/-1}}
  @container vista (max-width:559px){.cw-dash .grid{grid-template-columns:repeat(2,1fr);gap:11px}}
  @container vista (min-width:560px){.cw-dash .grid{grid-template-columns:repeat(4,1fr);gap:11px}}
  @container vista (min-width:760px){.cw-dash .grid{gap:14px}}
  /* as metades a partir de 560px; os terços só a partir de 900px — abaixo
     disso um terço é estreito demais para o donut e as barras, e atravessa */
  @container vista (min-width:560px){.cw-dash{gap:11px}.cw-dash>.cw-wide{grid-column:span 6}}
  @container vista (max-width:899px){.cw-dash>.cw-terco{grid-column:1/-1}}
  @container vista (min-width:900px){.cw-dash>.cw-terco{grid-column:span 4}}
  @container vista (min-width:760px){.cw-dash{gap:14px}}
}
/* o que atravessa a grelha toda: a fila dos indicadores, o aviso âmbar e um
   cartão sozinho na sua fila */
.cw-dash>.cw-full{grid-column:1/-1}
.cw-dash>.cw-full>.section-title{margin:8px 0 0}
.cw-blk{position:relative;min-width:0;display:flex;flex-direction:column}
.cw-blk .cw-h{display:none}
#view.cw-edit .cw-blk{border:1.5px dashed var(--line2);border-radius:18px;padding:9px;background:var(--tint);touch-action:none;cursor:grab}
#view.cw-edit .cw-blk>*{pointer-events:none}
/* a seta do indicador vive no mesmo canto que o punho de arrasto */
#view.cw-edit .cw-blk .kic{opacity:0}
#view.cw-edit .cw-blk .cw-h{display:grid;place-items:center;position:absolute;top:6px;right:8px;width:26px;height:26px;border-radius:9px;background:var(--chip);color:var(--muted)}
#view.cw-edit .cw-blk.cw-drag{cursor:grabbing;box-shadow:var(--shadow);border-color:var(--accent);position:relative;z-index:70;opacity:.97}
/* ---- web/cloud/novidades.js, web/cloud/guia.js, web/cloud/selecao.js,
        web/cloud/selecao-listas.js, web/app/visitas.js ---- */
/* As classes destes módulos, e as quatro folhas que estes ficheiros criavam
   por JavaScript: as regras passaram para aqui tal e qual, pela mesma ordem e
   com os mesmos comentários. */
/* O tempo da roda que gira enquanto a app se atualiza (cloud/novidades.js).
   Fica num token porque nenhuma declaração de movimento desta folha traz o
   tempo escrito à mão; fora da escala das reações, como o --desenho e o
   --pulso — não é uma reação a um toque, é uma espera a dar sinal de vida. */
:root{--roda:.8s}
/* cloud/novidades.js:caixaDosPassos — a roda do passo que está a correr no
   ecrã de atualização (o canvas M-Atualizar). Uma classe do módulo, e não
   utilitários: o border e o border-top-color sobrepõem-se, e o
   border-radius e a animação não estão na tabela. Assenta sempre no
   azul-noite: o traço é o das divisórias da barra e o topo o cobalto claro
   (#9fb4ff, o do canvas, igual nos dois temas). */
#raiz#raiz .nov-roda{flex:0 0 20px;width:20px;height:20px;border-radius:50%;border:2.5px solid var(--side-line);border-top-color:#9fb4ff;animation:cwgira var(--roda) linear infinite}
@keyframes cwgira{to{transform:rotate(360deg)}}
@media(prefers-reduced-motion:reduce){#cwUpdRoda{animation:none;border-color:#9fb4ff}} /* parada, a roda é um anel cobalto claro inteiro: o passo atual, sem girar */
/* cloud/guia.js — o cartão flutuante do tutorial.
   Flutua, não é modal: quem segue os passos tem de poder mexer na app por
   baixo enquanto lê. Acima do botão flutuante, abaixo dos modais — menos
   quando um está aberto, e aí sobe acima dele (sobre-janela).
   Acima do botão flutuante e não por cima dele: o tutorial manda carregar
   nesse botão, e estava a tapá-lo.
   Entra em vez de aparecer. O cartão nasce logo a seguir a uma mudança de
   ecrã — o passo leva a pessoa às Definições e a vista inteira é repintada no
   mesmo instante — e um cartão parado no canto de baixo perde-se nisso tudo,
   ainda por cima quando o texto manda olhar para o topo. Sobe de fora do
   ecrã, com a curva de quem atravessa distância. */
#cwGuia{position:fixed;left:12px;right:12px;bottom:calc(88px + var(--inset-bottom));z-index:59;pointer-events:none;display:flex;justify-content:center;animation:guiaEntra var(--lento) var(--curva-entra)}
@keyframes guiaEntra{from{opacity:0;transform:translateY(28px)}}
#cwGuia .guia-cartao{pointer-events:auto;width:100%;max-width:420px}
/* Por cima de uma janela aberta, e encostado ao topo, longe dos botões.
   O número segue o do .modal (index.html): esteve em 61 contra os 60 de
   então, e quando o modal subiu para 70 o cartão ficou por baixo — que é
   exatamente o defeito que este ajuste existe para não deixar acontecer. */
#cwGuia.sobre-janela{z-index:71;bottom:auto;top:calc(12px + var(--inset-top));animation:guiaEntra var(--lento) var(--curva-entra)}
@media(min-width:900px){#cwGuia{left:auto;right:22px;max-width:420px;bottom:calc(22px + var(--inset-bottom))}#cwGuia.sobre-janela{top:calc(16px + var(--inset-top))}}
/* cloud/guia.js:cartaoPassos — a lista dos primeiros passos: passou para a
   secção «redesign: 1.3.9», com o desenho do canvas (M-PrimeirosPassos). */
/* cloud/selecao.js — a seleção de vários movimentos.
   A caixa de marcar, desenhada e não um campo do sistema: um checkbox do
   sistema destoava de tudo o resto e não aceita o tamanho que aqui é preciso. */
.selbox{flex:0 0 auto;display:inline-flex;align-items:center;padding:10px 12px 10px 2px;cursor:pointer}
.selck{width:22px;height:22px;border-radius:7px;border:1.8px solid var(--line2);display:grid;place-items:center;color:transparent;background:var(--field)}
.selck.on{background:var(--accent);border-color:var(--accent);color:var(--accent-ink)}
.selck.meio{border-color:var(--accent)}
.selck.meio i{width:10px;height:2.5px;border-radius:2px;background:var(--accent);display:block}
/* a caixa de tudo acompanha o scroll: sem isso, a meio de uma lista longa
   deixava de haver como marcar tudo sem voltar ao topo. Vive no cabeçalho, no
   lugar do título (cloud/selecao.js:patchHdrSel, e o das Casas,
   cloud/selecao-listas.js:selLCabNovo) — numa barra por cima da lista
   empurrava-a ~64px ao entrar na seleção. Entra a desvanecer, em @keyframes
   por ser um nó acabado de inserir. */
.sel-cab{display:flex;align-items:center;min-width:0;animation:veuEntra var(--medio) var(--curva-entra) backwards}
.sel-cab .selbox{padding:0 10px 0 0}
.sel-cab .small{margin-top:1px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* a contagem numa linha só: «nenhum movimento» partia em duas no telemóvel,
   o cabeçalho crescia 19px e a lista descia ao entrar na seleção */
.sel-cab b{display:block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
body.sel-on #pageTitle,body.sel-on #pageSub{display:none}
/* as caixas são alcançáveis pelo teclado (role=checkbox): o foco vê-se */
.selbox:focus-visible{outline:2px solid var(--accent);outline-offset:2px;border-radius:8px}
/* Ao ENTRAR na seleção dos Movimentos as caixas das linhas desvanecem, como
   as das Casas (estilos.css:.sel-entra): no --medio, com a curva de quem
   chega. A classe só se põe ao entrar (cloud/selecao.js:selCaixasEntram) e
   sai no fim; a regra do prefers-reduced-motion desliga-a. */
#view .mov-linha>.selbox.sel-entra{animation:veuEntra var(--medio) var(--curva-entra) backwards}
/* A barra das ações da seleção (selecao.js:selBarraHtml, e a dos imóveis e
   contratos em selecao-listas.js). No telemóvel é a barra de baixo, de ponta a
   ponta, no lugar da de atalhos. */
.sel-fundo{position:fixed;left:0;right:0;bottom:0;z-index:45;display:flex;gap:8px;align-items:center;background:var(--card);border-top:1px solid var(--line);padding:8px calc(10px + var(--inset-right)) calc(8px + var(--inset-bottom)) calc(10px + var(--inset-left))}
body.sel-on .tabbar{display:none!important}
body.sel-on .wrap{padding-bottom:calc(120px + var(--inset-bottom))}
/* a dos Movimentos (cloud/selecao.js, a classe body.sel-mov) tem duas linhas
   no telemóvel, com 120px: a última linha da lista para acima dela, e o
   «Topo» (index.html:#toTop), que ficava por cima da contagem, sobe para
   fora dela */
body.sel-mov .wrap{padding-bottom:calc(140px + var(--inset-bottom))}
@media(max-width:900px){body.sel-mov .totop{bottom:calc(132px + var(--inset-bottom))}}
/* em seleção a barra do fundo tem o Cancelar e as ações: o botão do
   cabeçalho (cloud/selecao.js:patchHdrSel) repetia-os, e sai, como o das
   Casas (estilos.css:body.sel-on #hdrFilt.lst-hdr-sel) */
body.sel-on #hdrFilt.mov-hdr-sel{display:none}
/* A barra dos Movimentos (cloud/selecao.js:selBarraHtml) é a das Casas —
   × Cancelar, a contagem ao meio e as ações —, com os botões dos Movimentos.
   No telemóvel em duas linhas, como na prévia escolhida: em cima o Cancelar e
   a contagem, com o quanto somam por baixo dela; em baixo os botões lado a
   lado, em partes iguais, cada um com o ícone por cima de um rótulo curto
   («Categoria», «Etiquetas», «Editar», «Apagar 2»). A 375px cabem os quatro
   sem régua, com mais de 44px de alvo em cada sentido. A contagem fica ao
   meio da barra: as duas colunas de lado repartem o resto, e a do Cancelar
   só cresce o que ele precisar. */
.sel-fundo.mov-sel .sel-info{margin:0;min-width:0;font-variant-numeric:tabular-nums}
.sel-fundo.mov-sel #selFundoSoma:empty{display:none}
@media(max-width:900px){
  .sel-fundo.mov-sel{display:grid;grid-template-columns:1fr auto 1fr;column-gap:8px;row-gap:6px}
  .sel-fundo.mov-sel .sel-fim{justify-self:start;padding:0 14px}
  .sel-fundo.mov-sel .sel-info{grid-column:2;display:flex;flex-direction:column;align-items:center;text-align:center;line-height:1.3}
  .sel-fundo.mov-sel .sel-info b,.sel-fundo.mov-sel #selFundoSoma{white-space:nowrap}
  .sel-fundo.mov-sel .sel-acoes{grid-column:1/-1;display:grid;grid-auto-flow:column;grid-auto-columns:minmax(0,1fr);gap:6px}
  .sel-fundo.mov-sel .sel-acao{flex-direction:column;gap:3px;min-width:0;min-height:54px;padding:6px 4px;font-size:12.5px;line-height:1.15}
  .sel-fundo.mov-sel .sel-acao>span{max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
  .sel-fundo.mov-sel .sel-rot-longo{display:none}
}
/* No ecrã largo é a barra azul-noite do canvas (D-Movimentos) e das Casas:
   × Cancelar, quantos estão marcados e quanto somam ao meio, «Mudar
   categoria», «Adicionar etiquetas» e «Apagar N» por extenso (o Editar sai:
   os outros dois repartem-no). Flutua no fundo da coluna, e não por cima da
   tabela, para não a empurrar ao primeiro visto. */
@media(min-width:901px){
  .sel-fundo{left:calc(var(--rail) + 24px + var(--inset-left));right:calc(24px + var(--inset-right));bottom:calc(20px + var(--inset-bottom));max-width:1100px;margin:0 auto;
    flex-wrap:wrap;gap:10px;padding:10px 10px 10px 18px;border:1px solid var(--side-line);border-radius:14px;background:var(--side);color:var(--side-ink);box-shadow:var(--shadow)}
  /* os botões em cima do azul-noite usam os véus da barra lateral: --side-hover
     em repouso, --side-on por baixo do rato, e premido os dois um por cima do
     outro (o --side-hover numa camada por cima do --side-on) */
  .sel-fundo .btn{min-height:36px;padding:0 12px;font-size:14px;border-radius:10px;border-color:var(--side-line);background:var(--side-hover);color:var(--side-ink)}
  .sel-fundo .btn:active{background:linear-gradient(var(--side-hover),var(--side-hover)),var(--side-on)}
  .sel-fundo .btn.danger{border-color:var(--danger);background:var(--danger);color:var(--danger-ink)}
  .sel-fundo .btn.danger:active{background:var(--danger);filter:brightness(.82)}
  .sel-fundo .btn:focus-visible{outline:2px solid var(--side-ink);outline-offset:2px}
  /* a soma não se corta (é o número que importa): sem lugar, os botões descem
     para a linha de baixo (a barra embrulha) */
  .sel-fundo.mov-sel .sel-info{display:block;flex:1 0 auto;white-space:nowrap;text-align:center}
  .sel-fundo.mov-sel #selFundoSoma{font-size:14px;color:var(--side-text)}
  .sel-fundo.mov-sel #selFundoSoma::before{content:" · "}
  .sel-fundo.mov-sel .sel-acoes{display:flex;flex-wrap:wrap;gap:10px;margin-left:auto}
  .sel-fundo.mov-sel .sel-rot-curto,.sel-fundo.mov-sel .sel-estreito{display:none}
}
/* o realce só onde há rato: num ecrã de dedo com 901px ou mais ficava preso
   depois do toque */
@media(min-width:901px) and (hover:hover) and (pointer:fine){
  .sel-fundo .btn:hover{background:var(--side-on)}
  .sel-fundo .btn.danger:hover{border-color:var(--danger-press);background:var(--danger-press)}
}
/* o ecrã largo de dedo (o telemóvel deitado passa dos 900px, o tablet): a
   barra compacta do computador com os alvos de toque inteiros */
@media(min-width:901px) and (pointer:coarse){
  .sel-fundo .btn{min-height:44px}
}
/* cloud/selecao-listas.js — a seleção de vários imóveis e contratos. O
   «Selecionar vários» que entra no menu de um cartão tinha o estilo escrito
   no JavaScript; é esta classe. */
.sel-on-card{border-color:var(--accent)!important;background:var(--tint)}
.card.sel-varios{display:flex;align-items:center;gap:11px;padding:12px 14px}
#view [data-selbox]{margin-right:10px}
/* app/visitas.js:vVisits — o espaço por baixo de cada bloco de visitas (o
   antigo atributo de estilo que ia no listaViva). Não há utilitário de 16px. */
#raiz#raiz .vis-bloco{margin-bottom:16px}
/* ---- web/app/painel-geral.js, web/app/imovel.js ---- */
/* As ações que o cargo de quem colabora abre (acessos.js:acoesNoImovel), no
   cartão «O que podes fazer» da vista geral e na ficha do imóvel: botões da
   largura do dedo, lado a lado enquanto o rótulo couber numa linha e, quando
   não cabe, cada um na largura toda — quem acabou de aceitar um convite tem
   de os ler de relance. */
#raiz#raiz .colab-acoes{display:flex;flex-wrap:wrap;gap:8px}
#raiz#raiz .colab-acoes .btn{flex:1 1 auto;justify-content:center;min-height:44px;white-space:nowrap}
/* ---- web/app/tarefas.js ---- */
/* A lista de tarefas de um imóvel ou de um contrato (tarefas.js:tfLista): uma
   secção é um cabeçalho com o nome, a conta e o ⋯ dela, e as tarefas por
   baixo, uma por linha. A caixa de marcar vive dentro de um label de 44px,
   que é a área de toque dela: a caixa nativa tem 18, e um dedo que falha a
   caixa caía no nome e abria o formulário em vez de marcar. O nome é um botão
   da largura que sobra, com a altura do dedo. Cumprida, a tarefa fica riscada
   e em cinzento, no mesmo sítio: saltar para o fim da lista ao marcar tirava
   a linha de debaixo do dedo. */
#raiz#raiz .tf-seccao{margin-top:6px;border-radius:12px}
#raiz#raiz .tf-cab{display:flex;align-items:center;gap:8px;padding:0;border-bottom:1px solid var(--line)}
#raiz#raiz .tf-cab b{flex:1 1 auto;min-width:0;font-size:14px;font-weight:650;color:var(--ink);overflow-wrap:anywhere}
#raiz#raiz .tf-conta{font-size:12px;color:var(--muted);white-space:nowrap}
#raiz#raiz .tf-itens{display:flex;flex-direction:column}
#raiz#raiz .tf-item{display:flex;align-items:center;gap:2px;border-bottom:1px solid var(--line)}
#raiz#raiz .tf-marca{display:flex;align-items:center;justify-content:center;width:44px;height:44px;flex:0 0 auto;margin-left:-12px;cursor:pointer}
#raiz#raiz .tf-marca input{width:18px;height:18px;margin:0;padding:0;accent-color:var(--accent);cursor:pointer}
#raiz#raiz .tf-marca input:disabled{cursor:default}
#raiz#raiz .tf-nome{flex:1 1 auto;min-width:0;min-height:44px;display:flex;flex-direction:column;justify-content:center;align-items:flex-start;gap:2px;
  padding:8px 0;border:0;background:none;text-align:left;font:inherit;font-size:14px;font-weight:500;color:var(--ink);overflow-wrap:anywhere}
#raiz#raiz button.tf-nome{cursor:pointer}
#raiz#raiz .tf-quando{font-size:11.5px;color:var(--muted);text-decoration:none}
#raiz#raiz .tf-feita .tf-nome>span{text-decoration:line-through;color:var(--muted)}
/* O cabeçalho de uma secção é um botão da largura toda (tarefas.js:tfDobrar):
   a seta roda para o lado quando a secção está recolhida, e recolhida as
   tarefas somem — continuam no HTML, para a pesquisa e o arrasto. O lugar
   das tarefas sem secção que só existe para largar (.tf-so-alvo) não ocupa
   nada fora de um arrasto. */
#raiz#raiz .tf-dobra{flex:1 1 auto;min-width:0;min-height:44px;display:flex;align-items:center;gap:6px;margin:0 0 0 -6px;padding:0 6px;
  border:0;border-radius:9px;background:none;font:inherit;color:inherit;text-align:left;cursor:pointer}
#raiz#raiz span.tf-dobra{cursor:default}
/* o lugar do ⋯ nas soltas: a largura do .iconbtn (32, e 44 ao dedo) */
#raiz#raiz .tf-sem-menu{flex:0 0 32px}
@media(pointer:coarse){#raiz#raiz .tf-sem-menu{flex-basis:44px}}
#raiz#raiz .tf-chev{display:flex;flex:0 0 auto;color:var(--muted);transition:transform var(--medio) var(--curva)}
#raiz#raiz .tf-recolhida .tf-chev{transform:rotate(-90deg)}
#raiz#raiz .tf-recolhida .tf-itens{display:none}
#raiz#raiz .tf-so-alvo{display:none}
#raiz#raiz .tf-a-arrastar .tf-so-alvo{display:block}
@media(hover:hover) and (pointer:fine){#raiz#raiz button.tf-dobra:hover{background:var(--tint)}}
#raiz#raiz button.tf-dobra:active{background:var(--press)}
/* A pega de arrastar (tarefas.js:tfArrastar): à esquerda da caixa, com a
   altura do dedo, e a única coisa da linha com touch-action:none — arrastar
   no nome continua a rolar a lista. Agarrada, a linha levanta-se e segue o
   dedo; a secção por cima de cujo nome se está acende, e entre duas tarefas
   aparece a linha de onde vai ficar. Sem movimento (prefers-reduced-motion)
   a seta não roda devagar, e o realce e a linha ficam iguais. */
#raiz#raiz .tf-pega{display:grid;place-items:center;width:40px;height:44px;flex:0 0 auto;margin-left:-10px;padding:0;border:0;border-radius:9px;
  background:none;color:var(--faint);cursor:grab;touch-action:none;-webkit-user-select:none;user-select:none;-webkit-touch-callout:none}
#raiz#raiz .tf-pega+.tf-marca{margin-left:-6px}
@media(hover:hover) and (pointer:fine){#raiz#raiz .tf-pega:hover{color:var(--ink);background:var(--tint)}}
#raiz#raiz .tf-pega:active{color:var(--ink);background:var(--press)}
#raiz#raiz .tf-dobra:focus-visible,#raiz#raiz .tf-pega:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
#raiz#raiz .tf-a-arrastar{-webkit-user-select:none;user-select:none}
#raiz#raiz .tf-a-arrastar .tf-pega{cursor:grabbing}
#raiz#raiz .tf-seccao.tf-alvo{background:var(--accent-soft);box-shadow:0 0 0 6px var(--accent-soft),0 0 0 8px var(--accent)}
#raiz#raiz .tf-seccao.tf-alvo .tf-cab{border-bottom-color:transparent}
#raiz#raiz .tf-item.tf-agarrada{position:relative;z-index:5;background:var(--card);border-radius:12px;border-bottom-color:transparent;box-shadow:var(--shadow)}
/* a tarefa agarrada flutua logo acima do dedo e a linha fica onde o dedo
   está; se uma tarefa alta se chegar a ela, a linha continua por cima */
#raiz#raiz .tf-linha{position:relative;z-index:6;height:0;pointer-events:none}
#raiz#raiz .tf-linha::before{content:'';position:absolute;left:4px;right:0;top:-1.5px;height:3px;border-radius:2px;background:var(--accent)}
#raiz#raiz .tf-linha::after{content:'';position:absolute;left:-4px;top:-5px;width:10px;height:10px;box-sizing:border-box;border-radius:50%;border:2px solid var(--accent);background:var(--card)}
/* ---- web/cloud/partilha.js ---- */
/* A folha dos documentos legais (os termos e a privacidade, que o
   cloud/ajuda.js embrulha numa div .lg): texto corrido, legível, sem cartões.
   O partilha.js criava-a por JavaScript e pendurava-a na cabeça do documento —
   CSS em linha, que a CSP sem 'unsafe-inline' recusa na mesma. As regras ficam
   aqui tal e qual, sem o #raiz#raiz dos utilitários, para manterem a
   especificidade que tinham.
   Ficam em ÚLTIMO lugar entre as classes dos módulos, e é de propósito:
   penduradas na cabeça em tempo de execução, eram as últimas regras do
   documento e ganhavam todos os empates. Nenhuma das regras acima casa com
   .lg, .lg p, .lg ul, .lg li, .lg b ou .lg .lg-h — conferido seletor a seletor
   —, e enquanto este for o último bloco dos módulos nenhuma que se venha a
   escrever lhes rouba um empate. */
.lg{max-width:70ch;line-height:1.68;font-size:14.5px;color:var(--ink)}
.lg p{margin:0 0 12px}
.lg ul{margin:0 0 14px;padding-left:20px}
.lg li{margin:0 0 7px}
.lg .lg-h{font-size:15.5px;font-weight:650;margin:26px 0 10px;letter-spacing:-.01em}
.lg b{font-weight:650}
/* ===== redesign: 1.3.1 — a Visão geral ===== */
/* A Visão geral do canvas de 2026-10 (Main no computador, M-Inicio e M-Escuro
   no telemóvel). As classes são .vg-… (painel-geral.js, prazos.js:prazosCard,
   vistas.js:contasCard) e as variantes dos indicadores (.vg-kpi, .kdot). O
   corte entre o telemóvel e o computador é o da casca: 900px. */

/* A cabeça de um cartão: o título na letra dos títulos, a nota curta ao lado
   e, no canto, uma ação (uma ligação ou um botão de ícone). */
.vg-cartao{display:flex;flex-direction:column;gap:14px}
.vg-card-cab{display:flex;align-items:baseline;flex-wrap:wrap;gap:2px 10px;min-width:0}
.vg-tit{margin:0;font-size:16px;line-height:1.3;min-width:0}
.vg-nota{margin:0;font-size:12.5px;line-height:1.45}
/* o portefólio da jornada é o cartão genérico (vistas.js:card): o título toma
   a mesma letra dos outros cartões da vista */
.card:has(.vg-port) .title{font-family:var(--letra-titulo);font-size:16px;font-weight:650;letter-spacing:-.015em}
/* uma ligação que é um botão: cobalto, sem caixa («Ver todos», «Avaliação») */
.vg-ligacao{display:inline-flex;align-items:center;min-height:32px;padding:0 4px;margin:0 -4px;border:0;border-radius:8px;background:transparent;color:var(--accent);font:inherit;font-size:14px;font-weight:600;cursor:pointer;white-space:nowrap}
@media(hover:hover) and (pointer:fine){.vg-ligacao:hover{color:var(--accent-text);text-decoration:underline}}
.vg-ligacao:active{opacity:.7}
.vg-ligacao:focus-visible{outline:2px solid var(--accent);outline-offset:1px}
/* a ação no canto da cabeça de um cartão: depois da .vg-ligacao, que lhe
   apagava a margem da esquerda */
.vg-cab-acao{margin-left:auto;align-self:center}
/* uma ligação no canto lê-se na linha de base do título, como no canvas
   («Portefólio» · «Avaliação»): ao centro, com os 44px do dedo, descia 11px; a
   margem negativa deixa o alvo inteiro sem engrossar a cabeça */
@media(min-width:901px){.vg-card-cab>.vg-ligacao.vg-cab-acao{align-self:baseline;margin-block:-12px}}
/* no telemóvel, com uma ação no canto, a cabeça é uma grelha: o título e a
   nota por baixo dele à esquerda, a ação à direita — em linha, a ação caía
   sozinha numa segunda linha */
@media(max-width:900px){
  .vg-card-cab:has(>.vg-cab-acao){display:grid;grid-template-columns:minmax(0,1fr) auto;column-gap:10px;align-items:center}
  .vg-card-cab:has(>.vg-cab-acao)>.vg-tit,.vg-card-cab:has(>.vg-cab-acao)>.small{grid-column:1}
  .vg-card-cab:has(>.vg-cab-acao)>.vg-cab-acao{grid-column:2;grid-row:1/span 2;margin:0 -8px 0 0}
  /* sem nota, o span 2 criava uma segunda linha vazia e a ação descia 11px
     abaixo do título («Portefólio» · «Avaliação»): fica na linha dele, e a
     margem negativa deixa o alvo de 44px sem engrossar a cabeça */
  .vg-card-cab:has(>.vg-cab-acao):not(:has(>.small))>.vg-cab-acao{grid-row:1;margin-block:-12px}
  /* uma ligação no canto acaba o texto na margem do conteúdo (o padding dela
     é de 4px; os 8px eram do botão de ícone) */
  .vg-card-cab:has(>.vg-cab-acao)>.vg-ligacao.vg-cab-acao{margin-right:-4px}
  /* o «Topo» flutuante (index.html:#toTop) fica centrado por cima da barra de
     baixo, à altura do «Personalizar painel» no fim da página: o padding (as
     utilidades do botão ganham à margem) sobe o botão para fora dele */
  #dashPersonalizar:not(:empty){padding-bottom:64px}
}

/* --- Pede atenção --- */
.vg-atencao{min-width:0}
.vg-atencao-cab h2{margin:0}
/* no telemóvel, um cartão com uma linha por assunto (.linha, componente da casa) */
.vg-atencao-linhas .linha{width:100%;border:0;border-radius:0;background:transparent;color:inherit;font:inherit;text-align:left}
/* o border:0 de cima limpa a borda do botão e apagava também a divisória da
   casa entre linhas (.linha+.linha): volta, só entre linhas — por baixo do
   título não há (o canvas: .ar+.ar) */
.vg-atencao-linhas .linha+.linha{border-top:1px solid var(--line)}
@media(hover:hover) and (pointer:fine){.vg-atencao-linhas .linha:hover{background:var(--tint)}}
.vg-atencao-linhas .linha:active{background:var(--press)}
.vg-atencao-linhas .linha:focus-visible{outline-offset:-2px}
.vg-atencao-linhas .txt>*{display:block;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.vg-atencao-linhas .txt b{font-weight:650}
@media(min-width:901px){
  .vg-atencao{display:flex;flex-direction:column;gap:12px;margin:0 0 22px}
  .vg-atencao-cab{display:flex;align-items:baseline;flex-wrap:wrap;gap:2px 12px}
  .vg-atencao-cab h2{font-size:20px;line-height:1.25}
  .vg-atencao-linhas{display:none}
  /* auto-fill, e não auto-fit: um cartão sozinho (só os prazos) fica com a
     largura de uma coluna, em vez de esticar a página toda para três linhas */
  .vg-atencao-grade{display:grid;grid-template-columns:repeat(auto-fill,minmax(min(320px,100%),1fr));gap:14px;align-items:start}
  /* o cartão dos por confirmar (planeados.js:pendingCard) traz a margem de
     baixo de quando vivia solto; numa grelha, o espaço é o gap */
  #raiz#raiz .vg-atencao-grade>.card,#raiz#raiz .vg-atencao-pilha>*{margin:0}
  .vg-atencao-pilha{display:flex;flex-direction:column;gap:14px;min-width:0}
  .vg-atencao-pilha:empty{display:none}
  .vg-atencao-pedidos{display:flex;flex-direction:column}
}
@media(max-width:900px){
  .vg-atencao{background:var(--card);border:1px solid var(--line);border-radius:16px;overflow:hidden;margin:0 0 14px}
  .vg-atencao-cab{padding:14px 14px 4px}
  .vg-atencao-cab h2{font-family:var(--letra);font-size:12px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--muted)}
  .vg-atencao-cab .small{display:none}
  .vg-atencao-grade{display:none}
  /* os convites de ligação não estão no sino, e por isso não têm linha: o
     cartão dos pedidos fica à vista quando os traz (cloud/painel.js) */
  .vg-atencao-grade:has(.com-convites){display:block;padding:4px 14px 14px}
  .vg-atencao-grade:has(.com-convites)>:not(.vg-atencao-pilha),.vg-atencao-pilha>:not(.com-convites){display:none}
}

/* --- As linhas curtas dos cartões do «Pede atenção» (prazos, atividade) --- */
.vg-itens{display:flex;flex-direction:column;margin:-4px 0 -8px;min-width:0}
.vg-item{display:flex;align-items:center;gap:4px;border-top:1px solid var(--line);min-width:0}
.vg-item-abrir{flex:1;min-width:0;display:flex;align-items:center;gap:12px;padding:12px 8px;margin:0 -8px;border:0;border-radius:10px;background:transparent;color:inherit;font:inherit;text-align:left}
button.vg-item-abrir{cursor:pointer}
@media(hover:hover) and (pointer:fine){button.vg-item-abrir:hover{background:var(--tint)}}
button.vg-item-abrir:active{background:var(--press)}
.vg-item-abrir:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.vg-item-txt{flex:1;min-width:0;display:flex;flex-direction:column}
.vg-item-txt b{font-weight:600}
.vg-item-txt .small{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.vg-item .badge{flex:0 0 auto}
.vg-item .avatar{width:32px;height:32px;flex-basis:32px;font-size:12px}
.vg-silenciar{color:var(--faint);flex:0 0 auto;margin-right:-8px}
/* 44px no dedo: com .btn.sm.so-icone no seletor, para ganhar à largura de 36
   do botão pequeno de ícone (.btn.sm.so-icone) e à altura de 40 do pequeno no
   dedo (.btn.sm) — só com a classe da folha perdia, e o ⓘ das contas ficava
   36×44 e o ✕ dos prazos 36×40 */
@media(pointer:coarse){.btn.sm.so-icone.vg-silenciar,.btn.sm.so-icone.vg-cab-acao{width:44px;min-height:44px}.vg-ligacao{min-height:44px}}

/* --- Os quatro indicadores --- */
/* o rótulo com a bolinha da cor da série, o valor a tinta na letra dos
   títulos, a variação numa linha e a frase curta; a silhueta dos doze meses
   vai para o canto de cima, onde estava o ícone da evolução */
.vg-kpi{display:flex;flex-direction:column;gap:6px}
.vg-kpi .kic{display:none}
.vg-kpi .label{font-size:14px;gap:8px;padding-right:52px}
.kdot{width:10px;height:10px;border-radius:3px;flex:0 0 10px}
/* 30px no ecrã largo, a encolher com o CARTÃO (cqi — o cartão é o
   contentor): logo acima do corte da casca (900px) a barra lateral come 264px
   e os quatro indicadores ficam com ~107px de texto. Com os cêntimos
   («10 860,00 €», o canvas) o valor tem 11 ou 12 letras, e a 2,3vw da janela
   saía 9px da caixa a 920px. */
.vg-kpi{container-type:inline-size}
.vg-kpi .value{font-size:clamp(16px,15cqi,30px);margin:0;line-height:1.1}
.vg-kpi .kserie{min-height:19px;margin:0;flex-wrap:nowrap;gap:4px}
.vg-kpi .kserie .ksilhueta{position:absolute;top:20px;right:18px;width:44px;flex:none}
.vg-kpi .kserie .kvar{font-size:13px;font-weight:600}
.vg-kpi .kserie .kvsub{font-size:13px;flex:0 1 auto}
.vg-kpi .kserie .kvsub::before{content:"· "}
.vg-kpi .foot{font-size:12.5px;margin:0;line-height:1.4}
.vg-kpi-extra{font-size:13px;color:var(--muted)}
/* num custo (Despesas, Prestações) subir não é bom: a variação fica neutra,
   como no canvas, em vez do verde de quem sobe */
.vg-kpi.custo .kserie .kvar.pos,.vg-kpi.custo .kserie .kvar.neg{color:var(--muted)}
/* o passar por cima só com rato: no dedo ficava pintado depois do toque */
@media(hover:hover) and (pointer:fine){.vg-kpi:hover{border-color:var(--line2);background:var(--tint)}}
.vg-kpi:active{background:var(--press)}
/* o Cashflow é o cartão azul-noite, com texto claro */
.vg-kpi.cf{background:var(--side);border-color:var(--side)}
@media(hover:hover) and (pointer:fine){.vg-kpi.cf:hover{background:var(--side) linear-gradient(var(--side-hover),var(--side-hover));border-color:var(--side)}}
.vg-kpi.cf:active{background:var(--side) linear-gradient(var(--side-on),var(--side-on))}
.vg-kpi.cf .label,.vg-kpi.cf .kvar,.vg-kpi.cf .kvsub,.vg-kpi.cf .foot{color:var(--side-text)}
.vg-kpi.cf .value{color:var(--side-ink)}
.vg-kpi.cf .kvar.pos{color:#4cc79a} /* o --in do tema escuro: o cartão é azul-noite nos dois temas, e o verde do claro não se lê sobre ele */
.vg-kpi.cf .kvar.neg{color:#ff9a62} /* o --out do tema escuro, pela mesma razão */
.vg-kpi.cf .ksilhueta{color:var(--side-muted)}
:root.dark .vg-kpi.cf{background:var(--accent-soft);border-color:var(--line2)}
@media(hover:hover) and (pointer:fine){:root.dark .vg-kpi.cf:hover{background:var(--accent-soft) linear-gradient(var(--side-hover),var(--side-hover));border-color:var(--line2)}}
:root.dark .vg-kpi.cf:active{background:var(--accent-soft) linear-gradient(var(--side-on),var(--side-on))}
:root.dark .vg-kpi.cf .label,:root.dark .vg-kpi.cf .kvsub,:root.dark .vg-kpi.cf .foot{color:var(--accent-text)}
:root.dark .vg-kpi.cf .ksilhueta{color:var(--accent)}
@media(max-width:900px){
  .vg-kpi{gap:4px}
  .vg-kpi .label{font-size:13px;gap:6px;padding-right:40px}
  .vg-kpi .kdot{width:8px;height:8px;border-radius:2px;flex-basis:8px}
  .vg-kpi .value{font-size:min(21px,15cqi)}
  .vg-kpi .kserie .kvar,.vg-kpi .kserie .kvsub,.vg-kpi-extra{font-size:12px}
  .vg-kpi .kserie .ksilhueta{top:16px;right:14px;width:34px}
  .vg-kpi .foot{display:none}
}

/* --- O aviso âmbar das despesas sem imóvel --- */
.vg-aviso{display:flex;flex-wrap:wrap;align-items:center;gap:10px 14px;padding:12px 16px;margin-top:14px;background:var(--warn-soft);border-color:color-mix(in srgb,var(--warn) 24%,var(--warn-soft))}
.cw-blk>.vg-aviso{margin-top:0}
.vg-aviso p{flex:1 1 220px;margin:0;min-width:0}
.vg-aviso strong{font-weight:650}
.vg-aviso-ic{display:inline-flex;color:var(--warn);flex:0 0 auto;align-self:flex-start;margin-top:1px}

/* --- Os gráficos --- */
/* a leitura acesa antes de alguém tocar (graficos.js:cabecaDaLeitura com ler) */
.chartler.fixa .chartlido{opacity:1}
/* a legenda do donut diz o nome e a parte (o canvas): o valor de cada fatia
   espremia os nomes num terço de ecrã, e o total está no centro do anel */
.vg-cartao .donut .legend .vl{display:none}
/* num cartão largo (o tablet, onde o terço atravessa) a parte não foge para a
   outra ponta do ecrã, longe do nome */
.vg-cartao .donut .leg{max-width:420px}
/* «Percorre com o dedo» só num ecrã de dedo */
.vg-dedo{display:none}
@media(pointer:coarse){.vg-dedo{display:block}}
/* No telemóvel o desenho de 360 unidades encolhe para ~328px, e os rótulos a
   9 (meses e eixo) ficavam com 8,2px; a 11,5 dão ~10,5px, os meses do canvas.
   O CSS ganha ao atributo font-size do SVG; o donut fica de fora, que o total
   dele (15) encolhia. No computador o desenho cresce e os 9 já dão ~13px. */
@media(max-width:900px){.vg-cartao .chartbox:not(.pie) svg text{font-size:11.5px}}

/* --- O Portefólio: uma grelha de números no computador, linhas no telemóvel --- */
.vg-port{display:grid;grid-template-columns:repeat(auto-fill,minmax(150px,1fr));gap:16px 20px}
.vg-port .stat{display:flex;flex-direction:column;justify-content:flex-start;gap:2px;padding:0;border:0;font-size:13px;min-width:0}
.vg-port .stat>span:first-child{color:var(--muted)}
.vg-port .stat b{font-family:var(--letra-titulo);font-size:22px;font-weight:650;letter-spacing:-.015em;line-height:1.2;font-optical-sizing:auto;overflow-wrap:anywhere}
.vg-port .stat b .small{font-family:var(--letra);font-size:13px;font-weight:400;letter-spacing:0}
.vg-port .stat.vg-so-estreito{display:none}
.vg-port-nota{font-size:12px}
/* Os valores de cada fila na mesma linha, mesmo com um rótulo partido em duas
   («Renda líquida de impostos (estim.)» descia o valor 19px) ou com a nota das
   mais-valias por baixo: cada número ocupa três linhas da grelha (rótulo,
   valor, nota) e partilha-as com os vizinhos (subgrid). O espaço entre filas
   passa a ser o padding de baixo; a margem negativa tira-o à última. */
@media(min-width:901px){
  .vg-port{row-gap:0;margin-bottom:-16px}
  .vg-port .stat{display:grid;grid-row:span 3;grid-template-rows:subgrid;row-gap:2px;align-content:start;padding-bottom:16px}
}
@media(max-width:900px){
  .vg-port{display:block}
  .vg-port .stat{flex-direction:row;justify-content:space-between;align-items:baseline;gap:12px;padding:10px 0;border-top:1px solid var(--line);font-size:14.5px}
  .vg-port .stat b{font-family:var(--letra);font-size:14.5px;font-weight:600;letter-spacing:0;text-align:right}
  .vg-port .stat.vg-so-largo{display:none}
  .vg-port .stat.vg-so-estreito{display:flex}
  .vg-nota.vg-so-largo{display:none}
}

/* --- As contas entre proprietários --- */
.vg-saldos{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(200px,100%),1fr));gap:12px}
.vg-saldo{padding:14px;border-radius:12px;background:var(--chip);min-width:0}
.vg-saldo p{margin:0}
.vg-saldo-nome{font-weight:600;overflow-wrap:anywhere}
.vg-saldo-valor{font-weight:700;font-size:18px;color:var(--muted)}
.vg-saldo.in{background:var(--in-soft)}
.vg-saldo.in .vg-saldo-valor{color:var(--in)}
.vg-saldo.out{background:var(--out-soft)}
.vg-saldo.out .vg-saldo-valor{color:var(--out)}
.vg-plano{display:flex;flex-wrap:wrap;align-items:center;gap:12px;padding:12px 14px;border:1px dashed var(--line2);border-radius:12px}
.vg-plano p{flex:1 1 220px;margin:0;display:flex;flex-direction:column;gap:2px;min-width:0}
.vg-plano b{font-weight:650}
.vg-contas>p.small{margin:0}
.vg-acertos{display:flex;flex-direction:column;gap:4px}
.vg-acertos .lbl{margin:0 0 2px}
.vg-acerto{display:flex;justify-content:space-between;gap:12px;font-size:14px}
.vg-acerto b{font-weight:600;flex:0 0 auto}
/* «Pedidos e atividade»: as linhas dos pedidos (cloud/painel.js:pedidosNaPilha)
   no cimo do cartão da atividade; a última não perde o ar de baixo, porque a
   atividade vem a seguir */
.vg-pedidos-linhas{margin-top:-4px}
.pd-lista.vg-pedidos-linhas>.pd-linha:last-child{padding-bottom:12px}
/* ===== fim: 1.3.1 ===== */
/* ===== redesign: 1.3.2 — os Imóveis ===== */
/* web/app/lista-imoveis.js, web/app/imovel.js, web/app/tarefas.js e a secção
   dos proprietários de web/cloud/utilizadores.js: a lista (prancheta M-Casas),
   a ficha (M-Imovel) e o formulário (M-NovoImovel). No computador a lista é
   uma grelha de cartões e a ficha uma janela larga com os cartões em duas
   colunas — a mesma família, sem prancheta própria. */

/* O mosaico das capas sem fotografia (o .tile do canvas): um arco em cada um
   de dois cantos opostos e um ponto ao meio, num quadrado de 28px que se
   repete. Quatro cores, as do contrato do redesign (§4: cobalto, âmbar, verde,
   ardósia), escolhidas pelo imóvel de forma estável (lista-imoveis.js:imvMosaico).
   Os hex do claro são os do canvas e só vivem aqui: um mosaico é um desenho,
   não uma superfície da app, e não há token para ele. No escuro saem dos
   tokens suaves e de cor, para não acender um pastel claro no meio do ecrã. */
.imv-mosaico{--imv-fundo:#dce4fb;--imv-traco:#3a5fd6;background-color:var(--imv-fundo);
  background-image:radial-gradient(circle at 0 0,transparent 12px,var(--imv-traco) 12.5px,var(--imv-traco) 15px,transparent 15.5px),
    radial-gradient(circle at 100% 100%,transparent 12px,var(--imv-traco) 12.5px,var(--imv-traco) 15px,transparent 15.5px),
    radial-gradient(circle at 50% 50%,var(--imv-traco) 2.5px,transparent 3px);background-size:28px 28px}
.imv-t1{--imv-fundo:#fae6d2;--imv-traco:#b65a16} /* âmbar do mosaico (canvas, contrato §4) */
.imv-t2{--imv-fundo:#d9efe5;--imv-traco:#1e7a5b} /* verde do mosaico (canvas, contrato §4) */
.imv-t3{--imv-fundo:#e3e6ec;--imv-traco:#5b6478} /* ardósia do mosaico (canvas, contrato §4) */
:root.dark .imv-t0{--imv-fundo:var(--accent-soft);--imv-traco:var(--accent)}
:root.dark .imv-t1{--imv-fundo:var(--warn-soft);--imv-traco:var(--warn)}
:root.dark .imv-t2{--imv-fundo:var(--in-soft);--imv-traco:var(--in)}
:root.dark .imv-t3{--imv-fundo:var(--chip);--imv-traco:var(--faint)}
/* A etiqueta por cima de uma fotografia (quantas fotos, «capa»): escura nos
   dois temas, porque assenta numa imagem e não numa superfície da app — o véu
   do canvas, rgba(14,24,48,.78), que é o --side a 78%. */
.imv-nfotos{position:absolute;left:6px;bottom:6px;z-index:1;padding:1px 6px;border-radius:6px;background:rgba(14,24,48,.78);color:#fff;font-size:11px;font-weight:600;font-variant-numeric:tabular-nums;line-height:1.5}
/* Só para leitores de ecrã (o estado de uma tarefa na ficha, que a caixa desenha). */
.imv-so-leitor{position:absolute;width:1px;height:1px;margin:-1px;padding:0;overflow:hidden;clip-path:inset(50%);white-space:nowrap;border:0}

/* --- a lista (lista-imoveis.js:vProperties) --- */
/* As ações rápidas da ficha (imovel.js:imvAcoesRapidas): uma fila de chips
   que desliza de lado no telemóvel e que, no computador, cabe inteira. O
   enchimento à volta deixa o anel do foco por inteiro dentro da fila que
   corta. */
.imv-acoes{flex-wrap:nowrap;overflow-x:auto;scrollbar-width:none;padding:4px;margin:-4px}
.imv-acoes::-webkit-scrollbar{display:none}
/* No dedo, o chip cresce dos 36px do desenho para os 40 (os das ações
   rápidas do canvas, e o mínimo do .btn.sm), e a área de toque chega aos 44:
   dois pixéis por cima e por baixo, invisíveis. */
.imv-acoes>.chip{position:relative;flex:0 0 auto}
/* o «Movimentos · N» da ficha vai à frente e a cheio, no cobalto do que se
   carrega (imovel.js:imvAcoesRapidas): os outros chips são ações, este é o
   caminho que mais se procura */
.imv-acoes .chip.destaque{background:var(--accent);border-color:var(--accent);color:var(--accent-ink);font-weight:600}
@media(hover:hover) and (pointer:fine){.imv-acoes .chip.destaque:hover{background:var(--accent);filter:brightness(1.08)}}
@media(pointer:coarse){.imv-acoes>.chip{min-height:40px}
  .imv-acoes>.chip::after{content:"";position:absolute;left:0;right:0;top:-2px;bottom:-2px}
  .imv-ficha .btn.sm,.imv-form .btn.sm{min-height:44px}
  /* o botão só de ícone (o apagar de uma hipoteca) chega aos 44 também de
     largura: a base dá 36 ao .btn.sm.so-icone */
  .imv-ficha .btn.sm.so-icone,.imv-form .btn.sm.so-icone{width:44px}}
.list.imv-lista{gap:12px}
@media(min-width:900px){.list.imv-lista{grid-template-columns:repeat(auto-fill,minmax(400px,1fr));gap:14px}}
/* O cartão: a capa à esquerda, da altura do cartão, e o texto à direita. */
.card.imv-card{display:grid;grid-template-columns:84px minmax(0,1fr);gap:12px;padding:12px;align-items:stretch}
@media(min-width:900px){.card.imv-card{grid-template-columns:112px minmax(0,1fr);gap:14px;padding:14px}}
.imv-capa{position:relative;min-height:112px;border-radius:12px;overflow:hidden}
.imv-capa img,.imv-fcapa img,.imv-gfoto img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
.imv-corpo{display:flex;flex-direction:column;gap:6px;min-width:0}
.card .imv-topo{gap:8px}
.imv-topo>.badge{flex:0 0 auto}
#raiz .card .imv-topo>div:first-child>.imv-nome{white-space:normal;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden;
  font-family:var(--letra-titulo);font-size:17px;font-weight:650;letter-spacing:-.015em;line-height:1.25}
.imv-morada{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.imv-nums{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:6px;font-variant-numeric:tabular-nums}
.imv-kv{display:flex;flex-direction:column;min-width:0}
.imv-kv>span{font-size:11.5px;color:var(--muted)}
.imv-kv b{font-size:14px;font-weight:600;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.imv-selos{display:flex;flex-wrap:wrap;gap:6px}

/* --- a ficha (imovel.js:propFicha) --- */
/* No computador a janela da ficha alarga para os cartões irem em duas colunas. */
@media(min-width:900px){.sheet:has(.imv-ficha){width:min(940px,calc(100vw - 48px))}}
.imv-ficha{display:flex;flex-direction:column;gap:12px}
/* A capa ocupa a largura toda da janela, colada ao cabeçalho: tira o
   enchimento do corpo (.sheet .body, 18px 20px). */
.imv-fcapa{position:relative;flex:0 0 auto;height:190px;margin:-18px -20px 2px;overflow:hidden}
@media(min-width:900px){.imv-fcapa{height:240px}}
.imv-fotos-btn{position:absolute;right:12px;bottom:12px;z-index:1;display:inline-flex;align-items:center;gap:6px;min-height:36px;padding:0 12px;border:0;border-radius:999px;
  background:rgba(14,24,48,.82);color:#fff;font:inherit;font-size:13px;font-weight:600;cursor:pointer;transition:transform var(--rapido) var(--curva)} /* o véu da etiqueta da foto (.imv-nfotos), mais cheio para ser botão */
@media(hover:hover) and (pointer:fine){.imv-fotos-btn:hover{background:rgba(14,24,48,.9)}}
.imv-fotos-btn:active{background:rgba(14,24,48,.97);transform:scale(.97)}
.imv-fotos-btn:focus-visible{outline:2px solid #fff;outline-offset:2px} /* branco: o anel assenta na fotografia */
@media(pointer:coarse){.imv-fotos-btn{min-height:44px}}
.imv-ftopo{display:flex;flex-direction:column;gap:8px}
.imv-fmorada{margin:0;font-size:15px;color:var(--muted)}
.imv-donos{margin:0;font-size:14px;color:var(--ink)}
.imv-nota{padding:12px 14px;border-radius:14px;background:var(--chip);color:var(--ink)}
.imv-nota-podes{display:block;margin-top:4px;color:var(--muted)}
.card.imv-numeros{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:14px;padding:14px}
@media(min-width:900px){.card.imv-numeros{grid-template-columns:repeat(auto-fit,minmax(150px,1fr));padding:18px}}
.imv-cel{display:flex;flex-direction:column;gap:2px;min-width:0}
.imv-cel b{font-size:20px;line-height:1.2;overflow-wrap:anywhere}
.imv-cel b .small{font-family:var(--letra);font-weight:500;letter-spacing:0}
.imv-grelha{display:flex;flex-direction:column;gap:12px}
@media(min-width:900px){.imv-grelha{display:block;columns:2;column-gap:14px}.imv-grelha>.card{break-inside:avoid;margin-bottom:14px}}
.card.imv-sec{padding:0;overflow:hidden}
.imv-sec-cab{display:flex;align-items:baseline;justify-content:space-between;gap:8px;padding:14px 14px 8px}
.imv-sec-cab h3{margin:0;font-size:16px;min-width:0}
.imv-sec-cab>.small{text-align:right}
.imv-sec-cab>.badge{align-self:center;flex:0 0 auto}
.imv-sec-corpo{display:flex;flex-direction:column;gap:10px;padding:2px 14px 14px}
.imv-sec-corpo p{margin:0}
/* Uma linha de um cartão da ficha (um quarto, um contrato, um por confirmar,
   uma despesa fixa, uma tarefa): 56px no mínimo, a do canvas. A que se toca
   tem o passar por cima, o premido e o anel por dentro. */
.imv-linha{display:flex;align-items:center;gap:12px;min-height:56px;padding:10px 14px;border-top:1px solid var(--line)}
.imv-linha.tap,.imv-pend>.imv-linha-txt.tap{cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.imv-linha.tap:hover,.imv-pend>.imv-linha-txt.tap:hover{background:var(--tint)}}
.imv-linha.tap:active,.imv-pend>.imv-linha-txt.tap:active{background:var(--press)}
.imv-linha.tap:focus-visible,.imv-pend>.imv-linha-txt.tap:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
/* Um por confirmar: o alvo de «rever» é o bloco do texto, que enche a linha
   até ao «Confirmar» (irmão dele, fora do alvo — um botão dentro de outro não
   se anuncia). O enchimento passa da linha para o bloco, para o passar por
   cima e o premido pintarem a linha toda menos o botão. */
.imv-linha.imv-pend{align-items:stretch;padding:0 14px 0 0}
.imv-pend>.imv-linha-txt{justify-content:center;padding:10px 0 10px 14px}
.imv-pend>.btn{align-self:center}
.imv-linha-txt{flex:1;min-width:0;display:flex;flex-direction:column;align-items:flex-start;gap:2px}
.imv-linha-txt>b{font-weight:600;overflow-wrap:anywhere}
.imv-linha-txt>.badge{margin-top:2px}
.imv-linha>b.num{white-space:nowrap;font-weight:600}
.imv-linha .seta{display:inline-flex;flex:0 0 auto;color:var(--faint);margin-right:-4px}
.imv-livre{flex-wrap:wrap}
.imv-livre>.imv-botoes{flex:1 0 100%}
.imv-botoes{display:flex;flex-wrap:wrap;gap:8px}
.imv-botoes>.btn{flex:1 1 auto}
.imv-par{display:grid;grid-template-columns:1fr 1fr;gap:10px}
.imv-par>div{display:flex;flex-direction:column;min-width:0}
.imv-par b{font-size:17px;font-weight:700}
.imv-par b .small{font-weight:500}
.imv-fixa-n{flex:1;min-width:0}
.imv-fixa>b{min-width:96px;text-align:right;white-space:nowrap}
.imv-rot{color:var(--ink);font-weight:600;margin-right:4px}
.imv-texto{margin:0;padding:2px 14px 14px;white-space:pre-wrap;overflow-wrap:anywhere;font-size:14px}
/* As tarefas na ficha (tarefas.js:tfCartaoDaFicha): a caixa é um desenho e
   não um campo — a ficha lê-se; marcar é na lista, a um toque. */
.tf-caixa{width:22px;height:22px;flex:0 0 22px;display:grid;place-items:center;border:1.5px solid var(--line2);border-radius:6px;background:var(--card);color:var(--accent-ink)}
.tf-fl.tf-feita .tf-caixa{background:var(--accent);border-color:var(--accent)}
.tf-fl-nome{flex:1;min-width:0;overflow-wrap:anywhere}
.tf-fl.tf-feita .tf-fl-nome{color:var(--muted);text-decoration:line-through}
.tf-fl-pe{display:flex;flex-wrap:wrap;justify-content:space-between;gap:4px;padding:4px 6px;border-top:1px solid var(--line)}
.btn.ghost.tf-fl-mais{color:var(--accent-text)}
/* A galeria das fotos (imovel.js:imvGaleria). */
.imv-galeria{display:grid;grid-template-columns:repeat(auto-fill,minmax(140px,1fr));gap:8px}
.imv-gfoto{position:relative;aspect-ratio:4/3;padding:0;border:0;border-radius:12px;overflow:hidden;background:var(--chip);cursor:pointer;transition:transform var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.imv-gfoto:hover{background:var(--tint)}}
.imv-gfoto:active{background:var(--press);transform:scale(.98)}
.imv-gfoto:focus-visible{outline:2px solid var(--accent);outline-offset:2px}

/* --- o formulário (imovel.js:propBody) --- */
.form.imv-form{gap:14px}
.sect.imv-grupo{gap:16px}
.imv-grupo>.imv-sec-cab{padding:0}
.imv-campo{display:flex;flex-direction:column;gap:7px;min-width:0}
.imv-campo>.flabel{margin:0}
.imv-2col{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:12px}
@media(max-width:360px){.imv-2col{grid-template-columns:1fr}}
/* O seguro e o mês dele: no telemóvel uma coluna só, porque o valor por
   omissão do menu («O mês em que o guardares») não cabe em meia coluna. */
@media(max-width:480px){.imv-2col.imv-2col-largo{grid-template-columns:1fr}}
/* As dobras do formulário (fotos, dados registais, anúncio): o título numa
   linha inteira e o resumo por baixo, como o canvas — lado a lado, no
   telemóvel, o resumo comia o título («Dados re…»). O resumo é uma nota e
   pode ficar com reticências. Só no formulário do imóvel: as dobras das
   outras folhas ficam como estão. */
.imv-form .fold-head{display:grid;grid-template-columns:34px minmax(0,1fr) auto;column-gap:10px;row-gap:2px}
.imv-form .fold-head .ic{grid-column:1;grid-row:1/span 2}
.imv-form .fold-head b{grid-column:2;grid-row:1;white-space:normal;overflow-wrap:anywhere}
.imv-form .fold-head .fsum{grid-column:2;grid-row:2;margin-left:0;text-align:left}
.imv-form .fold-head .chev{grid-column:3;grid-row:1/span 2}
.imv-colado{margin-top:-10px}
.imv-donos-lista{display:flex;flex-direction:column;gap:8px}
.imv-dono{display:flex;align-items:center;gap:10px}
.imv-dono-nome{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-weight:500}
/* A quota: o campo com o «%» dentro, à direita, como o canvas. */
.imv-pct{position:relative;flex:0 0 104px;width:104px}
.imv-pct input{padding-right:32px;text-align:right;font-variant-numeric:tabular-nums}
.imv-pct>span{position:absolute;right:12px;top:50%;transform:translateY(-50%);color:var(--muted);font-size:13px;pointer-events:none}
.imv-quartos{display:flex;flex-direction:column;gap:8px}
.imv-quartos>.imv-mais{align-self:flex-start}
.imv-grupo>.btn.imv-mais{width:100%}
.imv-frase{margin:-4px 0 0;display:flex;gap:6px;font-size:13px;color:var(--accent-text)}
.cw-donos-quotas .stat:first-child{padding-top:0}
/* O telemóvel de «O meu perfil» (cloud/utilizadores.js:injectPhoneCountry): o
   menu do indicativo (componentes.js:sel) à esquerda e o número à direita. */
.cw-tel{display:flex;gap:8px;min-width:0}
.cw-tel>.sel{flex:0 1 auto;width:auto;max-width:60%}
.cw-tel>input{flex:1;min-width:0}
/* a lista dos países é mais larga do que o botão: «+239 São Tomé e Príncipe» */
.cw-tel .selpop{right:auto;min-width:min(260px,80vw)}
/* ===== fim: 1.3.2 ===== */
/* ===== ajustes-v40c: 1.1 — o formulário e a ficha do imóvel ===== */
/* A caixa que cresce ou encolhe (continuidade.js:crescerEmAltura). Durante a
   viagem a altura dela é a animada; a encolher é maior do que o que já leva
   dentro, e numa grelha (o .sect do formulário do imóvel) a altura a mais
   repartia-se pelas linhas — o nome descia 70px, a morada 210px, o
   segmentado 280px, e voltavam. Encostadas ao topo, as linhas que ficam não
   se mexem e só a borda de baixo sobe. */
.a-crescer{align-content:start}
/* o sítio de onde se medem as peças que saem, postas de volta por cima a
   desvanecer (continuidade.js:acompanharPartes) */
.tem-saidas{position:relative}
/* O realce de um segmentado no escuro: era o --card (#141c2c), MAIS escuro do
   que a pista (--chip, #1a2335), e com uma sombra que no escuro não se vê —
   «o slider desapareceu». Passa ao --line2 (#33405c), 1.52:1 contra a pista,
   sem a sombra; o mesmo para o aceso de todos os segmentados, que tinham o
   mesmo defeito (o tipo do movimento, o tema, as abas da área). No claro fica
   o de sempre: o branco com a sombra sobre a pista clara, como o resto da
   app. */
:root.dark .segm.desliza>.segm-polegar,
:root.dark .segm>.on,:root.dark .segm>[aria-checked="true"],:root.dark .segm>[aria-current="page"],:root.dark .segm>[aria-selected="true"]{background:var(--line2);box-shadow:none}
:root.dark .segm.desliza>.on,:root.dark .segm.desliza>[aria-checked="true"],:root.dark .segm.abas-pessoas>.on{background:transparent}
/* A capa da ficha com fotos abre a galeria (imovel.js:imvCapaDaFicha): um
   botão a cobri-la, por baixo do «N fotos» (que tem z-index 1) e por cima da
   fotografia, que o paintThumbs mete antes dele. O premido escurece a capa
   com o véu das janelas; o passar por cima, só com rato, menos. */
.imv-capa-abre{position:absolute;inset:0;width:100%;height:100%;margin:0;padding:0;border:0;background:transparent;cursor:pointer;-webkit-tap-highlight-color:transparent}
.imv-capa-abre::after{content:"";position:absolute;inset:0;background:var(--veu);opacity:0;transition:opacity var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.imv-capa-abre:hover::after{opacity:.15}}
.imv-capa-abre:active::after{opacity:.3}
/* o anel por dentro, com uma margem da cor do cartão: assenta em qualquer fotografia */
.imv-capa-abre:focus-visible{outline:2px solid var(--accent);outline-offset:-6px;box-shadow:inset 0 0 0 4px var(--card)}
/* ===== fim: ajustes-v40c 1.1 ===== */
/* ===== ajustes-v40d: 1.1 — o realce dos segmentados em qualquer escuro ===== */
/* A escolha acesa de um segmentado: um contorno de 2px no cobalto, o fundo
   --accent-soft e o texto --accent-text — o desenho do .chip.on e do .opt.on.
   O realce era só luz: o branco sobre a pista quase branca, e no escuro o
   --line2 sobre o --chip (1.52:1). O Samsung Internet, com o telemóvel em
   escuro, responde prefers-color-scheme:light e escurece a página à força sem
   olhar ao color-scheme: inverte a luz dos fundos, e o branco do realce e o
   quase branco da pista caíam em dois pretos iguais. Para esse filtro o
   contorno é cor da frente, e passa a um azul claro sobre a pista escurecida
   (3.3:1 medido no Chromium com o escurecimento forçado): a diferença está no
   matiz e na luz, e não num cinzento quase igual ao outro. Uma sombra por
   dentro (inset) não servia: o filtro não lhe toca, e o cobalto escuro sobre a
   pista escurecida fica a 2.5:1.
   Vale em todos os segmentados (o tipo do movimento, o Tema, as abas da área,
   a entrada, as categorias, o titular A/B, o pedido de ajuda), menos nas abas
   sublinhadas das Pessoas, que já são um traço; e nos dois temas: as regras
   do :root.dark da secção de cima pesam o mesmo e ficam antes destas. Um
   segmentado pode dar outra cor ao texto aceso pela variável --segm-texto
   (o tipo do movimento, abaixo); o contorno é sempre o cobalto.
   O contorno é um ::after por cima do botão, e não a borda dele: a borda
   comia 4px à largura do texto, e piorava as reticências que os segmentados
   apertados já tinham a 375px (a regra seguinte). */
.segm:not(.abas-pessoas):not(.desliza)>.on,.segm:not(.abas-pessoas):not(.desliza)>[aria-checked="true"],
.segm:not(.abas-pessoas):not(.desliza)>[aria-current="page"],.segm:not(.abas-pessoas):not(.desliza)>[aria-selected="true"]{
  position:relative;background:var(--accent-soft);color:var(--segm-texto,var(--accent-text));box-shadow:none}
.segm:not(.abas-pessoas):not(.desliza)>.on::after,.segm:not(.abas-pessoas):not(.desliza)>[aria-checked="true"]::after,
.segm:not(.abas-pessoas):not(.desliza)>[aria-current="page"]::after,.segm:not(.abas-pessoas):not(.desliza)>[aria-selected="true"]::after{
  content:"";position:absolute;inset:0;border:2px solid var(--accent);border-radius:inherit;pointer-events:none}
/* O aceso escreve-se a 600 e fica mais largo do que os outros, e nos
   segmentados apertados não cabia: a 375px «Despes…», «Não declarad…» e o
   «Planeados» com o número perdiam o fim (já antes do contorno). As colunas
   ficam iguais (flex:1 1 0, a regra de base), e com flex:1 1 0 cada botão
   recebe a mesma largura de texto mais o seu enchimento: «Despesa» a 600 e
   14px (59px) não cabia num quinto da linha. Nos dois mais apertados (os
   cinco tipos do movimento; Por indicar, Declarado, Não declarado) a letra
   passa a 13px e o enchimento baixa em todos os botões do grupo; nas abas da
   área chega menos enchimento. */
.segm.mov-tipo-segm>button{font-size:13px;padding-left:3px;padding-right:3px}
.segm.ct-at-segm>button[type="button"]{font-size:13px;padding-left:1px;padding-right:1px}
.segm.abas-area>a{padding-left:6px;padding-right:6px}
/* O que desliza (imovel.js:imvSegmentado): o contorno e o fundo vão na peça
   que corre por baixo (.segm-polegar), e o botão aceso fica só com o texto.
   Os dois seletores, para o :root.dark da secção de cima não ganhar no escuro. */
.segm.desliza>.segm-polegar,:root.dark .segm.desliza>.segm-polegar{border:2px solid var(--accent);background:var(--accent-soft);box-shadow:none}
.segm.desliza>.on,.segm.desliza>[aria-checked="true"]{color:var(--accent-text)}
/* O tipo do movimento: o realce no cobalto, como os outros, e o texto na cor
   do dinheiro dele (movimento.js:txTipoSegm, lista-movimentos.js:txTomDoTipo)
   — a receita verde, a despesa laranja, a prestação roxa; a dívida e a
   transferência no --accent-text. O contorno não muda de cor com o tipo: no
   escurecimento forçado o verde e o laranja ficam escuros (2.1:1 e 2.7:1
   contra a pista, medido), e o cobalto fica claro. */
.mov-tipo-segm>button.on.pos{--segm-texto:var(--in)}
.mov-tipo-segm>button.on.neg{--segm-texto:var(--out)}
.mov-tipo-segm>button.on.prest{--segm-texto:var(--loan)}
/* A nota do Samsung Internet na linha do Tema (definicoes.js:linhaDoTema):
   texto pequeno por baixo do segmentado, alinhado com ele */
.def-tema-samsung{margin:0;font-size:13px;line-height:1.45;color:var(--muted)}
.def-tema-samsung b{font-weight:600;color:var(--ink)}
/* ===== fim: ajustes-v40d 1.1 ===== */
/* ===== redesign: 1.3.3 — os Contratos ===== */
/* web/app/lista-contratos.js, web/app/contrato.js e web/app/contrato-pdf.js:
   a lista (pranchetas M-Contratos e D-Contratos), a ficha (M-Contrato), o
   formulário (M-NovoContrato) e a folha do contrato em PDF (M-ContratoPDF).
   A lista é um HTML só: no telemóvel linhas dentro de um cartão por imóvel; a
   partir de 1100px uma tabela, com as mesmas peças em colunas. */

/* --- a lista (lista-contratos.js:vContracts) --- */

/* Um grupo por imóvel: o nome na letra dos títulos, o que é, e a renda do mês
   à direita; as linhas num cartão. */
.list.ct-lista{display:flex;flex-direction:column;gap:16px}
.ct-grupo{display:flex;flex-direction:column;gap:8px;min-width:0}
.ct-grupo-cab{display:flex;align-items:baseline;gap:8px;min-width:0;padding:4px 2px 0}
.ct-grupo-nome{margin:0;min-width:0;font-family:var(--letra-titulo);font-size:16px;font-weight:650;letter-spacing:-.015em;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.ct-grupo-desc{flex:1 1 auto;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.ctrenda{flex:0 0 auto;margin-left:auto;font-size:13px;color:var(--muted);white-space:nowrap}
.list.ct-linhas{display:block;background:var(--card);border:1px solid var(--line);border-radius:16px;overflow:hidden}
.ct-linha{position:relative;min-width:0}
.ct-linha+.ct-linha{border-top:1px solid var(--line)}
.ct-linha.sel-on-card{background:var(--accent-soft)}
/* A linha que se toca (a de dentro): 64px no mínimo, o passar por cima, o
   premido e o anel por dentro. */
.row-between.ct-cols{align-items:center;gap:12px;min-height:64px;padding:12px 14px;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.ct-cols:hover{background:var(--tint)}}
.ct-cols:active{background:var(--press)}
.ct-cols:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.ct-cols>.selbox{padding:0}
.ct-c-quem{flex:1 1 auto;display:flex;flex-direction:column;gap:2px;min-width:0}
.ct-nome{font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.ct-sub{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.ct-selos{display:flex;flex-wrap:wrap;gap:6px;margin-top:4px}
.ct-c-renda{flex:0 0 auto;display:flex;flex-direction:column;align-items:flex-end;text-align:right;font-variant-numeric:tabular-nums}
.ct-c-renda b{font-weight:600;white-space:nowrap}
.ct-c-per,.ct-c-imp,.ct-c-liq,.ct-c-at,.ct-c-seta,.ct-cab{display:none}
/* O bloco dos por confirmar que a nuvem pendura no fim de cada linha
   (cloud/painel.js:decoratePending): as linhas do cartão dos Planeados num
   quadro da superfície 2, por baixo do contrato, alinhado com o texto. */
.ct-linha>.cw-pend{margin:0 14px 12px;padding:0 12px;border-radius:12px;background:var(--chip)}
.ct-linha>.cw-pend .cw-pend-tit{padding:10px 0 2px}
.ct-linha>.cw-pend .plan-pend-linha:first-of-type{border-top:0}
.ct-sem-vigor,.ct-dica-sel{margin:12px 2px 0}
.ct-ligacao{min-height:32px;padding:0 2px;border:0;background:transparent;color:var(--accent-text);font:inherit;font-weight:600;cursor:pointer;text-decoration:underline;text-underline-offset:2px}
.ct-ligacao:focus-visible{outline:2px solid var(--accent);outline-offset:2px;border-radius:6px}
@media(pointer:coarse){.ct-ligacao{min-height:44px}}
.ct-dica-sel{display:none}

/* No computador, a tabela (D-Contratos): um cartão só, o cabeçalho das
   colunas, o imóvel numa faixa da superfície 2 e uma fila por contrato. As
   colunas são áreas com nome: em seleção entra a da caixa à cabeça. Abaixo
   de ~1360px a tabela rola de lado dentro do cartão, como o canvas. */
@media(min-width:1100px){
  .ct-tabela{background:var(--card);border:1px solid var(--line);border-radius:16px;overflow-x:auto}
  .ct-cab,.list.ct-lista{min-width:980px}
  .ct-cab,.row-between.ct-cols{display:grid;grid-template-columns:minmax(0,1.6fr) minmax(0,1.5fr) 112px 128px 112px minmax(0,1.4fr) 24px;
    grid-template-areas:"quem per renda imp liq at seta";align-items:center;column-gap:12px;row-gap:0;padding:8px 16px}
  body.sel-on .ct-cab,body.sel-on .row-between.ct-cols{grid-template-columns:28px minmax(0,1.6fr) minmax(0,1.5fr) 112px 128px 112px minmax(0,1.4fr) 24px;
    grid-template-areas:"sel quem per renda imp liq at seta"}
  .ct-cab{min-height:42px;font-size:12px;font-weight:600;letter-spacing:.04em;text-transform:uppercase;color:var(--muted)}
  .ct-cab>span{display:block}
  .ct-cols>.selbox{grid-area:sel}
  .ct-c-quem{grid-area:quem}.ct-c-per{grid-area:per}.ct-c-renda{grid-area:renda}.ct-c-imp{grid-area:imp}.ct-c-liq{grid-area:liq}.ct-c-at{grid-area:at}.ct-c-seta{grid-area:seta}
  .ct-so-estreito{display:none}
  .list.ct-lista{gap:0}
  .ct-grupo{gap:0}
  .ct-grupo-cab{align-items:center;gap:10px;padding:12px 16px;background:var(--chip);border-top:1px solid var(--line)}
  .ct-grupo-nome{font-family:var(--letra);font-size:15px;letter-spacing:0}
  .ctrenda{font-size:14.5px;font-weight:600;color:var(--ink);font-variant-numeric:tabular-nums}
  .list.ct-linhas{background:transparent;border:0;border-radius:0;overflow:visible}
  .ct-linha{border-top:1px solid var(--line)}
  .row-between.ct-cols{font-size:14.5px}
  .ct-c-per{display:flex;flex-direction:column;align-items:flex-start;gap:4px;min-width:0;font-variant-numeric:tabular-nums}
  .ct-c-imp{display:flex;flex-direction:column;min-width:0;font-variant-numeric:tabular-nums}
  .ct-c-imp .small{font-size:12px}
  .ct-c-liq{display:block;text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}
  .ct-cab .ct-c-renda,.ct-cab .ct-c-liq{text-align:right}
  .ct-c-at{display:flex;flex-wrap:wrap;gap:6px;min-width:0}
  .ct-c-seta{display:flex;justify-content:flex-end;color:var(--faint)}
  .ct-linha>.cw-pend{margin:0 16px 12px}
  .ct-dica-sel{display:block}
}

/* --- a ficha (contrato.js:ctFicha) --- */
@media(min-width:900px){.sheet:has(.ct-ficha){width:min(900px,calc(100vw - 48px))}}
.ct-ficha{display:flex;flex-direction:column;gap:12px}
.ct-recusa{margin:0;padding:12px 14px;border-radius:14px;background:var(--chip);color:var(--ink);font-size:14px}
.ct-topo{display:flex;flex-direction:column;gap:8px}
.ct-topo-selos{display:flex;flex-wrap:wrap;align-items:center;gap:8px}
.ct-onde{margin:0;font-size:15px;color:var(--muted)}
.ct-periodo{display:flex;justify-content:space-between;align-items:baseline;gap:8px;margin-top:4px;font-size:13.5px;font-variant-numeric:tabular-nums}
.ct-barra{height:8px;border-radius:4px;background:var(--line);overflow:hidden}
.ct-barra-feita{display:block;width:0;height:100%;border-radius:4px;background:var(--accent)}
.ct-periodo-so,.ct-op{margin:0}
.ct-op b{color:var(--ink)}
/* O cartão de um prazo: o fundo suave da cor do selo (âmbar, vermelho ou a
   superfície 2), o ícone na cor, o selo do que falta em branco por cima. */
.ct-prazo{display:flex;flex-direction:column;gap:10px;padding:14px;border-radius:16px;border:1px solid var(--line)}
.ct-prazo-amber{background:var(--warn-soft);border-color:color-mix(in srgb,var(--warn) 24%,var(--warn-soft))}
.ct-prazo-red{background:var(--danger-soft);border-color:color-mix(in srgb,var(--danger) 22%,var(--danger-soft))}
.ct-prazo-grey{background:var(--chip)}
.ct-prazo-cab{display:flex;align-items:center;gap:8px}
.ct-prazo-ic{display:inline-flex;flex:0 0 auto;color:var(--muted)}
.ct-prazo-amber .ct-prazo-ic,.ct-prazo-amber .badge.ct-prazo-quando{color:var(--warn)}
.ct-prazo-red .ct-prazo-ic,.ct-prazo-red .badge.ct-prazo-quando{color:var(--danger)}
.ct-prazo-tit{flex:1;min-width:0;margin:0;font-weight:700}
.badge.ct-prazo-quando{flex:0 0 auto;background:var(--card);color:var(--muted)}
.ct-prazo-txt{margin:0;font-size:14px}
.ct-prazo-acoes{display:flex;gap:8px}
.ct-prazo-acoes>.btn:not(.so-icone){flex:1 1 0}
.ct-prazo-acoes>.ct-silenciar{margin-left:auto}
@media(min-width:900px){.ct-prazo-acoes>.btn:not(.so-icone){flex:0 1 auto;min-width:140px}}
/* Os cartões: o título com o selo à direita, as linhas rótulo/valor com o
   traço entre elas. */
.card.ct-sec{padding:0;overflow:hidden}
.ct-sec-cab{display:flex;align-items:baseline;justify-content:space-between;gap:8px;padding:14px 14px 6px}
.ct-sec-cab h3{margin:0;min-width:0;font-size:16px}
.ct-sec-cab>.badge{align-self:center;flex:0 0 auto}
.ct-sec-corpo{display:flex;flex-direction:column}
.ct-kv{display:flex;justify-content:space-between;gap:12px;padding:10px 14px;border-top:1px solid var(--line);font-size:14.5px;font-variant-numeric:tabular-nums}
.ct-sec-corpo>.ct-kv:first-child,.ct-sec-kv>.ct-kv:first-child{border-top:0}
.ct-kv>span{color:var(--muted)}
.ct-kv>b{min-width:0;text-align:right;font-weight:500;overflow-wrap:anywhere}
.ct-sec-corpo>.hint{margin:0;padding:2px 14px 14px}
.ct-nota{padding:10px 14px;border-top:1px solid var(--line);font-size:13px;line-height:1.5;color:var(--muted)}
.ct-nota b{color:var(--ink)}
/* Os três números: cada coluna da largura do que diz (a frase do imposto
   parte-se), e o espaço que sobra entre elas. */
.ct-tres{display:grid;grid-template-columns:repeat(3,auto);justify-content:space-between;gap:8px 12px;padding:14px}
.ct-tres>div{display:flex;flex-direction:column;min-width:0}
.ct-tres b.disp{font-size:19px;line-height:1.25;font-variant-numeric:tabular-nums;white-space:nowrap}
.ct-tres .small+b+.small{font-size:11.5px}
.ct-sem-renda{margin:0;padding:14px}
.ct-botoes{display:flex;gap:8px;padding:12px 14px 14px;border-top:1px solid var(--line)}
.ct-botoes>.btn{flex:1 1 0}
.ct-pessoa{display:flex;align-items:center;gap:12px;padding:8px 14px 12px}
.ct-pessoa+.ct-pessoa{padding-top:12px;border-top:1px solid var(--line)}
.avatar.ct-av{width:40px;height:40px;flex:0 0 40px;font-size:14px}
.ct-pessoa-txt{flex:1;min-width:0;display:flex;flex-direction:column;align-items:flex-start;gap:2px}
.ct-pessoa-txt>b{font-weight:600;overflow-wrap:anywhere}
.ct-pessoa-txt a{max-width:100%;color:var(--accent-text);overflow-wrap:anywhere}
/* o telefone e o email são as portas para ligar e escrever: no dedo, cada
   um com a altura de um toque (a linha deles é só deles, contrato.js:
   ctInquilinosDaFicha) */
@media(pointer:coarse){.ct-pessoa-txt a{display:inline-flex;align-items:center;min-height:44px}}
.ct-pessoa-selos{display:flex;flex-wrap:wrap;gap:6px;margin-top:4px}
.ct-iban{user-select:text;-webkit-user-select:text}
.ct-tarefas{padding:0 14px 14px;font-size:13px;color:var(--muted)}
.ct-notas{padding:0 14px 14px;font-size:14px;overflow-wrap:anywhere}
.ct-minis{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:8px}
.ct-mini{display:flex;flex-direction:column;align-items:flex-start;gap:2px;min-width:0;min-height:60px;padding:12px;border:1px solid var(--line);border-radius:12px;background:var(--card);color:var(--ink);font:inherit;text-align:left;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.ct-mini:hover{background:var(--tint)}}
.ct-mini:active{background:var(--press)}
.ct-mini:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
.ct-mini b{font-weight:600;font-variant-numeric:tabular-nums}
.btn.ct-gerar-pdf{width:100%}
.ct-grelha{display:flex;flex-direction:column;gap:12px}
@media(min-width:900px){.ct-grelha{display:block;columns:2;column-gap:14px}.ct-grelha>*{break-inside:avoid;margin-bottom:14px}}
@media(pointer:coarse){.ct-ficha .btn.sm,.ct-pdf .btn.sm{min-height:44px}.ct-ficha .btn.sm.so-icone{width:44px}}
/* A lista de um mosaico (contrato.js:ctVerAnexos). */
.ct-lista-anexos{display:flex;flex-direction:column}
.ct-lista-anexos>.ct-kv{padding:12px 0}
.ct-lista-anexos>.ct-kv:first-child{border-top:0}
.ct-fotos{display:grid;grid-template-columns:repeat(auto-fill,minmax(140px,1fr));gap:10px}
.ct-foto{display:flex;flex-direction:column;gap:4px;margin:0}
.ct-foto-img{position:relative;aspect-ratio:4/3;border-radius:12px;overflow:hidden;background:var(--chip)}
.ct-foto-img img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
.ct-anexo{display:flex;align-items:center;gap:10px;min-height:52px;padding:0 4px;border:0;border-top:1px solid var(--line);background:transparent;color:var(--ink);font:inherit;text-align:left;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
.ct-anexo:first-child{border-top:0}
.ct-anexo>span{flex:1;min-width:0;overflow-wrap:anywhere}
.ct-anexo>svg{flex:0 0 auto;color:var(--muted)}
@media(hover:hover) and (pointer:fine){.ct-anexo:hover{background:var(--tint)}}
.ct-anexo:active{background:var(--press)}
.ct-anexo:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}

/* --- o formulário (contrato.js:ctBody) --- */
.form.ct-form{gap:14px}
.sect.ct-gf{gap:16px}
.ct-gf-tit{margin:0;font-size:16px}
.ct-campo{display:flex;flex-direction:column;gap:7px;min-width:0}
.ct-campo>.flabel{margin:0}
.ct-colado{margin-top:-10px}
.ct-quartos .chip{min-height:40px}
.ct-quartos .chip.ct-ja:not(.on){background:var(--chip)}
/* 44px no dedo para tudo o que se toca no formulário: os botões pequenos
   (com .btn.sm.so-icone no seletor, para ganhar à largura de 36 que a base
   dá ao lixo do inventário e das chaves — como o .imv-form), os chips do
   quarto, o «+ Adicionar» dos inquilinos e, no × de cada inquilino (28px,
   da base), uma área de toque à volta sem lhe mudar o desenho. */
@media(pointer:coarse){
  .ct-form .btn.sm{min-height:44px}
  .ct-form .btn.sm.so-icone{width:44px}
  .ct-quartos .chip{min-height:44px}
  #c_tenants .tagadd{min-height:44px}
  #c_tenants .tag>button{position:relative}
  #c_tenants .tag>button::after{content:"";position:absolute;inset:-8px}
}
.ct-ja-txt{font-weight:400;color:var(--muted)}
.ct-quartos .chip.on .ct-ja-txt{color:inherit}
#c_tenants.err>.tagbox{border:2px solid var(--danger)}
.ct-dias>label{font-weight:500;color:var(--muted)}
.ct-net{display:flex;flex-direction:column;gap:2px;padding:12px 14px;border-radius:12px;background:var(--chip)}
.ct-net-linha{display:flex;justify-content:space-between;gap:12px;padding:4px 0;font-size:14px;font-variant-numeric:tabular-nums}
.ct-net-linha>span{min-width:0}
.ct-net-linha>b{font-weight:600;white-space:nowrap}
.ct-net-total{margin-top:4px;padding-top:8px;border-top:1px solid var(--line)}
.ct-net-total>b{font-size:16px}
/* Dois campos lado a lado, também no telemóvel (a prancheta): os campos
   alinham pelo fundo quando um rótulo parte em duas linhas, e a data perde
   um pouco de enchimento para o ícone do calendário caber a 390px. */
.ct-par{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));align-items:end;gap:12px}
.ct-par>label{min-width:0}
.ct-par input{min-width:0}
.ct-par input[type=date]{padding-left:10px;padding-right:8px}
@media(max-width:340px){.ct-par{grid-template-columns:1fr}}
/* O interruptor do formulário: a caixa de marcar da casa com o aspeto do
   .interruptor (46×28, ligado cobalto), dentro de um rótulo que se toca
   inteiro. */
label.ct-sw-linha{display:flex;align-items:center;gap:12px;min-height:44px;font-weight:400;cursor:pointer}
.ct-sw-txt{flex:1;min-width:0;display:flex;flex-direction:column;gap:2px}
.ct-sw-txt>b{font-weight:600}
.ct-form input.ct-sw{appearance:none;-webkit-appearance:none;position:relative;flex:0 0 46px;width:46px;height:28px;min-height:0;margin:0;padding:0;border:0;border-radius:999px;background:var(--line2);box-shadow:none;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
.ct-form input.ct-sw::after{content:"";position:absolute;top:3px;left:3px;width:22px;height:22px;border-radius:50%;background:var(--card);box-shadow:0 1px 2px rgba(16,24,40,.2);transition:transform var(--rapido) var(--curva)}
.ct-form input.ct-sw:checked{background:var(--accent)}
.ct-form input.ct-sw:checked::after{transform:translateX(18px)}
.ct-form input.ct-sw:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
.segm.ct-at-segm>button{padding:0 4px}
.ct-contacto{display:flex;flex-direction:column;gap:12px;min-width:0}
.ct-contacto+.ct-contacto{padding-top:16px;border-top:1px solid var(--line)}
.ct-contacto-cab{display:flex;flex-direction:column;gap:2px}
.ct-contacto-cab>b{font-size:14px;font-weight:600}
.ct-contacto-escolhido{padding:0}

/* --- a folha do contrato em PDF (contrato-pdf.js:ctPdfFicha) --- */
.ct-pdf{display:flex;flex-direction:column;gap:14px}
.ct-pdf-quem{margin:-6px 0 0}
.ct-pdf-topo{display:flex;align-items:stretch;gap:14px}
/* A miniatura do documento é papel: branca nos dois temas, com as linhas e o
   título nos cinzentos e na tinta do tema claro (o canvas). */
.ct-pdf-mini{display:flex;flex-direction:column;gap:5px;flex:0 0 128px;width:128px;height:176px;padding:12px 10px;border-radius:6px;background:#fff;box-shadow:0 6px 18px rgba(16,24,40,.16)} /* #fff: o papel, branco nos dois temas */
.ct-pdf-mini>p{margin:0;font-family:Georgia,'Times New Roman',serif;font-size:6.6px;font-weight:700;line-height:1.25;letter-spacing:.02em;text-align:center;text-transform:uppercase;color:#121826} /* a tinta do tema claro: é papel */
.ct-pdf-ln{display:block;height:5px;border-radius:2px;background:#d9dce2} /* o cinzento das linhas do papel (canvas) */
.ct-pdf-ln.ct-pdf-t{width:40%;height:4px;margin-top:4px;background:#9aa1b0} /* o cinzento dos títulos do papel (canvas) */
.ct-pdf-ln.ct-pdf-55{width:55%}.ct-pdf-ln.ct-pdf-70{width:70%}.ct-pdf-ln.ct-pdf-80{width:80%}.ct-pdf-ln.ct-pdf-90{width:90%}
.ct-pdf-faixa{display:block;height:18px;margin-top:auto;border-radius:3px;background:#e9eefc} /* o --accent-soft do tema claro: o total, no papel */
.ct-pdf-sobre{flex:1;min-width:0;display:flex;flex-direction:column;justify-content:center;gap:8px}
.ct-pdf-sobre p{margin:0}
.ct-pdf-modelo{font-weight:600}
.ct-pdf-ficheiro{font-size:12.5px;overflow-wrap:anywhere}
.card.ct-pdf-lista{padding:4px 14px 6px}
.ct-pdf-lista>.lbl{margin:0;padding:10px 0 6px}
.ct-pdf-ck{display:flex;align-items:flex-start;gap:10px;padding:10px 0;border-top:1px solid var(--line);font-size:14px}
.ct-pdf-ck>.btn{flex:0 0 auto}
.ct-pdf-ck-txt{flex:1;min-width:0}
.ct-pdf-ck-txt p{margin:0}
.ct-pdf-ic{display:grid;place-items:center;flex:0 0 22px;width:22px;height:22px;border-radius:50%}
.ct-pdf-ic svg{stroke-width:2.6}
.ct-pdf-ok{background:var(--in-soft);color:var(--in)}
.ct-pdf-wn{background:var(--warn-soft);color:var(--warn)}
.ct-pdf-mau{background:var(--danger-soft);color:var(--danger)}
.card.ct-pdf-bloqueio{border-color:color-mix(in srgb,var(--danger) 30%,var(--line))}
.ct-pdf-bloqueio>.lbl{color:var(--danger)}
.ct-pdf-nada{margin:0;padding:10px 0;border-top:1px solid var(--line)}
.ct-pdf-total{display:flex;align-items:center;gap:12px;padding:14px;border-radius:14px;background:var(--accent-soft);color:var(--accent-text);font-variant-numeric:tabular-nums}
.ct-pdf-total>div{flex:1;min-width:0}
.ct-pdf-total p{margin:0;font-size:13px}
.ct-pdf-total .small{font-size:12.5px;color:inherit}
.ct-pdf-total>b{font-size:20px;white-space:nowrap}
/* ===== fim: 1.3.3 ===== */
/* ===== redesign: 1.3.4 — as Pessoas e as Visitas ===== */
/* web/app/lista-pessoas.js, web/app/pessoas.js e web/app/visitas.js: as
   listas dos inquilinos e dos proprietários (prancheta M-Pessoas), as fichas
   (M-Inquilino, M-Proprietario), a lista das visitas (M-Visitas) e a ficha da
   visita (M-VisitaFicha). No computador a linha de uma pessoa ganha a coluna
   do contacto e as próximas e as passadas vão lado a lado — a mesma família,
   sem prancheta própria. */

/* --- os chips das ações rápidas (pessoas.js:pesFichaInquilino) ---
   Uma fila que desliza de lado no telemóvel e que, no computador, cabe
   inteira. O enchimento à volta deixa o anel do foco por inteiro dentro da
   fila que corta. No dedo, o chip cresce dos 36px do desenho para os 40, e a
   área de toque chega aos 44 (dois pixéis por cima e por baixo, invisíveis). */
.pes-acoes{flex-wrap:nowrap;overflow-x:auto;scrollbar-width:none;padding:4px;margin:-4px}
.pes-acoes::-webkit-scrollbar{display:none}
.pes-acoes>.chip{position:relative;flex:0 0 auto}
@media(pointer:coarse){.pes-acoes>.chip{min-height:40px}
  .pes-acoes>.chip::after{content:"";position:absolute;left:0;right:0;top:-2px;bottom:-2px}}

/* --- a lista das pessoas (lista-pessoas.js:personCard) ---
   Um cartão com uma linha por pessoa (o .linha da casa, com o avatar no lugar
   do ícone). O passar por cima pinta a linha; o premido e o anel são os do
   .linha, com o anel por dentro por causa do cartão que corta. */
/* a coluna da grelha pode encolher abaixo do texto sem quebra: sem o minmax(0,…)
   o nome comprido alargava a linha para lá do cartão, e a renda saía cortada */
.list.pes-lista,.list.vis-lista{grid-template-columns:minmax(0,1fr);gap:0;background:var(--card);border:1px solid var(--line);border-radius:16px;overflow:hidden}
.linha.pes-linha{gap:12px;min-height:64px;padding:12px 14px}
@media(hover:hover) and (pointer:fine){.pes-lista>.pes-linha:hover{background:var(--tint)}}
.pes-lista>.pes-linha:focus-visible{outline-offset:-2px}
.avatar.pes-av{width:40px;height:40px;flex:0 0 40px;font-size:13px}
.avatar.pes-av.pes-av-g{width:56px;height:56px;flex:0 0 56px;font-size:18px}
.avatar.pes-av-sem{background:var(--chip);color:var(--muted)}
.pes-txt{flex:1;min-width:0;display:flex;flex-direction:column;align-items:flex-start;gap:2px}
.pes-nome{max-width:100%;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.pes-nome .small{font-weight:500}
.pes-sub{max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.pes-selos,.vis-selos{display:flex;flex-wrap:wrap;gap:6px}
.pes-txt>.pes-selos{margin-top:4px}
.pes-contacto{display:none}
.pes-valor{flex:0 0 auto;font-weight:600;white-space:nowrap}
.pes-valor:empty{display:none}
/* No computador a linha é uma grelha: o avatar, o nome com o que diz dela, o
   contacto e a renda, alinhados de linha para linha. */
@media(min-width:900px){
  .linha.pes-linha{display:grid;grid-template-columns:40px minmax(0,1.4fr) minmax(0,1fr) minmax(96px,auto);gap:16px;padding:12px 18px}
  .pes-contacto{display:block;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
  .pes-valor,.pes-valor:empty{display:block;text-align:right}}

/* --- a lista das visitas (visitas.js:vVisits, visCard) ---
   Dois grupos com o título e quantas são; cada um um cartão com uma linha por
   visita: o bloco da data, o texto e os selos. A linha serve também as
   próximas visitas da Visão geral de quem colabora, sem o cartão à volta —
   por isso o enchimento lateral e o separador só existem dentro da lista. */
.vis-grupos{display:flex;flex-direction:column;gap:16px}
@media(min-width:1100px){.vis-grupos{display:grid;grid-template-columns:repeat(auto-fit,minmax(400px,1fr));gap:14px;align-items:start}}
.vis-grupo{display:flex;flex-direction:column;gap:10px;min-width:0}
.vis-grupo-cab{display:flex;align-items:baseline;justify-content:space-between;gap:8px;padding:4px 2px 0}
.vis-grupo-cab h2{margin:0;font-size:17px}
.vis-linha{display:flex;align-items:flex-start;gap:12px;min-width:0;padding:10px 0;color:inherit;cursor:pointer}
.vis-lista>.vis-linha{padding:12px 14px;transition:background-color var(--rapido) var(--curva),transform var(--rapido) var(--curva)}
.vis-lista>.vis-linha+.vis-linha{border-top:1px solid var(--line)}
@media(hover:hover) and (pointer:fine){.vis-lista>.vis-linha:hover{background:var(--tint)}}
.vis-lista>.vis-linha:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.vis-data{flex:0 0 52px;width:52px;min-height:48px;display:flex;flex-direction:column;align-items:center;justify-content:center;padding:6px 0;border-radius:10px;background:var(--chip);color:var(--ink)}
.vis-data b{font-family:var(--letra-titulo);font-size:18px;font-weight:650;line-height:1.1}
.vis-data span{font-size:11px;font-weight:600;color:var(--muted)}
.vis-data.hoje{background:var(--accent);color:var(--accent-ink)}
.vis-data.hoje span{color:var(--accent-ink);opacity:.86}
.vis-txt{flex:1;min-width:0;display:flex;flex-direction:column;align-items:flex-start;gap:2px}
.vis-nome{max-width:100%;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.vis-txt>.small{max-width:100%;overflow-wrap:anywhere}
.vis-txt>.vis-selos{margin-top:4px}
.vis-selos-dir{flex:0 0 auto;flex-direction:column;align-items:flex-end}

/* --- as fichas (pessoas.js:pesFichaInquilino, pesFichaDono; visitas.js:visFicha) ---
   O topo com o avatar, os cartões com o título e as linhas rótulo/valor (o
   .kv do canvas), as linhas que abrem (um contrato, um documento) com a seta,
   e as que ligam (o telemóvel, o email), com o valor a cobalto. */
.pes-ficha,.vis-ficha{display:flex;flex-direction:column;gap:12px}
.pes-ficha>.hint,.vis-ficha>.hint{margin:0}
.pes-topo{display:flex;align-items:center;gap:14px}
.pes-topo-txt{display:flex;flex-direction:column;align-items:flex-start;gap:6px;min-width:0}
.pes-papel{margin:0;font-weight:600;color:var(--muted)}
.card.pes-sec,.card.vis-sec{padding:0;overflow:hidden}
.pes-sec-cab{display:flex;align-items:baseline;justify-content:space-between;gap:8px;padding:14px 14px 6px}
.pes-sec-cab h3{margin:0;font-size:16px;min-width:0}
.pes-kv,.vis-kv{display:flex;justify-content:space-between;align-items:baseline;gap:12px;padding:10px 14px;border-top:1px solid var(--line);font-size:14.5px;color:inherit;text-decoration:none}
.pes-sec-cab+.pes-kv,.vis-sec>.vis-kv:first-child{border-top:0}
.pes-kv>span:first-child,.vis-kv>span:first-child{flex:0 0 auto;max-width:48%;color:var(--muted)}
.pes-kv>span:last-child,.vis-kv>span:last-child{min-width:0;text-align:right;font-weight:500;overflow-wrap:anywhere;user-select:text;-webkit-user-select:text}
.pes-kv>span.pes-forte{flex:1 1 auto;max-width:none;color:var(--ink);font-weight:500}
.pes-kv>span:last-child>.small,.pes-mau{display:block}
.pes-mau{color:var(--danger);font-size:13px;font-weight:600}
.pes-kv.pes-total{background:var(--chip)}
.pes-kv.pes-total b{font-weight:700}
.pes-kv .seta{display:inline-flex;vertical-align:-4px;margin:0 -4px 0 6px;color:var(--faint)}
a.pes-liga>span:last-child{color:var(--accent-text)}
a.pes-liga,.pes-kv.tap,.pes-linha-f.tap{cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){a.pes-liga:hover,.pes-kv.tap:hover,.pes-linha-f.tap:hover{background:var(--tint)}a.pes-liga:hover>span:last-child{text-decoration:underline}}
a.pes-liga:active,.pes-kv.tap:active,.pes-linha-f.tap:active{background:var(--press)}
a.pes-liga:focus-visible,.pes-kv.tap:focus-visible,.pes-linha-f.tap:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
@media(pointer:coarse){a.pes-liga,.pes-kv.tap{min-height:48px;align-items:center}}
/* uma linha que abre (um contrato, um documento): 56px no mínimo, a do canvas */
.pes-linha-f{display:flex;align-items:center;gap:12px;min-height:56px;padding:10px 14px;border-top:1px solid var(--line)}
.pes-sec-cab+.pes-linha-f,.pes-sec-cab+.pes-mais{border-top:0}
.pes-linha-txt{flex:1;min-width:0;display:flex;flex-direction:column;align-items:flex-start;gap:2px}
.pes-linha-txt>b{font-weight:600;overflow-wrap:anywhere}
.pes-linha-txt>.badge{margin-top:3px}
.pes-renda{flex:0 0 auto;white-space:nowrap;font-weight:600}
.pes-renda .small{font-weight:500}
.pes-linha-f .seta{display:inline-flex;flex:0 0 auto;margin-right:-4px;color:var(--faint)}
.pes-doc-ic{display:inline-flex;flex:0 0 auto;color:var(--muted)}
/* «Adicionar documentos»: a última linha do cartão, a cobalto */
.pes-mais{display:flex;align-items:center;gap:12px;width:100%;min-height:52px;padding:10px 14px;border:0;border-top:1px solid var(--line);border-radius:0;background:transparent;
  color:var(--accent-text);font:inherit;font-weight:600;text-align:left;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.pes-mais:hover{background:var(--tint)}}
.pes-mais:active{background:var(--press)}
.pes-mais:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.pes-texto{padding:2px 14px 14px;font-size:14.5px;overflow-wrap:anywhere;user-select:text;-webkit-user-select:text}
/* as contas entre proprietários: laranja suave a pagar, verde suave a
   receber (as cores do dinheiro, como o cartão da Visão geral) */
.card.pes-contas{display:flex;flex-direction:column;align-items:flex-start;gap:10px;padding:14px}
.card.pes-contas.out{background:var(--out-soft);border-color:color-mix(in srgb,var(--out) 22%,var(--out-soft))}
.card.pes-contas.in{background:var(--in-soft);border-color:color-mix(in srgb,var(--in) 22%,var(--in-soft))}
.pes-contas-cab{display:flex;align-items:baseline;justify-content:space-between;gap:12px;width:100%}
.pes-contas-cab p{margin:0;font-weight:600}
.pes-contas-valor{font-weight:700;white-space:nowrap}
.pes-contas.out .pes-contas-valor{color:var(--out)}
.pes-contas.in .pes-contas-valor{color:var(--in)}
.pes-contas>.small{margin:0;color:var(--ink)}
/* o «Acertar contas» é um .btn.sm (36px); no dedo sobe aos 44, como os
   pequenos das fichas do imóvel e do contrato */
@media(pointer:coarse){.pes-contas .btn.sm{min-height:44px}}
.btn.pes-quota{width:100%}
/* a ficha da visita */
.vis-topo{display:flex;flex-direction:column;align-items:flex-start;gap:8px}
.vis-quando{margin:0;font-size:14.5px;color:var(--muted)}
.vis-converte{display:flex;flex-direction:column;gap:10px;padding:16px;border-radius:16px;border:1px solid color-mix(in srgb,var(--accent) 22%,var(--accent-soft));background:var(--accent-soft);color:var(--accent-text)}
.vis-converte p{margin:0;font-size:14px}
.vis-converte .vis-converte-tit{font-size:15px;font-weight:700}
.vis-converte .btn{width:100%;min-height:48px}
.vis-sec>.lbl{margin:0;padding:14px 14px 6px}
.vis-texto{margin:0;padding:0 14px 14px;font-size:14.5px;overflow-wrap:anywhere;user-select:text;-webkit-user-select:text}
.vis-outras>.small{margin:0;padding:0 14px 14px;font-size:14px;line-height:1.6}
/* ===== fim: 1.3.4 ===== */
/* ===== redesign: 1.3.5 — os Movimentos ===== */
/* (lista-movimentos.js, movimento.js, cloud/selecao.js) As pranchetas
   M-Movimentos, D-Movimentos, M-Novo movimento e M-Filtros. Até 1099px a
   lista é a do telemóvel; a partir de 1100px é uma tabela com colunas e as
   caixas da seleção sempre à vista (cloud/selecao.js:selNaTabela lê a mesma
   largura). */

/* --- a pesquisa, sempre à vista, e o botão dos filtros (txBarraHtml) --- */
.mov-barra{display:flex;align-items:center;gap:8px;margin:0 0 10px}
.mov-busca{position:relative;display:block;flex:1;min-width:0}
.mov-busca input{min-height:44px;padding:0 42px}
.mov-busca input::-webkit-search-cancel-button{-webkit-appearance:none;appearance:none}
.mov-busca .qclear{right:6px}
/* a lupa, desenhada no traço dos ícones da casa (o icones.js ainda não a tem):
   uma máscara pintada com a cor terciária, para seguir o tema */
.mov-lupa{position:absolute;left:13px;top:50%;width:18px;height:18px;margin-top:-9px;background:var(--faint);pointer-events:none;
  -webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='1.8' stroke-linecap='round'%3E%3Cpath d='M11 18a7 7 0 1 0 0-14 7 7 0 0 0 0 14zM20 20l-4-4'/%3E%3C/svg%3E") center/18px 18px no-repeat;
  mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='1.8' stroke-linecap='round'%3E%3Cpath d='M11 18a7 7 0 1 0 0-14 7 7 0 0 0 0 14zM20 20l-4-4'/%3E%3C/svg%3E") center/18px 18px no-repeat}
.mov-filt{position:relative;flex:0 0 auto}
.mov-filt.on{border-color:var(--accent);background:var(--accent-soft);color:var(--accent-text)}
.mov-filt-n{position:absolute;top:-6px;right:-6px;min-width:18px;height:18px;padding:0 5px;border-radius:999px;background:var(--accent);color:var(--accent-ink);font-size:11px;font-weight:700;line-height:18px;text-align:center;font-variant-numeric:tabular-nums}

/* --- os chips dos filtros (txChipsHtml): o menu da casa vestido de chip --- */
.mov-chips{margin:0 0 12px}
.mov-chip{position:relative;display:inline-flex;align-items:center;max-width:100%;min-height:36px;border:1px solid var(--line2);border-radius:999px;background:var(--card);
  transition:background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.mov-chip:hover{background:var(--tint)}}
.mov-chip .sel{position:static;width:auto;min-width:0}
.mov-chip .selbtn{position:relative;width:auto;min-height:34px;padding:0 10px 0 12px;gap:6px;border:0;border-radius:999px;background:transparent;font-size:14px;font-weight:500;color:var(--ink)}
.mov-chip .selbtn span{flex:0 1 auto;max-width:220px}
.mov-chip .selbtn svg{width:16px;height:16px;color:var(--muted)}
.mov-chip.on{background:var(--accent-soft);border-color:var(--accent)}
.mov-chip.on .selbtn{padding-right:2px;color:var(--accent-text)}
.mov-chip.on .selbtn svg{display:none}
.mov-chip-txt{padding:0 2px 0 12px;font-size:14px;font-weight:500;color:var(--accent-text);white-space:nowrap}
.mov-chip-x{position:relative;display:grid;place-items:center;flex:0 0 30px;width:30px;height:30px;margin-right:2px;padding:0;border:0;border-radius:50%;background:transparent;color:var(--accent-text);cursor:pointer}
@media(hover:hover) and (pointer:fine){.mov-chip-x:hover{background:var(--card)}}
.mov-chip-x:active{background:var(--press)}
.mov-chip-x:focus-visible{outline:2px solid var(--accent);outline-offset:1px}
/* no dedo o chip parece o mesmo, mas acerta-se em 44px */
@media(pointer:coarse){.mov-chip .selbtn::after,.mov-chip-x::after{content:"";position:absolute;inset:-5px 0}.mov-chip-x::after{inset:-7px}}
.mov-chip.mov-comum{border-style:dashed}
.mov-so-largo{display:none}
@media(min-width:901px){.mov-chip.mov-so-largo,.chip.limpar.mov-so-largo{display:inline-flex}}
/* no telemóvel a fila tem de caber numa linha, como no canvas: sem a seta */
@media(max-width:900px){.mov-chip .selbtn svg{display:none}.mov-chip .selbtn{padding:0 12px}.mov-chip.on .selbtn{padding-right:2px}}

/* --- os totais, em cartões tocáveis (o kpi da casa, compacto) --- */
.mov-tot{grid-template-columns:repeat(auto-fit,minmax(min(160px,100%),1fr));gap:10px;margin:0 0 2px}
.mov-tot .kpi{display:grid;grid-template-columns:auto minmax(0,1fr);align-content:start;column-gap:5px;padding:12px 14px;border-radius:12px}
.mov-tot .kpi .label{grid-row:1;grid-column:1;font-size:13px;font-weight:500}
.mov-tot .kpi .foot{grid-row:1;grid-column:2;align-self:center;margin:0;font-size:13px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.mov-tot .kpi .foot::before{content:"· "}
.mov-tot .kpi .value{grid-row:2;grid-column:1/-1;margin-top:2px;font-family:var(--letra);font-size:18px;font-weight:650;letter-spacing:0;font-variant-numeric:tabular-nums;white-space:nowrap}
.mov-tot .kic{display:none}
/* no telemóvel numa fila que se arrasta de lado e sai pela borda do ecrã */
@media(max-width:600px){
  .mov-tot{display:flex;overflow-x:auto;scroll-snap-type:x proximity;scroll-padding:0 16px;scrollbar-width:none;margin:0 calc(-16px - var(--inset-right)) 2px calc(-16px - var(--inset-left));padding:0 16px 2px}
  .mov-tot::-webkit-scrollbar{display:none}
  .mov-tot .kpi{flex:0 0 auto;min-width:124px;scroll-snap-align:start}
}
/* as cores do dinheiro que a casa não tinha: a dívida a terceiros em cobalto
   e o acerto entre proprietários, que não é entrada nem saída, apagado */
.mov-div{color:var(--accent-text)}
.mov-acerto{color:var(--muted)}

/* --- os meses e as linhas (txMesHtml, txLinhaHtml) — o telemóvel --- */
.txmes>.mov-mes{display:flex;align-items:center;justify-content:space-between;gap:10px;min-height:32px;margin:16px 0 8px;padding:0 2px;
  font-size:13px;font-weight:400;letter-spacing:0;text-transform:none;color:var(--muted)}
.txmes-nome{font-family:var(--letra-titulo);font-size:16px;font-weight:650;letter-spacing:-.015em;color:var(--ink);white-space:nowrap}
.txnet{font-size:13px;white-space:nowrap;font-variant-numeric:tabular-nums}
.txnet b{font-weight:650;color:var(--ink)}
.txnet b.pos{color:var(--in)}
.txnet b.neg{color:var(--out)}
.mov-lista{display:block;background:var(--card);border:1px solid var(--line);border-radius:16px;overflow:hidden}
.mov-linha{min-height:64px;padding:12px 14px;background:var(--card);transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.mov-linha:hover{background:var(--tint)}}
.mov-linha:active{transform:none;background:var(--press)}
.mov-linha .txcorpo{flex:1;min-width:0}
.mov-linha .title{font-size:15px}
.mov-linha .mov-curta{font-variant-numeric:tabular-nums}
/* a frase da parte («a tua parte · total …») é uma nota como a linha curta:
   13px, numa linha, com reticências quando não cabe (o .txrow .small) */
.mov-linha .mov-parte{margin-top:1px;font-variant-numeric:tabular-nums}
.mov-linha .selbox{padding:0}
/* A linha marcada tem o realce dos cartões das Casas (estilos.css:.sel-on-card):
   o contorno no --accent e o fundo das linhas dos Contratos (.ct-linha). O
   contorno é o traço de cima da linha (o .sel-on-card pinta-o) e uma sombra
   por dentro nos outros três lados: com o anel inteiro, duas linhas marcadas
   seguidas ficavam com um traço triplo entre elas. A primeira linha do mês
   não tem traço em cima, e leva o anel inteiro; no telemóvel as pontas dela
   (e as da última) acompanham a curva do cartão, para o anel não ser cortado.
   O que a distingue pela cor da frente, também com o escurecimento forçado do
   Samsung Internet, é o contorno e a caixa cheia com o visto. */
.mov-linha.sel-on-card{background:var(--accent-soft);box-shadow:inset 1px 0 0 var(--accent),inset -1px 0 0 var(--accent),inset 0 -1px 0 var(--accent)}
@media(max-width:1099px){
  .mov-lista>.mov-linha.sel-on-card:first-child{box-shadow:inset 0 0 0 1px var(--accent)}
  .mov-lista>.mov-linha:first-child{border-top-left-radius:15px;border-top-right-radius:15px}
  .mov-lista>.mov-linha:last-child{border-bottom-left-radius:15px;border-bottom-right-radius:15px}
}
.mov-marcas{display:flex;flex-wrap:wrap;gap:6px;margin-top:5px}
.mov-c-valor{display:flex;align-items:center;justify-content:flex-end;gap:6px;flex:0 0 auto;margin-left:auto;white-space:nowrap;font-variant-numeric:tabular-nums}
.mov-c-valor b{font-size:15px;font-weight:650}
.mov-nota{display:inline-flex;color:var(--faint)}
.mov-vazio{color:var(--faint)}
/* as peças que só a tabela mostra, e as caixas fora da seleção */
.mov-cab,.mov-tipo,.mov-c-data,.mov-c-imovel,.mov-c-cat,.mov-c-quem,.selbox.fora{display:none}

/* --- a tabela do ecrã largo (D-Movimentos) --- */
@media(min-width:1100px){
  .mov-cab,.mov-linha{display:grid;grid-template-columns:44px 92px minmax(0,2.2fr) minmax(0,1.4fr) minmax(0,1.4fr) minmax(0,1fr) 130px;align-items:center;column-gap:12px}
  .mov-cab{min-height:44px;margin-top:14px;padding:0 16px;background:var(--card);border:1px solid var(--line);border-bottom:0;border-radius:16px 16px 0 0;
    font-size:12px;font-weight:600;letter-spacing:.04em;text-transform:uppercase;color:var(--muted)}
  .mov-tabela{background:var(--card);border:1px solid var(--line);border-radius:0 0 16px 16px;overflow:hidden}
  .mov-tabela .txmes>.mov-mes{justify-content:flex-start;gap:12px;min-height:44px;margin:0;padding:0 16px;border-top:1px solid var(--line);background:var(--chip);color:var(--muted)}
  .mov-tabela .txmes-nome{flex:1;font-family:var(--letra);font-size:14.5px}
  /* o mês não tem caixa: o nome fica na coluna da Data, por cima da das caixas */
  .mov-tabela .txmes>.mov-mes{padding-left:72px}
  .mov-tabela .mov-mes .txnet{flex:0 0 auto;text-align:right}
  .mov-tabela .mov-lista{border:0;border-radius:0;background:transparent}
  .mov-linha{min-height:56px;padding:8px 16px;font-size:14.5px}
  .mov-tabela .mov-linha{border-top:1px solid var(--line)}
  .mov-linha .ic{display:none}
  .mov-linha>.selbox,.mov-cab-caixa{grid-column:1}
  .mov-c-data{grid-column:2}
  .mov-linha .txcorpo,.mov-c-desc{grid-column:3}
  .mov-c-imovel{grid-column:4}
  .mov-c-cat{grid-column:5}
  .mov-c-quem{grid-column:6}
  .mov-cab .mov-c-valor,.mov-linha .mov-c-valor{grid-column:7;margin:0;text-align:right}
  .mov-c-data,.mov-c-imovel,.mov-c-cat,.mov-c-quem,.mov-tipo,.mov-cab-caixa{display:block;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
  .mov-c-data{font-variant-numeric:tabular-nums}
  .mov-c-cat{font-size:14px;color:var(--muted)}
  .mov-cab .mov-c-imovel,.mov-cab .mov-c-cat,.mov-cab .mov-c-quem{font-size:12px;color:var(--muted)}
  .mov-cab .mov-c-valor{display:block}
  .mov-linha .mov-curta{display:none}
  .selbox.fora{display:inline-flex}
  .mov-cab .selbox{padding:0}
  /* as caixas já estão à vista: o «Selecionar vários» do cabeçalho sai */
  #hdrFilt.mov-hdr-sel{display:none!important}
  /* em seleção o título fica (a contagem e a caixa de tudo estão na barra e na
     coluna das caixas) */
  body.sel-on header.top #pageTitle,body.sel-on header.top #pageSub{display:block}
  body.sel-on .sel-cab{display:none}
}

/* --- o painel dos filtros (txFilterPainel, o M-Filtros) --- */
/* O cartão rola por dentro quando não cabe, e isso tem de se ver: enquanto há
   mais por cima ou por baixo, uma sombra na borda diz-o. São as quatro camadas
   do fundo: as duas sombras ficam presas às bordas da caixa (scroll), e duas
   tampas da cor do cartão andam com o conteúdo (local) e tapam-nas quando se
   chega ao princípio ou ao fim. No telemóvel o painel não cabe por baixo da
   pesquisa (o «Ordenar por» e o interruptor ficavam escondidos sem sinal); no
   computador cresce até ao fundo do ecrã, e a 900px de altura cabe inteiro. */
.mov-fwrap .fpanel>.mov-filtros-card{padding:14px 16px 18px;background-color:var(--bg);
  background-image:linear-gradient(var(--bg) 30%,transparent),linear-gradient(transparent,var(--bg) 70%),
    radial-gradient(farthest-side at 50% 0,color-mix(in srgb,var(--ink) 22%,transparent),transparent),
    radial-gradient(farthest-side at 50% 100%,color-mix(in srgb,var(--ink) 22%,transparent),transparent);
  background-position:center top,center bottom,center top,center bottom;background-repeat:no-repeat;
  background-size:100% 40px,100% 40px,100% 14px,100% 14px;background-attachment:local,local,scroll,scroll}
@media(min-width:901px){
  .mov-fwrap .fpanel{left:auto;width:min(560px,100%)}
  /* até 16px do fundo do ecrã: o cartão começa a 178px (o cabeçalho, a
     pesquisa e os 6px do .fpanel) */
  .mov-fwrap .fpanel>.mov-filtros-card{max-height:calc(100vh - 194px);max-height:calc(100dvh - 194px)}
}
.mov-filtros{display:flex;flex-direction:column;gap:16px}
.mov-filtros-cab{display:flex;align-items:center;gap:8px}
.mov-filtros-tit{flex:1;margin:0;font-size:22px}
.mov-filtros-cab .btn.ghost{color:var(--accent-text)}
.mov-filtros-n{margin:-10px 0 0;font-variant-numeric:tabular-nums}
.mov-campo{display:flex;flex-direction:column;gap:8px;min-width:0}
.mov-campo .flabel{margin:0}
/* --- as etiquetas no painel e na fila (lista-movimentos.js:txEtiquetasHtml) ---
   escolha múltipla: o visto só no chip ligado, que a cor sozinha não chega; o
   nome inteiro, a fila parte em linhas; no dedo, 44px */
.mov-etiq .chip{white-space:normal;max-width:100%;text-align:left;line-height:1.25}
.mov-etiq .chip svg{display:none}
.mov-etiq .chip.on svg{display:block}
@media(pointer:coarse){.mov-etiq .chip{min-height:44px}}
.mov-etiq-d{margin:-2px 0 0;color:var(--muted)}
/* o chip rápido: o texto é um botão que abre o painel, e corta com reticências
   para a fila caber a 390px (o nome inteiro está no aria-label e no painel) */
.mov-chip-etiq{min-width:0}
.mov-chip-etiq .mov-chip-txt{position:relative;display:flex;align-items:center;min-width:0;max-width:200px;min-height:34px;border:0;border-radius:999px;background:transparent;font-family:inherit;cursor:pointer}
.mov-chip-etiq-t{min-width:0;overflow:hidden;text-overflow:ellipsis}
.mov-chip-etiq .mov-chip-txt:focus-visible{outline:2px solid var(--accent);outline-offset:1px}
@media(pointer:coarse){.mov-chip-etiq .mov-chip-txt::after{content:"";position:absolute;inset:-5px 0}}
/* «Pago por» em chips (movimento.js:txPagoPorHtml): o nome inteiro, a fila
   parte em linhas e um nome que não caiba sozinho numa linha parte dentro do
   chip — nunca reticências; o visto só no aceso, que a cor sozinha não chega;
   no dedo, 44px */
.pago-por .chip{white-space:normal;max-width:100%;text-align:left;padding:6px 14px;line-height:1.25}
.pago-por .chip svg{display:none}
.pago-por .chip.on svg{display:block}
@media(pointer:coarse){.pago-por .chip{min-height:44px}}
.mov-grelha{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:12px 10px}
.mov-ligado .selbtn{border-color:var(--accent);background:var(--accent-soft);color:var(--accent-text);font-weight:600}
.mov-ligado .selbtn svg{color:var(--accent-text)}
/* um campo de data tem largura própria e saía da coluna: encolhe com ela */
.mov-grelha>label,.mov-par>label{min-width:0}
.mov-grelha input,.mov-par input{min-width:0}
/* o interruptor vai num <label> com o texto: o toque no texto chega ao
   botão (é ele o controlo do label), e o alvo é a linha inteira */
label.mov-interr{display:flex;align-items:center;gap:12px;min-height:44px;padding:12px 14px;border:1px solid var(--line);border-radius:12px;background:var(--card);font-size:14.5px;font-weight:400;cursor:pointer}
.mov-interr span{flex:1;min-width:0}

/* --- o formulário (txBody, o M-Novo movimento) --- */
.mov-form{gap:14px}
.mov-tipo-segm>button.on.pos{color:var(--in)}
.mov-tipo-segm>button.on.neg{color:var(--out)}
.mov-tipo-segm>button.on.prest{color:var(--loan)}
.mov-tipo-segm>button.on.mov-div{color:var(--accent-text)}
.mov-montante{display:flex;align-items:center;gap:8px}
.mov-montante-campo{position:relative;display:block;flex:1;min-width:0}
.mov-montante-campo input{min-height:64px;padding:6px 46px 6px 14px;font-size:34px;font-weight:650;letter-spacing:-.015em;line-height:1.1;color:inherit;font-variant-numeric:tabular-nums}
.mov-euro{position:absolute;right:16px;top:50%;margin-top:-15px;font-size:24px;line-height:30px;font-weight:650;color:var(--muted);pointer-events:none}
.mov-repor{flex:0 0 auto}
/* a data e o imóvel lado a lado (o canvas); a data com menos folga de lado,
   para o dia e o ícone do calendário caberem a 390px */
.mov-par{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1.15fr);gap:10px}
.mov-par input[type=date]{padding-left:12px;padding-right:10px}
@media(max-width:340px){.mov-par{grid-template-columns:1fr}}
.mov-grp-cab{display:flex;align-items:center;justify-content:space-between;gap:10px;font-size:15px}
.mov-rot-fraco{font-size:13px;font-weight:500;color:var(--muted)}
.mov-divisao-dica{display:grid;gap:10px}
.mov-partes{display:flex;flex-direction:column;gap:8px;font-variant-numeric:tabular-nums}
.mov-pfila{display:flex;align-items:center;gap:10px;font-size:14.5px}
.mov-pnome{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.mov-pfila b{min-width:90px;text-align:right;font-weight:650}
.mov-pbarra{display:flex;height:8px;border-radius:4px;overflow:hidden;background:var(--chip)}
.mov-pbarra span{display:block;height:100%;background:var(--accent)}
.mov-pbarra span+span{border-left:2px solid var(--card)}
.mov-pbarra span:nth-child(even){opacity:.45}
.mov-soma{display:flex;align-items:center;gap:6px;margin:0;font-size:13px;font-weight:600;color:var(--in)}
.mov-soma.perigo{color:var(--danger)}
.mov-soma svg{flex:0 0 auto}
.mov-form .mov-etiquetas .flabel{margin-bottom:8px}
.mov-form .tagbox{min-height:0;padding:0;border:0;background:transparent}
.mov-form .tag{min-height:36px;border-color:transparent;background:var(--accent-soft);color:var(--accent-text)}
.mov-form .tag button{color:var(--accent-text)}
.mov-form .tagadd{min-height:36px}
/* ===== fim: 1.3.5 ===== */
/* ===== ajustes-v40b: 1.1 — as listas como os Movimentos ===== */
/* (vistas.js:lfCabeca) A barra, os chips e o painel das listas são os dos
   Movimentos, com as mesmas classes (.mov-barra, .mov-chip, .mov-fwrap,
   .mov-filtros-card, .mov-grelha): o desenho é um, e mexer-lhe ali muda-o em
   todo o lado. Aqui só o que é das listas. */
/* Nos Imóveis e nos Contratos o botão do cabeçalho é o «Selecionar vários»
   (cloud/selecao-listas.js:selLCabecalho); em seleção sai, como o dos
   Movimentos: a barra de baixo já tem o Cancelar e o Apagar. Ao contrário do
   dos Movimentos, fica no ecrã largo, onde estas listas não têm caixas à vista. */
body.sel-on #hdrFilt.lst-hdr-sel{display:none}
/* Em seleção, a caixa de tudo e a contagem no lugar do título
   (cloud/selecao-listas.js:selLCabNovo, a .sel-cab dos Movimentos). No ecrã
   largo os Movimentos têm a caixa de tudo na coluna da tabela e devolvem o
   título; estas listas não têm tabela de caixas, e a do cabeçalho fica. */
@media(min-width:1100px){
  body.sel-on .sel-cab.lst-sel-cab{display:flex}
  body.sel-on.lst-sel header.top #pageTitle,body.sel-on.lst-sel header.top #pageSub{display:none}
}
/* ===== fim: ajustes-v40b 1.1 ===== */
/* ===== ajustes-v40b: 1.2 — as outras listas como os Movimentos ===== */
/* (vistas.js:lfCabeca nos Inquilinos, nos Proprietários, nas Visitas, nos
   Planeados e nos Créditos) O desenho continua a ser o dos Movimentos; aqui só
   o que estas listas trazem de novo. */
/* Um chip que não é um seletor e leva ao painel (o «Dias e horas» das
   visitas, visitas.js:visChips): o texto é um botão, com o aspeto do botão
   do .mov-chip desligado e o do .mov-chip-txt ligado; no dedo, 44px. */
.lfm-chip-abre .mov-chip-txt{position:relative;display:flex;align-items:center;min-height:34px;border:0;border-radius:999px;background:transparent;font-family:inherit;cursor:pointer}
.lfm-chip-abre:not(.on) .mov-chip-txt{padding:0 12px;color:var(--ink)}
.lfm-chip-abre .mov-chip-txt:focus-visible{outline:2px solid var(--accent);outline-offset:1px}
@media(pointer:coarse){.lfm-chip-abre .mov-chip-txt::after{content:"";position:absolute;inset:-5px 0}}
/* Os Créditos: as liquidadas abrem-se por baixo das ativas em todos os
   ecrãs (creditos.js:credPagasAlternar), e o estado é o chip do
   vistas.js:lfCabeca — os chips Ativas / Liquidadas do computador saíram.
   Abertas (ou as únicas que o filtro deixa), as liquidadas mostram-se; no
   computador o título e o botão das liquidadas ficam na coluna, e o «Nova
   hipoteca» fica só no cabeçalho. */
.cred-corpo.abertas .cred-pagas{display:flex;flex-direction:column;gap:12px}
@media(min-width:901px){
  .cred-corpo>.cred-col>.plan-cab{display:flex}
  .cred-corpo>.cred-col>.btn.cred-liq{display:flex}
  .cred-corpo .cred-cab>.btn.plan-novo{display:none}
}
/* ===== fim: ajustes-v40b 1.2 ===== */
/* ===== ajustes-v40c: 1.2 — contratos e visitas ===== */
/* O quarto do contrato (contrato.js:ctQuartosHtml): com quartos arrendados,
   os arrendados ficam à vista mas não se escolhem — o chip desligado perde a
   mão e a tinta, e o contorno tracejado diz «não está livre» sem depender só
   da cor. O erro do ctSaver (falhaCampo no grupo) acende o contorno dos que
   se podem escolher, e não um anel à volta da fila. */
.ct-quartos .chip:disabled{cursor:default;color:var(--muted);border-style:dashed}
.ct-quartos .chip:disabled .ct-ja-txt{color:var(--muted)}
#c_roomEsc.err{box-shadow:none}
#c_roomEsc.err>.chip:not(:disabled){border-color:var(--danger)}
/* O contacto escolhido (contrato.js:contactSect, contrato.js:ctMeiosDeContacto):
   a linha da líquida (.ct-net-linha) não parte o valor, e um email ou um nome
   comprido saía da caixa a 375px. Aqui a linha embrulha — o contacto desce
   para baixo do nome quando não cabe ao lado —, o telefone fica inteiro e o
   email e o nome partem onde for preciso. */
.ct-net-linha.ct-contacto-escolhido{flex-wrap:wrap;row-gap:2px;min-width:0}
.ct-contacto-escolhido>span,.ct-net-linha.ct-contacto-escolhido>b{min-width:0;max-width:100%;white-space:normal;overflow-wrap:anywhere}
.ct-contacto-tel{white-space:nowrap}
/* O Início e o Fim da visita (visitas.js:visBody): lado a lado também no
   telemóvel, em duas colunas iguais que enchem a linha. Numa .row
   empilhavam-se abaixo dos 520px; do tamanho da hora, encostados à esquerda,
   deixavam meia linha vazia. A altura é a do campo da casa (46px). */
.vis-par{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));align-items:end;gap:12px}
.vis-par>label{min-width:0}
.vis-par input{min-width:0;padding-left:12px;padding-right:10px}
/* ===== fim: ajustes-v40c 1.2 ===== */
/* ===== ajustes-v40d: 1.3 — o quarto à espera de uma data (contrato.js:ctQuartosMiolo) ===== */
/* Um chip à espera de uma data (o início do contrato antes do fim do
   contrato desse quarto, ou do último fim para a casa inteira) não vale
   neste início, mas toca-se: muda o início para essa data e escolhe-o
   (contrato.js:ctComecaNoFim). Lê-se como os desligados — o tracejado e a
   tinta esbatida —, mas a data vai na cor do realce, a dizer que é por ali,
   e guarda a mão. O erro do grupo não o pinta de vermelho: não é a escolha. */
.ct-quartos .chip.ct-espera:not(.on){color:var(--muted);border-style:dashed}
.ct-quartos .chip.ct-espera:not(.on) .ct-ja-txt{color:var(--accent-text)}
#c_roomEsc.err>.chip.ct-espera:not(.on){border-color:var(--line2)}
@media(hover:hover) and (pointer:fine){.ct-quartos .chip.ct-espera:not(.on):hover{border-color:var(--accent)}}
/* ===== fim: ajustes-v40d 1.3 ===== */
/* ===== ajustes-v40d: 1.2 — as fotos de um imóvel em carrossel (anexos.js:fotoCarrossel) ===== */
/* O palco tem um tamanho fixo — quadrado, até 60% da altura do ecrã — e cada
   foto cabe lá inteira (contain): de uma foto ao alto para uma ao comprido a
   janela não muda de altura, nem a meio da viagem. A fita leva três lugares
   (a anterior, a de agora e a seguinte) separados pela --fc-folga, que o
   anexos.js:fotoPasso também lê para saber o tamanho de um passo. O pan-y
   deixa o vertical ao browser: o corpo da janela continua a rolar. A foto
   não se arrasta à moda do browser nem abre o menu do toque longo — o
   «Guardar» é o caminho para a guardar. */
.fc-palco{--fc-folga:16px;position:relative;overflow:hidden;width:100%;aspect-ratio:1/1;max-height:60vh;max-height:60dvh;border-radius:12px;background:var(--tint);touch-action:pan-y;user-select:none;-webkit-user-select:none}
.fc-fita{position:absolute;inset:0}
.fc-slide{position:absolute;inset:0;display:flex;align-items:center;justify-content:center}
.fc-slide.fc-ant{transform:translateX(calc(-100% - var(--fc-folga)))}
.fc-slide.fc-seg{transform:translateX(calc(100% + var(--fc-folga)))}
.fc-img{display:block;width:100%;height:100%;object-fit:contain;pointer-events:none;-webkit-user-drag:none;-webkit-touch-callout:none}
.fc-falta{display:none;padding:0 24px;text-align:center;color:var(--muted);font-size:13px}
.fc-slide.fc-sem .fc-img{display:none}
.fc-slide.fc-sem .fc-falta{display:block}
.fc-palco.arrasta{cursor:grabbing}
.fc-pos{color:var(--ink);font-weight:600}
/* As setas ‹ ›, à beira do palco, para o rato. No dedo ficam só para o
   leitor de ecrã (o arrasto é o caminho), e aparecem quando o Tab lá chega.
   A posição vem da margem e não de um transform, para o premido poder
   encolher a seta sem a tirar do sítio. */
.fc-seta{position:absolute;top:50%;width:44px;height:44px;margin-top:-22px;padding:0;border-radius:50%;border:1px solid var(--line);background:var(--card);color:var(--ink);display:grid;place-items:center;cursor:pointer;transition:transform var(--rapido) var(--curva)}
.fc-seta-ant{left:10px}
.fc-seta-seg{right:10px}
.fc-seta:active{transform:scale(.94);background:var(--press)}
@media(hover:hover) and (pointer:fine){.fc-seta:hover{background:var(--tint)}}
@media(hover:none),(pointer:coarse){.fc-seta:not(:focus-visible){width:1px;height:1px;margin:-1px;overflow:hidden;clip-path:inset(50%);border:0}}
/* ===== fim: ajustes-v40d 1.2 ===== */
/* ===== redesign: 1.3.6 — os Planeados, os Créditos e a Agenda ===== */
/* --- o cartão dos por confirmar (planeados.js:pendingCard), também na Visão
   geral: sem a borda colorida à esquerda — o estado diz-se no selo. O
   cabeçalho inteiro abre e fecha; as linhas separam-se por um traço. --- */
.plan-pend{padding:0}
.plan-pend-cab{display:grid;grid-template-columns:minmax(0,1fr) auto auto;grid-template-areas:"tit total chev" "sub sub sub";
  align-items:center;gap:2px 10px;padding:16px 18px;border-radius:16px;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
.plan-pend-cab[aria-expanded="true"]{border-radius:16px 16px 0 0}
@media(hover:hover) and (pointer:fine){.plan-pend-cab:hover{background:var(--tint)}}
.plan-pend-cab:active{background:var(--press)}
.plan-pend-tit{grid-area:tit;display:flex;flex-wrap:wrap;align-items:center;gap:6px 10px;min-width:0}
.plan-pend-tit h3{margin:0;font-size:16px}
.plan-pend-total{grid-area:total;font-weight:600;white-space:nowrap;font-variant-numeric:tabular-nums}
.plan-pend-chev{grid-area:chev;display:inline-flex;color:var(--faint);transition:transform var(--rapido) var(--curva)}
.plan-pend-chev.aberto{transform:rotate(180deg)}
.plan-pend-sub{grid-area:sub;margin:0}
.plan-pend-linhas.list{gap:0;padding:0 18px}
/* numa grelha (.list) um item não encolhe abaixo do seu conteúdo sem isto: o
   título que corta com reticências empurrava o valor para fora do cartão */
.plan-pend-linhas>*,.plan-linhas>*,.plan-modelos>*,.cred-ativas>.list>*,.cred-pagas>.list>*{min-width:0}
.plan-pend-linha{display:flex;flex-wrap:wrap;align-items:center;gap:8px 12px;padding:12px 0;border-top:1px solid var(--line)}
.plan-pend-dica{margin:0;padding:10px 18px 16px}
/* a linha de um planeado: o texto encolhe e corta, o valor e o selo à direita */
.plan-txt{flex:1 1 190px;min-width:0}
/* no cartão dos por confirmar o texto e o valor andam juntos: quando a linha
   não chega, só as ações descem (um valor largo não arrasta o valor e o selo
   para baixo, ao lado dos botões) */
.plan-pend-topo{display:flex;align-items:center;gap:12px;flex:1 1 190px;min-width:0}
.plan-pend-topo>.plan-txt{flex:1 1 auto}
.plan-txt p{margin:0}
.plan-txt .title{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.plan-pend-linha .plan-txt.tap{margin:-6px -8px;padding:6px 8px;border-radius:10px;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.plan-pend-linha .plan-txt.tap:hover{background:var(--tint)}}
.plan-pend-linha .plan-txt.tap:active{background:var(--press)}
.plan-valor{display:flex;flex-direction:column;align-items:flex-end;gap:4px;flex:0 0 auto}
.plan-num{font-weight:600;white-space:nowrap;font-variant-numeric:tabular-nums}
.plan-acoes{display:flex;align-items:center;justify-content:flex-end;gap:8px;flex:0 0 auto;margin-left:auto}
@media(max-width:520px){
  .plan-pend-cab{padding:14px}
  .plan-pend-linhas.list{padding:0 14px}
  .plan-pend-dica{padding:10px 14px 14px}
}
/* num cartão estreito (a coluna da Visão geral) as ações descem para a linha
   de baixo antes de o nome ficar cortado: o quarto é o que distingue duas rendas */
@media(min-width:521px){.plan-pend-topo{flex-basis:260px}}
/* no dedo, os botões pequenos desta área chegam aos 44px do toque, e os chips
   dos Modelos também (sem o ::after das irmãs: a fila rola de lado com 2px de
   folga, e o que passasse disso ficava cortado) */
@media(pointer:coarse){
  .plan-acoes .btn,.plan-retro-acoes .btn,.btn.plan-novo,.cred-hp-acoes .btn,.cred-det-acoes .btn,.cred-aviso .btn,.cal-nav .btn{min-height:44px}
  .plan-modelo{min-height:44px}
}
/* --- a página dos Planeados (o canvas M-Planeados) --- */
/* a faixa de quem vem de trás: o suave do cobalto, como a do âmbito; o
   contorno é o cobalto a um quarto (sem color-mix fica o --line2) */
.plan-retro{display:flex;flex-direction:column;gap:10px;padding:14px;margin:0 0 14px;border-radius:16px;
  background:var(--accent-soft);color:var(--accent-text);border:1px solid var(--line2);border-color:color-mix(in srgb,var(--accent) 24%,transparent)}
.plan-retro h2{margin:0;font-size:16px;color:inherit}
.plan-retro p{margin:0;font-size:14px}
.plan-retro .plan-retro-mais{font-size:13px;color:inherit}
.plan-retro-acoes{display:flex;gap:8px}
.plan-retro-acoes .btn{flex:1 1 0}
@media(min-width:901px){.plan-retro-acoes .btn{flex:0 0 auto;min-width:160px}}
/* a lista num cartão só, as linhas separadas por um traço */
.plan-lista{padding:0;overflow:hidden}
.plan-linhas.list{gap:0}
.plan-linha{display:flex;align-items:center;gap:12px;min-height:60px;padding:12px 14px;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
.plan-linha+.plan-linha{border-top:1px solid var(--line)}
@media(hover:hover) and (pointer:fine){.plan-linha:hover{background:var(--tint)}}
.plan-linha:active{background:var(--press)}
.plan-lista .plan-linha:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.plan-linha>.plan-num{flex:0 0 auto}
.plan-selos{display:flex;flex-wrap:wrap;gap:6px;margin-top:6px}
/* o título de uma secção com a ação ao lado (Modelos, Ativas) */
.plan-cab{display:flex;align-items:center;justify-content:space-between;gap:12px;min-height:36px;margin:22px 2px 10px}
.plan-cab h2{margin:0;font-size:16px}
.btn.ghost.plan-novo{color:var(--accent-text)}
/* os modelos: chips com o valor */
.plan-modelos.list{display:flex;flex-wrap:wrap;gap:8px}
.plan-modelo{max-width:100%}
.plan-modelo-nome{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

/* --- os Créditos (os canvas M-Creditos e D-Creditos) --- */
/* o resumo: no telemóvel o cartão azul-noite (a cor da barra lateral) com a
   dívida grande e as barras da dívida ano a ano; no computador três cartões */
.cred-resumo{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:10px 12px;margin:0 0 14px;padding:16px;
  border-radius:18px;background:var(--side);color:var(--side-ink)}
:root.dark .cred-resumo{border:1px solid var(--line)}
.cred-r p{margin:0}
.cred-r-divida,.cred-r-graf{grid-column:1/-1}
.cred-r-rot{font-size:13px;color:var(--side-text)}
.cred-r-v{font-size:32px;line-height:1.1}
.cred-r-v2{font-family:var(--letra);font-size:15px;font-weight:600;letter-spacing:0}
.cred-r-mes{font-size:13px;font-weight:500;color:var(--side-text)}
.cred-barras{display:block;width:100%;height:56px}
.cred-barras rect{fill:var(--side-text);opacity:.6}
.cred-barras rect.agora{opacity:1}
.cred-r-eixo{display:flex;justify-content:space-between;gap:8px;margin-top:4px;font-size:11.5px;color:var(--side-text)}
/* as barras leem-se com o dedo (creditos.js:credBarrasLer): a leitura e a
   guia nas cores da barra lateral, legíveis no azul-noite nos dois temas; a
   guia desce até ao fundo das barras (o eixo está fora do desenho) */
.cred-resumo .chartcab{margin-bottom:8px}
.cred-r-caixa .cred-barras{height:56px}   /* o .chartbox svg dá height:auto, e o desenho crescia com a largura */
.cred-resumo .chartlido{background:var(--side-on);color:var(--side-ink)}
.cred-resumo .chartguia{bottom:0;width:2px;margin-left:-1px;background:var(--side-ink)}
/* os pagamentos sem hipoteca: a faixa do cobalto suave, com o «Associar» */
.cred-aviso{display:flex;flex-wrap:wrap;align-items:center;gap:10px 14px;margin:0 0 14px;padding:12px 16px;border-radius:16px;
  background:var(--accent-soft);color:var(--accent-text);border:1px solid var(--line2);border-color:color-mix(in srgb,var(--accent) 24%,transparent)}
.cred-aviso-ic{display:inline-flex;flex:0 0 auto}
.cred-aviso p{flex:1 1 260px;min-width:0;margin:0;font-size:14.5px}
/* o corpo: no telemóvel uma coluna; as liquidadas abrem por baixo */
.cred-col{display:flex;flex-direction:column;gap:12px;min-width:0}
.cred-col>.plan-cab{margin:4px 2px 0}
.cred-ativas>.list,.cred-pagas>.list{gap:12px}
.cred-det,.cred-pagas{display:none}
.cred-pagas>.hint{margin:0 2px}
.cred-liq{justify-content:space-between;width:100%;font-weight:500}
.cred-liq-chev{display:inline-flex;color:var(--faint);transition:transform var(--rapido) var(--curva)}
.cred-liq-chev.aberto{transform:rotate(180deg)}
/* o cartão de uma hipoteca: a parte de cima lê-se (tocar), os botões por baixo */
.cred-hp{padding:0;overflow:hidden}
.cred-hp-corpo{display:flex;flex-direction:column;gap:10px;padding:14px;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.cred-hp-corpo:hover{background:var(--tint)}}
.cred-hp-corpo:active{background:var(--press)}
.cred-hp .cred-hp-corpo:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.cred-hp-corpo p{margin:0}
.cred-hp-cab{display:flex;align-items:flex-start;gap:8px}
.cred-hp-nome{flex:1;min-width:0}
.cred-hp-nome h3{margin:0;font-size:17px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cred-hp-taxa{font-size:14px}
.cred-selo{align-self:flex-start}
.cred-hp-nums{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:10px}
.cred-v{font-weight:700;font-size:15px;white-space:nowrap}
.cred-v .small{font-weight:500}
.cred-sub{font-size:12px}
.cred-barra{height:6px;border-radius:3px;background:var(--line);overflow:hidden}
.cred-barra i{display:block;width:0;height:100%;border-radius:3px;background:var(--loan)}
.cred-hp-acoes{display:flex;gap:6px;padding:0 14px 14px}
.cred-hp-acoes .btn{flex:1 1 0;min-width:0}
/* o plano ano a ano: a tabela rola dentro da sua caixa, com o cabeçalho preso */
.cred-plano{overflow:auto;border:1px solid var(--line);border-radius:12px;max-height:52vh;max-height:52dvh;-webkit-overflow-scrolling:touch}
.cred-plano:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
.cred-tab{min-width:560px}
.cred-tab th,.cred-tab td{padding:9px 14px}
.cred-tab th{position:sticky;top:0;z-index:1;background:var(--chip);text-transform:uppercase;letter-spacing:.04em}
/* a «Dívida no fim» fica presa à direita da caixa: numa caixa estreita (a
   janela do Plano a 390px) era a coluna que o corte escondia, e nada dizia
   que a tabela rolava; o traço à esquerda diz que há mais por baixo dela */
.cred-tab-plano th:last-child,.cred-tab-plano td:last-child{position:sticky;right:0;background:var(--card)}
.cred-tab-plano th:last-child{z-index:2;background:var(--chip)}
@media(max-width:900px){.cred-tab-plano th:last-child,.cred-tab-plano td:last-child{box-shadow:inset 1px 0 0 var(--line)}}
.cred-tab-fim td{color:var(--muted)}
/* o plano: a taxa e as prestações de um ano parcial por baixo do período; a
   linha «Anos seguintes» separa os meses dos anos — não fica presa em cima
   nem à direita como os cabeçalhos, e o rótulo fica à vista ao rolar de lado */
.cred-tab-sub{display:block;font-size:11.5px;font-weight:500;color:var(--muted)}
.cred-tab-plano .cred-tab-grupo th{position:static;padding-top:14px;text-align:left;background:var(--chip);box-shadow:none;color:var(--ink)}
.cred-tab-grupo th>span{position:sticky;left:14px}
.cred-tab-total td{border-top:1px solid var(--line)}
/* o painel da hipoteca aberta (só no computador) */
.cred-det-cab{display:flex;flex-wrap:wrap;align-items:flex-end;gap:12px;padding:18px 18px 12px}
.cred-det-nome{flex:1 1 300px;min-width:0}
.cred-det-nome h2{margin:0;font-size:20px}
.cred-det-nome p{margin:2px 0 0}
.cred-det-acoes{display:flex;gap:8px}
.cred-det-stats{display:grid;grid-template-columns:repeat(auto-fit,minmax(160px,1fr));gap:12px;padding:4px 18px 16px}
.cred-det-stats p{margin:0}
.cred-det-nada{margin:0;padding:0 18px 18px}
.cred-det>.hint{margin:0;padding:18px}
.cred-det .cred-plano{border:0;border-top:1px solid var(--line);border-radius:0;max-height:none}
@media(min-width:901px){
  .cred-resumo{grid-template-columns:repeat(3,minmax(0,1fr));gap:14px;padding:0;border-radius:0;background:transparent;color:var(--ink)}
  :root.dark .cred-resumo{border:0}
  .cred-r{padding:16px 18px;border:1px solid var(--line);border-radius:16px;background:var(--card)}
  .cred-r-divida{grid-column:auto}
  .cred-r-rot,.cred-r-mes{color:var(--muted)}
  .cred-r-v,.cred-r-v2{font-family:var(--letra-titulo);font-size:26px;font-weight:650;letter-spacing:-.015em;line-height:1.2}
  .cred-r-graf{display:none}
  .cred-corpo{display:flex;align-items:flex-start;gap:16px}
  .cred-col{flex:1 1 300px;max-width:380px;gap:10px}
  .cred-ativas>.list,.cred-pagas>.list{gap:10px}
  .cred-det{display:block;flex:999 1 560px;min-width:0;padding:0;overflow:hidden}
  .cred-hp-acoes,.cred-barra,.cred-rot,.cred-sub{display:none}
  .cred-hp-corpo{gap:8px;padding:16px}
  .cred-hp-nome h3{font-family:var(--letra);font-size:15px;font-weight:600;letter-spacing:0}
  .cred-hp-nums{display:flex;justify-content:space-between;align-items:baseline;gap:12px}
  .cred-hp-nums .cred-v{font-weight:500}
  .cred-hp-nums .cred-hp-div .cred-v{font-weight:700}
  .cred-hp.on{border-color:var(--accent);box-shadow:0 0 0 1px var(--accent)}
}

/* --- a Agenda (o canvas M-Agenda): o cartão do mês e o painel do dia; no
   computador lado a lado --- */
.cal-pag{display:flex;flex-direction:column;gap:12px}
.cal-mes{padding:8px 8px 10px;border-radius:18px}
.cal-nav{display:flex;align-items:center;gap:4px;padding:0 0 6px}
.cal-nav-tit{flex:1;min-width:0;text-align:center}
.cal-nav-tit h2{margin:0;font-size:18px}
.cal-nav-tit p{margin:0}
.cal-legenda{display:flex;flex-wrap:wrap;justify-content:center;gap:4px 16px;padding-top:8px;font-size:12.5px;color:var(--muted)}
.cal-legenda span{display:inline-flex;align-items:center;gap:6px}
.cal-legenda .pt{width:8px;height:8px}
.cal-dica{flex-basis:100%;justify-content:center}
.cal-dia{display:flex;flex-direction:column;gap:12px;min-width:0}
.cal-dia-tit{margin:2px 2px 0;font-size:17px}
.cal-dia-lista{padding:0;overflow:hidden}
.cal-dia-lista .lbl{margin:0;padding:12px 14px 8px}
.cal-dia-lista .cal-ev+.lbl{border-top:1px solid var(--line)}
.cal-ev{display:flex;align-items:center;gap:12px;min-height:60px;padding:12px 14px;border-top:1px solid var(--line);cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.cal-ev:hover{background:var(--tint)}}
.cal-ev:active{background:var(--press)}
.cal-dia-lista .cal-ev:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.cal-ev-hora{flex:0 0 52px;width:52px}
.cal-ev-hora p{margin:0;font-weight:700}
.cal-ev-hora .small{font-weight:500}
.cal-ev-ic{flex:0 0 52px;width:52px;display:flex}
.cal-ev-txt{flex:1;min-width:0}
.cal-ev-txt p{margin:0}
.cal-ev-txt .title{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cal-ev-valor{flex:0 0 auto;font-weight:600;white-space:nowrap}
.cal-dia-vazio{margin:0;padding:14px}
.cal-dia-acoes{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:8px}
.cal-dia-acoes.um{grid-template-columns:minmax(0,1fr)}
@media(min-width:901px){
  .cal-pag{display:grid;grid-template-columns:minmax(0,1.4fr) minmax(300px,1fr);gap:16px;align-items:start}
  .cal-mes{padding:12px 12px 14px}
  .calday{height:64px}
  .cal-dica{flex-basis:auto}
}
/* ===== fim: 1.3.6 ===== */
/* ===== ajustes-v40c: 1.3 — a seleção nos Planeados e nos Modelos ===== */
/* (cloud/selecao-listas.js:selLDecorar com os tipos 'rec' e 'tpl') A caixa de
   marcar entra na linha do planeado antes do texto, sem padding nem margem:
   o gap da linha já a afasta. No modelo vai dentro do chip, mais pequena,
   para o chip não crescer. */
.plan-linha>[data-selbox]{padding:0;margin-right:0}
.plan-modelo>[data-selbox]{padding:0;margin-right:8px}
.plan-modelo>[data-selbox] .selck{width:20px;height:20px;border-radius:6px}
/* Ao ENTRAR na seleção as caixas desvanecem (selecao-listas.js:selLEntrou),
   como as dos Movimentos: no --medio, a curva de quem chega. Marcar e as
   repinturas de fundo não as voltam a animar — a classe só se põe ao entrar. */
#view [data-selbox].sel-entra{animation:veuEntra var(--medio) var(--curva-entra) backwards}
/* O outro tipo, em seleção (os modelos enquanto se marcam planeados, e o
   contrário): atenuado, porque ou se marcam uns ou outros (CW.selLOutro).
   Sem transição: a classe chega com os nós novos da repintura, de uma vez. */
#view .sel-fora{opacity:.5}
/* A barra dos planeados passou a ser a das visitas, com a contagem à vista
   no telemóvel: está na secção «ajustes-v40-5: 1.3», a seguir (.sel-l-duas). */
.sel-fundo #selLMudo[hidden]{display:none}
/* ===== fim: ajustes-v40c 1.3 ===== */
/* ===== ajustes-v40-5: 1.3 — Inquilinos e Visitas na seleção das Casas, e a barra dos Planeados ===== */
/* A barra dos planeados e das visitas (selecao-listas.js:selLBarraHtml, a
   classe .sel-l-duas): a das Casas — × Cancelar, a contagem ao meio e as
   ações —, com a razão de uma ação estar fora por baixo da contagem
   (#selLPorque). No telemóvel as ações descem para uma segunda linha: a
   .sel-l-quebra ocupa a largura toda e empurra-as; numa linha só, com a
   contagem, não cabiam a 375px. Sem espaço entre linhas, o da quebra (8px,
   o gap da barra) separa as duas. */
.sel-fundo.sel-l-duas{flex-wrap:wrap;row-gap:0}
.sel-fundo.sel-l-duas .sel-l-info{flex:1 1 0;min-width:0;margin:0;display:flex;flex-direction:column;align-items:center;text-align:center;line-height:1.25}
.sel-fundo.sel-l-duas .sel-l-info .small{color:var(--muted)}
.sel-fundo.sel-l-duas .sel-l-info .small:empty{display:none}
.sel-fundo.sel-l-duas .sel-l-quebra{flex:0 0 100%;height:0;margin-top:8px}
.sel-fundo.sel-l-duas>.btn:not(:first-child){flex:1 1 auto}
/* no ecrã largo é a barra azul-noite de uma linha só, a contagem à esquerda */
@media(min-width:901px){
  .sel-fundo.sel-l-duas{row-gap:10px}
  .sel-fundo.sel-l-duas .sel-l-quebra{display:none}
  .sel-fundo.sel-l-duas>.btn:not(:first-child){flex:0 0 auto}
  .sel-fundo.sel-l-duas .sel-l-info{flex:1 1 auto;align-items:flex-start;text-align:left}
  .sel-fundo.sel-l-duas .sel-l-info b{white-space:nowrap}
  .sel-fundo.sel-l-duas .sel-l-info .small{color:var(--side-text)}
}
/* A caixa entra na linha do inquilino antes do avatar e na da visita antes
   do bloco da data (selecao-listas.js:selLDecorar), sem padding nem margem:
   o gap da linha já a afasta (com o #view: a margem de todas as caixas,
   #view [data-selbox], ganhava-lhe). Na visita fica à altura do bloco da
   data, ao meio dele — a linha cresce com o texto, e ao meio da linha ficava
   abaixo do dia. */
#view .pes-linha>[data-selbox],#view .vis-linha>[data-selbox]{padding:0;margin-right:0}
#view .vis-linha>[data-selbox]{align-self:flex-start;min-height:48px}
/* no computador a linha do inquilino é uma grelha: em seleção (body.lst-sel)
   ganha à cabeça a coluna da caixa */
@media(min-width:900px){
  body.lst-sel .linha.pes-linha{grid-template-columns:22px 40px minmax(0,1.4fr) minmax(0,1fr) minmax(96px,auto)}
}
/* Marcada: o fundo cobalto suave da linha dos Contratos (.ct-linha.sel-on-card)
   e um filete cobalto à esquerda — o escurecimento forçado do Samsung Internet
   come os fundos, e o filete, com a caixa com o visto, distingue-a pela cor
   da frente. */
.pes-lista>.pes-linha.sel-on-card,.vis-lista>.vis-linha.sel-on-card{background:var(--accent-soft);box-shadow:inset 3px 0 0 var(--accent)}
/* o avatar e o selo cobalto têm o mesmo fundo da linha marcada, e sumiam nela:
   ficam no fundo do cartão, como o selo do prazo dos Contratos */
.pes-lista>.pes-linha.sel-on-card .pes-av:not(.pes-av-sem),
.vis-lista>.vis-linha.sel-on-card .badge:not(.grey):not(.amber):not(.red):not(.in):not(.out):not(.loan){background:var(--card)}
/* ===== fim: ajustes-v40-5 1.3 ===== */
/* ===== ajustes-v40c: 1.4 — a Agenda: o cartão «Por confirmar» ===== */
/* A coluna do dia (calendario.js:vCalendar): o painel do dia e, por baixo, o
   cartão dos por confirmar. No computador é a segunda coluna da .cal-pag. */
.cal-coluna{display:flex;flex-direction:column;gap:12px;min-width:0}
/* O cartão (calendario.js:calPendCard): o cabeçalho é um botão inteiro, com o
   desenho do cabeçalho do cartão dos Planeados (.plan-pend-cab); as linhas e a
   dica são as de lá (.plan-pend-linhas, .plan-pend-dica). O número vai num
   selo com a cor do crachá da barra de baixo (.tabbar a .cnt), que é o mesmo
   número: é o que liga o ícone ao cartão. */
.cal-pend{padding:0}
.cal-pend-h{margin:0;font:inherit;letter-spacing:0}
.cal-pend-cab{display:grid;grid-template-columns:minmax(0,1fr) auto auto;grid-template-areas:"tit n chev" "sub sub sub";align-items:center;gap:2px 10px;
  width:100%;min-height:44px;padding:16px 18px;border:0;border-radius:15px;background:transparent;color:var(--ink);font:inherit;text-align:left;cursor:pointer;
  transition:background-color var(--rapido) var(--curva)}
.cal-pend:not(.fechado) .cal-pend-cab{border-bottom-left-radius:0;border-bottom-right-radius:0}
@media(hover:hover) and (pointer:fine){.cal-pend-cab:hover{background:var(--tint)}}
.cal-pend-cab:active{background:var(--press)}
.cal-pend-cab:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.cal-pend-tit{grid-area:tit;display:flex;flex-wrap:wrap;align-items:center;gap:6px 10px;min-width:0}
.cal-pend-nome{font-family:var(--letra-titulo);font-size:16px;font-weight:650;letter-spacing:-.015em}
.cal-pend-n{grid-area:n;display:inline-grid;place-items:center;min-width:22px;height:22px;padding:0 7px;border-radius:999px;
  background:var(--out);color:var(--accent-ink);font-size:12.5px;font-weight:700;font-variant-numeric:tabular-nums}
.cal-pend-chev{grid-area:chev;display:inline-flex;color:var(--faint);transition:transform var(--medio) var(--curva)}
.cal-pend:not(.fechado) .cal-pend-chev{transform:rotate(180deg)}
.cal-pend-sub{grid-area:sub;margin:0}
.cal-pend:not(.fechado) .cal-pend-ver{display:none}
/* A dobra: uma transição num nó vivo (calendario.js:calPendAlternar troca o
   .fechado), retomada do sítio onde ia se se tocar outra vez a meio. A altura
   anda pelo grid-template-rows de 1fr a 0fr, com os dois valores escritos —
   como as secções da gaveta (.navsec-corpo); a partir de uma linha medida pelo
   conteúdo não interpolava (a nota do .fold). O conteúdo desvanece com ela.
   As duas na --curva-entra e no --medio, a abrir e a fechar: a que fecha
   também é uma saída, e uma saída que arranca devagar (a --curva-sai) atrasa
   o instante para que se está a olhar. O corte (overflow) só existe fechado e
   durante a viagem (.viagem): aberto e parado, os menus ⋯ das linhas abrem
   para fora do cartão. Fechado, o visibility tira as linhas do Tab e do leitor
   de ecrã — no FIM da viagem, para se verem a sair; a abrir, logo no início.
   Sem movimento, a regra geral desliga as transições e tudo é de uma vez. */
.cal-pend-corpo{display:grid;grid-template-rows:1fr;transition:grid-template-rows var(--medio) var(--curva-entra)}
.cal-pend.fechado>.cal-pend-corpo{grid-template-rows:0fr}
.cal-pend-dentro{min-height:0;min-width:0;opacity:1;visibility:visible;transition:opacity var(--medio) var(--curva-entra),visibility 0s}
.cal-pend.fechado .cal-pend-dentro{opacity:0;visibility:hidden;transition:opacity var(--medio) var(--curva-entra),visibility 0s var(--medio)}
.cal-pend.fechado .cal-pend-dentro,.cal-pend.viagem .cal-pend-dentro{overflow:hidden}
@media(max-width:520px){.cal-pend-cab{padding:14px}}
/* ===== fim: ajustes-v40c 1.4 ===== */
/* ===== redesign: 1.3.7 — a Análise ===== */
/* A Avaliação, as Projeções e o IRS · Anexo F como as pranchetas D-Avaliacao,
   D-Projecoes, D-Declaracao e M-SituacaoFiscal (avaliacao.js, projecoes.js,
   fisco.js). As três páginas são uma coluna de blocos com 14px entre eles; a
   barra do topo diz o âmbito em chips e tem as ações da página; os cartões
   têm o título na letra dos títulos; as tabelas rolam dentro da caixa e, nas
   que começam pelo nome, a primeira coluna fica presa ao rolar. */
.ana{display:flex;flex-direction:column;gap:14px;min-width:0}
.ana>*{min-width:0}
.ana>.cols{margin-top:0}
/* a barra do âmbito: chips, os campos da página e as ações */
.ana-barra{display:flex;flex-wrap:wrap;align-items:center;gap:10px 12px}
.ana-ambito{flex:1 1 auto;min-width:0}
.ana-ambito .chip{min-height:40px;max-width:100%;min-width:0}
/* um nome comprido (de imóvel ou de proprietário) leva reticências no texto
   do chip, que nunca passa da largura da barra: era a página a rolar de lado
   no telemóvel, com o chip cortado a meio da palavra e sem o × */
.ana-ambito .chip>span{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.ana-ambito .lbl+.chip{margin-left:-2px}
/* o rótulo «Titular» e o chip dele numa caixa só: quebram de linha juntos */
.fis-titular{display:inline-flex;align-items:center;gap:8px;min-width:0;max-width:100%;margin-left:8px}
.ana-acoes{display:flex;flex-wrap:wrap;gap:10px}
/* o cartão da Análise: cabeçalho com o título e o subtítulo, e o resto em coluna */
.ana-cartao{display:flex;flex-direction:column;gap:12px}
.ana-cab{display:flex;flex-wrap:wrap;align-items:baseline;gap:2px 10px;min-width:0}
.ana-extra{margin-left:auto;align-self:center;display:inline-flex}
.ana-tit{font-size:18px;line-height:1.25;margin:0}
.ana-tit .badge{margin-left:4px;vertical-align:3px;font-family:var(--letra);letter-spacing:0}
.ana-cartao>.livre{flex:1;justify-content:center}
.ana-cartao .hint,.ana-cartao p{margin:0}
@media(max-width:520px){.ana-tit{font-size:16px}}
/* as tabelas da Análise: cabeçalho em maiúsculas pequenas (as tabelas das
   pranchetas), linhas que se tocam com hover e premido diferentes, e a linha
   dos totais em cinzento */
.ana .table th{text-transform:uppercase;letter-spacing:.04em}
.ana .table td{vertical-align:middle}
.ana .table td .small{font-weight:400}
.ana .table tr[data-click]{cursor:pointer}
@media(hover:hover) and (pointer:fine){.ana .table tr[data-click]:hover td{background:var(--tint)}}
.ana .table tr[data-click]:active td{background:var(--press)}
.ana .table tr[data-click]:focus-visible td{background:var(--tint)}
.ana .table .ana-total td{background:var(--chip)}
.ana-fixa th:first-child,.ana-fixa td:first-child,.ana-fixa-1 .table th:first-child,.ana-fixa-1 .table td:first-child{position:sticky;left:0;z-index:1;background:var(--card)}
.ana-fixa-1 .table td:first-child{min-width:150px}
/* a célula presa da linha dos totais é cinzenta como o resto da linha (a
   regra de cima, da mesma força, pintava-a de branco) */
.ana-fixa-1 .table tr.ana-total td{background:var(--chip)}

/* ---- a Avaliação ---- */
/* o herói: o valor de mercado e o valor por rendimento em barras à mesma
   escala, e a diferença em grande ao lado */
.ava-heroi{display:flex;flex-wrap:wrap;align-items:center;gap:20px 40px;padding:22px}
.ava-barras{flex:1 1 360px;display:flex;flex-direction:column;gap:14px;min-width:0}
.ava-barra-bloco{display:flex;flex-direction:column;gap:6px;min-width:0;width:100%}
button.ava-barra-bloco,.ava-pct-btn{margin:-6px;padding:6px;width:calc(100% + 12px);border:0;border-radius:12px;background:transparent;color:inherit;font:inherit;text-align:left;cursor:pointer;transition:background var(--rapido) var(--curva)}
.ava-pct-btn{width:auto;align-self:flex-start}
@media(hover:hover) and (pointer:fine){button.ava-barra-bloco:hover,.ava-pct-btn:hover{background:var(--tint)}}
button.ava-barra-bloco:active,.ava-pct-btn:active{background:var(--press)}
button.ava-barra-bloco:focus-visible,.ava-pct-btn:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
.ava-barra-lin{display:flex;justify-content:space-between;align-items:baseline;gap:12px;font-weight:600;font-variant-numeric:tabular-nums}
.ava-barra-lin b{font-size:20px;font-weight:650;white-space:nowrap}
.ava-rend{color:var(--accent)}
.ava-trilho{display:block;height:14px;border-radius:7px;background:var(--chip);overflow:hidden}
.ava-enche{display:block;width:0;height:100%;border-radius:7px;background:var(--faint)}
.ava-enche-rend{background:var(--accent)}
.ava-dif{flex:1 1 280px;display:flex;flex-direction:column;align-items:flex-start;gap:6px;min-width:0}
.ava-dif p{margin:0}
.ava-pct{display:block;font-size:44px;line-height:1;font-variant-numeric:tabular-nums}
.ava-frase{font-size:15px}
.ava-porque{margin-left:-12px}
.ava-expl{display:none}
.ava-heroi.open .ava-expl{display:block}
@media(max-width:520px){.ava-heroi{padding:16px;gap:16px}.ava-pct{font-size:34px}.ava-barra-lin b{font-size:18px}}
/* os cinco rácios */
.ava-metricas,.prj-kpis,.fis-kpis{grid-template-columns:repeat(auto-fit,minmax(170px,1fr));gap:10px}
@media(min-width:521px){.ava-metricas .kpi .value,.prj-kpis .kpi .value,.fis-kpis .kpi .value{font-size:24px}}
/* o rótulo não passa por baixo do sinal da evolução (ou do «?»), no canto */
.ava-metricas .kpi .label,.prj-kpis .kpi .label,.fis-kpis .kpi .label{padding-right:20px}
@media(max-width:520px){.ava-metricas,.prj-kpis,.fis-kpis{grid-template-columns:repeat(2,minmax(0,1fr))}}
/* a conta de exploração: linhas com risca, o NOI numa faixa cinzenta */
.ava-conta{gap:0}
.ava-conta .ana-cab{margin-bottom:8px}
.ava-ce{display:flex;justify-content:space-between;gap:12px;padding:11px 0;border-top:1px solid var(--line);font-size:14.5px;font-variant-numeric:tabular-nums}
.ava-ce b{font-weight:600;white-space:nowrap}
.ava-ce-noi{margin:0 -18px;padding:11px 18px;background:var(--chip);font-weight:600}
.ava-ce-cf,.ava-ce-cf b{font-weight:700}
@media(max-width:520px){.ava-ce-noi{margin:0 -14px;padding:11px 14px}}
/* as contas entre proprietários: um quadrado por pessoa, verde quem recebe e
   laranja quem paga; por baixo, as rendas anuais e o NOI */
.ava-saldos{display:grid;grid-template-columns:repeat(auto-fill,minmax(150px,1fr));gap:12px}
.ava-saldo{display:flex;flex-direction:column;gap:2px;padding:14px;border-radius:12px;background:var(--chip);font-variant-numeric:tabular-nums;min-width:0}
.ava-saldo b{font-weight:600;overflow-wrap:anywhere}
.ava-saldo span{font-weight:700;color:var(--muted)}
.ava-saldo.in{background:var(--in-soft)}
.ava-saldo.in span{color:var(--in)}
.ava-saldo.out{background:var(--out-soft)}
.ava-saldo.out span{color:var(--out)}
.ava-acerto{display:flex;flex-wrap:wrap;gap:10px}
.ava-ind{display:grid;grid-template-columns:repeat(auto-fit,minmax(140px,1fr));gap:12px;font-size:14px}
.ava-ind>div{display:flex;flex-direction:column;gap:2px}
.ava-ind b{font-weight:600;font-variant-numeric:tabular-nums}
/* a ficha de um imóvel: o nome e a ocupação à cabeça */
.ava-cab-imovel{display:flex;align-items:flex-start;justify-content:space-between;gap:12px}
.ava-cab-imovel p{margin:2px 0 0}
.ava-nome{font-size:22px;margin:0;overflow-wrap:anywhere}
.ava-cab-imovel .badge{margin-top:4px;flex:0 0 auto}
.ava-tabela td:first-child{min-width:180px;white-space:normal}
/* as hipotecas de um imóvel: os números e o gráfico da dívida lado a lado
   (um por baixo do outro no telemóvel) — o gráfico escala pelo viewBox, e a
   toda a largura ficava com letras do dobro do corpo */
.ava-hip{display:grid;grid-template-columns:repeat(auto-fit,minmax(290px,1fr));gap:14px 28px;align-items:center}
.ava-hip>*{min-width:0}

/* ---- as Projeções ---- */
.prj-aviso{display:flex;flex-wrap:wrap;align-items:center;gap:10px 16px;padding:14px 18px;border-radius:16px;background:var(--warn-soft);color:var(--ink)}
.prj-aviso>svg{flex:0 0 auto;color:var(--warn)}
.prj-aviso p{flex:1 1 320px;margin:0;font-size:14.5px}
/* o cashflow de cada ano por baixo da sua coluna: as colunas do cBars vivem
   entre x=44 e x=354 num desenho de 360 de largura, e o desenho ocupa a
   largura toda — a grelha começa e acaba nas mesmas frações */
.prj-cfs{display:grid;grid-auto-flow:column;grid-auto-columns:minmax(0,1fr);padding:0 1.667% 0 12.222%;margin-top:-2px;font-size:12.5px;font-weight:700;text-align:center;font-variant-numeric:tabular-nums;white-space:nowrap}
@media(max-width:520px){.prj-cfs{font-size:11px}}
.prj-tabela td{white-space:nowrap}
/* o nome de cada contrato no cabeçalho parte em linhas: em maiúsculas, quatro
   nomes compridos empurravam o cashflow para fora da caixa no computador */
@media(min-width:521px){.prj-tabela thead th{white-space:normal;vertical-align:bottom;min-width:76px;max-width:150px}}

/* ---- o IRS · Anexo F ---- */
/* a faixa das regras do ano, em cobalto suave */
.fis-regras{display:flex;flex-direction:column;gap:8px;background:var(--accent-soft);border-color:var(--accent-soft);color:var(--accent-text)}
.fis-regras-cab{display:flex;flex-wrap:wrap;align-items:center;gap:6px 12px}
.fis-regras .badge{background:var(--card);color:var(--accent-text)}
.fis-regras .badge.amber{background:var(--warn-soft);color:var(--warn)}
.fis-regras .ana-tit{color:var(--ink)}
.fis-entrega{flex:1 1 260px;font-size:14.5px;font-weight:500}
.fis-guia-btn{margin-left:auto}
.fis-regras-txt{margin:0;font-size:14px}
.fis-novas .lbl{color:var(--accent-text)}
.fis-novas ul{margin:4px 0 0;padding-left:18px;font-size:13.5px}
.fis-novas li+li{margin-top:2px}
/* o imposto estimado em destaque, no azul-noite da barra lateral */
.fis-kpis>.kpi:last-child{background:var(--side);border-color:var(--side-line)}
.fis-kpis>.kpi:last-child .label,.fis-kpis>.kpi:last-child .foot,.fis-kpis>.kpi:last-child .expl{color:var(--side-text)}
.fis-kpis>.kpi:last-child .value{color:var(--side-ink)}
.fis-kpis>.kpi:last-child .expl{border-top-color:var(--side-line)}
.fis-kpis>.kpi:last-child::after{background:var(--side-on);color:var(--side-ink)}
/* as obrigações e o englobamento, a situação e os prazos, dois a dois */
.fis-grelha{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(440px,100%),1fr));gap:14px;align-items:start}
.fis-tratar{gap:10px}
.fis-ob{display:flex;flex-wrap:wrap;align-items:center;gap:8px 12px;padding:12px 0;border-top:1px solid var(--line)}
.fis-ob .fis-num{flex:0 0 26px;width:26px;justify-content:center;padding:0}
.fis-ob p{flex:1 1 200px;min-width:0;font-size:14.5px}
.fis-ob .btn{flex:0 0 auto;margin-left:auto}
.fis-outros{gap:6px}
.fis-eur{display:flex;align-items:center;gap:8px;max-width:260px;min-height:46px;padding:0 14px;border:1px solid var(--line2);border-radius:12px;background:var(--field)}
.fis-eur input{min-height:0;padding:0;border:0;border-radius:0;background:transparent}
.fis-eur input:focus-visible{outline:0}
.fis-eur:has(input:focus-visible){border-color:var(--accent);box-shadow:0 0 0 3px var(--accent-soft)}
.fis-eur>span{color:var(--muted);font-weight:500}
.fis-veredito{display:flex;align-items:center;gap:12px;padding:14px;border-radius:12px;background:var(--chip);font-size:14.5px}
.fis-veredito.bom{background:var(--in-soft);color:var(--in)}
.fis-veredito svg{flex:0 0 auto}
/* a situação fiscal em linhas (M-SituacaoFiscal): interruptores e o A/B */
.fis-sit{gap:0;padding:0;overflow:hidden}
.fis-sit .ana-cab{padding:16px 16px 10px}
.fis-linha{display:flex;align-items:center;gap:12px;min-height:60px;padding:10px 16px;border-top:1px solid var(--line)}
.fis-linha-txt{flex:1;min-width:0;margin:0}
.fis-linha-txt b{display:block;font-weight:600}
.fis-linha-txt .small{display:block}
.fis-sit-nota{padding:0 16px 14px}
.fis-sit-lbl{margin:0;padding:12px 16px 2px;border-top:1px solid var(--line)}
.fis-sit-lbl+.fis-linha{border-top:0}
/* a linha de um interruptor é o rótulo dele: toca-se inteira */
.fis-linha-toque{font-size:inherit;font-weight:400;cursor:pointer;transition:background-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.fis-linha-toque:hover{background:var(--tint)}}
.fis-linha-toque:active{background:var(--press)}
.fis-ab{flex:0 0 auto}
.fis-ab>button{flex:0 0 44px;width:44px}
/* os prazos da AT: o que é, e o selo da urgência à direita */
.fis-prazos{gap:10px}
.fis-pz{display:flex;align-items:center;gap:12px;min-height:48px;padding:10px 0;border-top:1px solid var(--line)}
.fis-pz.tap{margin:0 -18px;padding:10px 18px;cursor:pointer}
@media(hover:hover) and (pointer:fine){.fis-pz.tap:hover{background:var(--tint)}}
.fis-pz.tap:active{background:var(--press)}
.fis-pz>div{flex:1;min-width:0}
.fis-pz b{display:block;font-weight:600;font-size:14.5px}
.fis-pz .small{display:block}
.fis-pz .badge{flex:0 0 auto}
@media(max-width:520px){.fis-pz.tap{margin:0 -14px;padding:10px 14px}}
.fis-resumo .fis-ct{min-width:200px}
@media(pointer:coarse){
  .ana-ambito .chip,.fis-ab>button,.ana .btn.sm{min-height:44px}
  /* um botão só de ícone pequeno (o ⓘ das contas entre proprietários) fica 44×44 */
  .ana .btn.sm.so-icone{width:44px}
}
@media(max-width:520px){
  .ana-barra{gap:8px}
  /* no telemóvel as ações da página (o «Partilhar resumo» da Declaração)
     ficam numa linha delas, lado a lado, a dividir a largura */
  .ana-acoes{width:100%;gap:8px}
  .ana-acoes>.btn{flex:1 1 auto;padding:0 10px;font-size:14px}
  .fis-ob .btn{margin-left:38px}
  /* o rótulo do titular desce com o chip para a fila seguinte: sem recuo */
  .fis-titular{margin-left:0}
  /* o botão do canto do cabeçalho (o ⓘ das contas) fica à direita do título
     e do subtítulo, em vez de cair numa fila só dele por baixo */
  .ana-cab:has(>.ana-extra){display:grid;grid-template-columns:minmax(0,1fr) auto;column-gap:10px}
  .ana-cab>.ana-extra{grid-column:2;grid-row:1/3;margin-left:0}
  /* no guia, o título da dobra inteiro vale mais do que a contagem dos passos */
  #fold_fiscoGuia .fsum{display:none}
}
/* ===== fim: 1.3.7 ===== */
/* ===== ajustes-v40c: 1.5 — Projeções e Avaliação: chips e a roda dentada ===== */
/* O topo das Projeções e da Avaliação é a fila de chips das listas
   (vistas.js:anaChips: .mov-chips, .mov-chip), sem pesquisa nem funil. Na
   Avaliação o botão de partilha vai na mesma linha, encostado à direita,
   também no telemóvel (a secção ajustes-v40d 1.5). */
.ana-topo{display:flex;flex-wrap:wrap;align-items:center;gap:8px 12px;margin:0 0 12px}
.ana-topo>.mov-chips{flex:1 1 auto;min-width:0;margin:0}
.ana-topo>.ana-acoes{margin-left:auto}
/* um nome comprido no chip leva reticências e o chip não passa da largura:
   a 375px a página não rola de lado */
.ana-chips .mov-chip{min-width:0}
.ana-chips .mov-chip .sel,.ana-chips .mov-chip .selbtn{min-width:0;max-width:100%}
.ana-chips .mov-chip .selbtn span{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
/* a janela das opções (vistas.js:anaOpcoes): as linhas das Definições ›
   Valores por omissão (.def-vr) numa lista, e a nota por baixo */
.ana-opcoes{margin:0}
.ana-opcoes-nota{margin:12px 0 0}
/* ===== fim: ajustes-v40c 1.5 ===== */
/* ===== ajustes-v40d: 1.5 — o botão de partilha da Avaliação ===== */
/* As ações da Avaliação são um botão só, de ícone (avaliacao.js:avaPartilha:
   o .btn.so-icone, 44×44), que abre o menu de ações da casa (.menupop). No
   telemóvel fica na linha do chip, à direita, em vez de descer para uma linha
   dele (a regra do .ana-acoes de largura inteira, na secção 1.3.7, é a da
   Declaração). O menu tem a largura das opções, sem partir «Exportar
   movimentos (CSV)» em duas linhas, e nunca passa da largura do ecrã. */
@media(max-width:520px){.ana-topo>.ana-acoes{width:auto}}
.ava-partilha .menupop{width:max-content;max-width:calc(100vw - 32px)}
/* ===== fim: ajustes-v40d 1.5 ===== */
/* ===== redesign: 1.3.8 — as Definições ===== */
/* A raiz (definicoes.js:raizDasDefinicoes, o canvas M-Definicoes): secções
   com o rótulo e as linhas numa lista com divisórias; no computador correm
   em duas colunas. */
.def-raiz{display:flex;flex-direction:column;gap:18px}
.def-sec{display:flex;flex-direction:column;gap:10px;min-width:0}
.def-sec>.card{margin:0}
.def-sec-tit{margin:4px 4px 0;font-family:var(--letra);font-size:12px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--muted)}
.card.def-lista{padding:0;overflow:hidden;margin-bottom:14px}
.def-lista>*+*{border-top:1px solid var(--line)}
.linha.def-linha{width:100%;border:0;border-radius:0;background:transparent;font:inherit;color:inherit;text-align:left}
@media(hover:hover) and (pointer:fine){.def-linha:hover{background:var(--tint)}}
.def-linha .ic{background:var(--chip);color:var(--muted)}
.def-linha .txt b{font-weight:600}
.def-linha .txt .small{display:block}
.def-cracha{flex:0 0 auto}
.def-sair{width:100%}
@media(min-width:1100px){
  .def-raiz{display:block;columns:2 360px;column-gap:24px}
  .def-sec{break-inside:avoid;margin-bottom:22px}
  .def-sair{width:auto}
}
/* o Tema na própria raiz: o que o automático resolve, e o segmentado */
.def-tema{display:flex;flex-direction:column;gap:10px;padding:12px 14px 14px}
.def-tema-cab{display:flex;align-items:center;gap:8px;width:100%;min-height:36px;padding:0;border:0;border-radius:8px;background:transparent;font:inherit;color:inherit;text-align:left;cursor:pointer}
.def-tema-cab b{font-weight:600}
.def-tema-cab .small{flex:1;text-align:right}
.def-tema-cab .seta{display:inline-flex;color:var(--faint)}
.def-tema .segm>button{min-height:40px}
/* A cabeça das subpáginas (definicoes.js:cabecaDaSubpagina): no telemóvel o
   Voltar; no computador a navegação lateral das Definições, posta ao lado do
   conteúdo — o canvas, D-DefCategorias. */
.def-nav{display:none}
.def-nav-item{display:flex;align-items:center;justify-content:space-between;gap:8px;min-height:40px;padding:0 12px;border:0;border-radius:10px;background:transparent;color:var(--muted);font:inherit;font-size:14.5px;text-align:left;cursor:pointer;
  transition:background-color var(--rapido) var(--curva),color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.def-nav-item:hover{background:var(--tint);color:var(--ink)}}
.def-nav-item:active{background:var(--press)}
.def-nav-item.on{background:var(--card);color:var(--ink);font-weight:600;box-shadow:0 1px 2px rgba(16,24,40,.1)}
@media(min-width:901px){
  .wrap:has(>.def-nav){position:relative;padding-left:calc(22px + var(--inset-left) + 252px)}
  .wrap>.def-voltar{display:none}
  .def-nav{display:flex;flex-direction:column;gap:2px;position:absolute;top:18px;left:calc(22px + var(--inset-left));width:228px;padding:0;overflow:visible}
  .def-nav .lbl{padding:14px 12px 4px}
  .def-nav .lbl:first-child{padding-top:0}
}
/* o que as subpáginas têm em comum: a frase do que a página é, a linha das
   ações, os blocos (cartões com título) e os pares lado a lado */
.def-intro{margin:0 0 14px;max-width:72ch;color:var(--muted);font-size:14px}
.def-cab{display:flex;flex-wrap:wrap;align-items:center;gap:10px 12px;margin-bottom:14px}
.def-cab>.def-intro{flex:1 1 320px;margin:0}
.def-cab-acoes{display:flex;flex-wrap:wrap;gap:8px;margin-left:auto}
.def-cab-acoes>.btn.ghost{color:var(--muted);font-weight:500}
.segm.def-abas{display:inline-flex;flex:0 0 auto}
.def-abas>button{flex:0 0 auto;padding:0 16px}
.def-nota{margin:14px 0}
.def-ligacao{border:0;padding:0;background:transparent;color:var(--accent);font:inherit;font-weight:600;cursor:pointer;text-decoration:underline;text-underline-offset:2px}
@media(hover:hover) and (pointer:fine){.def-ligacao:hover{color:var(--accent-text)}}
.def-bloco{display:flex;flex-direction:column;gap:10px;margin-bottom:14px}
.def-bloco h3{margin:0;font-size:17px}
.def-bloco p{margin:0}
.def-bloco-cab{display:flex;flex-wrap:wrap;align-items:center;gap:8px 10px}
.def-bloco-cab h3{flex:1 1 auto}
.def-botoes{display:flex;flex-wrap:wrap;gap:8px}
.def-par{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(320px,100%),1fr));gap:14px;margin-bottom:14px}
.def-par>.def-bloco{margin:0}
.def-ficheiro{display:flex;flex-wrap:wrap;align-items:center;gap:8px;padding:14px;border:1px dashed var(--line2);border-radius:12px;background:var(--chip)}
.def-perigo{flex-direction:row;flex-wrap:wrap;align-items:center;gap:12px 24px;border-color:color-mix(in srgb,var(--danger) 28%,var(--line))}
.def-perigo-txt{flex:1 1 380px;display:flex;flex-direction:column;gap:6px}
/* Valores por omissão (M-ValoresOmissao): o que é à esquerda, o campo e a
   unidade à direita; o rótulo é a linha inteira */
.def-vr{display:flex;align-items:center;justify-content:space-between;gap:12px;min-height:64px;padding:10px 14px;font-weight:400;font-size:15px;cursor:text}
.def-vr-txt{display:flex;flex-direction:column;flex:1;min-width:0}
.def-vr-txt b{font-weight:600}
.def-valor{display:flex;align-items:center;gap:8px;flex:0 0 auto}
.def-valor input{width:96px;min-height:44px;padding:8px 12px;text-align:right;font-variant-numeric:tabular-nums}
/* a unidade tem a mesma largura em todas as linhas («%» e «anos»), para os
   campos ficarem numa coluna direita também no telemóvel */
.def-unidade{min-width:32px;color:var(--muted);font-size:14px}
@media(max-width:520px){.def-valor{gap:6px}.def-valor input{width:84px;padding:8px 10px}}
/* os filtros comuns: a linha abre a edição, o lixo apaga */
.def-filtro{display:flex;align-items:center;gap:4px;padding-right:8px}
.def-filtro .def-linha{flex:1;min-width:0}
/* Categorias, etiquetas e IRS (D-DefCategorias): a tabela de cada árvore,
   com as subcategorias recolhidas por baixo; quando a tabela é estreita cada
   linha parte-se em duas, com os rótulos à vista (ver o @container defcat,
   mais abaixo) */
.card.def-tabela{padding:0;overflow:hidden;margin-bottom:14px}
.def-cat{display:grid;grid-template-columns:minmax(0,1.6fr) 96px minmax(0,1.5fr) 110px 44px;align-items:center;gap:12px;min-height:52px;padding:4px 14px;border-top:1px solid var(--line);font-size:14.5px}
.def-tabela.sem-irs .def-cat{grid-template-columns:minmax(0,1.6fr) 96px 110px 44px}
.def-cat-tit{border-top:0;min-height:42px;font-size:12px;font-weight:600;color:var(--muted);letter-spacing:.04em;text-transform:uppercase}
.def-cat-tit>span:nth-child(2){text-align:right}
.def-cat-tit>span:nth-last-child(2){text-align:center}
.def-cat-nome{display:flex;align-items:center;gap:6px;min-width:0}
.def-cat-nome b,.def-cat-nome>span:last-child{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.def-cat-nome b{font-weight:600}
.def-cat-abre{flex:0 0 32px;width:32px;height:32px;display:inline-grid;place-items:center;padding:0;border:0;border-radius:8px;background:transparent;color:var(--muted);cursor:pointer}
@media(hover:hover) and (pointer:fine){button.def-cat-abre:hover{background:var(--tint)}}
button.def-cat-abre:active{background:var(--press)}
.def-cat-abre svg{transition:transform var(--rapido) var(--curva)}
.def-cat.aberta .def-cat-abre svg{transform:rotate(90deg)}
.def-cat-n{text-align:right;color:var(--muted);font-variant-numeric:tabular-nums}
.def-cat-col{display:block;min-width:0;font-weight:400}
.def-cat-col .selbtn{min-height:36px;padding:0 10px;border-radius:10px;font-size:13.5px}
.def-cat-col.nao .selbtn span{color:var(--out)}
.def-cat-col.herda .selbtn span{color:var(--muted)}
/* o «Fora dos totais» é um <label> com o interruptor: o rótulo também liga */
.def-cat-fora{display:flex;align-items:center;justify-content:center;justify-self:center;gap:8px;font-weight:400;cursor:pointer}
.def-cat-fora:has(:disabled){cursor:not-allowed}
.def-cat-menu{display:flex;justify-content:flex-end}
.def-sub{background:var(--chip)}
.def-sub .def-cat-nome{padding-left:38px}
.def-so-tel{display:none}
.def-oculto{position:absolute;width:1px;height:1px;margin:-1px;overflow:hidden;clip-path:inset(50%);white-space:nowrap}
/* as opções da coluna do Anexo F partem em linhas em vez de se cortarem:
   «Obras antes do arrendamento (24 meses)» tem a regra no nome */
.def-cat-col .selopt span{white-space:normal;overflow:visible;text-overflow:clip}
/* A linha parte-se em duas quando a TABELA é estreita, e não o ecrã: dos
   901px para cima a navegação lateral das Definições come 274px, e a 920px a
   tabela ficava com 360 (os nomes com 0px e os títulos uns por cima dos
   outros). Mede-se o cartão; um browser sem container queries fica com a
   regra do ecrã de antes. A lista da coluna do Anexo F, estreita, vai até à
   borda do cartão (100cqi menos o padding); larga, até 340px. */
@supports (container-type:inline-size){
  .card.def-tabela{container:defcat/inline-size}
  @container defcat (max-width:640px){
    .def-cat,.def-tabela.sem-irs .def-cat{grid-template-columns:minmax(0,1fr) auto 40px;grid-template-areas:"nome n menu" "col fora fora";gap:6px 10px;padding:8px 8px 10px 12px}
    .def-tabela.sem-irs .def-cat{grid-template-areas:"nome n menu" "fora fora fora"}
    .def-cat-tit{display:none}
    .def-cat-nome{grid-area:nome}
    .def-cat-n{grid-area:n}
    .def-cat-col{grid-area:col}
    .def-cat-fora{grid-area:fora;justify-self:end;justify-content:flex-end}
    .def-cat-menu{grid-area:menu}
    .def-so-tel{display:inline}
    .def-sub .def-cat-nome{padding-left:16px}
    .def-cat-col .selpop{right:auto;width:max-content;min-width:100%;max-width:calc(100cqi - 24px)}
  }
  @container defcat (min-width:760px){
    .def-cat-col .selpop{right:auto;width:max-content;min-width:100%;max-width:340px}
  }
}
@supports not (container-type:inline-size){
  @media(max-width:700px){
    .def-cat,.def-tabela.sem-irs .def-cat{grid-template-columns:minmax(0,1fr) auto 40px;grid-template-areas:"nome n menu" "col fora fora";gap:6px 10px;padding:8px 8px 10px 12px}
    .def-tabela.sem-irs .def-cat{grid-template-areas:"nome n menu" "fora fora fora"}
    .def-cat-tit{display:none}
    .def-cat-nome{grid-area:nome}
    .def-cat-n{grid-area:n}
    .def-cat-col{grid-area:col}
    .def-cat-fora{grid-area:fora;justify-self:end;justify-content:flex-end}
    .def-cat-menu{grid-area:menu}
    .def-so-tel{display:inline}
    .def-sub .def-cat-nome{padding-left:16px}
  }
}
/* «Repor as colunas do Anexo F» numa linha só dela, por baixo da nota: no
   meio do parágrafo, os 44px do dedo abriam um vão entre duas linhas */
.def-repor{margin:-6px 0 14px}
.def-etiquetas{display:flex;flex-wrap:wrap;gap:8px}
.def-etiqueta{display:inline-flex;align-items:center;gap:6px;min-height:36px;padding:0 4px 0 12px;border:1px solid var(--line2);border-radius:999px;background:var(--card);font-size:14px;font-weight:500}
.def-etiqueta .n{color:var(--muted);font-variant-numeric:tabular-nums}
.def-etiqueta button{display:inline-grid;place-items:center;width:28px;height:28px;padding:0;border:0;border-radius:999px;background:transparent;color:var(--muted);cursor:pointer}
@media(hover:hover) and (pointer:fine){.def-etiqueta button:hover{background:var(--tint);color:var(--danger)}}
.def-etiqueta button:active{background:var(--press)}
.def-art41 p{font-size:14px}
/* Grupos (M-Grupos): um cartão por grupo; os partilhados com a ligação, os
   pedidos e os membros */
.grp-lista{display:grid;gap:14px;margin-bottom:14px}
@media(min-width:1100px){.grp-lista{grid-template-columns:repeat(2,minmax(0,1fr));align-items:start}}
.grp-cartao{display:flex;flex-direction:column;gap:10px}
.grp-cartao>p{margin:0}
.grp-cab{display:flex;flex-wrap:wrap;align-items:center;gap:6px 10px}
.grp-cab h3{margin:0;min-width:0;font-size:18px;overflow-wrap:anywhere}
.grp-parte{display:flex;flex-direction:column;gap:6px;padding-top:10px;border-top:1px solid var(--line)}
.grp-parte p{margin:0}
.grp-ligacao{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:space-between;gap:8px 12px}
.grp-pedido{padding:12px;border:0;border-radius:12px;background:var(--accent-soft)}
.grp-pedido+.grp-pedido{margin-top:-2px}
.grp-acoes{display:flex;flex-wrap:wrap;gap:8px}
.grp-membros{display:flex;flex-direction:column;gap:4px;margin:0;padding:0;list-style:none;font-size:14.5px}
/* um pedido por responder destaca o cartão inteiro (o contorno de 2px do
   canvas: o segundo pixel é a sombra, para o cartão não saltar), e o
   «Desativar» da ligação tem o texto vermelho */
.card.grp-partilhado:has(.grp-pedido){border-color:var(--accent);box-shadow:0 0 0 1px var(--accent)}
.btn.grp-perigo{color:var(--danger)}
/* a janela do grupo privado: o erro de um grupo sem membros na caixa deles */
#g_membros.err{box-shadow:none}
#g_membros.err>.tagbox{border:2px solid var(--danger)}
/* Colaboradores e cargos (D-Colaboradores) */
.colab-cartao{display:flex;flex-direction:column;margin-bottom:14px}
.colab-cartao>.def-bloco-cab{margin-bottom:6px}
.colab-cartao h3{margin:0;font-size:17px}
.colab-linha{display:flex;flex-wrap:wrap;align-items:center;gap:10px 12px;padding:12px 0;border-top:1px solid var(--line)}
.colab-txt{display:flex;flex-direction:column;flex:1 1 200px;min-width:0}
.colab-txt b{font-weight:600}
.colab-acoes{display:flex;gap:6px;margin-left:auto}
.colab-vazio,.colab-nota{margin:8px 0 0}
.colab-cargo{display:flex;flex-direction:column;gap:6px;padding:12px 0;border-top:1px solid var(--line)}
.colab-cargo>p{margin:0}
.colab-cargo-cab{display:flex;align-items:center;gap:10px}
.colab-abre{align-self:flex-start;display:inline-flex;align-items:center;gap:6px;min-height:36px;padding:0 10px 0 6px;border:0;border-radius:10px;background:transparent;color:var(--accent-text);font:inherit;font-size:14px;font-weight:600;cursor:pointer}
@media(hover:hover) and (pointer:fine){.colab-abre:hover{background:var(--tint)}}
.colab-abre:active{background:var(--press)}
.colab-abre svg{transition:transform var(--rapido) var(--curva)}
.colab-abre[aria-expanded="true"] svg{transform:rotate(90deg)}
.colab-perms{max-width:520px;border:1px solid var(--line);border-radius:12px;overflow:hidden}
.colab-perms[hidden]{display:none}
.colab-perm{display:grid;grid-template-columns:minmax(0,1fr) 72px 92px;align-items:center;min-height:40px;padding:0 12px;border-top:1px solid var(--line);font-size:14px}
.colab-perm:first-child{border-top:0}
.colab-perm-tit{min-height:36px;background:var(--chip);font-size:12px;font-weight:600;color:var(--muted);letter-spacing:.04em;text-transform:uppercase}
.colab-perm>span:not(:first-child){display:flex;justify-content:center}
.colab-sim{color:var(--in)}
.colab-traco{display:block;width:12px;height:2px;border-radius:2px;background:var(--faint)}
/* com dois cargos ou mais e o cartão largo (o canvas, D-Colaboradores), o
   primeiro à esquerda com a tabela e os outros à direita, com a divisória ao
   meio; estreito, uns por baixo dos outros. Mede-se o cartão, e não o ecrã:
   a navegação lateral das Definições também come largura. */
@supports (container-type:inline-size){
  .colab-cargos-cartao{container:colabcargos/inline-size}
  @container colabcargos (min-width:700px){
    .colab-cargos-dois{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1fr)}
    .colab-cargos-dois>.colab-cargo{padding-right:18px;border-right:1px solid var(--line)}
    .colab-cargos-resto{min-width:0}
    .colab-cargos-resto>.colab-cargo{padding-left:18px}
  }
}
/* a app vista por um colaborador (M-Colaborador): «Colaboras com …» */
.colab-com{display:flex;flex-direction:column;gap:12px;margin-bottom:14px}
.colab-com p{margin:0;font-size:14.5px}
.colab-com-cab{display:flex;align-items:center;gap:12px}
.colab-com-cab b{font-size:17px;font-weight:700}
.avatar.colab-com-av{width:42px;height:42px;flex:0 0 42px;background:var(--side);color:var(--side-ink)}
.colab-aviso{display:flex;align-items:flex-start;gap:8px;margin:0;padding:10px 12px;border-radius:12px;background:var(--chip);color:var(--muted);font-size:14px}
.colab-aviso svg{flex:0 0 auto;margin-top:1px}
/* as janelas do convite (M-Convidar, M-ConviteCriado) */
.colab-cargos{display:flex;flex-direction:column;gap:8px}
.colab-cargos .flabel{margin:0}
.colab-cargos>.btn{align-self:flex-start}
.colab-cargo-op{display:flex;align-items:flex-start;gap:12px;width:100%;padding:12px 14px;border:1px solid var(--line2);border-radius:12px;background:var(--card);color:var(--ink);font:inherit;text-align:left;cursor:pointer;
  transition:background-color var(--rapido) var(--curva),border-color var(--rapido) var(--curva)}
@media(hover:hover) and (pointer:fine){.colab-cargo-op:hover{background:var(--tint)}}
.colab-cargo-op:active{background:var(--press)}
.colab-cargo-op.on{border-color:var(--accent);background:var(--accent-soft)}
.colab-radio{flex:0 0 20px;width:20px;height:20px;margin-top:1px;border:2px solid var(--line2);border-radius:50%;background:var(--card)}
.colab-cargo-op.on .colab-radio{border:6px solid var(--accent)}
.colab-grupos{display:flex;flex-wrap:wrap;align-items:center;gap:8px;margin-bottom:10px}
/* os imóveis do convite e do «Mudar» (o canvas, M-Convidar): uma lista num
   cartão, linhas de 52px com divisórias, a caixa de 22px */
.colab-casas{display:flex;flex-direction:column;border:1px solid var(--line);border-radius:14px;background:var(--card);overflow:hidden}
.check.colab-casa{gap:12px;min-height:52px;padding:6px 14px;font-weight:400;
  transition:background-color var(--rapido) var(--curva)}
.colab-casa+.colab-casa{border-top:1px solid var(--line)}
.check.colab-casa input{width:22px;height:22px}
@media(hover:hover) and (pointer:fine){.colab-casa:hover{background:var(--tint)}}
.colab-casa:active{background:var(--press)}
/* as caixas Ver/Adicionar/Editar da janela do cargo: o rótulo é a área de
   toque (44px no dedo, mais abaixo) */
.colab-perm-caixas{display:flex;gap:14px;flex:0 0 auto}
.check.colab-perm-caixa{gap:6px;font-size:14px}
.colab-pronto{display:flex;flex-direction:column;gap:14px}
.colab-pronto-ic{align-self:center;display:grid;place-items:center;width:60px;height:60px;border-radius:50%;background:var(--in-soft);color:var(--in)}
.colab-pronto-sub{margin:0;text-align:center}
.colab-pronto-lig{display:flex;flex-direction:column;gap:8px;padding:14px;border:1px solid var(--line);border-radius:14px;background:var(--chip)}
.colab-pronto-lig p{margin:0}
.colab-url{font-family:ui-monospace,Menlo,Consolas,monospace;font-size:13px}
.colab-pronto .colab-aviso{background:var(--warn-soft);color:var(--warn)}
/* o foco vê-se nos botões desenhados aqui, como nos da casa */
.def-tema-cab:focus-visible,.def-nav-item:focus-visible,.def-cat-abre:focus-visible,.def-etiqueta button:focus-visible,.def-ligacao:focus-visible,
.colab-abre:focus-visible,.colab-cargo-op:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
@media(pointer:coarse){
  .def-tema-cab,.def-tema .segm>button,.def-abas>button,.def-nav-item,.def-ligacao,.colab-abre,.def-cat-col .selbtn,.def-cat-fora{min-height:44px}
  /* a seta fica com 40px de largura (os nomes já se apertam a 390), e a área
     de toque cresce 2px para cada lado */
  .def-cat-abre{width:40px;height:40px;flex-basis:40px}
  button.def-cat-abre{position:relative}
  button.def-cat-abre::before{content:"";position:absolute;inset:-2px;border-radius:10px}
  /* o × da etiqueta tem 44px e come o contorno do chip, para ele não crescer */
  .def-etiqueta{min-height:44px;padding-right:0}
  .def-etiqueta button{width:44px;height:44px;margin:-1px -1px -1px 0}
  .colab-perm-caixas{gap:2px}
  .check.colab-perm-caixa{min-height:44px;padding:0 8px}
  .stat.colab-perm-linha{padding:0}
}
@media(max-width:520px){
  .segm.def-abas{display:flex;width:100%}
  .def-abas>button{flex:1 1 0;padding:0 8px}
  .def-cab-acoes{width:100%}
  .def-cab-acoes>.btn{flex:1 1 auto}
  .colab-acoes{width:100%}
  .colab-acoes>.btn{flex:1 1 0}
  .colab-convite .colab-acoes{width:auto}
  .colab-convite .colab-acoes>.btn{flex:0 0 auto}
}
/* ===== fim: 1.3.8 ===== */
/* ===== redesign: 1.3.9 — a conta, a entrada, a ajuda, as novidades e os primeiros passos ===== */
/* web/cloud/guia.js, web/cloud/partilha.js, web/cloud/ajuda.js,
   web/cloud/entrada.js e web/cloud/novidades.js: as pranchetas
   M-PrimeirosPassos, M-Tutorial, M-Partilha, M-ConviteAceitar, M-Entrar,
   M-CriarConta, M-Termos, M-Atualizar, M-Ajuda, M-NovoPedido e M-Novidades.
   Classes novas com prefixo da área: pp- (primeiros passos), guia- (o
   tutorial), pd- (os pedidos), pt- (a segurança e a partilha entre contas), cv- (os convites),
   ent- (a entrada), tg- (os termos), upd- (a atualização), aj- (a ajuda),
   tk- (o pedido ao suporte) e nov- (as novidades). */

/* ---- cloud/guia.js:cartaoPassos e :jornadaInicial (M-PrimeirosPassos) ----
   As boas-vindas são um cartão azul-noite (o --side, igual nos dois temas)
   com o mosaico cobalto por cima (lista-imoveis.js:imvMosaico, a classe
   .imv-mosaico da folha dos Imóveis — o mesmo desenho das capas sem foto).
   Depois o cartão dos passos: o título e a conta, a barra verde do que está
   feito, e um passo por linha. Sem traço entre os círculos: numa lista não
   há nada a ligar, e o do passo atual é cheio (era transparente, e o traço da
   fita antiga passava-lhe por cima). Sem transição nem animação, de
   propósito: o cartão nasce novo a cada render (design.md, Movimento). */
.pp-jornada{display:grid;gap:14px;margin-bottom:14px;min-width:0}
.pp-boas{border-radius:20px;overflow:hidden;background:var(--side);color:var(--side-ink);border:1px solid var(--side-line)}
.pp-boas-mosaico{height:76px;opacity:.9}
.pp-boas-txt{padding:18px;display:grid;gap:6px}
.pp-boas-txt h2{margin:0;font-size:24px;line-height:1.15;color:var(--side-ink)}
.pp-boas-txt p{margin:0;font-size:14.5px;color:var(--side-text)}
.card.pp-cartao{padding:0;overflow:hidden}
.pp-cab{display:flex;align-items:center;gap:10px;padding:14px 14px 10px}
.pp-cab h2{flex:1;min-width:0;margin:0;font-size:17px}
.pp-cab .small{font-variant-numeric:tabular-nums;white-space:nowrap}
.pp-barra{height:6px;margin:0 14px 6px;border-radius:3px;background:var(--line);overflow:hidden}
.pp-barra>span{display:block;width:0;height:100%;border-radius:3px;background:var(--in)}
.jornada{list-style:none;margin:0;padding:0}
.jornada-passo{display:flex;gap:14px;padding:14px}
.jornada-passo+.jornada-passo{border-top:1px solid var(--line)}
.jornada-passo.atual{background:var(--accent-soft)}
.jornada-n{flex:0 0 28px;width:28px;height:28px;border-radius:50%;display:grid;place-items:center;font-size:13px;font-weight:700;font-variant-numeric:tabular-nums;background:var(--chip);color:var(--muted);border:1px solid var(--line2)}
.jornada-n svg{stroke-width:2.4}
.jornada-passo.feito .jornada-n{background:var(--in-soft);border-color:var(--in-soft);color:var(--in)}
.jornada-passo.atual .jornada-n{background:var(--accent);border-color:var(--accent);color:var(--accent-ink)}
.jornada-txt{flex:1;min-width:0;display:flex;flex-direction:column;gap:2px}
.jornada-l{display:block;font-weight:600;color:var(--ink);overflow-wrap:anywhere}
.jornada-passo.feito .jornada-l{color:var(--muted);text-decoration:line-through}
.jornada-passo.atual .jornada-l{font-size:16px;font-weight:700}
.jornada-porque{font-size:14px;color:var(--accent-text)}
.jornada-acoes{display:flex;flex-wrap:wrap;gap:8px;margin-top:8px}
.btn.ghost.pp-fora{justify-self:center;color:var(--muted);font-weight:500;font-size:14px}
/* no computador, com as boas-vindas, as duas lado a lado: o olá à esquerda
   (o mosaico estica até ao fundo) e os passos à direita */
@media(min-width:1100px){
  .pp-jornada.pp-com-boas{grid-template-columns:minmax(0,5fr) minmax(0,7fr);align-items:stretch}
  .pp-com-boas>.pp-boas{display:flex;flex-direction:column}
  .pp-com-boas>.pp-boas>.pp-boas-mosaico{flex:1 1 76px;min-height:76px}
  .pp-com-boas>.pp-fora{grid-column:2}
}

/* ---- cloud/guia.js:guiaPintar — o cartão do tutorial (M-Tutorial) ----
   O azul-noite da barra lateral, por cima do claro: lê-se como uma camada
   que não é da página. Dois tons escritos à mão, do canvas, que valem nos
   dois temas porque assentam sempre no --side: o texto do passo (#dce2f0) e
   o traço aceso da fita (#9fb4ff, o cobalto claro). */
.guia-cartao{display:flex;flex-direction:column;gap:10px;padding:16px;border-radius:18px;background:var(--side);color:var(--side-ink);border:1px solid var(--side-line);box-shadow:var(--shadow)}
.guia-cab{display:flex;align-items:center;gap:10px}
.guia-conta{flex:1;min-width:0;margin:0;font-size:12.5px;font-weight:600;color:var(--side-text);font-variant-numeric:tabular-nums}
.guia-fechar{flex:0 0 auto;width:36px;height:36px;display:grid;place-items:center;border:0;border-radius:10px;background:var(--side-hover);color:var(--side-ink);cursor:pointer}
@media(hover:hover) and (pointer:fine){.guia-fechar:hover{background:var(--side-on)}}
.guia-fechar:focus-visible{outline:2px solid var(--side-ink);outline-offset:2px}
.guia-tit{margin:0;font-size:19px;color:var(--side-ink)}
.guia-txt{margin:0;font-size:14.5px;color:#dce2f0} /* o texto do passo sobre o azul-noite (canvas M-Tutorial), igual nos dois temas */
.guia-txt b{color:var(--side-ink)}
.guia-fita{display:flex;gap:4px;padding:2px 0}
.guia-fita span{flex:1;height:4px;border-radius:2px;background:rgba(255,255,255,.18)}
.guia-fita span.on{background:#9fb4ff} /* o cobalto claro do canvas sobre o azul-noite, igual nos dois temas */
.guia-botoes{display:flex;gap:8px}
.guia-botoes .btn{flex:1}
.btn.guia-ant{background:transparent;border-color:var(--side-line);color:var(--side-ink)}
@media(hover:hover) and (pointer:fine){.btn.guia-ant:hover{background:var(--side-hover)}}
.btn.guia-seg{background:var(--side-ink);border-color:var(--side-ink);color:var(--side)}
@media(hover:hover) and (pointer:fine){.btn.guia-seg:hover{background:var(--side-text);border-color:var(--side-text)}}
/* premido na paleta da barra, mais fundo do que o passar por cima */
.btn.guia-ant:active{background:var(--side-on)}
.guia-fechar:active{background:rgba(255,255,255,.2)}
.btn.guia-seg:active{background:var(--side-muted);border-color:var(--side-muted)}
.guia-botoes .btn:focus-visible{outline:2px solid var(--side-ink);outline-offset:2px}
@media(pointer:coarse){.guia-fechar{width:44px;height:44px}}
/* Com o tutorial aberto (guia.js:guiaAjustar, que mede o cartão para o
   --guia-alto), no telemóvel e no tablet, onde ele ocupa a largura: a página
   guarda espaço em baixo para o último registo sair de trás dele (o cartão
   fica a 88px do fundo, mais 16 de folga), e uma janela aberta começa abaixo
   dele, em vez de lhe ficar o título, o ✕ e o primeiro campo por baixo (o
   cartão está a 12px do topo, mais 12 de folga). No telemóvel a folha de
   baixo encolhe; no tablet a janela centra-se no que sobra. No computador o
   cartão vai para o canto e não precisa. */
@media(max-width:899px){body.com-guia #view{padding-bottom:calc(var(--guia-alto,300px) + 104px + var(--inset-bottom))}}
@media(max-width:520px){body.guia-sobre .sheet{max-height:calc(100vh - var(--guia-alto,300px) - 24px - var(--inset-top));max-height:calc(100dvh - var(--guia-alto,300px) - 24px - var(--inset-top))}}
@media(min-width:521px) and (max-width:899px){body.guia-sobre .sheet{top:calc(50% + (var(--guia-alto,300px) + 24px + var(--inset-top)) / 2);max-height:calc(100vh - var(--guia-alto,300px) - 36px - var(--inset-top));max-height:calc(100dvh - var(--guia-alto,300px) - 36px - var(--inset-top))}}

/* ---- cloud/partilha.js — os pedidos por responder (pedidosDashCard,
   linhasDosPedidos, pedidosCard) ----
   Linhas soltas com um traço por cima (o .it do canvas Main), e não cartões
   dentro de um cartão: juntam-se a outras linhas num cartão só. */
.pd-lista{display:flex;flex-direction:column}
.pd-linha{display:flex;flex-direction:column;gap:3px;padding:12px 0;border-top:1px solid var(--line);min-width:0}
.pd-lista>.pd-linha:last-child{padding-bottom:0}
.pd-linha b{font-weight:600;overflow-wrap:anywhere}
.pd-botoes{display:flex;flex-wrap:wrap;gap:8px;margin-top:7px}

/* ---- cloud/partilha.js:vCloud — Segurança, e a partilha entre contas
   (M-Partilha) ----
   Secções com o título por cima e um cartão de linhas por baixo: na
   Segurança, as quatro linhas (a palavra-passe, as sessões, sair e apagar a
   conta); por baixo dos Proprietários (partilha.js:comproprietariosHtml), o
   meu id com «Copiar», o campo de ligar, as ligações, os pedidos e a ligação
   de partilha. */
.pt-pagina{display:grid;gap:22px;max-width:760px;min-width:0}
.pt-seccao{display:grid;gap:10px;min-width:0}
.pt-seccao-cab h2{margin:0;font-size:20px}
.pt-seccao-cab .small{margin:3px 0 0}
.card.pt-cartao{padding:0;overflow:hidden}
.pt-linha{display:flex;flex-wrap:wrap;align-items:center;gap:8px 12px;min-height:60px;padding:12px 14px;width:100%;min-width:0}
.pt-linha+.pt-linha{border-top:1px solid var(--line)}
button.pt-linha{border:0;border-radius:0;background:transparent;font:inherit;color:inherit;text-align:left;cursor:pointer}
@media(hover:hover) and (pointer:fine){button.pt-linha:hover{background:var(--tint)}}
button.pt-linha:active{background:var(--press)}
button.pt-linha:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.pt-txt{flex:1 1 150px;min-width:0}
.pt-txt b{font-weight:600;overflow-wrap:anywhere}
.pt-txt .small{display:block}
.pt-id{font-variant-numeric:tabular-nums}
.pt-acoes{flex:0 0 auto;display:flex;align-items:center;gap:6px;margin-left:auto}
.pt-av{font-size:12.5px}
/* o convite de ligação por responder salta à vista (o canvas M-Partilha): a
   faixa cobalto suave, o avatar branco e o texto cobalto */
.pt-linha.pt-convite{background:var(--accent-soft)}
.pt-convite .pt-txt b,.pt-convite .pt-txt .small{color:var(--accent-text)}
.pt-convite .pt-av{background:var(--card);color:var(--accent-text)}
/* o meu id (partilha.js:comproprietariosCorpo): um toque longo apanha o código
   inteiro, para quem o quiser copiar à mão */
.pt-meuid{font-size:16px;font-weight:650;letter-spacing:.08em;font-variant-numeric:tabular-nums;user-select:all}
.pt-abre{flex-wrap:nowrap}
.pt-abre .seta{flex:0 0 auto;color:var(--faint)}
.pt-perigo b{color:var(--danger)}
.pt-ligar{display:block}
.pt-ligar .small{margin:8px 0 0}
/* o campo de ligar e o botão lado a lado; o botão alinha pelo campo (a linha
   do rótulo, 14px × 1,45, os 6px do espaço, e 1px para centrar os 44 nos 46
   do campo) e não pelo fundo do rótulo, que cresce quando o erro aparece por
   baixo do campo (partilha.js:CW.addConn, componentes.js:falhaCampo) */
.pt-ligar-campo{display:flex;align-items:flex-start;gap:9px}
.pt-ligar-campo>label{flex:1;min-width:0}
.pt-ligar-campo>.btn{flex:0 0 auto;margin-top:27px}
.pt-vazio{min-height:52px}
.pt-nota{margin:0}
.pt-mais{display:grid;min-width:0}
.card.pt-ligacao{display:grid;gap:8px}
.pt-ligacao-cab{display:flex;align-items:center;gap:10px}
.pt-ligacao-cab h3{flex:1;min-width:0;margin:0;font-size:16px}
.pt-ligacao p{margin:0}
.pt-botoes{display:flex;flex-wrap:wrap;gap:8px;margin-top:4px}
/* as quotas de uma casa nova na janela das partilhas (partilha.js:quotasHtml):
   as linhas do canvas M-Quotas — o nome, e o campo estreito com o % */
.pt-quotas{display:grid;margin-top:10px;border-top:1px solid var(--line)}
.pt-quotas-cab{display:grid;grid-template-columns:minmax(0,1fr) 112px;gap:8px;padding:8px 0 2px}
.pt-quotas-cab span:last-child{text-align:left}
label.pt-quota{grid-template-columns:minmax(0,1fr) 88px 16px;align-items:center;gap:8px;padding:6px 0;font-weight:500}
.pt-quota-nome{min-width:0;overflow-wrap:anywhere}
.pt-quota input{text-align:right;font-variant-numeric:tabular-nums}
.pt-pct{color:var(--muted);font-weight:600}
.pt-quotas .hint{margin:8px 0 0}
/* a divisão em vigor de uma casa já partilhada (partilha.js:quotasDaCasaHtml):
   as mesmas linhas, com a quota escrita em vez do campo */
div.pt-quota{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:center;gap:8px;padding:6px 0;font-weight:500}
div.pt-quota b{text-align:right}
.pt-quotas .pt-botoes{margin-top:8px}
.pt-sai{margin:10px 0 0;color:var(--warn)}
/* a partilha entre contas por baixo da lista dos Proprietários (partilha.js:comproprietariosHtml) */
.pt-pagina.pes-partilha{margin-top:22px}

/* ---- cloud/entrada.js:modalConvite, modalLigar e modalGrupo — os convites
   (M-ConviteAceitar) ----
   Quem convida e para quê numa frase grande, os imóveis em cartões (o
   mosaico de 64px por cima e o nome dentro), o que se vai poder fazer numa
   secção em cartão, com um visto (e o cadeado no que fica com os donos), e
   quem está a entrar. Dentro da janela o fundo já é o --card: é o contorno
   que os separa. */
.cv{display:grid;gap:14px;min-width:0}
.cv p{margin:0}
.cv-tit{font-size:22px;line-height:1.2}
.cv-frase{font-size:15px}
.cv-casas{display:grid;grid-template-columns:repeat(auto-fill,minmax(128px,1fr));gap:10px}
.cv-casa{display:grid;gap:0;min-width:0;border:1px solid var(--line);border-radius:14px;overflow:hidden;background:var(--card)}
.cv-capa{height:64px;border-radius:0}
.cv-casa b{padding:8px 10px;font-size:14px;font-weight:600;overflow-wrap:anywhere}
.cv-pode{display:grid;gap:10px;padding:16px;border:1px solid var(--line);border-radius:16px;background:var(--card)}
.cv-pode ul{list-style:none;margin:0;padding:0;display:grid;gap:8px}
.cv-pode li{display:flex;align-items:flex-start;gap:10px;font-size:14.5px}
.cv-pode li svg{flex:0 0 auto;margin-top:1px;color:var(--in)}
.cv-pode li.cv-nao,.cv-pode li.cv-nao svg{color:var(--muted)}
.cv-quem a{color:var(--accent-text);font-weight:600}

/* ---- cloud/entrada.js:showAuth — entrar e criar conta (M-Entrar,
   M-CriarConta) ----
   No telemóvel o ecrã é a página toda; a partir de 521px é um cartão ao meio.
   Quem chega por uma ligação vê a faixa do mosaico com a marca num selo
   branco por cima, e a nota de quem convida. Os campos são os de ecrã
   inteiro (48px). O «Mostrar» assenta no canto direito do campo: a 28px do
   topo do bloco (a linha do rótulo, 14px a 1,45, e o espaço de 6px), centrado
   nos 48 do campo. */
#cwAuth{padding:0}
.ent{width:100%;max-width:440px;min-height:100%;margin:0 auto;display:flex;flex-direction:column;background:var(--bg)}
@media(min-width:521px){
  #cwAuth{padding:32px 20px}
  .ent{min-height:0;margin:auto;background:var(--card);border:1px solid var(--line);border-radius:20px;overflow:hidden;box-shadow:var(--shadow)}
}
.ent-marca{display:flex;align-items:center;gap:10px;padding:calc(28px + var(--inset-top)) 20px 0}
.ent-nome{font-size:20px}
.ent-faixa{position:relative;flex:0 0 132px}
.ent-chip{position:absolute;left:20px;bottom:-22px;display:flex;align-items:center;gap:10px;padding:8px 14px 8px 8px;border-radius:14px;background:var(--card);box-shadow:var(--shadow)}
.ent-chip .ent-nome{font-size:18px}
.ent-corpo{flex:1;display:flex;flex-direction:column;gap:16px;padding:16px 20px calc(24px + var(--inset-bottom))}
.ent-com-faixa .ent-corpo{padding-top:40px}
.ent-tit{margin:0;font-size:26px;line-height:1.15}
.ent-convite{display:flex;gap:12px;padding:14px;border-radius:16px;background:var(--accent-soft);border:1px solid var(--accent-soft)}
.ent-convite-av{flex:0 0 40px;width:40px;height:40px;font-size:14px;background:var(--accent);color:var(--accent-ink)}
.ent-convite p{margin:0;font-size:14.5px;color:var(--accent-text)}
.ent-convite b{font-weight:700}
.ent-msg-erro{margin:0;padding:12px 14px;border-radius:12px;background:var(--danger-soft);color:var(--danger);font-size:14px;font-weight:600}
.segm.ent-segm>button{min-height:42px;font-size:15px}
/* no dedo, 44px (contrato §6): o segmentado da entrada (42 no rato, o do
   canvas) e os botões pequenos da Segurança e da partilha entre contas, dos pedidos e da Ajuda
   (a base dá 40 ao .btn.sm no dedo) */
@media(pointer:coarse){.segm.ent-segm>button,.pt-pagina .btn.sm,.pd-botoes .btn.sm,.aj-cab .btn.sm{min-height:44px}}
.form.ent-form{gap:14px}
.ent-form input:not([type=checkbox]){min-height:48px}
.ent-pw{position:relative;display:grid}
.ent-pw input{padding-right:100px}
.ent-ver{position:absolute;right:4px;top:30px;min-height:40px;padding:0 12px;border:0;border-radius:9px;background:transparent;color:var(--accent-text);font:inherit;font-size:14px;font-weight:600;cursor:pointer}
@media(hover:hover) and (pointer:fine){.ent-ver:hover{background:var(--chip)}}
.ent-ver:active{background:var(--press)}
.ent-ver:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
@media(pointer:coarse){.ent-ver{min-height:44px;top:28px}}
.ent-esqueci{justify-self:end;margin-top:-8px;padding:6px 0;font-size:14px;font-weight:600;color:var(--accent-text);text-decoration:none}
@media(hover:hover) and (pointer:fine){.ent-esqueci:hover{text-decoration:underline}}
.ent-reqs{display:grid;grid-template-columns:1fr 1fr;gap:4px 12px;margin-top:-6px}
.ent-req{display:flex;align-items:center;gap:6px;font-size:13px;color:var(--muted)}
.ent-req.ok{color:var(--in)}
.ent-req svg{flex:0 0 auto;stroke-width:2.4}
.ent-req-circ{flex:0 0 auto;width:13px;height:13px;margin:1.5px;border-radius:50%;border:1.5px solid currentColor}
.ent-so-leitor{position:absolute;width:1px;height:1px;margin:-1px;padding:0;overflow:hidden;clip-path:inset(50%);white-space:nowrap;border:0}
.check.ent-termos{align-items:flex-start;font-size:14px;font-weight:500;line-height:1.45}
.check.ent-termos input{width:22px;height:22px}
.ent-termos a,.ent-rodape a{color:var(--accent-text)}
#cwa_err:empty,#cwa_info:empty{display:none}
#cwa_err,.ent-info{margin:0}
.ent-info{color:var(--ink)}
.btn.ent-botao{width:100%}
.ent-ou{display:flex;align-items:center;gap:12px;margin:0 0 12px;color:var(--faint);font-size:13px}
.ent-ou span{flex:1;height:1px;background:var(--line)}
.ent-google{display:flex;justify-content:center;min-height:44px}
.ent-rodape{margin:auto 0 0;text-align:center}
/* no dedo, as ligações soltas (o «Esqueci-me», os documentos do rodapé, o
   «Não sou eu», o fim da ajuda) têm a altura de um toque */
@media(pointer:coarse){.ent-esqueci,.ent-rodape a,.cv-quem a,.aj-rodape a{display:inline-flex;align-items:center;min-height:44px}.ent-esqueci{margin-top:-14px}}

/* ---- cloud/ajuda.js:showTermsGate — os termos novos (M-Termos) ---- */
.tg-caixa{width:100%;max-width:460px;margin:auto;display:flex;flex-direction:column;gap:16px}
.tg-ic{width:56px;height:56px;border-radius:16px;display:grid;place-items:center;background:var(--accent-soft);color:var(--accent-text)}
.tg-cab{display:grid;gap:6px}
.tg-cab h1{margin:0;font-size:26px;line-height:1.15}
#tgTit:focus-visible{outline:none} /* o título recebe o foco ao abrir só para o leitor de ecrã começar ali; não é um controlo */
.tg-cab p{margin:0;font-size:15px;color:var(--muted)}
.card.tg-docs{padding:0;overflow:hidden}
.tg-doc{display:flex;align-items:center;gap:12px;width:100%;min-height:60px;padding:14px;border:0;background:transparent;font:inherit;color:inherit;text-align:left;cursor:pointer}
.tg-doc+.tg-doc{border-top:1px solid var(--line)}
@media(hover:hover) and (pointer:fine){.tg-doc:hover{background:var(--tint)}}
.tg-doc:active{background:var(--press)}
.tg-doc:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.tg-doc-txt{flex:1;min-width:0;display:grid;gap:2px}
.tg-doc-txt b{font-weight:600}
.tg-doc .seta{flex:0 0 auto;color:var(--faint)}
.tg-aviso{display:grid;gap:8px;padding:14px;border-radius:14px;background:var(--chip)}
.tg-aviso-tit{margin:0;font-weight:600}
.tg-aviso ul{list-style:none;margin:0;padding:0;display:grid;gap:8px}
.tg-aviso li{display:flex;gap:10px;font-size:14.5px}
.tg-aviso li::before{content:"";flex:0 0 6px;width:6px;height:6px;margin-top:8px;border-radius:50%;background:var(--accent)}
.tg-botoes{display:grid;gap:8px}
.btn.ghost.tg-recusa{color:var(--danger);font-weight:500}
#cwt_err{margin:0}
#cwt_err:empty{display:none}
/* a confirmação da recusa abre por cima do ecrã dos termos (196), que tapava
   um modal normal (70) */
.modal.sobre-portao{z-index:197}

/* ---- cloud/novidades.js:gateAtualizar e :ecraAtualizar — a atualização
   (M-Atualizar) ----
   O azul-noite da barra de ponta a ponta, o mosaico por cima, e a caixa dos
   passos. O visto dos passos feitos é o verde-menta do canvas (#8fe3c0), que
   assenta sempre no azul-noite, nos dois temas. */
/* O mosaico azul-noite (o .tile do canvas M-Entrar e M-Atualizar), na
   atualização e na faixa de entrar por uma ligação: igual nos dois temas, e
   não o cobalto claro das capas (imv-t0), que sobre o --side dava um
   cinzento-lavanda e na entrada uma faixa clara. */
.imv-mosaico.imv-noite{--imv-fundo:#16244A;--imv-traco:#9FB4FF} /* o fundo e os arcos do .tile do canvas M-Entrar/M-Atualizar, iguais nos dois temas */
.upd-ecra{display:flex;flex-direction:column;background:var(--side);color:var(--side-ink)}
.upd-mosaico{flex:0 0 200px;opacity:.55}
.upd-corpo{flex:1 0 auto;display:flex;flex-direction:column;gap:18px;width:100%;max-width:520px;margin:0 auto;padding:28px 22px calc(28px + var(--inset-bottom))}
.upd-tit{margin:0;font-size:26px;line-height:1.15;color:var(--side-ink)}
.upd-frase,.upd-nota{margin:0;font-size:15px;color:var(--side-text)}
.upd-nota{font-size:14px}
.btn.upd-botao{width:100%;margin-top:auto;background:var(--side-ink);border-color:var(--side-ink);color:var(--side)}
@media(hover:hover) and (pointer:fine){.btn.upd-botao:hover{background:var(--side-text);border-color:var(--side-text)}}
.btn.upd-botao:active{background:var(--side-muted);border-color:var(--side-muted)}
.btn.upd-botao:focus-visible{outline:2px solid var(--side-ink);outline-offset:2px}
.upd-passos{list-style:none;margin:0;display:grid;gap:12px;padding:16px;border-radius:16px;background:var(--side-hover);border:1px solid var(--side-line)}
.upd-passo{display:flex;align-items:center;gap:10px;font-size:14.5px;color:var(--side-text)}
.upd-passo.feito,.upd-passo.atual{color:var(--side-ink)}
.upd-passo.atual{font-weight:600}
.upd-passo.feito svg{flex:0 0 auto;color:#8fe3c0;stroke-width:2.4} /* o verde-menta do canvas (M-Atualizar) sobre o azul-noite */
.upd-circulo{flex:0 0 20px;width:20px;height:20px;border-radius:50%;border:1.5px solid var(--side-muted)}
/* o que correu mal no ecrã trancado (novidades.js:CW.atualizarAgora, sem
   servidor), por cima do botão: âmbar, como o «Sem ligação» da
   sincronização; no telemóvel desce com o botão para o fundo */
.upd-erro{margin:0;padding:12px 14px;border-radius:12px;background:var(--warn-soft);color:var(--warn);font-size:14px;font-weight:600}
.upd-erro:empty{display:none}
@media(max-width:899px){.upd-erro:not(:empty){margin-top:auto}.upd-erro:not(:empty)+.btn.upd-botao{margin-top:0}}
/* no ecrã largo o botão fica logo a seguir ao texto, e não no fundo da janela */
@media(min-width:900px){.btn.upd-botao{margin-top:6px}}

/* ---- cloud/novidades.js:novHtml — as novidades (M-Novidades) ----
   Por versão, o rótulo e a data, e as secções que abrem e fecham (o .ar do
   canvas), a primeira aberta. Na página das Definições num cartão; na
   janela, sem cartão, só com os traços entre as secções. */
.nov-sub{margin:-4px 0 14px}
.nov-lista{display:grid;gap:18px}
.nov-versao{display:grid;gap:8px;min-width:0}
.nov-v-cab{display:flex;align-items:baseline;justify-content:space-between;gap:10px}
.nov-v-cab .lbl{margin:0}
.card.nov-secs{padding:0;overflow:hidden}
.nov-ar{display:flex;align-items:center;gap:10px;width:100%;min-height:52px;padding:10px 14px;border:0;background:transparent;font:inherit;font-size:15px;font-weight:600;color:var(--ink);text-align:left;cursor:pointer}
.nov-secs>*+.nov-ar{border-top:1px solid var(--line)}
@media(hover:hover) and (pointer:fine){.nov-ar:hover{background:var(--tint)}}
.nov-ar:active{background:var(--press)}
.nov-ar:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.nov-ar-tit{flex:1;min-width:0}
.nov-ar-tit .small{font-weight:500}
.nov-ar svg{flex:0 0 auto;color:var(--faint);transition:transform var(--rapido) var(--curva)}
.nov-ar[aria-expanded="true"] svg{transform:rotate(180deg)}
.nov-itens{list-style:none;margin:0;padding:0 14px 12px;display:grid;gap:8px}
.nov-itens li{display:flex;gap:10px;font-size:14.5px}
.nov-itens li::before{content:"";flex:0 0 6px;width:6px;height:6px;margin-top:8px;border-radius:50%;background:var(--accent)}
.modal .card.nov-secs{border:0;border-radius:0;background:transparent;overflow:visible}
.modal .nov-secs>.nov-ar:first-child{border-top:1px solid var(--line)}
.modal .nov-ar,.modal .nov-itens{padding-left:0;padding-right:0}

/* ---- cloud/ajuda.js:vAjuda e partilha.js:vFaq — a ajuda (M-Ajuda) ----
   «Como se faz» num carrossel de mosaicos que se desliza de lado (no
   telemóvel encosta às margens do ecrã), as perguntas que abrem e fecham, os
   pedidos com o selo do estado e a resposta da equipa numa caixa. */
.aj-pagina{display:grid;gap:12px;max-width:760px;min-width:0}
.aj-cab{display:flex;align-items:baseline;justify-content:space-between;gap:10px;margin-top:12px}
.aj-pagina>.aj-cab:first-child{margin-top:0}
.aj-cab h2{margin:0;font-size:20px}
.aj-cab .small{white-space:nowrap}
.aj-tutoriais{display:flex;gap:10px;overflow-x:auto;scroll-snap-type:x mandatory;scrollbar-width:none;padding-bottom:2px}
.aj-tutoriais::-webkit-scrollbar{display:none}
@media(max-width:900px){.aj-tutoriais{margin:0 calc(-16px - var(--inset-right)) 0 calc(-16px - var(--inset-left));padding-left:calc(16px + var(--inset-left));padding-right:calc(16px + var(--inset-right));scroll-padding:0 16px}}
/* no ecrã largo cabem todos: uma grelha em vez do carrossel */
@media(min-width:901px){.aj-tutoriais{display:grid;grid-template-columns:repeat(auto-fill,minmax(136px,1fr));overflow:visible}}
.aj-tu{flex:0 0 156px;scroll-snap-align:start;display:flex;flex-direction:column;align-items:flex-start;gap:6px;min-height:116px;padding:12px;border-radius:14px;border:1px solid var(--line);background:var(--card);font:inherit;color:inherit;text-align:left;cursor:pointer}
.aj-tu b{font-weight:600;line-height:1.3}
@media(hover:hover) and (pointer:fine){.aj-tu:hover{background:var(--tint)}}
.aj-tu:active{background:var(--press)}
.aj-tu:focus-visible{outline:2px solid var(--accent);outline-offset:2px}
.card.aj-perguntas,.card.aj-cartao{padding:0;overflow:hidden}
.aj-fq{display:flex;align-items:center;gap:10px;width:100%;min-height:52px;padding:10px 14px;border:0;background:transparent;font:inherit;font-size:14.5px;font-weight:500;color:var(--ink);text-align:left;cursor:pointer}
.aj-perguntas>*+.aj-fq{border-top:1px solid var(--line)}
.aj-fq>span{flex:1;min-width:0}
.aj-fq svg{flex:0 0 auto;color:var(--faint);transition:transform var(--rapido) var(--curva)}
.aj-fq[aria-expanded="true"] svg{transform:rotate(180deg)}
@media(hover:hover) and (pointer:fine){.aj-fq:hover{background:var(--tint)}}
.aj-fq:active{background:var(--press)}
.aj-fq:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}
.aj-fr{padding:0 14px 14px;font-size:14px;line-height:1.55;color:var(--muted)}
.aj-fr[hidden]{display:none}
.aj-fr b{color:var(--ink);font-weight:600}
.aj-fq.aj-todas{font-weight:600;color:var(--accent-text)}
.aj-pedido{display:grid;gap:6px;padding:14px}
.aj-pedido+.aj-pedido{border-top:1px solid var(--line)}
.aj-pedido p{margin:0}
.aj-pedido-cab{display:flex;flex-wrap:wrap;align-items:center;gap:8px}
.aj-pedido-cab .small{margin-left:auto} /* a data encosta à direita do selo, como no canvas */
.aj-pedido-tit{font-weight:600;overflow-wrap:anywhere}
/* a resposta da equipa em cobalto suave, para se distinguir do pedido */
.aj-resposta{padding:10px 12px;border-radius:12px;background:var(--accent-soft);color:var(--accent-text);font-size:14px}
.aj-rodape{margin:10px 0 0;text-align:center}
.aj-rodape a{color:var(--accent-text)}

/* ---- cloud/ajuda.js:CW.newTicket — o pedido ao suporte (M-NovoPedido) ----
   O contador de caracteres fica no canto do rótulo, fora dele (não entra no
   nome do campo). */
.tk-campo{position:relative;display:grid;gap:6px}
.tk-conta{position:absolute;top:1px;right:0;font-variant-numeric:tabular-nums}
.tk-junto{display:flex;gap:10px;padding:12px 14px;border-radius:12px;background:var(--chip);color:var(--muted);font-size:13.5px}
.tk-junto svg{flex:0 0 auto;margin-top:1px}
.tk-junto p{margin:0}
#tk_e:empty{display:none}
@media(pointer:coarse){.segm.tk-tipo>button{min-height:44px}}
/* ===== fim: 1.3.9 ===== */
/* =========================== UTILITÁRIOS ===========================
   Uma classe por declaração «propriedade:valor», com o nome
   u-<abreviatura>-<valor>: é o que tomou o lugar dos atributos de estilo da
   app, que a CSP sem 'unsafe-inline' deixou de aplicar. Nasceram de um gerador
   que correu uma vez, fora do repositório; daqui em diante são CSS normal,
   escrito e mantido à mão como o resto desta folha — não há gerador nenhum
   para voltar a correr.

   O seletor leva o id do <html> duas vezes (#raiz#raiz; index.html:#raiz) para
   a especificidade ser (2,1,0) e ganhar a qualquer regra desta folha, que é o
   que um atributo de estilo fazia. Ganham-lhes, como lhe ganhavam a ele, o
   !important e o que o JavaScript escreve no el.style — por isso um elemento
   cujo estilo o JavaScript apague ou reponha (removeAttribute, cssText='')
   não pode depender de um utilitário para o estado inicial.

   Para acrescentar um à mão: uma linha só, com este seletor e UMA declaração,
   pela ordem alfabética do nome —
   «#raiz#raiz .u-mt-18px{margin-top:18px}». O nome é a propriedade abreviada e
   o valor, com o que não é letra nem dígito trocado por hífen (u-bg-v-tint é
   background:var(--tint); u-op-055 é opacity:.55). Duas declarações que se
   sobreponham (margin com margin-top, border com border-color) não se partem
   em dois utilitários: fazem uma classe do módulo, na secção de cima. O
   testes/csp.test.js confere que cada classe u-… usada em web/ existe aqui. */
#raiz#raiz .u-ai-center{align-items:center}
#raiz#raiz .u-ai-end{align-items:end}
#raiz#raiz .u-ai-flex-start{align-items:flex-start}
#raiz#raiz .u-b-0{border:0}
#raiz#raiz .u-bb-1px-solid-v-line{border-bottom:1px solid var(--line)}
#raiz#raiz .u-bc-v-accent{border-color:var(--accent)}
#raiz#raiz .u-bg-transparent{background:transparent}
#raiz#raiz .u-bg-v-accent{background:var(--accent)}
#raiz#raiz .u-bg-v-accent-soft{background:var(--accent-soft)}
#raiz#raiz .u-bg-v-bg{background:var(--bg)}
#raiz#raiz .u-bg-v-chip{background:var(--chip)}
#raiz#raiz .u-bg-v-line{background:var(--line)}
#raiz#raiz .u-bg-v-tint{background:var(--tint)}
#raiz#raiz .u-bg-v-warn{background:var(--warn)}
#raiz#raiz .u-bg-v-warn-soft{background:var(--warn-soft)}
#raiz#raiz .u-bl-3px-solid-v-accent{border-left:3px solid var(--accent)}
#raiz#raiz .u-bl-3px-solid-v-warn{border-left:3px solid var(--warn)}
#raiz#raiz .u-br-10px{border-radius:10px}
#raiz#raiz .u-br-12px{border-radius:12px}
#raiz#raiz .u-br-99px{border-radius:99px}
#raiz#raiz .u-bt-1px-solid-v-line{border-top:1px solid var(--line)}
#raiz#raiz .u-bw-2px{border-width:2px}
#raiz#raiz .u-c-v-accent{color:var(--accent)}
#raiz#raiz .u-c-v-accent-ink{color:var(--accent-ink)}
#raiz#raiz .u-c-v-danger{color:var(--danger)}
#raiz#raiz .u-c-v-ink{color:var(--ink)}
#raiz#raiz .u-c-v-muted{color:var(--muted)}
#raiz#raiz .u-c-v-warn{color:var(--warn)}
#raiz#raiz .u-cur-pointer{cursor:pointer}
#raiz#raiz .u-d-block{display:block}
#raiz#raiz .u-d-flex{display:flex}
#raiz#raiz .u-d-grid{display:grid}
#raiz#raiz .u-d-inline-flex{display:inline-flex}
#raiz#raiz .u-d-none{display:none}
#raiz#raiz .u-ff-monospace{font-family:monospace}
#raiz#raiz .u-font-13px-1p5-ui-monospace-menlo-monospace{font:13px/1.5 ui-monospace,Menlo,monospace}
#raiz#raiz .u-font-13px-1p6-ui-monospace-menlo-monospace{font:13px/1.6 ui-monospace,Menlo,monospace}
#raiz#raiz .u-fs-11px{font-size:11px}
#raiz#raiz .u-fs-12p5px{font-size:12.5px}
#raiz#raiz .u-fs-12px{font-size:12px}
#raiz#raiz .u-fs-13p5px{font-size:13.5px}
#raiz#raiz .u-fs-13px{font-size:13px}
#raiz#raiz .u-fs-14p5px{font-size:14.5px}
#raiz#raiz .u-fs-14px{font-size:14px}
#raiz#raiz .u-fs-15px{font-size:15px}
#raiz#raiz .u-fs-16px{font-size:16px}
#raiz#raiz .u-fs-18px{font-size:18px}
#raiz#raiz .u-fw-400{font-weight:400}
#raiz#raiz .u-fw-500{font-weight:500}
#raiz#raiz .u-fw-600{font-weight:600}
#raiz#raiz .u-fw-650{font-weight:650}
#raiz#raiz .u-fw-750{font-weight:750}
#raiz#raiz .u-fw-800{font-weight:800}
#raiz#raiz .u-fx-0-0-28px{flex:0 0 28px}
#raiz#raiz .u-fx-0-0-30px{flex:0 0 30px}
#raiz#raiz .u-fx-0-0-32px{flex:0 0 32px}
#raiz#raiz .u-fx-0-0-34px{flex:0 0 34px}
#raiz#raiz .u-fx-0-0-54px{flex:0 0 54px}
#raiz#raiz .u-fx-0-0-84px{flex:0 0 84px}
#raiz#raiz .u-fx-0-0-auto{flex:0 0 auto}
#raiz#raiz .u-fx-1{flex:1}
#raiz#raiz .u-fxd-column{flex-direction:column}
#raiz#raiz .u-fxw-wrap{flex-wrap:wrap}
#raiz#raiz .u-g-10px{gap:10px}
#raiz#raiz .u-g-11px{gap:11px}
#raiz#raiz .u-g-12px{gap:12px}
#raiz#raiz .u-g-13px{gap:13px}
#raiz#raiz .u-g-14px{gap:14px}
#raiz#raiz .u-g-3px-12px{gap:3px 12px}
#raiz#raiz .u-g-4px{gap:4px}
#raiz#raiz .u-g-5px{gap:5px}
#raiz#raiz .u-g-6px{gap:6px}
#raiz#raiz .u-g-7px{gap:7px}
#raiz#raiz .u-g-8px{gap:8px}
#raiz#raiz .u-g-9px{gap:9px}
#raiz#raiz .u-gtc-1fr-1fr-auto{grid-template-columns:1fr 1fr auto}
#raiz#raiz .u-gtc-auto-1fr-62px-auto{grid-template-columns:auto 1fr 62px auto}
#raiz#raiz .u-gtc-minmax-0-1fr{grid-template-columns:minmax(0,1fr)}
#raiz#raiz .u-h-0{height:0}
#raiz#raiz .u-h-100pc{height:100%}
#raiz#raiz .u-h-10px{height:10px}
#raiz#raiz .u-h-14px{height:14px}
#raiz#raiz .u-h-16px{height:16px}
#raiz#raiz .u-h-18px{height:18px}
#raiz#raiz .u-h-1px{height:1px}
#raiz#raiz .u-h-28px{height:28px}
#raiz#raiz .u-h-30px{height:30px}
#raiz#raiz .u-h-32px{height:32px}
#raiz#raiz .u-h-34px{height:34px}
#raiz#raiz .u-h-44px{height:44px}
#raiz#raiz .u-h-66px{height:66px}
#raiz#raiz .u-h-76px{height:76px}
#raiz#raiz .u-h-8px{height:8px}
#raiz#raiz .u-jc-center{justify-content:center}
#raiz#raiz .u-jc-flex-end{justify-content:flex-end}
#raiz#raiz .u-jc-space-between{justify-content:space-between}
#raiz#raiz .u-js-start{justify-self:start}
#raiz#raiz .u-lh-1p6{line-height:1.6}
#raiz#raiz .u-ls-2px{letter-spacing:2px}
#raiz#raiz .u-m-0{margin:0}
#raiz#raiz .u-m-0-0-0{margin:0 0 0}
#raiz#raiz .u-m-0-0-10px{margin:0 0 10px}
#raiz#raiz .u-m-0-0-12px{margin:0 0 12px}
#raiz#raiz .u-m-0-0-8px{margin:0 0 8px}
#raiz#raiz .u-m-0-auto{margin:0 auto}
#raiz#raiz .u-m-11px-0-0{margin:11px 0 0}
#raiz#raiz .u-m-12px-0-0{margin:12px 0 0}
#raiz#raiz .u-m-13px-0-0{margin:13px 0 0}
#raiz#raiz .u-m-14px-0-0{margin:14px 0 0}
#raiz#raiz .u-m-15px-0-0{margin:15px 0 0}
#raiz#raiz .u-m-20px-0-0{margin:20px 0 0}
#raiz#raiz .u-m-2px-0-0{margin:2px 0 0}
#raiz#raiz .u-m-2px-0-10px{margin:2px 0 10px}
#raiz#raiz .u-m-4px-0{margin:4px 0}
#raiz#raiz .u-m-4px-0-0{margin:4px 0 0}
#raiz#raiz .u-m-4px-0-8px{margin:4px 0 8px}
#raiz#raiz .u-m-6px-0{margin:6px 0}
#raiz#raiz .u-m-8px-0{margin:8px 0}
#raiz#raiz .u-m-8px-0-0{margin:8px 0 0}
#raiz#raiz .u-m-9px-0-0{margin:9px 0 0}
#raiz#raiz .u-m-auto{margin:auto}
#raiz#raiz .u-m-n16px{margin:-16px}
#raiz#raiz .u-m-n2px-0-0{margin:-2px 0 0}
#raiz#raiz .u-m-n4px-0-0{margin:-4px 0 0}
#raiz#raiz .u-m-n4px-0-12px{margin:-4px 0 12px}
#raiz#raiz .u-m-n6px-0-10px{margin:-6px 0 10px}
#raiz#raiz .u-m-n6px-0-6px{margin:-6px 0 6px}
#raiz#raiz .u-maxw-220px{max-width:220px}
#raiz#raiz .u-maxw-320px{max-width:320px}
#raiz#raiz .u-maxw-400px{max-width:400px}
#raiz#raiz .u-maxw-420px{max-width:420px}
#raiz#raiz .u-maxw-460px{max-width:460px}
#raiz#raiz .u-maxw-720px{max-width:720px}
#raiz#raiz .u-mb-10px{margin-bottom:10px}
#raiz#raiz .u-mb-12px{margin-bottom:12px}
#raiz#raiz .u-mb-14px{margin-bottom:14px}
#raiz#raiz .u-mb-2px{margin-bottom:2px}
#raiz#raiz .u-mb-4px{margin-bottom:4px}
#raiz#raiz .u-mb-5px{margin-bottom:5px}
#raiz#raiz .u-mb-6px{margin-bottom:6px}
#raiz#raiz .u-mb-7px{margin-bottom:7px}
#raiz#raiz .u-mb-8px{margin-bottom:8px}
#raiz#raiz .u-mb-9px{margin-bottom:9px}
#raiz#raiz .u-minh-120px{min-height:120px}
#raiz#raiz .u-minh-130px{min-height:130px}
#raiz#raiz .u-minh-150px{min-height:150px}
#raiz#raiz .u-minh-40px{min-height:40px}
#raiz#raiz .u-minh-66px{min-height:66px}
#raiz#raiz .u-minw-0{min-width:0}
#raiz#raiz .u-minw-140px{min-width:140px}
#raiz#raiz .u-minw-150px{min-width:150px}
#raiz#raiz .u-minw-170px{min-width:170px}
#raiz#raiz .u-minw-230px{min-width:230px}
#raiz#raiz .u-minw-38px{min-width:38px}
#raiz#raiz .u-minw-40px{min-width:40px}
#raiz#raiz .u-ml-7px{margin-left:7px}
#raiz#raiz .u-ml-8px{margin-left:8px}
#raiz#raiz .u-ml-auto{margin-left:auto}
#raiz#raiz .u-mr-4px{margin-right:4px}
#raiz#raiz .u-mt-0{margin-top:0}
#raiz#raiz .u-mt-0px{margin-top:0px}
#raiz#raiz .u-mt-10px{margin-top:10px}
#raiz#raiz .u-mt-11px{margin-top:11px}
#raiz#raiz .u-mt-12px{margin-top:12px}
#raiz#raiz .u-mt-13px{margin-top:13px}
#raiz#raiz .u-mt-14px{margin-top:14px}
#raiz#raiz .u-mt-16px{margin-top:16px}
#raiz#raiz .u-mt-18px{margin-top:18px}
#raiz#raiz .u-mt-2px{margin-top:2px}
#raiz#raiz .u-mt-3px{margin-top:3px}
#raiz#raiz .u-mt-4px{margin-top:4px}
#raiz#raiz .u-mt-6px{margin-top:6px}
#raiz#raiz .u-mt-7px{margin-top:7px}
#raiz#raiz .u-mt-8px{margin-top:8px}
#raiz#raiz .u-mt-9px{margin-top:9px}
#raiz#raiz .u-mt-n4px{margin-top:-4px}
#raiz#raiz .u-mt-n6px{margin-top:-6px}
#raiz#raiz .u-op-055{opacity:.55}
#raiz#raiz .u-op-07{opacity:.7}
#raiz#raiz .u-ov-hidden{overflow:hidden}
#raiz#raiz .u-p-0{padding:0}
#raiz#raiz .u-p-0-15px-14px{padding:0 15px 14px}
#raiz#raiz .u-p-10px-12px{padding:10px 12px}
#raiz#raiz .u-p-10px-13px{padding:10px 13px}
#raiz#raiz .u-p-11px-13px{padding:11px 13px}
#raiz#raiz .u-p-12px{padding:12px}
#raiz#raiz .u-p-12px-13px{padding:12px 13px}
#raiz#raiz .u-p-12px-14px{padding:12px 14px}
#raiz#raiz .u-p-13px{padding:13px}
#raiz#raiz .u-p-13px-14px{padding:13px 14px}
#raiz#raiz .u-p-13px-15px{padding:13px 15px}
#raiz#raiz .u-p-14px{padding:14px}
#raiz#raiz .u-p-16px{padding:16px}
#raiz#raiz .u-p-18px{padding:18px}
#raiz#raiz .u-p-24px{padding:24px}
#raiz#raiz .u-p-2px-0{padding:2px 0}
#raiz#raiz .u-p-4px-0{padding:4px 0}
#raiz#raiz .u-p-5px-11px{padding:5px 11px}
#raiz#raiz .u-p-6px-0-12px{padding:6px 0 12px}
#raiz#raiz .u-p-6px-9px{padding:6px 9px}
#raiz#raiz .u-p-7px{padding:7px}
#raiz#raiz .u-p-8px-0{padding:8px 0}
#raiz#raiz .u-p-9px-11px{padding:9px 11px}
#raiz#raiz .u-p-9px-12px{padding:9px 12px}
#raiz#raiz .u-pi-center{place-items:center}
#raiz#raiz .u-pl-10px{padding-left:10px}
#raiz#raiz .u-pl-18px{padding-left:18px}
#raiz#raiz .u-pos-relative{position:relative}
#raiz#raiz .u-pos-sticky{position:sticky}
#raiz#raiz .u-pt-0{padding-top:0}
#raiz#raiz .u-pt-10px{padding-top:10px}
#raiz#raiz .u-t-0{top:0}
#raiz#raiz .u-t-calc-57px-v-inset-top{top:calc(57px + var(--inset-top))}
#raiz#raiz .u-ta-center{text-align:center}
#raiz#raiz .u-ta-left{text-align:left}
#raiz#raiz .u-ta-right{text-align:right}
#raiz#raiz .u-td-line-through{text-decoration:line-through}
#raiz#raiz .u-td-none{text-decoration:none}
#raiz#raiz .u-td-underline{text-decoration:underline}
#raiz#raiz .u-tf-rotate-180deg{transform:rotate(180deg)}
#raiz#raiz .u-tf-rotate-90deg{transform:rotate(90deg)}
#raiz#raiz .u-tf-rotate-n90deg{transform:rotate(-90deg)}
#raiz#raiz .u-tf-scalex-n1{transform:scaleX(-1)}
#raiz#raiz .u-to-ellipsis{text-overflow:ellipsis}
#raiz#raiz .u-tt-none{text-transform:none}
#raiz#raiz .u-tt-uppercase{text-transform:uppercase}
#raiz#raiz .u-va-middle{vertical-align:middle}
#raiz#raiz .u-w-100pc{width:100%}
#raiz#raiz .u-w-18px{width:18px}
#raiz#raiz .u-w-28px{width:28px}
#raiz#raiz .u-w-30px{width:30px}
#raiz#raiz .u-w-32px{width:32px}
#raiz#raiz .u-w-34px{width:34px}
#raiz#raiz .u-w-54px{width:54px}
#raiz#raiz .u-w-84px{width:84px}
#raiz#raiz .u-ws-normal{white-space:normal}
#raiz#raiz .u-ws-nowrap{white-space:nowrap}
#raiz#raiz .u-z-1{z-index:1}
#raiz#raiz .u-z-20{z-index:20}
/* ========================= FIM DOS UTILITÁRIOS ========================= */

/* folha 2.2 (formularios-ex): o asterisco vermelho dos obrigatórios fica na
   linha do rótulo. O <label> é uma grelha de uma coluna, e o texto e o
   <span class="req"> caíam em duas linhas («Nome» e, por baixo, «*»): com o
   asterisco, a primeira linha tem duas colunas e o campo ocupa a linha toda. */
label:has(>.req){grid-template-columns:minmax(0,max-content) 1fr;column-gap:4px}
label:has(>.req)>:not(.req){grid-column:1/-1}

/* folha 2.4 (formularios-ex): um campo que escreve em maiúsculas (o id de
   outro utilizador) não grita o exemplo — o «Ex: A7KQ2MPX» fica como foi
   escrito, e não «EX: A7KQ2MPX». */
.u-tt-uppercase::placeholder{text-transform:none}
/* folha 2.4: um rótulo com marcas lá dentro («Escreve <b>APAGAR</b> para
   confirmar») vai num <span class="rotulo-txt">, para o texto ser um só
   item da grelha do rótulo e o asterisco ficar ao lado dele — e não um
   bocado de texto por linha, com o asterisco no fim. */
label:has(>.req)>.rotulo-txt{grid-column:1}

/* === listas por origem (folha 1.3) === */
/* As secções «Os meus …», «Partilhados comigo» e «Em que colaboro» das listas
   dos Imóveis, Inquilinos, Visitas e Contratos (vistas.js). */
/* Cada secção com registos existe sempre, mesmo sendo a única
   (vistas.js:listaPorOrigem); uma vazia não aparece. Cada secção: o título e quantos tem, no feitio do
   cabeçalho dos grupos das visitas (.vis-grupo-cab), e a lista por baixo.
   O título distingue-se dos grupos de dentro pela cor da FRENTE — o texto e o
   número a cobalto (--accent-text), e o traço por baixo —, e não só pelo
   tamanho: o Samsung Internet escurece a página à força e passa o cobalto a
   um azul claro, e o --ink dos grupos a um quase branco, que continuam a ser
   dois. Os grupos de dentro (as Próximas e as Passadas, os imóveis dos
   contratos) ficam um nível abaixo, a --ink e mais pequenos. */
.org-seccoes{display:flex;flex-direction:column;gap:28px;min-width:0}
.org-seccao{display:flex;flex-direction:column;gap:12px;min-width:0}
.org-cab{display:flex;align-items:baseline;justify-content:space-between;gap:8px;min-width:0;padding:4px 2px 8px;border-bottom:1px solid var(--line2)}
.org-tit{margin:0;min-width:0;font-size:19px;color:var(--accent-text);overflow-wrap:anywhere}
.org-n{flex:0 0 auto;font-weight:600;color:var(--accent-text)}
/* as Próximas e as Passadas dentro de uma secção: um h3, abaixo do título dela */
.org-seccao .vis-grupo-cab h3{margin:0;font-size:15px;font-weight:600;letter-spacing:0;color:var(--ink)}
/* === fim das listas por origem === */
/* === grupos selecionáveis (folha 1.1) === */
/* Os cartões dos grupos (definicoes.js:cartaoDoGrupo,
   cloud/grupos.js:cartaoDoGrupoPartilhado) abrem com um toque e selecionam-se
   ao segurar (cloud/selecao-listas.js, o tipo 'grp'). Reagem como os outros
   cartões que se tocam (.card.tap): a mão, o premido (o encolher é o do
   [role="button"]:active) e o realce só onde há rato. */
#view .grp-cartao[data-click]{cursor:pointer;transition:border-color var(--rapido) var(--curva),transform var(--rapido) var(--curva),background var(--rapido) var(--curva)}
#view .grp-cartao[data-click]:active:not(:has(button:active)){background:var(--press)}
/* premir um botão de dentro (Partilhar, Aceitar…) não é premir o cartão: só o botão reage */
#view .grp-cartao[data-click]:has(button:active){transform:none}
@media(hover:hover) and (pointer:fine){#view .grp-cartao[data-click]:hover{border-color:var(--line2);background:var(--tint)}}
/* a caixa no canto de cima, antes do nome, sem a folga das linhas: o alvo é o cartão inteiro */
#view .grp-cab>[data-selbox]{padding:0;margin-right:0;align-self:center}
/* Marcado: além do fundo (.sel-on-card), o contorno mais grosso e o nome a
   cobalto — o Samsung Internet escurece à força e o fundo deixa de contar;
   o partilhado com um pedido por responder já tem o contorno cobalto
   (.grp-partilhado:has(.grp-pedido)), e só o fundo não o distinguia. */
#view .grp-cartao.sel-on-card{box-shadow:0 0 0 2px var(--accent)}
#view .grp-cartao.sel-on-card h3{color:var(--accent-text)}
/* em seleção, os botões de dentro (Partilhar, Aceitar, Copiar…) ficam
   inertes (cloud/selecao-listas.js:selLDecorar põe o inert) e veem-se apagados */
#view .grp-cartao [inert]{opacity:.45}
/* o cabeçalho do separador é só o segmentado (definicoes.js:vGrupos) */
.def-cab.grp-cab-tipos{margin-bottom:16px}
/* === fim: grupos selecionáveis (folha 1.1) === */
/* === novo grupo no + (folha 1.2) === */
/* === fim: novo grupo no + (folha 1.2) === */
/* === folha arrastável (folha 1.3) === */
/* A folha de baixo puxa-se para baixo para a fechar (componentes.js:folhaPousar).
   Só abaixo dos 520px, que é onde há barra. O cabeçalho é a pega: o gesto
   vertical ali é da app (touch-action:none — não há lá nada que role), e o
   texto não se seleciona a meio do arrasto. */
@media(max-width:520px){
  .sheet .head{touch-action:none}
  .sheet.arrastar{-webkit-user-select:none;user-select:none}
  /* uma folha que já se pegou já entrou: a entrada não volta a correr por
     cima do transform do dedo (nem a do véu, que segue a folha) */
  .modal.open.arrastou .sheet,.modal.open.arrastou .bg{animation:none}
  /* puxada para cima, o fundo dela descolava do fundo do ecrã: o cartão
     continua por baixo dela (componentes.js:folhaElastico, nunca mais de 24px) */
  .modal.arrastou .sheet{box-shadow:var(--shadow),0 32px 0 var(--card)}
  /* largada, sai de onde o dedo a deixou, na --curva: continua a velocidade
     do dedo, e não arranca devagar como a --curva-sai do X */
  .modal.sai.arrastada .sheet,.modal.sai.arrastada .bg{animation-timing-function:var(--curva)}
}
/* sem movimento a folha não segue o dedo: desvanece quando largar já a fecha */
@media(prefers-reduced-motion:reduce){.sheet.pronto{opacity:.72}}
/* === fim: folha arrastável (folha 1.3) === */
