/* Colors match the Android app's Theme.kt / AppColors (icon-matched blue). */
:root {
  --bg: #F6F4EE;
  --surface: #FFFFFF;
  --border: #E7E4DA;
  --text-primary: #1A1A18;
  --text-secondary: #6B6A64;
  --accent: #1C9AF0;
  --accent-bg: #DFF1FE;
  --red: #E24B4A;
  --red-bg: #FCEBEB;
  --offline-bg: #F1EFE8;
  --offline-text: #5F5E5A;
  --success-bg: #C0DD97;
}

* { box-sizing: border-box; }

body {
  margin: 0;
  background: var(--bg);
  color: var(--text-primary);
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Tahoma, sans-serif;
  min-height: 100vh;
}

.topbar {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 20px 20px 12px;
}
.topbar h1 { font-size: 20px; margin: 0; flex: 1; }

.icon-btn {
  border: 1px solid var(--border);
  background: var(--surface);
  border-radius: 50%;
  width: 36px;
  height: 36px;
  font-size: 16px;
  cursor: pointer;
}

main { padding: 0 20px 32px; }

.empty, .hint { color: var(--text-secondary); font-size: 14px; }
.hint.small { font-size: 12px; margin-top: 16px; }

.device-list { list-style: none; padding: 0; margin: 12px 0; display: flex; flex-direction: column; gap: 10px; }

.device-card {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 16px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: 14px;
}

.device-name { font-weight: 600; }
.device-last-alert { font-size: 12px; color: var(--text-secondary); margin-top: 4px; }

.device-badges {
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 4px;
}

.device-state {
  padding: 4px 10px;
  border-radius: 999px;
  font-size: 13px;
}
.state-dry { background: var(--success-bg); }
.state-wet { background: var(--red-bg); color: var(--red); font-weight: 700; }
.state-unknown { background: var(--offline-bg); color: var(--offline-text); }

/* Separate from .device-state on purpose: a device can be dry/leaking
   AND offline at the same time (its last known reading, plus the fact
   it hasn't checked in recently) — these are two independent facts, not
   mutually exclusive ones, so they're shown as two small stacked tags
   rather than one replacing the other. */
.device-offline-tag {
  padding: 2px 8px;
  border-radius: 999px;
  font-size: 11px;
  background: var(--offline-bg);
  color: var(--offline-text);
}

.primary-btn {
  width: 100%;
  padding: 14px;
  margin-top: 12px;
  border: none;
  border-radius: 14px;
  background: var(--accent);
  color: #fff;
  font-size: 15px;
  font-weight: 600;
  cursor: pointer;
}

/* Cancel/dismiss action paired with a primary button in a form — e.g.
   the "join an existing household" form's Cancel + the actual submit
   button, side by side. */
.form-actions {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-top: 12px;
}
.form-actions .primary-btn { flex: 1; margin-top: 0; }
.text-btn {
  padding: 14px 4px;
  border: none;
  background: transparent;
  color: var(--text-secondary);
  font-size: 15px;
  font-weight: 600;
  cursor: pointer;
}

.secondary-btn {
  width: 100%;
  padding: 12px;
  margin-top: 12px;
  border: 1px dashed var(--border);
  border-radius: 14px;
  background: transparent;
  color: var(--accent);
  font-size: 14px;
  font-weight: 600;
  cursor: pointer;
}

/* ---------- Add-a-device screen ---------- */
.credential-box {
  margin-top: 16px;
  padding: 16px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: 14px;
}
.credential-box label { font-size: 12px; color: var(--text-secondary); margin-top: 10px; display: block; }
.credential-box label:first-child { margin-top: 0; }
.credential-row {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-top: 4px;
}
.credential-row code {
  flex: 1;
  min-width: 0;
  overflow-x: auto;
  white-space: nowrap;
  padding: 8px 10px;
  background: var(--bg);
  border-radius: 8px;
  font-size: 13px;
  direction: ltr;
  text-align: left;
}
.copy-btn {
  flex-shrink: 0;
  border: 1px solid var(--border);
  background: var(--surface);
  color: var(--accent);
  border-radius: 8px;
  padding: 8px 10px;
  font-size: 12px;
  font-weight: 600;
  cursor: pointer;
}
.pairing-steps {
  margin: 0;
  padding-inline-start: 20px;
  display: flex;
  flex-direction: column;
  gap: 10px;
  font-size: 14px;
  color: var(--text-primary);
}
.pairing-steps li { list-style: none; }

form { display: flex; flex-direction: column; gap: 14px; margin-top: 16px; }
label { display: flex; flex-direction: column; gap: 6px; font-size: 14px; color: var(--text-secondary); }
input {
  padding: 12px;
  border: 1px solid var(--border);
  border-radius: 10px;
  font-size: 15px;
  background: var(--surface);
  color: var(--text-primary);
}

section { margin-top: 24px; }
section h2 { font-size: 15px; color: var(--text-secondary); margin-bottom: 8px; }
section label { flex-direction: row; align-items: center; gap: 8px; margin-bottom: 6px; }

/* ==========================================================
   Startup loader — ported from the branded loader design
   (ab_ban_water_alarm_loader.html): shield/droplet logo with
   expanding ripple rings, floating bubbles, a progress bar with
   cycling status text, bilingual brand title + slogan. Rebuilt
   here as plain CSS instead of pulling in the Tailwind CDN build
   that file used — Tailwind's own docs warn that CDN build isn't
   meant for production, and on top of that this app already learned
   the hard way (see push-notification-system.md, 2026-10-03) that
   Google-hosted resources can be unreachable on Iranian networks;
   a startup screen is the worst possible place to add a new
   external dependency that could silently fail to load. Same
   reasoning is why this keeps the app's existing system-font stack
   rather than the loader's Google Fonts.
   ========================================================== */
.loader-overlay {
  position: fixed;
  inset: 0;
  z-index: 1000;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 16px;
  background: radial-gradient(circle at 50% 30%, #ffffff 0%, #f0f7ff 60%, #e0f0fe 100%);
  transition: opacity 0.25s ease;
  overflow: hidden;
}
.loader-overlay.loader-fade-out { opacity: 0; }

.loader-bubble {
  position: absolute;
  background: linear-gradient(135deg, rgba(56, 189, 248, 0.4), rgba(2, 132, 199, 0.15));
  border: 1px solid rgba(255, 255, 255, 0.8);
  border-radius: 50%;
  pointer-events: none;
  animation: loader-bubble-rise 5s ease-in-out infinite;
}
@keyframes loader-bubble-rise {
  0% { transform: translateY(40px) scale(0.6); opacity: 0; }
  50% { opacity: 0.6; }
  100% { transform: translateY(-140px) scale(1.1); opacity: 0; }
}

.loader-card {
  width: 100%;
  max-width: 360px;
  background: rgba(255, 255, 255, 0.9);
  border: 1px solid rgba(186, 225, 251, 0.8);
  border-radius: 36px;
  box-shadow: 0 25px 70px -15px rgba(2, 132, 199, 0.18);
  padding: 32px 28px;
  display: flex;
  flex-direction: column;
  align-items: center;
  text-align: center;
  position: relative;
  z-index: 1;
}

.loader-badge {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  background: rgba(240, 249, 255, 0.9);
  border: 1px solid rgba(186, 225, 251, 0.8);
  padding: 6px 16px;
  border-radius: 999px;
  margin-bottom: 20px;
  font-size: 11px;
  font-weight: 700;
  color: #0369a1;
  letter-spacing: 0.04em;
  text-transform: uppercase;
}
.loader-badge-dot {
  width: 9px;
  height: 9px;
  border-radius: 50%;
  background: #38bdf8;
  position: relative;
}
.loader-badge-dot::before {
  content: "";
  position: absolute;
  inset: 0;
  border-radius: 50%;
  background: #38bdf8;
  opacity: 0.75;
  animation: loader-badge-ping 1.6s cubic-bezier(0, 0, 0.2, 1) infinite;
}
@keyframes loader-badge-ping {
  75%, 100% { transform: scale(2.2); opacity: 0; }
}

.loader-logo-wrap {
  position: relative;
  width: 160px;
  height: 160px;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-bottom: 20px;
}
.loader-ripple {
  position: absolute;
  width: 128px;
  height: 128px;
  border-radius: 50%;
  border: 2px solid rgba(14, 165, 233, 0.35);
  animation: loader-ripple-expand 4s cubic-bezier(0.1, 0.8, 0.3, 1) infinite;
}
.loader-ripple:nth-child(2) { animation-delay: 1.3s; }
.loader-ripple:nth-child(3) { animation-delay: 2.6s; }
@keyframes loader-ripple-expand {
  0% { transform: scale(0.8); opacity: 0.6; }
  50% { opacity: 0.3; }
  100% { transform: scale(2.2); opacity: 0; }
}
.loader-logo {
  position: relative;
  z-index: 1;
  width: 128px;
  height: 128px;
  object-fit: contain;
  animation: loader-float 3.5s ease-in-out infinite;
  filter: drop-shadow(0 16px 30px rgba(2, 132, 199, 0.25));
}
@keyframes loader-float {
  0%, 100% { transform: translateY(0) scale(1); }
  50% { transform: translateY(-10px) scale(1.02); }
}

.loader-title {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  font-size: 26px;
  font-weight: 800;
  color: #1e293b;
  margin: 0 0 4px;
}
.loader-title .fa { color: #0284c7; }
.loader-subtitle { font-size: 11px; font-weight: 700; color: #0284c7; letter-spacing: 0.2em; text-transform: uppercase; margin: 0 0 16px; }

.loader-slogan {
  width: 100%;
  background: rgba(240, 249, 255, 0.6);
  border: 1px solid rgba(224, 242, 254, 0.9);
  border-radius: 16px;
  padding: 10px 16px;
  margin-bottom: 24px;
}
.loader-slogan p { margin: 2px 0; }
.loader-slogan .fa { color: #334155; font-size: 14px; font-weight: 700; }
.loader-slogan .en { color: #64748b; font-size: 12px; font-weight: 600; }

.loader-progress { width: 100%; }
.loader-progress-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
  font-size: 12px;
  font-weight: 700;
  color: #475569;
  padding: 0 2px;
  margin-bottom: 8px;
}
.loader-progress-status { color: #0369a1; transition: all 0.2s ease; }
.loader-progress-status.loader-done { color: #059669; }
.loader-progress-percent { font-family: ui-monospace, monospace; color: #0284c7; font-size: 14px; font-weight: 800; }

.loader-progress-track {
  width: 100%;
  height: 12px;
  background: #f1f5f9;
  border-radius: 999px;
  overflow: hidden;
  padding: 2px;
  border: 1px solid #e2e8f0;
  /* Forced LTR regardless of the page's dir (index.html defaults to
     dir="rtl" for Farsi) — otherwise .loader-progress-fill's width
     grows from the right edge instead of the left, since in an RTL
     block the inline-start is on the right. A progress bar isn't text,
     so it keeps the conventional left-to-right fill direction either
     way, matching how this same loader behaves in the Android app. */
  direction: ltr;
}
.loader-progress-fill {
  height: 100%;
  border-radius: 999px;
  transition: width 0.15s linear;
  /* Two stacked background-image layers, comma-separated — the striped
     overlay on top of the actual blue fill color. A second, separate
     `background-image:` declaration (as this used to be written) simply
     overwrites the first instead of layering on top of it, which is why
     the bar was only ever showing the faint white stripe pattern with no
     blue underneath it. background-size's two values below line up with
     the two layers in the same order (stripe tile size, then the color
     layer stretched to fill). */
  background-image:
    linear-gradient(
      135deg,
      rgba(255, 255, 255, 0.3) 25%, transparent 25%, transparent 50%,
      rgba(255, 255, 255, 0.3) 50%, rgba(255, 255, 255, 0.3) 75%, transparent 75%, transparent
    ),
    linear-gradient(90deg, #38bdf8, #3b82f6, #4338ca);
  background-size: 30px 30px, 100% 100%;
  animation: loader-stripes 1.5s linear infinite;
}
@keyframes loader-stripes {
  0% { background-position: 0 0; }
  100% { background-position: 30px 0; }
}

/* ---------- Login / registration screen ---------- */
.login-screen {
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: 100vh;
  padding: 24px;
}
.login-card {
  width: 100%;
  max-width: 360px;
  display: flex;
  flex-direction: column;
  align-items: stretch;
  text-align: center;
}
.login-logo { font-size: 48px; margin-bottom: 4px; }
.login-card h1 { font-size: 22px; margin: 0 0 6px; }
.login-card .hint { margin: 0 0 18px; }
.login-card form { text-align: right; }
html:not([dir="rtl"]) .login-card form { text-align: left; }
.error-text { color: var(--red); font-size: 13px; margin: 0; min-height: 16px; }
.login-lang-switch { display: flex; justify-content: center; gap: 8px; margin-top: 20px; }
.lang-chip {
  border: 1px solid var(--border);
  background: var(--surface);
  color: var(--text-secondary);
  border-radius: 999px;
  padding: 6px 14px;
  font-size: 13px;
  cursor: pointer;
}
.lang-chip.active { background: var(--accent-bg); color: var(--accent); border-color: var(--accent); font-weight: 600; }

/* ---------- Multi-household (2026-10-04) ---------- */

/* Section header above a group of devices sharing one household —
   only rendered at all when devices span 2+ households (see
   paintDevicesScreen's showGroupHeaders); a single-household browser
   never sees this. */
.household-group-header {
  font-size: 13px;
  font-weight: 700;
  color: var(--text-secondary);
  margin: 18px 0 8px;
}
.household-group-header:first-of-type { margin-top: 4px; }

/* "Which household is this device for?" picker, shown before
   #addDevice when there are 2+ households (see goToAddDevice()). */
.household-picker-list {
  list-style: none;
  padding: 0;
  margin: 16px 0;
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.household-picker-option {
  width: 100%;
  text-align: inherit;
  padding: 14px 16px;
  border: 1px solid var(--border);
  border-radius: 14px;
  background: var(--surface);
  color: var(--text-primary);
  font-size: 15px;
  cursor: pointer;
}

/* Settings' household-management list — each row shows a nickname,
   rename/remove actions, and its home_id/home_secret for syncing into
   another device. */
.household-list {
  list-style: none;
  padding: 0;
  margin: 10px 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.household-row {
  padding: 12px 14px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: 14px;
}
.household-row-main {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 6px;
}
/* Leading icon avatar, matching Android's HouseholdCard teal house-icon
   circle (2026-10-04 redesign). */
.household-row-icon {
  flex-shrink: 0;
  width: 32px;
  height: 32px;
  border-radius: 50%;
  background: var(--accent-bg);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 15px;
}
.household-row-nickname { font-weight: 600; font-size: 15px; flex: 1; }
.household-row-actions { display: flex; gap: 4px; }
.household-row-actions .icon-btn { width: 30px; height: 30px; font-size: 14px; }
.household-row .credential-row { margin-top: 6px; }
.household-row .credential-row span.hint.small { flex-shrink: 0; margin: 0; }

/* Households screen's "create new" / "join existing" button pair
   (2026-10-04 redesign — mirrors Android's HouseholdsScreen.kt). */
.household-add-actions {
  display: flex;
  gap: 10px;
  margin-top: 12px;
}
.household-add-actions .secondary-btn { margin-top: 0; }
