/* SnapLab · 全局动效层
   只补状态反馈，不改信息层级；所有持续动画都能被 prefers-reduced-motion 关掉。 */

:root {
  --m-fast: 150ms;
  --m-med: 260ms;
  --m-slow: 420ms;
  --m-ease: cubic-bezier(.22, .61, .36, 1);
  --m-pop: cubic-bezier(.2, .9, .28, 1.08);
  --m-sh: 0 14px 34px rgba(18, 34, 49, .10);
}

@keyframes m-view {
  from { opacity: 0; transform: translate3d(0, 10px, 0); }
  to { opacity: 1; transform: translate3d(0, 0, 0); }
}
@keyframes m-card {
  from { opacity: 0; transform: translate3d(0, 12px, 0) scale(.988); }
  to { opacity: 1; transform: translate3d(0, 0, 0) scale(1); }
}
@keyframes m-pop {
  from { opacity: 0; transform: translate3d(0, 6px, 0) scale(.96); }
  to { opacity: 1; transform: translate3d(0, 0, 0) scale(1); }
}
@keyframes m-fade {
  from { opacity: 0; }
  to { opacity: 1; }
}
@keyframes m-msg {
  from { opacity: 0; transform: translate3d(0, 8px, 0) scale(.985); }
  to { opacity: 1; transform: translate3d(0, 0, 0) scale(1); }
}
@keyframes m-cue {
  0% { opacity: 0; transform: scale(.92); }
  12% { opacity: .55; }
  55%, 100% { opacity: 0; transform: scale(1.18); }
}
@keyframes m-scan {
  from { transform: translate3d(-110%, 0, 0); }
  to { transform: translate3d(220%, 0, 0); }
}
@keyframes m-img {
  from { opacity: 0; transform: scale(.965); }
  to { opacity: 1; transform: scale(1); }
}
@keyframes m-toast {
  from { opacity: 0; transform: translate3d(-50%, 10px, 0) scale(.96); }
  to { opacity: 1; transform: translate3d(-50%, 0, 0) scale(1); }
}

html { scroll-behavior: smooth; }
body {
  transition: background-color var(--m-med) ease, color var(--m-med) ease;
}
main { scroll-behavior: smooth; }
::selection { background: var(--cyan); color: #172b29; }

/* 路由切换：每次换页有一个统一、很轻的落位 */
.view { animation: m-view var(--m-med) var(--m-ease) both; }

/* 通用控件：按压有反馈，桌面 hover 才抬起，移动端不粘滞 */
.btn, .ib, .fchip, .bar a, .bar button,
.chat-chip, .chat-open, .chat-opt, .chat-card, .chat-sess-open,
.home-q, .home-sugg-tab, .opt, .lab-shortcuts a, .fmt a {
  transition: transform var(--m-fast) var(--m-ease), border-color var(--m-fast) ease,
              background-color var(--m-fast) ease, color var(--m-fast) ease,
              box-shadow var(--m-med) var(--m-ease), opacity var(--m-fast) ease;
}
.btn:active, .ib:active, .fchip:active, .chat-chip:active, .chat-open:active,
.chat-opt:active, .chat-card:active, .chat-sess-open:active,
.home-q:active, .home-sugg-tab:active, .fmt a:active {
  transform: scale(.97);
}
@media (hover: hover) {
  .btn:hover, .ib:hover, .chat-open:hover, .chat-sess-open:hover {
    transform: translate3d(0, -1px, 0);
  }
  .btn.primary:hover, .chat-bar button:hover, .askhere:hover {
    box-shadow: 0 10px 24px rgba(18, 34, 49, .14);
  }
}

/* 表单控件：聚焦反馈更明确，错误/可用状态颜色平滑过渡 */
input[type=text], input[type=search], input[type=password], input[type=number],
input[type=date], input[type=datetime-local], select, textarea {
  transition: border-color var(--m-fast) ease, box-shadow var(--m-med) var(--m-ease),
              background-color var(--m-fast) ease, color var(--m-fast) ease;
}
.f input:focus, .f select:focus, .f textarea:focus,
#chatIn:focus, #chatFind:focus {
  box-shadow: 0 0 0 4px var(--blue-s);
}
.dlg-back, .notice-x, .chat-attach-x {
  transition: transform var(--m-fast) var(--m-ease), color var(--m-fast) ease,
              background-color var(--m-fast) ease, border-color var(--m-fast) ease;
}
.dlg-back:active, .notice-x:active, .chat-attach-x:active { transform: scale(.9); }

/* 卡片与列表：已有 rise 的基础上统一克制地上浮，不滚屏劫持 */
.card, .it, .gi, .pcard, .pw-img, .notice, .lab-card, .lab-shortcuts a,
.chat-it, .chat-opt, .chat-card, .home-agent, .home-agent-mark,
.lab-card-icon, .jd {
  transition: transform var(--m-fast) var(--m-ease), border-color var(--m-fast) ease,
              box-shadow var(--m-med) var(--m-ease), background-color var(--m-fast) ease,
              color var(--m-fast) ease, opacity var(--m-fast) ease;
}
.pwall > .pw, .jrows > .jrow, .lab-grid > .lab-card,
.lab-shortcuts > a, .home-sugg-list > .home-q,
.chat-empty .home-agent, .chat-empty .home-sugg-tabs,
.view > .card, .chat-list > .chat-sess {
  animation: m-card var(--m-med) var(--m-ease) both;
}
.rows > :nth-child(6), .gal > :nth-child(6), .pwall > :nth-child(6) { animation-delay: 140ms; }
.rows > :nth-child(7), .gal > :nth-child(7), .pwall > :nth-child(7) { animation-delay: 165ms; }
.rows > :nth-child(8), .gal > :nth-child(8), .pwall > :nth-child(8) { animation-delay: 190ms; }
.rows > :nth-child(n+9), .gal > :nth-child(n+9), .pwall > :nth-child(n+9) { animation-delay: 210ms; }
.lab-grid > .lab-card:nth-child(2), .lab-shortcuts > a:nth-child(2),
.home-sugg-list > .home-q:nth-child(2), .view > .card:nth-child(2) { animation-delay: 45ms; }
.lab-grid > .lab-card:nth-child(3), .lab-shortcuts > a:nth-child(3),
.home-sugg-list > .home-q:nth-child(3), .view > .card:nth-child(3) { animation-delay: 90ms; }
.lab-grid > .lab-card:nth-child(n+4), .lab-shortcuts > a:nth-child(n+4),
.home-sugg-list > .home-q:nth-child(n+4), .view > .card:nth-child(n+4) { animation-delay: 130ms; }

@media (hover: hover) {
  .it:hover, .pcard:hover, .lab-shortcuts a:hover, .notice:hover,
  .chat-card:hover, .chat-opt:hover {
    transform: translate3d(0, -2px, 0);
    box-shadow: var(--m-sh);
  }
  .gi:hover { transform: translate3d(0, -2px, 0); box-shadow: var(--m-sh); }
  .pw-img:hover { transform: translate3d(0, -2px, 0); box-shadow: var(--m-sh); }
  .gi:hover img, .pw-img:hover img, .chat-card:hover img, .chat-opt:hover img {
    transform: scale(1.035);
  }
  .lab-card:hover .lab-card-icon, .home-agent:hover .home-agent-mark {
    transform: translate3d(0, -2px, 0) rotate(-2deg);
  }
  .lab-card:hover::after { transform: scale(1.08); opacity: .9; }
}
.lab-card::after { transition: transform var(--m-slow) var(--m-ease), opacity var(--m-med) ease; }
.gi img, .pw-img img, .chat-card img, .chat-opt img, .chat-img img,
.chat-you-pics img, .chat-you-imgs img, .th img, .fig img, .srci {
  transition: transform var(--m-med) var(--m-ease), opacity var(--m-med) ease;
}
.th img, .gi img, .pw-img img, .chat-card img, .chat-you-pics img,
.chat-you-imgs img, .fig img, .srci { animation: m-img var(--m-med) ease both; }

/* 主导航：当前页给一个小而明确的位置反馈 */
.bar a { position: relative; }
@media (min-width: 761px) {
  .bar a::after {
    content: ""; position: absolute; left: 18%; right: 18%; bottom: 5px;
    height: 2px; border-radius: 999px; background: currentColor;
    transform: scaleX(0); opacity: 0;
    transition: transform var(--m-med) var(--m-ease), opacity var(--m-fast) ease;
  }
  .bar a.on::after { transform: scaleX(1); opacity: .85; }
}
.bar a .icon, .bar a img, .bar button .icon {
  transition: transform var(--m-med) var(--m-pop), color var(--m-fast) ease;
}
.bar a.on .icon, .bar a.on img { transform: translate3d(0, -1px, 0) scale(1.08); }

/* 页面右上/右下的聊天入口：常驻但只给一次很轻的提示脉冲 */
.askhere {
  overflow: visible;
  transition: transform var(--m-fast) var(--m-pop), box-shadow var(--m-med) var(--m-ease),
              background-color var(--m-fast) ease, border-color var(--m-fast) ease;
}
.askhere::after {
  content: ""; position: absolute; inset: -4px; border-radius: inherit;
  border: 1px solid var(--cyan); opacity: 0; pointer-events: none;
  animation: m-cue 3.4s ease-out 1;
}
.askhere:active { transform: scale(.95); }

/* 对话：用户消息靠右弹入，结果卡从左上方落下，状态点不夸张 */
.chat-you:last-child { transform-origin: right bottom; animation: m-msg .22s var(--m-ease) both; }
.chat-it:last-child { transform-origin: left top; animation: m-msg var(--m-med) var(--m-ease) both; }
.chat-it:last-child .chat-step, .chat-it:last-child .chat-done,
.chat-it:last-child .chat-watch, .chat-it:last-child .chat-next {
  animation: m-fade .22s ease both;
}
.chat-it:last-child .chat-confirm, .chat-it:last-child .chat-done .icon,
.chat-it:last-child .chat-opt.danger {
  animation: m-pop .22s var(--m-pop) both;
}
.chat-bar, .chat-attach, .chat-side, .chat-sess, .chat-opt, .chat-card {
  transition: border-color var(--m-fast) ease, box-shadow var(--m-med) var(--m-ease),
              background-color var(--m-fast) ease, transform var(--m-fast) var(--m-ease);
}
.chat-bar button { transition: transform var(--m-fast) var(--m-pop), filter var(--m-fast) ease,
                              box-shadow var(--m-med) var(--m-ease), background-color var(--m-fast) ease; }
.chat-bar button:active { transform: scale(.92); }
.chat-img-plus { transition: transform var(--m-med) var(--m-pop); }
@media (hover: hover) { .chat-imgbtn:hover .chat-img-plus { transform: scale(1.12); } }

/* 进度、队列、上传：让真实进度更容易被看见 */
.qi, .notice-row, .fr, .jrow { animation: m-fade .22s ease both; }
.qi { transition: background-color var(--m-fast) ease, transform var(--m-fast) var(--m-ease); }
.qi.ok { animation: m-pop .24s var(--m-pop) both; }
.qi.bad { animation: m-pop .24s var(--m-pop) both; }
.pbar { height: 4px; border-radius: 999px; overflow: hidden; background: var(--line); }
.pbar-fill {
  display: block; height: 100%; width: 0; border-radius: inherit;
  background: var(--blue); transition: width .22s var(--m-ease);
}
.pbar.indet .pbar-fill { width: 34%; animation: m-scan 1.2s ease-in-out infinite alternate; }
.qbar i, .cw-bar i, .pbar-fill { transition-timing-function: var(--m-ease); }
.drop2 { transition: border-color var(--m-fast) ease, background-color var(--m-fast) ease,
                    transform var(--m-fast) var(--m-ease); }
.drop2.over { transform: scale(1.01); }

/* 弹窗、底部面板、灯箱：进入有方向，退出仍由原状态控制 */
.mo[open] { animation: m-pop .22s var(--m-pop) both; }
.mo::backdrop, .lb::backdrop { animation: m-fade .18s ease both; }
.sheet.on .sheet-card { animation: none; }
.opt .oi, .sheet-card .icon { transition: transform var(--m-med) var(--m-pop); }
@media (hover: hover) {
  .opt:hover .oi, .sheet-card button:hover > .icon { transform: scale(1.05); }
}
.lb img { animation: m-img .24s var(--m-pop) both; }

/* 提示条：出现像一张小卡片，不靠闪烁吓人 */
.toast { transform-origin: center bottom; }
.toast.on { animation: m-toast .24s var(--m-pop) both; }
.toast.bad { animation-name: m-toast; }

/* 日历：选中日直接落位，有记录的日期不需要夸张提示 */
.jd { transform-origin: center; }
.jd.on { animation: m-pop .18s var(--m-pop) both; }

/* 低动态：保留状态变化本身，去掉位移、脉冲和缓动 */
@media (prefers-reduced-motion: reduce) {
  html, main, .chat-canvas { scroll-behavior: auto; }
  *, *::before, *::after {
    animation-duration: .01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: .01ms !important;
  }
  .askhere::after, .ring, .dots i, .cw-bar.indet i, .pbar.indet .pbar-fill { animation: none !important; }
  .pbar.indet .pbar-fill { width: 100%; opacity: .35; }
}

/* 读屏字号下限：说明文字保持次级，但不做 10–12px 的“小字”；
   笼卡打印页有自己的毫米制排版，不受这条影响。 */
body:not(.print-cards) small,
body:not(.print-cards) .sm,
body:not(.print-cards) .personal-eyebrow,
body:not(.print-cards) .personal-kicker,
body:not(.print-cards) .personal-private,
body:not(.print-cards) .personal-stats span,
body:not(.print-cards) .personal-feature p,
body:not(.print-cards) .personal-arrow,
body:not(.print-cards) .personal-actions small,
body:not(.print-cards) .personal-status,
body:not(.print-cards) .personal-status b,
body:not(.print-cards) .personal-status > a,
body:not(.print-cards) .tag,
body:not(.print-cards) .kb,
body:not(.print-cards) .lbwm,
body:not(.print-cards) .pw figcaption,
body:not(.print-cards) .pw-tag,
body:not(.print-cards) .notice-tag,
body:not(.print-cards) .movement-kind,
body:not(.print-cards) .tile-flag,
body:not(.print-cards) .tile-mark,
body:not(.print-cards) .jd i,
body:not(.print-cards) .strain-other::after,
body:not(.print-cards) .strain-label,
body:not(.print-cards) .tile-sub,
body:not(.print-cards) .tile-location,
body:not(.print-cards) .tile-weigh,
body:not(.print-cards) .tk-hits-more,
body:not(.print-cards) .tk-more-note,
body:not(.print-cards) .facts dt,
body:not(.print-cards) .trace-kicker,
body:not(.print-cards) .trace-intro,
body:not(.print-cards) .trace-main span,
body:not(.print-cards) .trace-main a,
body:not(.print-cards) .tk-when,
body:not(.print-cards) .chart-key,
body:not(.print-cards) .chart-colors-for,
body:not(.print-cards) .chart-color.reset,
body:not(.print-cards) .intervention-source span,
body:not(.print-cards) .intervention-step-top span,
body:not(.print-cards) .movement-hero p,
body:not(.print-cards) .movement-stats span,
body:not(.print-cards) .movement-filters button,
body:not(.print-cards) .movement-body time,
body:not(.print-cards) .movement-body b,
body:not(.print-cards) .cg-reminder,
body:not(.print-cards) .cg-reminder .btn,
body:not(.print-cards) .cg-todo small,
body:not(.print-cards) .jm-all,
body:not(.print-cards) .jweek span,
body:not(.print-cards) .jtag,
body:not(.print-cards) .review-grid th select,
body:not(.print-cards) .measured-col > b,
body:not(.print-cards) .measured-bar span,
body:not(.print-cards) .pbar-pct,
body:not(.print-cards) .qbytes,
body:not(.print-cards) .notice p,
body:not(.print-cards) .notice-when,
body:not(.print-cards) .totable th select,
body:not(.print-cards) .wdelta,
body:not(.print-cards) .ask-table thead th,
body:not(.print-cards) .ask-sql,
body:not(.print-cards) .chat-meta,
body:not(.print-cards) .chat-confirm-hint,
body:not(.print-cards) .cw-note,
body:not(.print-cards) .cw-pct,
body:not(.print-cards) .cw-open,
body:not(.print-cards) .chat-table thead th,
body:not(.print-cards) .chat-sql summary,
body:not(.print-cards) .chat-sql code,
body:not(.print-cards) .chat-card b,
body:not(.print-cards) .chat-next-label,
body:not(.print-cards) .chat-you-imgs,
body:not(.print-cards) .source-json,
body:not(.print-cards) .history-row small,
body:not(.print-cards) .foot,
body:not(.print-cards) .sig,
body:not(.print-cards) .mo.login .sig,
body:not(.print-cards) .kv .k,
body:not(.print-cards) .kv .v small,
body:not(.print-cards) .pill,
body:not(.print-cards) .fig figcaption,
body:not(.print-cards) .pcat,
body:not(.print-cards) .sheet-tip,
body:not(.print-cards) .kindbar .kbx i,
body:not(.print-cards) .plug i,
body:not(.print-cards) .pd-top i,
body:not(.print-cards) .pd-shot figcaption,
body:not(.print-cards) .pq-help,
body:not(.print-cards) .pq-tx i,
body:not(.print-cards) .pbody pre,
body:not(.print-cards) .personal-top .btn,
body:not(.print-cards) .chat-main.is-empty .chat-warn {
  font-size: 13.5px;
}

body:not(.print-cards) .pip-more,
body:not(.print-cards) .batch-n {
  font-size: 12.5px;
}

@media (max-width: 760px) {
  body:not(.print-cards) .bar a { font-size: 13px; }
}

/* 9.4：往下滚时「问一句」让开，往上滚 / 到底再出来 */
.askhere { transition: transform .28s cubic-bezier(.2, .8, .2, 1), opacity .22s ease; }
.askhere.ask-away { transform: translateY(24px) scale(.85); opacity: 0; pointer-events: none; }
