/* ══════════════════════════════════════════════════════════════════════════
   Threshold 申请表 —— 独立页面 + 弹窗，共用一套样式

   为什么单独一个文件，不写进 landing.css：
     landing.css 是设计侧在改的活文件。新功能塞进去会制造无意义的合并冲突，
     而仓库里已经有 case-detail.css 这个先例 —— 按功能分文件是既有约定。

   一套样式两种容器：
     .ap-page   独立页面（apply.html 的 <body>）
     .ap-dialog 弹窗（apply.js 建的 <dialog>）
   表单本体的样式对两者完全相同 —— 只有外壳的尺寸/边框/居中不同。
   ⚠️ 别给表单元素写 .ap-dialog 限定的规则，否则独立页面会掉样式。

   颜色一律走 tokens.css 的语义令牌，不写字面色值 ——
   深色带与将来的主题色都靠它自动跟上。
   ══════════════════════════════════════════════════════════════════════════ */

/* ── 独立页面外壳 ─────────────────────────────────────────────────────── */
.ap-page{background:var(--paper);color:var(--text);}
.ap-shell{max-width:680px;margin:0 auto;padding:88px 24px 96px;}
@media(max-width:700px){.ap-shell{padding:56px 20px 64px;}}

/* ── 抬头 ─────────────────────────────────────────────────────────────── */
.ap-eyebrow{font-size:10.5px;letter-spacing:.2em;text-transform:uppercase;
  color:var(--text-faint);margin:0 0 18px;}
.ap-title{font-family:var(--font-display);font-weight:350;letter-spacing:-.03em;
  font-size:38px;line-height:1.1;color:var(--text);margin:0 0 16px;}
.ap-title-sm{font-size:26px;}
.ap-intro{font-size:15px;line-height:1.62;color:var(--text-mute);margin:0;max-width:46ch;}
.ap-head{margin-bottom:38px;}

/* ── 表单网格 ─────────────────────────────────────────────────────────────
   两列，跟原型一致；≤700px 塌成一列。
   用 <p> 当字段容器（而不是 div）—— 无样式降级时它天然带段落间距，
   不会挤成一坨。 */
.ap-form{display:grid;grid-template-columns:1fr 1fr;gap:20px 18px;margin:0;}
.ap-full{grid-column:1/-1;}
.ap-field{display:flex;flex-direction:column;gap:7px;margin:0;}

/* ⚠️ 这三条不是多余的。`hidden` 属性靠 UA 样式的 display:none 生效，
   而**作者写的 display 一律赢过它** —— 上面 .ap-form 有 display:grid，
   于是 form.hidden = true **完全不起作用**，成功态出现时表单还挂在下面。
   实测踩到过。任何带 display 声明又要靠 hidden 收起的元素都得补这一条。 */
.ap-form[hidden], .ap-field[hidden], .ap-actions[hidden]{display:none;}
@media(max-width:700px){.ap-form{grid-template-columns:1fr;}}

.ap-label{font-size:10px;letter-spacing:.16em;text-transform:uppercase;
  color:var(--text-faint);}

/* 输入框沿用页面上 .chat-input 的做法：1px 实线 + 继承字体，不做圆角不做阴影。
   这套设计语言里「输入」和「容器」是同一种线，不该自成一格。 */
.ap-input{width:100%;box-sizing:border-box;
  font:inherit;font-size:14.5px;line-height:1.4;color:var(--text);
  background:var(--paper);border:1px solid var(--edge);border-radius:var(--radius);
  padding:11px 13px;outline:none;
  transition:border-color .16s ease;}
.ap-input::placeholder{color:var(--text-faint);}
.ap-input:hover{border-color:var(--rule);}
/* 焦点环用**加粗的边框**而不是外发光 —— 浅底上没有「亮」这个维度可用，
   焦点必须靠可测量的变化表达。inset 阴影补一道，键盘用户一眼能找到。 */
.ap-input:focus{border-color:var(--text);box-shadow:inset 0 0 0 1px var(--text);}
.ap-textarea{resize:vertical;min-height:132px;padding:12px 13px;}

/* 校验失败的字段。:invalid 不能直接用 —— 页面一加载空的必填框就是 invalid，
   还没输入就报错很粗鲁。所以由 apply.js 在提交后加 .ap-bad。 */
.ap-input.ap-bad{border-color:var(--ac-text);box-shadow:inset 0 0 0 1px var(--ac-text);}

.ap-error{grid-column:1/-1;margin:0;font-size:11px;letter-spacing:.08em;
  color:var(--ac-text);}

.ap-actions{display:flex;align-items:center;gap:16px;margin-top:6px;}
.ap-submit[disabled]{opacity:.5;cursor:default;}

.ap-back{margin:38px 0 0;font-size:13px;}
.ap-back a{color:var(--text-mute);text-decoration:none;
  border-bottom:1px solid var(--g4);}
.ap-back a:hover{color:var(--ac-text);border-bottom-color:var(--ac-base);}

.ap-done{padding:6px 0;}

/* ══ 弹窗 ═══════════════════════════════════════════════════════════════
   用原生 <dialog> 而不是自己搭一个 div：焦点陷阱、Esc 关闭、惰性化背景内容
   浏览器已经做好了，自己实现几乎必然漏掉其中一两条。
   ⚠️ ::backdrop 只有 showModal() 打开时才存在；apply.js 里用的就是它。 */
.ap-dialog{
  border:1px solid var(--rule);border-radius:var(--radius);
  background:var(--paper);color:var(--text);
  padding:0;width:min(680px, calc(100vw - 40px));max-height:calc(100vh - 64px);
  overflow:auto;
  /* ⚠️ **必须显式写 margin:auto。** 原生 <dialog> 是靠 UA 样式表里的 margin:auto
     居中的，而 landing.css 第 113 行有一条 `*{margin:0}` 全局重置，把它干掉了 ——
     弹窗会贴在视口左上角。实测过：不写这条，dialog 的矩形是 [0,0,680,756]。
     顺带一个不显然的后果：贴在左上角时「点遮罩关闭」也会失效，
     因为视口左上那一片其实落在弹窗自己身上。 */
  margin:auto;
}
.ap-dialog::backdrop{background:rgba(0,0,0,.42);}
/* 弹窗里内容自己留白；外壳不留白，滚动条才贴着边 */
.ap-dialog-in{padding:40px 40px 36px;}
@media(max-width:700px){.ap-dialog-in{padding:28px 22px 26px;}}

/* file:// 预览不能 fetch apply.html，外层 dialog 改用同页面 iframe。
   iframe 只替换“取内容”的方式，尺寸和关闭行为仍由同一个 dialog 外壳管理。 */
.ap-dialog-frame{height:min(760px, calc(100vh - 64px));overflow:hidden;}
.ap-dialog-frame-in{display:block;width:100%;height:100%;border:0;background:var(--paper);}
.ap-dialog-frame .ap-close{z-index:2;background:var(--paper);}
/* iframe 内仍是独立页，但嵌入时去掉返回入口并收紧外壳留白。 */
.ap-page.ap-embed{overflow:auto;}
.ap-embed .ap-shell{max-width:none;padding:40px 40px 36px;}
.ap-embed .ap-back{display:none;}
@media(max-width:700px){.ap-embed .ap-shell{padding:28px 22px 26px;}}

/* 关闭按钮。绝对定位在右上，不占版面 —— 弹窗里没有第二处可放它的地方。 */
.ap-close{position:absolute;top:12px;right:12px;
  width:34px;height:34px;display:flex;align-items:center;justify-content:center;
  background:none;border:1px solid transparent;border-radius:var(--radius);
  color:var(--text-mute);font-family:var(--font-mono);font-size:15px;line-height:1;
  cursor:pointer;}
.ap-close:hover{color:var(--text);border-color:var(--edge);}
/* ⚠️⚠️ **绝对不要给 .ap-dialog 写 position:relative。** 看着无害（想给上面这个
   绝对定位的关闭按钮一个包含块），实际会造成「点开弹窗页面平滑滚回顶部」：
   原生 <dialog> 在浏览器默认样式里是 position:fixed，改成 relative 就把它塞回了
   普通文档流（在 body 末尾）。于是 showModal() 把焦点送进第一个输入框时，
   浏览器为了「把焦点滚进视野」而滚动整个页面，又赶上页面有 scroll-behavior:smooth，
   表现就是一次优雅的回顶动画 —— 完全不像是定位属性造成的，极难往这边想。
   2026-08-05 实测：加这条 928 → 0，去掉 928 → 928。
   关闭按钮不需要它 —— position:fixed 本身就是绝对定位子元素的包含块。 */

/* 打开弹窗时锁住背景滚动。
   ⚠️ <dialog> 自己不锁 —— 滚轮在背后照样滚，弹窗看着像浮在流动的页面上。 */
html.ap-open, body.ap-open{overflow:hidden;}

/* 动效：只做一次很短的位移 + 淡入。
   ⚠️ prefers-reduced-motion 下整个动画撤掉（不是变快）—— 弹窗出现是内容变化，
      不需要靠动画交代，直接在那儿就行。 */
@media(prefers-reduced-motion:no-preference){
  .ap-dialog[open]{animation:ap-in .2s ease-out;}
  @keyframes ap-in{from{opacity:0;transform:translateY(6px);}
                     to{opacity:1;transform:none;}}
}
