/* Hallmark · shape: Gallery Hang · genre: editorial · theme: Atelier (deal 1/3, seed prompt-1320·811b928e·2026-10-30·r0) · job: sign up · draw: gallery-01
 * hero: Gallery Hang · nav: edge-aligned, wordmark and one action · footer: a mast, the wordmark over the links · imagery: matted prints · signature: the numbered wall label under each print
 * axes: light/roman-serif/cool · posture: restrained · contrast: pass · fold: pass · v2.0.0 */
/* Hallmark · pre-emit critique: P_H_E_S_R_V_ · weakest: photographs are stand-ins until the real album is wired */

@import url("./fonts.css");
@import url("./tokens.css");
@import url("./base.css");

/* ================================================================
   木芽芽 · 共享组件（Atelier）
   ================================================================ */

body { font-family: var(--font-body); color: var(--color-ink-2); line-height: 1.6; }

a { color: inherit; text-decoration: none; }

/* 纸的颗粒：整页一层，极淡 */
.grain {
  position: fixed;
  inset: 0;
  background: var(--grain, none);
  background-size: 180px;
  opacity: 0.14;
  mix-blend-mode: multiply;
  pointer-events: none;
  z-index: var(--z-base);
}

/* ---------------- 导航 ---------------- */
.site-nav {
  position: sticky;
  top: 0;
  z-index: var(--z-sticky-nav);
  background: color-mix(in oklab, var(--color-paper) 92%, transparent);
  border-bottom: var(--rule-hair) solid var(--color-rule);
  backdrop-filter: blur(6px);
}
.site-nav-inner {
  max-width: var(--container);
  margin-inline: auto;
  padding: 0 var(--gutter);
  min-height: 68px;
  display: flex;
  align-items: center;
  gap: var(--space-xl);
}

.wordmark {
  font-family: var(--font-display);
  font-weight: var(--serif-small);
  font-size: var(--text-lg);
  letter-spacing: var(--tracking-display);
  color: var(--color-ink);
  flex-shrink: 0;
}

.nav-links { display: flex; gap: var(--space-lg); margin-left: var(--space-xl); }
.nav-links a {
  font-size: var(--text-sm);
  color: var(--color-muted);
  padding: var(--space-xs) 0;
  border-bottom: var(--rule-hair) solid transparent;
  transition: color var(--dur-short) var(--ease-out),
    border-color var(--dur-short) var(--ease-out);
}
.nav-links a:hover { color: var(--color-ink); border-bottom-color: var(--color-accent); }
.nav-links a[aria-current="page"] { color: var(--color-ink); border-bottom-color: var(--color-ink); }

.nav-end { margin-left: auto; display: flex; align-items: center; gap: var(--space-md); }

/* 账号入口：名字 + 头像 */
.who-wrap { position: relative; }
.who {
  display: flex;
  align-items: center;
  gap: var(--space-sm);
  border: none;
  background: transparent;
  font: inherit;
  cursor: pointer;
  padding: var(--space-2xs) var(--space-xs) var(--space-2xs) var(--space-2xs);
  border-radius: var(--radius-pill);
  transition: background-color var(--dur-short) var(--ease-out);
}
.who:hover { background: var(--color-paper-2); }
.who .avatar {
  width: 30px; height: 30px;
  border-radius: var(--radius-pill);
  object-fit: cover;
  background: var(--color-paper-3);
  border: var(--rule-hair) solid var(--color-card-edge);
  flex-shrink: 0;
}
.who .name { font-size: var(--text-sm); color: var(--color-ink); }
.who .caret { font-size: var(--text-xs); color: var(--color-muted); }

/* 下拉 */
.dropdown {
  position: absolute;
  right: 0; top: calc(100% + var(--space-xs));
  min-width: 15rem;
  background: var(--color-card);
  border: var(--rule-hair) solid var(--color-card-edge);
  box-shadow: var(--shadow-card);
  z-index: var(--z-dropdown);
  padding: var(--space-xs) 0;
}
.dropdown .dh {
  display: flex; align-items: center; gap: var(--space-sm);
  padding: var(--space-sm) var(--space-md);
  border-bottom: var(--rule-hair) solid var(--color-rule);
}
.dropdown .dh img { width: 34px; height: 34px; border-radius: var(--radius-pill); object-fit: cover; }
.dropdown .dh .t { font-size: var(--text-sm); color: var(--color-ink); }
.dropdown .dh .s { font-size: var(--text-xs); color: var(--color-muted); }
.dropdown a, .dropdown button {
  display: block; width: 100%; text-align: left;
  padding: var(--space-xs) var(--space-md);
  font-size: var(--text-sm);
  color: var(--color-ink-2);
  background: none; border: none; cursor: pointer;
}
.dropdown a:hover, .dropdown button:hover { background: var(--color-paper-2); color: var(--color-ink); }
.dropdown .danger { color: var(--color-error); }

/* 工具栏：PhotoCraft 修图 / LightCraft 调色 / 姿势图库 / 本 agent
   外观是它的兄弟（同一层级的按钮 + 下拉），不再塞在工具里面 */
.tools-wrap { position: relative; }
.tools {
  display: inline-flex; align-items: center; gap: var(--space-2xs);
  border: none; background: transparent; font: inherit; cursor: pointer;
  padding: var(--space-2xs) var(--space-xs);
  border-radius: var(--radius-pill);
  font-size: var(--text-sm); color: var(--color-ink-2);
  transition: background-color var(--dur-short) var(--ease-out);
}
.tools:hover { background: var(--color-paper-2); color: var(--color-ink); }
.tools .caret { font-size: var(--text-xs); color: var(--color-muted); }
.tools-dd { min-width: 13rem; }

/* 手机上的菜单按钮：桌面上不显示（桌面有 .nav-links） */
.nav-burger { display: none; }

/* ---------------- 控制 ---------------- */
.btn {
  display: inline-flex; align-items: center; justify-content: center;
  gap: var(--space-xs);
  min-height: 44px;
  padding: 0 var(--space-lg);
  border: var(--rule-hair) solid var(--color-ink);
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--color-ink);
  font-family: var(--font-body);
  font-size: var(--text-sm);
  cursor: pointer;
  transition: background-color var(--dur-short) var(--ease-out),
    color var(--dur-short) var(--ease-out);
}
.btn:hover { background: var(--color-ink); color: var(--color-paper); }
.btn.quiet { border-color: var(--color-rule); color: var(--color-ink-2); }
.btn.quiet:hover { background: var(--color-paper-2); color: var(--color-ink); border-color: var(--color-ink); }
/* 上传进行中：两个按钮都锁住，防重复点开两个选择器 */
.btn[disabled],
.btn[disabled]:hover {
  cursor: default;
  background: transparent;
  color: var(--color-muted);
  border-color: var(--color-rule);
}

/* 上传进度：数字等宽，进度跳动时按钮不跟着晃 */
.up-status {
  margin-top: var(--space-md);
  font-size: var(--text-sm);
  color: var(--color-ink-2);
  font-variant-numeric: tabular-nums;
}
.up-status .bar {
  display: block;
  height: 3px;
  margin-top: var(--space-sm);
  background: var(--color-rule);
  overflow: hidden;
}
.up-status .bar i {
  display: block;
  height: 100%;
  width: 100%;
  background: var(--color-accent);
  /* 用 transform 推，不动 width：进度条每帧改宽度会触发布局（动效只走合成层） */
  transform: scaleX(0);
  transform-origin: left center;
  transition: transform var(--dur-short) var(--ease-out);
}
.up-status.is-error { color: var(--color-accent); }

/* 次级：下划线链接 */
.link {
  color: var(--color-ink);
  border-bottom: var(--rule-hair) solid var(--color-accent);
  padding-bottom: 1px;
}
.link:hover { color: var(--color-accent); }

/* ---------------- 棉纸卡 ---------------- */
.stock {
  position: relative;
  border-radius: 2px;
  background: var(--fibre, none) 0 0 / 220px,
    linear-gradient(160deg, var(--card-lit), var(--color-card) 55%, var(--card-shade));
  box-shadow: var(--shadow-card), inset 1px 1px 0 var(--lit);
}
.stock::before {
  content: "";
  position: absolute;
  inset: 0.875rem;
  border: var(--rule-hair) solid var(--color-card-edge);
  pointer-events: none;
}

/* ---------------- 装裱照片 ---------------- */
/* 相片在薄棉纸上，下沿一条铅笔写的编号 */
.print { margin: 0; }
.print .mat {
  position: relative;
  padding: 10px;
  background: linear-gradient(160deg, var(--card-lit), var(--color-card) 60%, var(--card-shade));
  box-shadow: var(--shadow-card), inset 1px 1px 0 var(--lit);
}
.print .mat::after {
  content: "";
  position: absolute; inset: 10px;
  border: var(--rule-hair) solid var(--color-mat-edge);
  pointer-events: none;
}
.print img {
  width: 100%;
  aspect-ratio: 4 / 5;
  object-fit: cover;
  display: block;
  /* 暖日光：轻微降饱和，压一点高光 */
  filter: sepia(0.16) saturate(0.9) contrast(0.95);
}
.print figcaption .fn, .album-photos figcaption .fn {
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap; min-width: 0;
}
.print figcaption .dt, .album-photos figcaption .dt { white-space: nowrap; }
.print figcaption {
  display: flex; justify-content: space-between; gap: var(--space-md);
  margin-top: var(--space-xs);
  font-size: var(--text-xs);
  color: var(--color-muted);
  font-variant-numeric: tabular-nums;
}
.print .no { color: var(--color-pencil); }

/* ---------------- 版式 ---------------- */
.rule { border: 0; border-top: var(--rule-head) solid var(--color-ink); margin: 0; }
.hair { border: 0; border-top: var(--rule-hair) solid var(--color-rule); margin: 0; }

.section { padding: var(--section-gap-s) 0; }
.section + .section { border-top: var(--rule-hair) solid var(--color-rule); }

.eyebrowless-head {
  font-family: var(--font-display);
  font-weight: var(--display-weight);
  color: var(--color-ink);
  letter-spacing: var(--tracking-display);
}

/* ---------------- 页脚 ---------------- */
.site-foot {
  border-top: var(--rule-head) solid var(--color-ink);
  padding: var(--space-2xl) 0 var(--space-xl);
  margin-top: var(--space-2xl);
}
.site-foot .mast {
  font-family: var(--font-display);
  font-weight: var(--display-weight);
  font-size: var(--text-title);
  color: var(--color-ink);
  letter-spacing: var(--tracking-display);
}
.site-foot .cols {
  display: flex; flex-wrap: wrap; gap: var(--space-xl);
  margin-top: var(--space-lg);
  font-size: var(--text-sm);
  color: var(--color-muted);
}
.site-foot a:hover { color: var(--color-ink); }

/* ---------------- 响应 ---------------- */
@media (max-width: 60rem) {
  /* 窄屏原来只有一个「隐藏」：相册 / 家庭 / 工具全够不着，这里补上菜单 */
  .nav-links { display: none; }
  .site-nav-inner { min-height: 60px; gap: var(--space-md); }
  .tools-wrap { display: none; }
  .nav-burger {
    display: inline-flex; align-items: center;
    border: var(--rule-hair) solid var(--color-card-edge);
    background: var(--color-card); color: var(--color-ink-2);
    font: inherit; font-size: var(--text-sm);
    padding: var(--space-2xs) var(--space-sm);
    border-radius: var(--radius-pill); cursor: pointer;
  }
  .nav-burger[aria-expanded="true"] { background: var(--color-paper-2); color: var(--color-ink); }
  .nav-panel {
    position: absolute; left: 0; right: 0; top: 100%;
    display: flex; flex-direction: column;
    background: var(--color-card);
    border-bottom: var(--rule-hair) solid var(--color-rule);
    box-shadow: var(--shadow-card);
    padding: var(--space-sm) var(--gutter) var(--space-md);
    max-height: 72vh; overflow-y: auto;
    z-index: var(--z-dropdown);
  }
  .nav-panel[hidden] { display: none; }
  .nav-panel a {
    padding: var(--space-sm) 0;
    font-size: var(--text-md); color: var(--color-ink-2);
    border-bottom: var(--rule-hair) solid var(--color-rule);
  }
  .nav-panel a:last-child { border-bottom: none; }
  .nav-panel a[aria-current="page"] { color: var(--color-ink); }
  .nav-panel .pnl-h {
    margin-top: var(--space-md); padding-bottom: var(--space-2xs);
    font-size: var(--text-xs); letter-spacing: .06em; color: var(--color-muted);
  }
  .nav-panel a.ext::after { content: " ↗"; color: var(--color-muted); }
}

/* ================================================================
   木芽芽 · 照片库 与 相册管理（Atelier 系统内的扩展页）
   沿用 tokens.css 的令牌，不引入新颜色／新字体。
   ================================================================ */

/* ---------------- 页头 ---------------- */
.lib-head { padding: var(--space-xl) 0 var(--space-lg); }
.lib-head .row {
  display: flex; flex-wrap: wrap; align-items: baseline;
  justify-content: space-between; gap: var(--space-md);
}
.lib-head h1 { font-size: var(--text-display-s); max-width: 24ch; }
.lib-head .sub {
  font-size: var(--text-sm); color: var(--color-muted);
  font-variant-numeric: tabular-nums;
}
.lib-tools {
  display: flex; flex-wrap: wrap; align-items: center;
  gap: var(--space-sm);
  margin-top: var(--space-md);
}
.lib-tools .spacer { margin-left: auto; }

/* ---------------- 照片墙：整页纵向滚动 ---------------- */
.lib-grid {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: var(--gap-columns) var(--gap-columns);
  padding-bottom: var(--space-xl);
}
@media (max-width: 75rem) { .lib-grid { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
@media (max-width: 48rem) { .lib-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }

.lib-cell { position: relative; min-width: 0; }
.lib-cell .print img { aspect-ratio: 1 / 1; }

/* 选择态：整张照片是个可切换的按钮 */
.lib-cell .hit {
  display: block; width: 100%; padding: 0; border: none; background: none;
  text-align: left; cursor: pointer; color: inherit; font: inherit;
}
.lib-cell .mark {
  position: absolute; top: var(--space-sm); left: var(--space-sm);
  z-index: var(--z-raised);
  width: 26px; height: 26px;
  display: grid; place-items: center;
  border: var(--rule-hair) solid var(--color-card-edge);
  border-radius: var(--radius-pill);
  background: var(--color-card);
  color: transparent;
  font-size: var(--text-xs);
  font-variant-numeric: tabular-nums;
  box-shadow: var(--shadow-card);
}
.lib-cell[data-picked="1"] .mark { background: var(--color-ink); color: var(--color-paper); border-color: var(--color-ink); }
.lib-cell[data-picked="1"] .mat { outline: 2px solid var(--color-accent); outline-offset: 2px; }
/* 选择模式下不做跳转提示，避免误以为点了会打开 */
.lib-grid.is-picking .hit { cursor: pointer; }
.lib-grid:not(.is-picking) .hit { cursor: pointer; }

.lib-more { display: flex; justify-content: center; padding: var(--space-lg) 0 var(--space-2xl); }
.lib-end { text-align: center; padding: var(--space-lg) 0 var(--space-2xl); font-size: var(--text-sm); color: var(--color-muted); }
.lib-sentinel { height: 1px; }

/* ---------------- 底部选择条 ---------------- */
.pickbar {
  position: fixed; left: 0; right: 0; bottom: 0;
  z-index: var(--z-sticky);
  background: color-mix(in oklab, var(--color-paper) 94%, transparent);
  backdrop-filter: blur(6px);
  border-top: var(--rule-head) solid var(--color-ink);
  padding: var(--space-sm) 0;
  /* iPhone 底部那条横杠会盖住「收进册子」，把安全区加进来 */
  padding-bottom: calc(var(--space-sm) + env(safe-area-inset-bottom, 0px));
}
.pickbar .inner {
  display: flex; flex-wrap: wrap; align-items: center;
  gap: var(--space-sm);
}
.pickbar .n { font-size: var(--text-sm); color: var(--color-ink); font-variant-numeric: tabular-nums; }
.pickbar .spacer { margin-left: auto; }

/* ---------------- 相册管理 ---------------- */
.mg-create {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto auto;
  gap: var(--space-sm);
  align-items: end;
  padding: var(--space-lg) 0;
  border-bottom: var(--rule-hair) solid var(--color-rule);
}
@media (max-width: 48rem) { .mg-create { grid-template-columns: minmax(0, 1fr); } }

.field { display: flex; flex-direction: column; gap: var(--space-2xs); min-width: 0; }
.field label { font-size: var(--text-xs); color: var(--color-muted); }
.field input, .field select {
  min-height: 44px;
  padding: 0 var(--space-sm);
  border: var(--rule-hair) solid var(--color-rule);
  border-radius: var(--radius-pill);
  background: var(--color-card);
  color: var(--color-ink);
}
.field input:hover, .field select:hover { border-color: var(--color-ink); }

.mg-list { display: flex; flex-direction: column; }
.mg-row {
  display: grid;
  grid-template-columns: 84px minmax(0, 1fr) auto;
  gap: var(--space-lg);
  align-items: center;
  padding: var(--space-lg) 0;
  border-bottom: var(--rule-hair) solid var(--color-rule);
}
@media (max-width: 48rem) {
  .mg-row { grid-template-columns: 64px minmax(0, 1fr); }
  .mg-row .acts { grid-column: 1 / -1; }
}
/* 家人行第一格是头像+名字（没有封面图），照 .mg-row 的三列会把名字挤成一列竖字 */
.mem-row { grid-template-columns: minmax(0, 1fr) auto; }
@media (max-width: 48rem) { .mem-row { grid-template-columns: minmax(0, 1fr); } }
.mg-row .cover {
  width: 100%; aspect-ratio: 1 / 1; object-fit: cover;
  background: var(--color-paper-2);
  border: var(--rule-hair) solid var(--color-card-edge);
}
.mg-row .t {
  font-family: var(--font-display); font-weight: var(--serif-small);
  font-size: var(--text-lg); color: var(--color-ink);
  letter-spacing: var(--tracking-display);
  overflow-wrap: break-word; min-width: 0;
}
.mg-row .facts { margin-top: var(--space-2xs); font-size: var(--text-sm); color: var(--color-muted); font-variant-numeric: tabular-nums; }
.mg-row .acts { display: flex; flex-wrap: wrap; gap: var(--space-xs); }
.mg-row .acts .btn { min-height: 40px; padding: 0 var(--space-md); }
.mg-row .acts .danger { border-color: var(--color-error); color: var(--color-error); }
.mg-row .acts .danger:hover { background: var(--color-error); color: var(--color-paper); border-color: var(--color-error); }

/* ---------------- 册子墙：首页与家庭页共用同一套画册网格 ----------------
   每张卡片 = 衬纸 + 4:5 封面 + 一条铅笔小字。家庭页的册子列表
   也用这一套，页面上「册子」永远长成同一个样子，不再有另一种列表形态。 */
.view-book {
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--space-xl) var(--space-lg);
  padding-top: var(--space-lg);
  border-top: var(--rule-head) solid var(--color-ink);
}
.view-book .bk {
  position: relative;
  display: block; background: var(--color-card);
  border: var(--rule-hair) solid var(--color-card-edge);
  box-shadow: var(--shadow-card);
  transition: transform var(--dur-short) var(--ease-out), box-shadow var(--dur-short) var(--ease-out);
}
.view-book .bk-open { display: block; color: inherit; text-decoration: none; }
.view-book .bk:hover { transform: translateY(-3px); box-shadow: 0 2px 4px oklch(25% 0.03 55 / .10), 0 22px 42px -20px oklch(25% 0.03 55 / .34); }
.view-book .mat { margin: var(--space-sm); padding: 6px; background: var(--card-lit); border: var(--rule-hair) solid var(--color-card-edge); }
.view-book .mat img, .view-book .mat .cover-empty { width: 100%; display: block; aspect-ratio: 4 / 5; object-fit: cover; }
.view-book .meta { display: block; padding: 0 var(--space-md) var(--space-md); }
.view-book .t {
  display: block; font-family: var(--font-display); font-weight: var(--serif-small);
  font-size: var(--text-lg); color: var(--color-ink); letter-spacing: var(--tracking-display);
}
.view-book .l {
  display: flex; justify-content: space-between; gap: var(--space-md);
  margin-top: 4px; font-size: var(--text-xs); color: var(--color-muted); font-variant-numeric: tabular-nums;
}
/* 窄卡片放不下「6 张 · 我的家 10月20日」一整行：日期不许折，左边不够就省略号，
   别让两段各自折行后在中间互相穿插。 */
.view-book .l > span { min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.view-book .l > span:last-child { flex: none; overflow: visible; }
.view-book .bk:hover .t { color: var(--color-accent); }
.view-book .empty-note { grid-column: 1 / -1; }
/* 卡片上的「收照片」：盖在封面右上角，点封面本身还是翻开 */
.view-book .bk-act {
  position: absolute; top: calc(var(--space-sm) + 10px); right: calc(var(--space-sm) + 10px);
  display: inline-flex; align-items: center; justify-content: center;
  width: 34px; height: 34px; padding: 0; cursor: pointer;
  border: var(--rule-hair) solid var(--color-card-edge); border-radius: var(--radius-pill);
  background: oklch(97.6% 0.007 82 / .92); color: var(--color-ink-2);
  opacity: 0; transition: opacity var(--dur-short) var(--ease-out);
}
.view-book .bk:hover .bk-act, .view-book .bk-act:focus-visible { opacity: 1; }
.view-book .bk-act:hover { color: var(--color-ink); border-color: var(--color-ink); }
.view-book .bk-act .ic { width: 17px; height: 17px; }
@media (hover: none) { .view-book .bk-act { opacity: 1; } }

@media (max-width: 980px) {
  .view-book { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 720px) {
  .view-book { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-lg) var(--space-md); }
}
/* 站点满宽后，宽屏不能还用 3 列——否则一张封面会长到 800px。
   断点按「卡片稳定在 340~430px」推：1560→4、2000→5、2440→6、2880→7。 */
@media (min-width: 1560px) { .view-book { grid-template-columns: repeat(4, minmax(0, 1fr)); } }
@media (min-width: 2000px) { .view-book { grid-template-columns: repeat(5, minmax(0, 1fr)); } }
@media (min-width: 2440px) { .view-book { grid-template-columns: repeat(6, minmax(0, 1fr)); } }
@media (min-width: 2880px) { .view-book { grid-template-columns: repeat(7, minmax(0, 1fr)); } }

/* ---------------- 弹层 ---------------- */
.sheet {
  border: var(--rule-hair) solid var(--color-card-edge);
  background: var(--color-card);
  color: var(--color-ink-2);
  box-shadow: var(--shadow-card);
  padding: var(--space-lg);
  max-width: 30rem;
  width: calc(100% - 2 * var(--space-md));
}
.sheet::backdrop { background: oklch(19% 0.024 52 / 0.42); }
.sheet h2 { font-size: var(--text-xl); margin-bottom: var(--space-md); }
.sheet .fields { display: flex; flex-direction: column; gap: var(--space-md); }
.sheet .foot { display: flex; gap: var(--space-sm); justify-content: flex-end; margin-top: var(--space-lg); }
.sheet .note { font-size: var(--text-sm); color: var(--color-muted); margin-top: var(--space-xs); }
.sheet .pick-list { display: flex; flex-direction: column; gap: var(--space-2xs); max-height: 40vh; overflow-y: auto; }
.sheet .pick-list label {
  display: flex; align-items: center; gap: var(--space-sm);
  padding: var(--space-xs) var(--space-sm);
  border: var(--rule-hair) solid var(--color-rule);
  border-radius: var(--radius-pill);
  cursor: pointer;
}
.sheet .pick-list label:hover { border-color: var(--color-ink); }
.sheet .pick-list .n { margin-left: auto; font-size: var(--text-xs); color: var(--color-muted); font-variant-numeric: tabular-nums; }
.sheet .pickgrid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(84px, 1fr));
  gap: var(--space-2xs);
  max-height: 46vh;
  overflow-y: auto;
}
.sheet .pickgrid button { padding: 0; border: 2px solid transparent; background: none; cursor: pointer; }
.sheet .pickgrid img { width: 100%; aspect-ratio: 1; object-fit: cover; display: block; }
.sheet .pickgrid button:hover { border-color: var(--color-ink); }
.sheet .pickgrid button.is-pick { border-color: var(--color-accent); }
.sheet .pickgrid button:focus-visible { outline: none; border-color: var(--color-focus); box-shadow: 0 0 0 3px color-mix(in oklab, var(--color-focus) 16%, transparent); }

/* ---------------- 空态 ---------------- */
.empty-note {
  font-size: var(--text-sm); color: var(--color-muted);
  padding: var(--space-lg) 0;
}

/* ---------------- 手指够得着 ---------------- */
/* 粗指针（手机/平板）下这些控件实测只有 18~32px 高，点起来老点不中，统一放到 44。 */
@media (pointer: coarse) {
  .btn, .back, select, .nav-burger, .who { min-height: 44px; }
  .back { display: inline-flex; align-items: center; gap: var(--space-3xs); }
  .mg-row .acts .btn { min-height: 44px; }
}

/* ---- 骨架屏：等照片的这几百毫秒，先把版面立起来，别让页面空着 ---- */
@keyframes sk-breathe { from { background-color: var(--color-paper-2); } to { background-color: var(--color-paper-3); } }
.sk-cell {
  aspect-ratio: 1 / 1;
  background-color: var(--color-paper-2);
  animation: sk-breathe 1600ms var(--ease-in-out) infinite alternate;
}
.sk-card {
  aspect-ratio: 3 / 4;
  background-color: var(--color-paper-2);
  animation: sk-breathe 1600ms var(--ease-in-out) infinite alternate;
}
.sk-row { height: 2.75rem; background-color: var(--color-paper-2); animation: sk-breathe 1600ms var(--ease-in-out) infinite alternate; }

/* ================================================================
   v2 视觉升级（2026-10-31）
   只动质感与层级，不改信息结构：纸面更柔、按钮分主次、
   小号数字换衬线、列表行距收紧、空态改成有框的便笺。
   ================================================================ */

/* ---- 纸面：一层极淡的天光，别让整页是死平色 ---- */
body {
  background:
    radial-gradient(120% 70% at 50% -12%, oklch(98.5% 0.006 84 / 0.9) 0%, transparent 58%),
    var(--color-paper);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}
.grain { opacity: 0.10; }
::selection { background: color-mix(in oklab, var(--color-accent) 22%, transparent); }

/* ---- 数字：凡是「张数 / 日期 / 页码」这类小号数字，走衬线 + 等宽 ---- */
.lib-head .sub,
.mg-row .facts,
.sec-head .count,
.facts,
.page-no,
.turner .pos,
.pickbar .n,
.tidy-bar .n {
  font-family: var(--font-display);
  font-variant-numeric: lining-nums tabular-nums;
  letter-spacing: 0.01em;
}

/* ---- 按钮：主次分明（实心 / 描边 / 纯文字）---- */
.btn {
  min-height: 42px;
  border-radius: 2px;
  background: var(--color-ink);
  color: var(--color-paper);
  border-color: var(--color-ink);
  transition: background-color var(--dur-short) var(--ease-out),
    color var(--dur-short) var(--ease-out),
    border-color var(--dur-short) var(--ease-out),
    transform var(--dur-short) var(--ease-out),
    box-shadow var(--dur-short) var(--ease-out);
}
.btn:hover {
  background: color-mix(in oklab, var(--color-ink) 86%, var(--color-paper));
  color: var(--color-paper);
  transform: translateY(-1px);
  box-shadow: 0 2px 6px -2px oklch(25% 0.03 55 / 0.35);
}
.btn.quiet {
  background: transparent;
  color: var(--color-ink-2);
  border-color: color-mix(in oklab, var(--color-rule) 88%, var(--color-ink));
  box-shadow: none;
}
.btn.quiet:hover {
  background: var(--color-paper-2);
  color: var(--color-ink);
  border-color: var(--color-ink);
}
.btn[disabled], .btn[disabled]:hover {
  background: transparent;
  color: var(--color-muted);
  border-color: var(--color-rule);
  transform: none;
  box-shadow: none;
}
.btn:focus-visible,
.back:focus-visible,
.nav-links a:focus-visible,
.album-row:focus-visible,
.print-link:focus-visible,
.field input:focus-visible,
.field select:focus-visible,
.sheet .pick-list label:focus-within {
  outline: 2px solid var(--color-focus);
  outline-offset: 2px;
  border-radius: 2px;
}

/* ---- 导航：矮一点、实一点 ---- */
.site-nav-inner { min-height: 64px; }
.wordmark { font-size: 1.1875rem; letter-spacing: -0.012em; }
.nav-links { gap: 30px; }
.nav-links a { padding: 6px 0 5px; border-bottom-width: 2px; }
.nav-links a[aria-current="page"] { border-bottom-color: var(--color-ink); }

/* ---- 表单 ---- */
.field input, .field select { min-height: 42px; border-radius: 2px; }
.field input:hover, .field select:hover { border-color: color-mix(in oklab, var(--color-ink) 55%, var(--color-rule)); }
.field input:focus, .field select:focus { outline: none; border-color: var(--color-focus); box-shadow: 0 0 0 3px color-mix(in oklab, var(--color-focus) 16%, transparent); }
.field label { letter-spacing: 0.02em; }

/* ---- 列表行：收紧一点，封面 76 ---- */
.mg-row { padding: var(--space-md) 0; }
.mg-row .t { font-size: 1.125rem; }
.mg-row .cover { border-radius: 1px; box-shadow: inset 0 0 0 1px oklch(20% 0.02 60 / 0.06); }
.mg-row:hover { background: color-mix(in oklab, var(--color-paper-2) 55%, transparent); }

/* ---- 空态：有框的便笺，别只飘一句话 ---- */
.empty-note {
  margin: var(--space-md) 0 0;
  padding: var(--space-xl) var(--space-lg);
  border: 1px dashed color-mix(in oklab, var(--color-rule) 85%, var(--color-muted));
  border-radius: 2px;
  background: color-mix(in oklab, var(--color-paper-2) 45%, transparent);
  text-align: center;
}

/* ---- 弹层 ---- */
.sheet {
  border-radius: 2px;
  box-shadow: 0 1px 0 oklch(25% 0.03 55 / 0.06), 0 8px 24px -12px oklch(25% 0.03 55 / 0.35), 0 40px 80px -40px oklch(25% 0.03 55 / 0.45);
  padding: var(--space-xl);
}
.sheet::backdrop { background: oklch(19% 0.024 52 / 0.38); backdrop-filter: blur(3px); }
.sheet h2 { letter-spacing: -0.015em; }
.sheet .pick-list label { border-radius: 2px; }
.sheet .pick-list label:hover { background: var(--color-paper-2); }

/* ---- 页脚 ---- */
.site-foot { margin-top: var(--space-xl); padding: var(--space-xl) 0 var(--space-lg); }
.site-foot .mast { font-size: 1.375rem; }
.site-foot .cols { gap: var(--space-lg); margin-top: var(--space-md); }

/* ---- 进场：轻微上浮；尊重系统的减少动效 ---- */
@keyframes v2-rise {
  from { opacity: 0; transform: translateY(8px); }
  to { opacity: 1; transform: none; }
}
main > section, main > .container > .lib-head, main > .container > .album-head {
  animation: v2-rise 380ms var(--ease-out) both;
}
@media (prefers-reduced-motion: reduce) {
  main > section, main > .container > .lib-head, main > .container > .album-head { animation: none; }
  .btn:hover { transform: none; }
}

/* ---- v2.1 图标：统一 16px 线稿，跟文字基线对齐 ---- */
.ic {
  width: 16px; height: 16px;
  display: inline-block; vertical-align: -2px;
  flex-shrink: 0;
}
.ic.lg { width: 20px; height: 20px; }
.btn .ic { margin-right: 1px; }
.btn.quiet .ic { opacity: 0.92; }
.nav-links a .ic, .site-foot .ic { width: 14px; height: 14px; }


/* ================================================================
   v3 素材层（2026-10-31）：外来素材 + 印刷语汇
   图案：Hero Patterns（MIT, heropatterns.com），用 mask 上色 → 主题可切
   插画：Open Doodles（CC0, opendoodles.com），同样走 mask，单色线描
   纸纹：自产噪点（tokens.css 的 --grain），不引 CC BY-SA 的位图纹理
   ================================================================ */

/* ---- 图案底：颜色取自 currentColor 的替代（mask + 背景色），透明度由主题控 ---- */
/* 共享层：点任一 tex-* 类即生效（不是 .tex，别记错）
   注意 content 必须写，否则伪元素根本不生成——上一版就是在这儿被误删，
   结果所有图案层静默失效（computed style 还照样报 mask，骗过眼睛）。 */
.tex-grid, .tex-dots, .tex-lines {
  position: relative;
  isolation: isolate;
}
.tex-grid::before, .tex-dots::before, .tex-lines::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  pointer-events: none;
  background-color: var(--color-ink);
  opacity: var(--tex-opacity, 0.045);
  -webkit-mask-repeat: repeat;
  mask-repeat: repeat;
  -webkit-mask-position: 0 0;
  mask-position: 0 0;
}
.tex-grid::before {
  -webkit-mask-image: url("./img/patterns/graphPaper.svg");
  mask-image: url("./img/patterns/graphPaper.svg");
  -webkit-mask-size: 100px 100px;
  mask-size: 100px 100px;
}
.tex-lines::before {
  -webkit-mask-image: url("./img/patterns/diagonalLines.svg");
  mask-image: url("./img/patterns/diagonalLines.svg");
  -webkit-mask-size: 6px 6px;
  mask-size: 6px 6px;
  --tex-opacity: 0.06;
}
.tex-dots::before {
  -webkit-mask-image: url("./img/patterns/pixelDots.svg");
  mask-image: url("./img/patterns/pixelDots.svg");
  -webkit-mask-size: 16px 16px;
  mask-size: 16px 16px;
  --tex-opacity: 0.05;
}

/* 顶栏与页脚各铺一层，给整页一个上下的「封面边」 */
.site-nav.tex-grid::before { opacity: 0.03; }
.site-foot.tex-dots::before { opacity: 0.035; }

/* ---- 裁切标记：印刷 crop marks，用在册子摊开页四角 ---- */
.crop { position: relative; }
.crop::before,
.crop::after {
  content: "";
  position: absolute;
  width: 14px;
  height: 14px;
  pointer-events: none;
  opacity: 0.5;
}
.crop::before {
  top: -7px; left: -7px;
  border-top: 1px solid var(--color-muted);
  border-left: 1px solid var(--color-muted);
}
.crop::after {
  bottom: -7px; right: -7px;
  border-bottom: 1px solid var(--color-muted);
  border-right: 1px solid var(--color-muted);
}

/* ---- 照片衬纸：一层极淡纤维，印刷味 ---- */
.print .mat,
.car-item .mat {
  background-image: var(--grain, none);
  background-size: 180px;
  background-blend-mode: multiply;
}

/* ---- 插画（Open Doodles，CC0）：单色 mask，跟随主题与文字色 ---- */
.art {
  display: block;
  width: var(--art-w, 200px);
  height: var(--art-h, 150px);
  background-color: var(--art-color, var(--color-muted));
  opacity: var(--art-opacity, 0.45);
  -webkit-mask-repeat: no-repeat;
  mask-repeat: no-repeat;
  -webkit-mask-position: center;
  mask-position: center;
  -webkit-mask-size: contain;
  mask-size: contain;
}
.art-levitate {
  -webkit-mask-image: url("./img/art/levitate.svg");
  mask-image: url("./img/art/levitate.svg");
}
.art-loving {
  -webkit-mask-image: url("./img/art/loving.svg");
  mask-image: url("./img/art/loving.svg");
}
.art-chilling {
  -webkit-mask-image: url("./img/art/chilling.svg");
  mask-image: url("./img/art/chilling.svg");
}
.art-empty { --art-w: 220px; --art-h: 170px; }

/* 空态容器：插画 + 一句话，居中 */
.empty-box {
  display: grid;
  justify-items: center;
  gap: var(--space-sm);
  padding: var(--space-xl) var(--space-md) var(--space-lg);
}
.empty-box[hidden] { display: none; }
.empty-box .empty-note {
  border: none;
  background: none;
  padding: 0;
  margin: 0;
  max-width: 26ch;
  text-align: center;
  text-wrap: balance;
}

/* ---- v3.1：自建弹框与轻提示（替掉原生 confirm / prompt / alert）---- */
.btn.danger {
  background: var(--color-error);
  border-color: var(--color-error);
  color: var(--color-paper);
}
.btn.danger:hover { filter: brightness(1.08); }
.btn.quiet.danger {
  background: transparent;
  color: var(--color-error);
  border-color: var(--color-error);
}
.btn.quiet.danger:hover { background: var(--color-error); color: var(--color-paper); }

.confirm-sheet { width: min(30rem, 92vw); }
.confirm-sheet .body {
  color: var(--color-ink-2);
  line-height: 1.6;
  text-wrap: pretty;
}
.confirm-sheet h2 + .body { margin-top: calc(var(--space-xs) * -1); }

.toast-stack {
  position: fixed;
  left: 50%;
  bottom: var(--space-lg);
  transform: translateX(-50%);
  z-index: var(--z-toast);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--space-xs);
  pointer-events: none;
  width: max-content;
  max-width: min(34rem, 92vw);
}
.toast {
  position: relative;
  background: var(--color-card);
  border: 1px solid var(--color-card-edge);
  box-shadow: var(--shadow-card);
  padding: 10px 14px 10px 30px;
  font-size: var(--text-sm);
  line-height: 1.5;
  color: var(--color-ink);
  animation: v2-rise var(--dur-short) var(--ease-out);
}
/* 提示语的身份用一个小圆点说，不用「左侧一道粗色条」——
   单边粗色条是最扎眼的 AI 生成味（impeccable 的 side-tab 规则）。 */
.toast::before {
  content: "";
  position: absolute;
  left: 13px;
  top: 50%;
  width: 6px;
  height: 6px;
  margin-top: -3px;
  border-radius: 999px;
  background: var(--color-ink);
}
.toast.is-error { border-color: color-mix(in oklab, var(--color-error) 45%, var(--color-card-edge)); }
.toast.is-error::before { background: var(--color-error); }
@media (prefers-reduced-motion: reduce) {
  .toast { animation: none; }
}

/* 还没选照片的大图位：src 被 JS 摘掉时别留一个破图框（photo.html 的空态） */
#bigImg:not([src]) { visibility: hidden; }
