/* frontend/css/base.css */
/* ═══════════════════════════════════════════════════════════════════════════
   Plateby — Base Layer
   Reset, element defaults, layout, scrollbar, a11y floor, empty states.
   ═══════════════════════════════════════════════════════════════════════════ */

/* ── Reset ────────────────────────────────────────────────────────────────── */
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
html { font-size: 16px; }
body {
  font-family: var(--font-body);
  background: var(--bg);
  color: var(--text-1);
  min-height: 100vh;
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
}

/* ── Paper Texture (global) ─────────────────────────────────────────────── */
body::before {
  content: "";
  position: fixed;
  inset: 0;
  pointer-events: none;
  z-index: -1;
  opacity: var(--paper);
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='256' height='256'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.65' numOctaves='4' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
  background-repeat: repeat;
}

a { color: var(--primary); text-decoration: none; }
a:hover { text-decoration: underline; }
button { cursor: pointer; font-family: inherit; border: none; background: none; }
input { font-family: inherit; }

/* ── Layout ───────────────────────────────────────────────────────────────── */
#app {
  display: grid;
  grid-template-columns: var(--sidebar-w) 1fr;
  min-height: 100vh;
}

/* ── Main Content ─────────────────────────────────────────────────────────── */
#main-content {
  padding: 40px 48px;
  /* play-launch-blockers T14: AdMob banner'ı NATIVE bir view ve WebView'in üstüne
     biner — bu kural ≥901px yerleşimi (Android tablet) için ve orada alt navigasyon
     yok, ama içeriğin son satırı yine banner'ın altında kalırdı. Değişkeni
     `js/ads.js` yazar; reklam yokken 0px, yani web'de bu satırın etkisi yok.
     Mobil kademelerin kendi payı `css/responsive.css`'te. */
  padding-bottom: calc(40px + var(--ad-banner-h, 0px));
  overflow-y: auto;
}

/* ── Empty States ─────────────────────────────────────────────────────────── */
.empty-state {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  min-height: 50vh;
  text-align: center;
  gap: 12px;
}
.empty-icon { font-size: 56px; }
.empty-state h3 {
  font-family: var(--font-display);
  font-size: 22px;
  font-weight: 600;
  color: var(--text-1);
}
.empty-state p { font-size: 15px; color: var(--text-3); max-width: 300px; line-height: 1.6; }
.empty-state .btn-primary { margin-top: 8px; }

.empty-msg { color: var(--text-3); font-size: 14px; padding: 16px 0; }

/* ── Scrollbar ────────────────────────────────────────────────────────────── */
::-webkit-scrollbar { width: 6px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-thumb { background: var(--border); border-radius: 3px; }
::-webkit-scrollbar-thumb:hover { background: var(--text-3); }

/* ── Responsive ───────────────────────────────────────────────────────────── */
/* Touch-shell rules migrated to css/responsive.css (≤600 / 601–900 tiers). */

/* ── A11y floor (PB-104c) ─────────────────────────────────────────────────── */
/* UI2: hareket azaltma tercihi (WCAG 2.3.3) */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}

/* UI2: her etkileşimli öğede tutarlı odak halkası */
:focus-visible {
  outline: 2px solid var(--primary, #C4622D);
  outline-offset: 2px;
}

/* ── Reklam banner'ının üstünde biten yüzeyler ────────────────────────────── */
/* AdMob banner'ı NATIVE bir view ve WebView'in ÜSTÜNE biniyor (`js/ads.js`) —
   alt kenarı ekranın dibine dayanan her açılır pencere onun arkasında kalıyor:
   mobilde makro alt-sayfası (`align-items:flex-end`) ve 90vh'lik modallerin
   düğme satırı. Tek levye `--ad-banner-h`; reklam yokken 0px, yani web'de bu
   blok hiçbir şeyi değiştirmez.
   `body` öneki bilerek: görünüm CSS'leri bu dosyadan SONRA enjekte oluyor
   (`ensureViewCSS`) ve eşit specificity'de sonradan gelen kazanırdı. */
body #modal-overlay,
body #loading-overlay,
body #cooking-mode-overlay,
body .modal-overlay {
  bottom: var(--ad-banner-h, 0px);
}
body .share-modal { height: calc(100% - var(--ad-banner-h, 0px)); }
body #toast-container { bottom: calc(24px + var(--ad-banner-h, 0px)); }

/* ── Aşağı çekince yenileme (live-state-sync T5) ──────────────────────────── */
/* Jestin kendisi `js/pull_refresh.js`; burada YALNIZ görünüm — modül sınıf adı yazar,
   stil yazmaz (`js/` altında ham renk literali yasak, `build.py` hex-lint).

   `overscroll-behavior-y: contain` WebView'in KENDİ yenileme jestini kapatır: o jest
   sayfayı gerçekten yeniden yüklüyor, AC7 ise tam bunu yasaklıyor. Platformun kendi
   davranışını JS ile değil CSS ile kapatmak tek satır ve geri alınması tek satır.
   Ayrı bir kural olarak yazıldı çünkü aynı seçicinin iki bloğu "sonraki kazanır"
   biçiminde değil, ÖZELLİK BAŞINA birleşir — yukarıdaki `html`/`body` blokları
   dokunulmadan duruyor. */
html, body { overscroll-behavior-y: contain; }

.ptr-indicator {
  position: fixed;
  /* Gösterge ÜSTTE: `--ad-banner-h` bloğu (aşağıda) alt kenara yaslanan yüzeyler için,
     bu onlardan biri değil. Çentik payı yine de şart. */
  top: calc(8px + env(safe-area-inset-top));
  /* FİZİKSEL `left` bilerek: ortalama `translateX(-50%)` ile yapılıyor ve `transform`
     mantıksal değil fiziksel. `inset-inline-start` yazılsaydı `ar`'da (i18n.js:105
     `dir="rtl"`) `right: 50%`'e çözülür, transform ise aynı yönde kalır ve gösterge
     32px yanlış yerde dururdu. Ortalanmış bir öğede iki eksen aynı olmalı. */
  left: 50%;
  width: 32px;
  height: 32px;
  border-radius: 50%;
  background: var(--surface);
  box-shadow: var(--shadow);
  /* Alt navigasyon 1000, `#loading-overlay` 2000: gösterge ikisinin arasında. */
  z-index: 1500;
  opacity: 0;
  pointer-events: none;
  transform: translateX(-50%) scale(.6);
  transition: opacity var(--transition), transform var(--transition);
}
/* `spin` keyframe'i `components/loading-overlay.css`'ten geliyor (index.html `<head>`) —
   ikinci bir kopya yazmaya gerek yok. */
.ptr-indicator::after {
  content: "";
  position: absolute;
  inset: 8px;
  border: 2px solid var(--border);
  border-top-color: var(--primary);
  border-radius: 50%;
}
.ptr-indicator.ptr-visible { opacity: 1; transform: translateX(-50%) scale(1); }
.ptr-indicator.ptr-busy::after { animation: spin 800ms linear infinite; }
.ptr-indicator.ptr-error::after { border-color: var(--danger); animation: none; }

/* Inline stille kurulan tam ekran overlay'ler (10 dosyada 18 aynı kopya:
   settings, shopping, inventory, admin/*, modal.js, planner.js). Inline bir
   bildirimi yalnız `!important` yener. İki seçici, iki yazım: `style.cssText`
   çağrıları boşluksuz, HTML şablonları boşluklu yazıyor. `position:fixed`
   koşulu şart — inline `height:100%` yazan görsel/ilerleme çubukları var. */
div[style*="position:fixed"][style*="height:100%"],
div[style*="position: fixed"][style*="height: 100%"] {
  height: calc(100% - var(--ad-banner-h, 0px)) !important;
}
