/* Janela da Loja (docs/specs/shop.md §7; janela `shop`, 592×276). Moldura, botões, abas e campo vêm de nine-slice.css/base.css;
   aqui só o arranjo, em px de ARTE (`calc(N * var(--px))`). Sem cor nova: text-gold/text-dim/text-danger de base.css. */
.shop-body { display: flex; flex-direction: column; gap: calc(4 * var(--px)); }
/* --- skins --- a faixa da janela: as abas, o tipo de skin (só na aba Skins) e o saldo na ponta direita (fora da lista de abas) */
.shop-head { display: flex; align-items: center; gap: calc(6 * var(--px)); flex: none; }
.shop-head > .shop-tabs { margin-bottom: 0; }
.shop-balance-slot { margin-left: auto; display: inline-flex; align-items: center; }
.shop-tabs { display: flex; align-items: center; gap: calc(2 * var(--px)); }
.shop-tabs > .shop-balance { margin-left: auto; }
.shop-offers { display: flex; flex-direction: column; gap: calc(2 * var(--px)); }
.shop-offer { display: flex; align-items: center; gap: calc(6 * var(--px)); min-height: calc(24 * var(--px)); padding: calc(2 * var(--px)); }
.shop-offer-ico { width: calc(16 * var(--px)); height: calc(16 * var(--px)); }
.shop-offer-text { display: flex; flex-direction: column; gap: calc(1 * var(--px)); flex: 1; min-width: 0; }
.shop-offer-desc { white-space: normal; }
.shop-offer-right { display: flex; align-items: center; gap: calc(4 * var(--px)); flex: none; }
.shop-seal { display: inline-block; padding: 0 calc(3 * var(--px)); border: var(--px) solid var(--c-text-dim); line-height: calc(9 * var(--px)); white-space: nowrap; }
.shop-seal.is-ok { border-color: var(--c-gold); color: var(--c-gold); }
.shop-seal.is-bad { border-color: var(--c-danger); color: var(--c-danger); }
/* desvio P10-2 (olhada de layout): o `inline-block` do selo não vale dentro de flex em coluna nem de célula de grade — sem isto o
   selo estica na largura toda e vira uma caixa que parece campo de texto (painel da troca e coluna do motivo no Extrato). */
.shop-rename > .shop-seal { align-self: flex-start; }
.shop-ledger-row > .shop-seal { justify-self: start; }
.shop-rename { display: flex; flex-direction: column; gap: calc(4 * var(--px)); }
.shop-rename-line { display: flex; align-items: center; gap: calc(4 * var(--px)); }
.shop-rename-line > .input { flex: 1; min-width: 0; }
/* --- vip --- (docs/specs/shop.md §11.10) o cartão VIP: o selo de estado ao lado do nome; o painel da compra em coluna, como o da
   troca. Os ícones da série são 16×16 de arte, sem escala fracionária (pixel art). */
.shop-offer-head { display: flex; align-items: center; gap: calc(4 * var(--px)); min-width: 0; }
/* a pista no selo (G4): o pontilhado de base.css cairia em cima da moldura e a apagaria — a moldura é que vira pontilhada embaixo, na cor do tom */
#ui-root .shop-seal[data-hint].has-more { border-bottom: var(--px) dotted currentColor; }
.shop-vip { display: flex; flex-direction: column; gap: calc(4 * var(--px)); }
.shop-vip-title { display: flex; align-items: center; gap: calc(4 * var(--px)); }
.shop-vip-ico { width: calc(16 * var(--px)); height: calc(16 * var(--px)); }
.shop-vip-benefits { display: flex; flex-wrap: wrap; align-items: center; gap: calc(8 * var(--px)); align-self: flex-start; }
.shop-vip-benefit { display: inline-flex; align-items: center; gap: calc(2 * var(--px)); white-space: nowrap; }
/* (F10) a ficha `[ico] 2.500 → [ico] 1.500` dos dois painéis: o `.itoken-label` é inline-flex com o ícone na frente, e a linha de base
   dele é a do ícone — a seta solta caía 3 px abaixo do número (medido no servidor real em 844×390). Em flex centrado os três se alinham
   pelo meio; o `gap` repõe o espaço que a seta perde nas pontas como item flex. */
#shop-vip-cost, #shop-rename-cost { display: flex; align-items: center; gap: calc(3 * var(--px)); }
/* --- /vip --- */
.shop-ledger { display: flex; flex-direction: column; gap: calc(2 * var(--px)); }
.shop-ledger-row { display: grid; grid-template-columns: calc(52 * var(--px)) 1fr auto auto; align-items: center; gap: calc(4 * var(--px)); min-height: calc(12 * var(--px)); }
.shop-ledger-row > .itoken-label:last-child { justify-self: end; }

/* --- skins --- (docs/specs/skins.md §10) a aba Skins: `Corpo · Arma` na faixa; a grade de cartões 64 × 104 (6 colunas = 394) e, à
   direita, a coluna da prova (o palco 148 × 150 do Inspecionar, a ação, o recibo). O corpo de 232 leva a faixa (16 + 4) e as 2
   fileiras do Corpo (104 + 2 + 104) sem rolar; a Arma (`Sem skin` + 1 + o rótulo + 13) rola, com o degradê de `scroll-fade.css`
   (a classe `scroll-fade` vem do JS) só quando ROLA de verdade (`is-scrollable`, medido em `shop.js › syncSkinOverflow`). */
.shop-skin-kinds { display: flex; gap: calc(2 * var(--px)); padding-left: calc(6 * var(--px)); border-left: var(--px) solid var(--c-text-dim); }
.shop-skins { flex: 1 1 auto; min-height: 0; display: flex; gap: calc(6 * var(--px)); }
.shop-skin-main { flex: 1 1 auto; min-width: 0; min-height: 0; display: flex; flex-direction: column; }
.shop-skin-grid {
  flex: 1 1 auto;
  display: grid;
  grid-template-columns: repeat(6, calc(64 * var(--px)));
  grid-auto-rows: calc(104 * var(--px));
  gap: calc(2 * var(--px));
  align-content: start;
  --scroll-fade-pad: calc(12 * var(--px));
}
.shop-skin-grid:not(.is-scrollable) { --scroll-fade: 0px; --scroll-fade-pad: 0px; }
/* O cartão: a moldura da casa (`slot_empty`/`slot_hover`, a série das grades) em 64 × 104; dentro, a miniatura 48 × 64 sem escala (a
   pixel art não aceita escala fracionária), o nome em até 2 linhas e o estado. Escolhido = o aro de ouro da casa escolhida. */
.shop-skin-card {
  position: relative;
  box-sizing: border-box;
  width: calc(64 * var(--px));
  height: calc(104 * var(--px));
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--px);
  border: calc(4 * var(--px)) solid transparent;
  border-image: url(../assets/ui/slots/slot_empty.png) 4 fill / calc(4 * var(--px)) stretch;
  image-rendering: pixelated;
  cursor: pointer;
}
.shop-skin-card:hover, .shop-skin-card:focus-visible { border-image-source: url(../assets/ui/slots/slot_hover.png); }
.shop-skin-card.is-selected { outline: var(--px) solid var(--c-gold); outline-offset: calc(-1 * var(--px)); }
.shop-skin-card:focus-visible { outline: calc(2 * var(--px)) solid var(--c-focus); outline-offset: calc(-1 * var(--px)); }
/* a que o herói não veste fica apagada (G5: a exceção se pinta uma vez, no rótulo da fila; o motivo vai no aria-label e no Vestir) */
.shop-skin-card.is-misfit > .shop-skin-thumb, .shop-skin-card.is-misfit > .shop-skin-name { opacity: 0.55; }
.shop-skin-thumb {
  position: relative;
  flex: none;
  width: calc(48 * var(--px));
  height: calc(64 * var(--px));
  display: flex;
  align-items: center;
  justify-content: center;
  background-color: var(--c-field-bg);
  background-repeat: no-repeat;
  background-size: 100% 100%;
  image-rendering: pixelated;
}
.shop-skin-ghost { width: calc(32 * var(--px)); height: calc(32 * var(--px)); opacity: 0.6; }
/* o brilho da miniatura (art-pipeline.md §4/§5, o molde do `.item-icon.has-glow::before`): a COR do dado recortada pela `.glow.png`
   (branca, A = o plano G), opacidade de `min × intensity` a `intensity` (`shop.js › skinGlowStyle`); movimento reduzido fixa no alto */
.shop-skin-glow {
  position: absolute;
  inset: 0;
  background: var(--glow-color, #fff);
  -webkit-mask-image: var(--skin-glow);
  mask-image: var(--skin-glow);
  -webkit-mask-size: 100% 100%;
  mask-size: 100% 100%;
  image-rendering: pixelated;
  opacity: var(--glow-hi, 0.7);
  pointer-events: none;
}
.shop-skin-glow.is-pulsing { animation: shop-skin-glow-pulse var(--glow-period, 0.5s) steps(6) infinite alternate; }
@keyframes shop-skin-glow-pulse {
  from { opacity: var(--glow-lo, 0.35); }
  to { opacity: var(--glow-hi, 0.7); }
}
@media (prefers-reduced-motion: reduce) {
  .shop-skin-glow.is-pulsing { animation: none; }
}
/* o brasão da classe no ↖ da skin de arma que não serve (a miniatura da arma não diz de quem é): filho do CARTÃO, fora da miniatura
   apagada — o brasão é a informação e fica inteiro */
.shop-skin-crest { position: absolute; left: var(--px); top: var(--px); width: calc(12 * var(--px)); height: calc(12 * var(--px)); z-index: 1; }
.shop-skin-name {
  flex: none;
  width: 100%;
  height: calc(18 * var(--px));
  font-size: calc(8 * var(--px));
  line-height: calc(9 * var(--px));
  text-align: center;
  overflow: hidden;
  overflow-wrap: break-word;
}
.shop-skin-state { flex: none; height: calc(10 * var(--px)); display: flex; align-items: center; justify-content: center; }
.shop-skin-state > .shop-seal { line-height: calc(8 * var(--px)); }
/* o rótulo do grupo (`Femininas` · `Masculinas` · `Outras classes`): uma casa da grade, antes das que não servem */
.shop-skin-group {
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0 calc(2 * var(--px));
  text-align: center;
  color: var(--c-text-dim);
  border-left: var(--px) solid var(--c-text-dim);
}
/* A coluna da prova: o palco (a caixa see-through do Inspecionar, `widgets/inspectDoll.js`) com a moldura `panel` aberta, a ação e
   o recibo/recusa embaixo. Não rola: o furo não acompanha rolagem. */
.shop-skin-side { flex: none; width: calc(160 * var(--px)); display: flex; flex-direction: column; align-items: center; gap: calc(4 * var(--px)); }
.shop-skin-stage { flex: none; width: calc(148 * var(--px)); height: calc(150 * var(--px)); }
.shop-skin-stage > .shop-skin-doll { box-sizing: border-box; width: 100%; height: 100%; min-height: 0; flex: none; }
.shop-skin-stage > .shop-skin-doll.is-see-through {
  background: none;
  border-image: var(--ui-panel, url(../assets/ui/windows/panel.png)) 8 / calc(8 * var(--px)) stretch;
}
.shop-skin-act { width: calc(148 * var(--px)); min-height: calc(16 * var(--px)); display: flex; }
.shop-skin-done, .shop-skin-msg { width: calc(148 * var(--px)); text-align: center; }
/* O painel de compra (no lugar da grade, o molde do VIP) */
.shop-skin-buy { display: flex; flex-direction: column; gap: calc(4 * var(--px)); }
.shop-skin-buy-desc { white-space: normal; }
#shop-skin-buy-cost { display: flex; align-items: center; gap: calc(3 * var(--px)); }
/* --- /skins --- */
