@font-face {
  font-family: 'Caveat';
  src: url('../fonts/caveat-700.woff2') format('woff2');
  font-weight: 700;
  font-display: swap;
}

:root {
  --bg-top: #241a12; --bg-mid: #362818; --bg-bottom: #2a1f14;
  --wood: #4a3521; --wood-light: #5d4429; --wood-dark: #3a2915;
  --ivory: #f0e6d2; --ink: #3a2d1d; --muted: #b8a583; --dim: #8f7d5f;
  --paper: #f3e9d0; --cardboard: #b3946a; --cardboard-dark: #997a4e;
  --lamp: #ffdf9e;
  --font-serif: Georgia, 'Times New Roman', serif;
  --font-hand: 'Caveat', 'Segoe Script', cursive;
  --font-sans: system-ui, 'Segoe UI', Arial, sans-serif;
}

* { margin: 0; padding: 0; box-sizing: border-box; }

body {
  background: var(--bg-top);
  color: var(--ivory);
  font-family: var(--font-serif);
}

.scene {
  position: relative;
  min-height: 100vh;
  overflow: hidden;
  background: linear-gradient(180deg, var(--bg-top) 0%, var(--bg-mid) 60%, var(--bg-bottom) 100%);
  display: flex;
  flex-direction: column;
}

/* ---------- dach ---------- */
.roof { position: relative; height: 120px; flex: none; }
.beam {
  position: absolute; z-index: 1;
  background: linear-gradient(180deg, var(--wood), var(--wood-dark));
  box-shadow: 0 3px 8px rgba(0,0,0,.5);
  border-radius: 3px;
}
/* narożne zastrzały: lewy „/", prawy „\" */
.beam--left  { top: 26px; left: -34px;  width: 210px; height: 22px; transform: rotate(-45deg); }
.beam--right { top: 26px; right: -34px; width: 210px; height: 22px; transform: rotate(45deg); }

.window {
  position: absolute; top: 16px; left: 50%; margin-left: -45px;
  width: 90px; height: 90px; border-radius: 50%;
  background: radial-gradient(circle at 60% 40%, #1c2a44 0%, #0e1626 80%);
  border: 7px solid #55402a;
  box-shadow: 0 0 40px rgba(160,190,255,.15), inset 0 0 18px rgba(0,0,0,.6);
}
.window__moon {
  position: absolute; top: 14px; right: 16px;
  width: 20px; height: 20px; border-radius: 50%;
  background: #e8e4d0; box-shadow: 0 0 14px rgba(255,255,230,.8);
}
.window__bar { position: absolute; background: #55402a; }
.window__bar--h { top: 50%; left: 0; width: 100%; height: 2px; }
.window__bar--v { left: 50%; top: 0; width: 2px; height: 100%; }

/* lampa — klikalna (włącz/wyłącz); body.lamp-off gasi żarówkę, snop i przyciemnia scenę */
.lamp {
  position: absolute; top: 0; left: 64%; z-index: 16;
  background: none; border: none; padding: 0; cursor: pointer;
}
.lamp svg { display: block; width: 60px; }
.lamp:focus-visible { outline: 2px dashed var(--lamp); outline-offset: 4px; }
.lamp__glass { fill: var(--lamp); transition: fill .2s; }
/* jedna, jednolita aureola wycentrowana na żarówce — bez szwów */
.lamp::after {
  content: ''; position: absolute; left: 50%; top: 212px;
  width: 560px; height: 560px; transform: translate(-50%, -50%);
  border-radius: 50%;
  background: radial-gradient(circle,
    rgba(255, 222, 150, .20) 0%,
    rgba(255, 210, 130, .10) 18%,
    rgba(255, 205, 120, .045) 42%,
    transparent 68%);
  transition: opacity .25s; pointer-events: none;
}
body.lamp-off .lamp__glass { fill: #6b6152; }
body.lamp-off .lamp::after { opacity: 0; }
body.lamp-off .lamp__filament { stroke: #55503f; }
.lamp__filament { transition: stroke .2s; }

/* zbita żarówka (8 szybkich klików) — do odświeżenia strony */
.lamp svg { overflow: visible; }
.lamp__glass-broken, .lamp__shards { display: none; }
body.lamp-broken .lamp__glass, body.lamp-broken .lamp__filament { display: none; }
body.lamp-broken .lamp__glass-broken { display: block; }
body.lamp-broken .lamp__shards { display: block; }
/* transform-box: fill-box — bez tego SVG obraca odłamki wokół (0,0) całego
   rysunku i "lecą" w lewo zamiast spadać */
body.lamp-broken .lamp__shards polygon {
  transform-box: fill-box; transform-origin: center;
  animation: shard-fall .8s ease-in forwards;
}
body.lamp-broken .lamp__shards polygon:nth-child(2) { animation-delay: .06s; }
body.lamp-broken .lamp__shards polygon:nth-child(3) { animation-delay: .12s; }
body.lamp-broken .lamp { cursor: default; }
@keyframes shard-fall {
  from { transform: translateY(0) rotate(0); opacity: 1; }
  to   { transform: translateY(110px) rotate(50deg); opacity: 0; }
}
@media (prefers-reduced-motion: reduce) {
  body.lamp-broken .lamp__shards { display: none; }
}

/* przyciemnienie sceny po zgaszeniu lampy */
.scene::after {
  content: ''; position: absolute; inset: 0; z-index: 15;
  background: rgba(8, 5, 2, .38);
  opacity: 0; transition: opacity .25s; pointer-events: none;
}
body.lamp-off .scene::after { opacity: 1; }

/* ---------- ściana / tytuł (na lewo, nad regałem, między belką a oknem) ---------- */
.wall { position: relative; text-align: left; padding: 0 16px 24px 10%; margin-top: -62px; flex: none; }
.wall__title {
  font-size: clamp(2.2rem, 6vw, 3.2rem);
  letter-spacing: .08em;
  color: var(--ivory);
  text-shadow: 0 2px 0 rgba(0,0,0,.5);
}
.wall__tagline { font-style: italic; color: var(--muted); font-size: 1rem; margin-top: 6px; }

/* ---------- attic (wypełniane w Taskach 3-5) ---------- */
.attic { position: relative; flex: 1; min-height: 520px; }

/* ---------- podłoga ---------- */
.floor {
  position: relative; flex: none; height: 68px;
  background:
    repeating-linear-gradient(90deg, transparent 0 90px, rgba(0,0,0,.25) 90px 94px),
    linear-gradient(180deg, #54402a, #3f2e1a);
  box-shadow: inset 0 6px 10px rgba(0,0,0,.45);
  display: flex; align-items: center; justify-content: center;
}

/* ---------- regał ---------- */
/* regał kotwiczony do podłogi ze stałym sufitem wysokości — nie rośnie,
   gdy tytuł nad nim zwalnia miejsce */
.shelf-unit { position: absolute; left: 3%; bottom: 0; width: 26%; height: min(100%, 660px); min-width: 240px; }
.shelf-unit__side { position: absolute; top: 0; width: 8px; height: 100%; background: var(--wood); }
.shelf-unit__side--l { left: 0; } .shelf-unit__side--r { right: 0; }
.shelf-unit__board {
  position: absolute; left: 0; width: 100%; height: 10px;
  top: calc(30% + var(--row) * 33%);
  background: linear-gradient(180deg, var(--wood-light), var(--wood-dark));
  box-shadow: 0 4px 6px rgba(0,0,0,.45);
}

/* ---------- przedmiot-projekt (wspólne) ---------- */
/* uwaga: filter/transform na samym .item tworzyłyby stacking context i więziły
   przywieszkę (z-index 30 przestaje być globalny) — dlatego filtry siedzą na svg */
.item {
  position: absolute; display: block; text-decoration: none;
  min-width: 44px; min-height: 44px;
  transition: transform .25s ease;
}
.item svg {
  display: block; width: 100%; height: auto;
  filter: drop-shadow(2px 4px 5px rgba(0,0,0,.5)) brightness(.96);
  transition: filter .25s ease;
}
.item:hover, .item:focus-visible {
  transform: translateY(-4px) rotate(-.5deg);
}
.item:hover svg, .item:focus-visible svg {
  filter: drop-shadow(2px 4px 5px rgba(0,0,0,.5)) brightness(1.15);
}
.item:focus-visible { outline: 2px dashed var(--lamp); outline-offset: 6px; }

.item-label {
  position: absolute; bottom: 8%; left: 8%;
  background: rgba(255,248,230,.9); color: var(--ink);
  font-family: var(--font-hand); font-weight: 700; font-size: 1.15rem;
  line-height: 1; padding: 3px 9px 5px; transform: rotate(-2deg);
  box-shadow: 1px 2px 3px rgba(0,0,0,.35);
}

/* przywieszka — ukryta domyślnie, odsłaniana w bloku "odsłanianie przywieszek" niżej */
.tag {
  position: absolute; z-index: 30; left: 55%; top: 100%; width: 190px;
  background: var(--paper); color: #4a3a26;
  font-family: var(--font-sans); font-size: .78rem; line-height: 1.45;
  padding: 9px 11px; box-shadow: 2px 3px 6px rgba(0,0,0,.5);
  transition: opacity .25s ease, transform .25s ease;
  transform: rotate(-2deg) translateY(-6px);
  opacity: 0; pointer-events: none;
}
.tag b { display: block; font-family: var(--font-hand); font-size: 1rem; margin-bottom: 2px; }
.tag::before {
  content: ''; position: absolute; top: -14px; left: 22px;
  width: 1px; height: 14px; background: #c9b795;
}

/* przedmioty stojące na podłodze / nisko: przywieszka otwiera się u góry
   przedmiotu (sznurek od dołu), zamiast wjeżdżać w podłogę */
.item--soundboard .tag, .item--sklep .tag, .item--duggies .tag,
.item--wesele .tag, .item--bingo .tag {
  top: auto; bottom: 72%; left: 60%;
}
.item--soundboard .tag::before, .item--sklep .tag::before, .item--duggies .tag::before,
.item--wesele .tag::before, .item--bingo .tag::before {
  top: auto; bottom: -14px;
}
/* Duggies stoi przy prawej krawędzi — jego przywieszka otwiera się w lewo */
.item--duggies .tag { left: auto; right: 55%; }
.item--duggies .tag::before { left: auto; right: 22px; }

/* ---------- pozycje na regale ---------- */
/* zakotwiczone od spodu procentowo (bottom = 100% - top-row%), więc krawędź
   przedmiotu trzyma się deski niezależnie od szerokości/wysokości kontenera */
.item--grzadka { left: 10%; bottom: 70%; width: 52%; }
.item--ddcards { left: 8%;  bottom: 37%; width: 56%; }
.item--wesele  { left: 6%;  bottom: 4%;  width: 52%; }
.item--bingo   { left: 62%; bottom: 4%;  width: 34%; }

/* ---------- środek podłogi ---------- */
.floor-middle { position: absolute; left: 31%; bottom: 0; width: 44%; height: 100%; }
.item--soundboard { left: 6%; bottom: 0; width: 36%; }
.item--soundboard .item-label { left: 24%; bottom: 5%; }  /* labelka na kartonie z winylami */
.item--sklep      { right: 4%; bottom: 0; width: 36%; }
.item--bingo .item-label { font-size: .95rem; bottom: 18%; }
.item--bingo:hover, .item--bingo:focus-visible { transform: translateY(-4px) rotate(-2deg); }

/* ---------- graty tła ---------- */
.prop { position: absolute; opacity: .92; }
.prop svg { display: block; width: 100%; height: auto; filter: drop-shadow(2px 3px 4px rgba(0,0,0,.5)); }
.prop--globe { right: 10%; bottom: 70%; width: 60px; }
.prop--books { left: 66%; bottom: 37%; width: 86px; }

/* ---------- prawy kąt ---------- */
.corner-right { position: absolute; right: 2%; bottom: 0; width: 27%; height: 100%; }
.item--duggies { right: 6%; bottom: 0; width: 58%; cursor: default; z-index: 2; }
.item--wip { opacity: .85; }
.item--wip:hover, .item--wip:focus-visible { transform: translateY(-2px); filter: brightness(1.08); }
.wip-badge {
  position: absolute; bottom: 0; left: 4%;
  background: #7a5c34; color: #f5ecd8;
  font-family: var(--font-sans); font-size: .68rem;
  border-radius: 8px; padding: 2px 8px; white-space: nowrap;
}
.prop--portrait  { right: 24%; top: 22%; width: 118px; }
/* labelka pod ramą, jak na skrzynkach */
.prop--portrait .item-label { bottom: -14%; left: 12%; font-size: 1rem; }
/* portret ma przywieszkę na hover/focus; otwiera się w dół-lewo (blisko prawej krawędzi) */
.prop--portrait .tag { left: auto; right: 55%; }
.prop--portrait .tag::before { left: auto; right: 22px; }
.prop--portrait:hover .tag, .prop--portrait:focus-visible .tag { opacity: 1; transform: rotate(-2deg) translateY(0); }
.prop--portrait:hover, .prop--portrait:focus-visible { z-index: 20; opacity: 1; }
.prop--portrait:focus-visible { outline: 2px dashed var(--lamp); outline-offset: 6px; }
.prop--mousehole { right: 64%; bottom: 0; width: 28px; }

/* ---------- odsłanianie przywieszek ---------- */
.item:hover .tag, .item:focus-visible .tag, .item.show-tag .tag {
  opacity: 1; transform: rotate(-2deg) translateY(0);
}
/* .show-tag (mobile) celowo BEZ z-index: item nie może tworzyć stacking contextu,
   bo przywieszka (z-index 30) ma unosić się nad wszystkimi sąsiadami */
.item:hover, .item:focus-visible { z-index: 20; }
@media (prefers-reduced-motion: reduce) {
  .item, .tag { transition: none; }
}

/* ---------- pajęczyna i pajączek ---------- */
/* sieć opięta między prawym zastrzałem a krawędzią ekranu; geometria SVG
   dopasowana do linii belki (y = x - 62 w układzie 150×150 przy right:0, top:20) */
.cobweb {
  position: absolute; top: 20px; right: 0; width: 150px;
  opacity: .4; z-index: 0;
}
/* pająk zwisa z centrum sieci (112,80); nitka rośnie razem ze zjazdem */
#spider {
  position: absolute; top: 130px; right: 26px; z-index: 5;
  transform: translateY(var(--spider-drop, 0px));
  transition: transform var(--spider-speed, 3s) ease-in-out;
  will-change: transform;
}
.spider__thread {
  position: absolute; bottom: 14px; left: 10px;
  width: 1px; height: calc(var(--spider-drop, 0px) + 34px);
  background: rgba(201,183,149,.5);
  transition: height var(--spider-speed, 3s) ease-in-out;
}
.spider__body { display: block; width: 22px; }
@media (prefers-reduced-motion: reduce) {
  #spider, .spider__thread { transition: none; }
  #spider { --spider-drop: 60px; }  /* statyczny, nisko pod siecią */
}

/* ---------- mobile: strych w pionie ---------- */
@media (max-width: 800px) {
  .attic { min-height: 0; padding: 12px 0 24px; }

  .shelf-unit, .floor-middle, .corner-right {
    position: static; width: auto; height: auto; min-width: 0;
    display: flex; flex-direction: column; align-items: center; gap: 40px;
    padding: 24px 8vw;
  }
  .shelf-unit__side { display: none; }
  /* oryginalne deski regału zastępuje mobilny regał niżej (półka pod każdym itemem) */
  .shelf-unit__board { display: none; }

  /* mobilny regał: dwie pionowe listwy przez całą kolumnę... */
  .attic::before, .attic::after {
    /* listwy zaczynają się dopiero pod portretem (padding-top attica) —
       regał obejmuje tylko pola projektów */
    content: ''; position: absolute; top: 236px; bottom: 0; width: 8px;
    background: var(--wood); z-index: 0;
  }
  .attic::before { left: 4vw; }
  .attic::after  { right: 4vw; }
  /* ...i deska-półka pod każdą skrzynką */
  .item::before {
    content: ''; position: absolute; left: 50%; bottom: -15px;
    transform: translateX(-50%);
    width: calc(92vw + 8px); max-width: 440px; height: 10px;
    background: linear-gradient(180deg, var(--wood-light), var(--wood-dark));
    box-shadow: 0 4px 6px rgba(0,0,0,.45);
  }

  /* pozycjonowanie itemów zmienia się na "relative" (nie "static"): item-label
     i .tag są position:absolute wewnątrz .item i muszą mieć kontekst pozycjonowania,
     inaczej "uciekną" do najbliższego position:relative przodka (np. .attic) */
  .item, .item--grzadka, .item--ddcards, .item--sklep,
  .item--soundboard, .item--wesele, .item--bingo, .item--duggies {
    position: relative; left: auto; right: auto; top: auto; bottom: auto;
    width: min(78vw, 340px);
  }
  /* bingo dostaje własną półkę jak wszystko inne — bez nakładania na walizkę */
  .item--bingo { margin-top: 0; }

  /* na mobile wszystkie przywieszki wracają pod przedmiot (kolumna ma miejsce);
     selektor .item .tag dorównuje specyficznością desktopowym override'om
     per-item i wygrywa kolejnością w pliku */
  .item .tag { left: 10%; right: auto; top: 100%; bottom: auto; width: min(70vw, 240px); }
  .item .tag::before { top: -14px; bottom: auto; left: 22px; right: auto; }

  .prop--globe, .prop--books { display: none; }
  /* portret wisi na ścianie nad regałem (pod oknem/tytułem); .attic robi mu
     miejsce paddingiem, a on sam jest wycentrowany absolutnie u góry */
  .attic { padding-top: 236px; }
  .prop--portrait {
    display: block; position: absolute; top: 12px; left: 50%; right: auto;
    transform: translateX(-50%); width: 140px;
  }
  .prop--portrait .tag { left: 14%; right: auto; top: 105%; bottom: auto; }
  .prop--portrait .tag::before { top: -14px; bottom: auto; left: 22px; right: auto; }
  .prop--mousehole {
    position: static; align-self: flex-end; opacity: .8; margin-top: -22px; margin-bottom: -24px;
  }

  /* wąski ekran: krótsze zastrzały, mniejsza pajęczyna, lampa dalej od wyśrodkowanego okna */
  .beam--left, .beam--right { width: 150px; }
  .cobweb { width: 100px; top: 19px; right: 0; }
  .lamp { left: 62%; top: -64px; }  /* krótszy strych na górze: sznurek ucieka za dach */
  .lamp svg { width: 44px; }
  .lamp::after { top: 155px; width: 340px; height: 340px; }
  /* na wąskim ekranie tytuł wraca na środek — brak miejsca obok okna */
  .wall { text-align: center; margin-top: 0; padding: 8px 16px 24px; }
  .wall__tagline { font-size: .9rem; }

  /* pajączek: JS losuje --spider-drop 30-140px inline na #spider. Przy dużym
     zjeździe pajączek wjechałby na tytuł (roof: 120px, tytuł ~128px), więc na
     mobile przycinamy translateY — i tym samym clampem nitkę, żeby nie
     wystawała ponad sieć. */
  #spider { top: 98px; right: 13px; transform: translateY(clamp(0px, var(--spider-drop, 0px), 32px)); }
  .spider__thread { height: calc(clamp(0px, var(--spider-drop, 0px), 32px) + 26px); }
}
