/* Button system. Loaded last on every page, so it settles shape, size and colour for all buttons.
   Tokens live in tokens.css (--btn-*). Four kinds, three sizes:
     primary   black pill: the one main action           .btn  .btn-primary
     secondary grey pill: everything else                 .btn.sec  .btn-secondary
     ghost     text only, grey pill on hover               .btn-ghost
     danger    red, only while confirming a removal        .btn-danger / .sure
     sizes     .btn-sm 32px · default 40px · .btn-lg 52px · .btn-float adds the floating shadow
   The second half maps the buttons that already exist across the site onto these. */

.btn,.btn-primary,.btn-secondary,.btn-ghost,.btn-danger{
  all:unset;box-sizing:border-box;cursor:pointer;display:inline-flex;align-items:center;justify-content:center;gap:8px;white-space:nowrap;
  min-height:var(--btn-h);padding:0 var(--btn-px);border-radius:var(--btn-r);font:var(--btn-fw) var(--btn-fs)/1 var(--sans);
  background:var(--btn-primary);color:var(--btn-primary-fg);
  transition:background-color var(--dur-base) ease,color var(--dur-base) ease,scale var(--dur-quick) ease,opacity var(--dur-base) ease}
.btn-secondary,.btn.sec{background:var(--btn-secondary);color:var(--btn-secondary-fg)}
.btn-ghost{background:transparent;color:var(--btn-ghost-fg)}
.btn-danger{background:var(--btn-danger);color:var(--btn-danger-fg)}
.btn-sm{min-height:var(--btn-h-sm);padding:0 var(--btn-px-sm);font-size:var(--btn-fs-sm)}
.btn-lg{min-height:var(--btn-h-lg);padding:0 var(--btn-px-lg);font-size:var(--btn-fs-lg)}
.btn-float{box-shadow:var(--btn-float-shadow)}
.btn:active,.btn-primary:active,.btn-secondary:active,.btn-ghost:active,.btn-danger:active{scale:var(--btn-press)}
.btn:focus-visible,.btn-primary:focus-visible,.btn-secondary:focus-visible,.btn-ghost:focus-visible,.btn-danger:focus-visible{outline:none;box-shadow:var(--btn-focus)}
@media (hover:hover){
  .btn:hover,.btn-primary:hover{background:var(--btn-primary-hover)}
  .btn-secondary:hover,.btn.sec:hover{background:var(--btn-secondary-hover)}
  .btn-ghost:hover{background:var(--btn-ghost-hover);color:var(--ink)}
}

/* ---- existing buttons, mapped onto the system ---- */

/* primary, default size */
.pk .send,.inbox-pill-dark,.pill.dark{border-radius:var(--btn-r);background:var(--btn-primary);color:var(--btn-primary-fg);font-weight:var(--btn-fw)}
.pk .send{min-height:var(--btn-h);height:auto}
.signin .btn{min-height:44px}
.act-pill{border-radius:var(--btn-r);background:var(--btn-primary)}
@media (hover:hover){.pk .send:hover,.pill.dark:hover,.act-pill:hover{background:var(--btn-primary-hover)}}

/* primary, large and floating: the pick pill, the choose buttons, the hub's pick button */
.pk-pill{border-radius:var(--btn-r);background:var(--btn-primary);color:var(--btn-primary-fg);font-weight:var(--btn-fw)}
#next .choose button{min-height:var(--btn-h-lg);padding:0 var(--btn-px-lg);border-radius:var(--btn-r);font:var(--btn-fw) var(--btn-fs-lg)/1 var(--sans);background:var(--btn-primary);color:var(--btn-primary-fg);box-shadow:var(--btn-float-shadow)}
@media (hover:hover){#next .choose button:hover{background:var(--btn-primary-hover);color:var(--btn-primary-fg)}}
.btn.pk{min-height:var(--btn-h-lg);padding:0 var(--btn-px-lg) 0 12px;font-size:var(--btn-fs-lg);box-shadow:var(--btn-float-shadow)}

/* secondary, default size */
.pill:not(.dark){min-height:var(--btn-h);border-radius:var(--btn-r);background:var(--btn-secondary);color:var(--btn-secondary-fg);font-size:var(--btn-fs);font-weight:var(--btn-fw)}
@media (hover:hover){.pill:not(.dark):hover{background:var(--btn-secondary-hover)}}
.ft-btn{border-radius:var(--btn-r);font-weight:var(--btn-fw)}
.ab-acct a,.ab-acct button{border-radius:var(--btn-r)}
.cm-btn{border-radius:var(--btn-r)}

/* secondary, small: the comment and pick dialog actions */
.cm-row button,.cm-box .cm-row button,.pk .row button,.bd-x,.cm-bub .cb-a button,.cc-ea button{
  min-height:var(--btn-h-sm);padding:0 var(--btn-px-sm);display:inline-flex;align-items:center;justify-content:center;border-radius:var(--btn-r);font:var(--btn-fw) var(--btn-fs-sm)/1 var(--sans)}

/* ghost: text-like buttons */
.ab-backbtn{border-radius:var(--btn-r)}
.seg button{border-radius:var(--btn-r)}

/* danger: the "Remove?" confirm state */
.del.sure,.btn.sure,.link.sure{background:var(--btn-danger)!important;color:var(--btn-danger-fg)!important;border-radius:var(--btn-r);padding:0 var(--btn-px-sm);min-height:var(--btn-h-sm);display:inline-flex;align-items:center}

/* ---- Fields: one look for every text input, textarea and select ----
   .field        white with a hairline, the default
   .field-fill   grey fill and no line until focused (sign-in, dialogs)
   .field-lg     44px, for a form that is the whole point of the page
   wrong: aria-invalid="true" (see Messages below); off: disabled
   A page's own rules (input.field in hub.css) still win where they exist; this fills every gap. */
:where(input,textarea,select).field{box-sizing:border-box;width:100%;min-height:var(--field-h);padding:0 var(--field-px);
  border:1px solid var(--field-line);border-radius:var(--field-r);background:var(--field-bg);color:var(--ink);font:var(--field-fs)/1.4 var(--sans);
  outline:none;transition:background-color var(--dur-base) ease,border-color var(--dur-base) ease,box-shadow var(--dur-base) ease}
:where(textarea).field{padding:10px var(--field-px);min-height:96px;resize:vertical}
:where(select).field{appearance:none;-webkit-appearance:none;padding-right:36px;
  background:var(--field-bg) url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M4.5 6.5 8 10l3.5-3.5' fill='none' stroke='%236F6F6F' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") right 12px center/14px no-repeat}
:where(input,textarea).field::placeholder{color:var(--field-ph)}
:where(input,textarea,select).field:focus{border-color:var(--field-line-focus);box-shadow:var(--field-ring)}
:where(input,textarea,select).field-fill{background-color:var(--field-fill);border-color:transparent}
:where(input,textarea,select).field-fill:focus{background-color:var(--field-bg);border-color:var(--field-line)}
:where(input,textarea,select).field-lg{min-height:var(--field-h-lg)}
:where(input,textarea,select).field:disabled{opacity:.5}
.btn:disabled,.btn[aria-disabled=true],.btn-primary:disabled,.btn-secondary:disabled,.btn-ghost:disabled{opacity:.4;pointer-events:none}
.btn[aria-busy=true]{opacity:.7}

/* ---- Messages: one system for every error, confirmation and status line on the site ----
   .msg with data-tone:
     err    something went wrong: red icon, ink text. The field itself gets aria-invalid (red edge and ring), so the
            sentence doesn't need to shout; it says what happened and what to do next
     ok     something worked: green tick, ink text
     info   worth knowing, nothing to fix: grey icon, grey text
     wait   in progress: a small spinner, grey text ("Sending…")
   .msg-box  the same on a tinted fill, for a result that stands on its own rather than under a field
   .in       plays the entrance (rise out of a soft blur); add .nudge to the field to shake it once on an error
   Older names map on: .msg-err .msg-ok .cf-err .err .am-msg.err/.ok (and .fmsg / .note[data-tone] in hub.css) */
.msg,.msg-err,.msg-ok,.cf-err,.am-msg.err,.am-msg.ok,.err{--msg-c:var(--danger);--msg-ico:var(--ico-err);
  display:flex;align-items:flex-start;gap:8px;margin:0;font-size:var(--fs-body);line-height:1.45;color:var(--ink-2);text-wrap:pretty}
.msg[data-tone=ok],.msg-ok,.am-msg.ok{--msg-c:var(--ok);--msg-ico:var(--ico-ok)}
.msg[data-tone=info]{--msg-c:var(--grey-2);--msg-ico:var(--ico-info);color:var(--grey)}
.msg[data-tone=wait]{color:var(--grey)}
.msg::before,.msg-err::before,.msg-ok::before,.cf-err::before,.am-msg.err::before,.am-msg.ok::before,.err:not(:empty)::before{content:"";flex:none;
  width:14px;height:14px;margin-top:calc((1.45em - 14px) / 2);background:var(--msg-c);-webkit-mask:var(--msg-ico) center/14px no-repeat;mask:var(--msg-ico) center/14px no-repeat}
.msg[data-tone=wait]::before{box-sizing:border-box;width:13px;height:13px;margin-left:.5px;margin-right:.5px;background:none;-webkit-mask:none;mask:none;
  border:1.5px solid var(--line-2);border-top-color:var(--ink-2);border-radius:50%;animation:msgSpin .8s linear infinite}
@keyframes msgSpin{to{rotate:360deg}}
.msg-box{gap:10px;padding:11px 13px;border-radius:var(--r-sm);background:var(--fill);box-shadow:inset 0 0 0 1px var(--line)}
.msg-box[data-tone=err],.msg-box.msg-err{background:var(--danger-fill);box-shadow:inset 0 0 0 1px var(--danger-line)}
.msg-box[data-tone=ok],.msg-box.msg-ok{background:var(--ok-fill);box-shadow:inset 0 0 0 1px var(--ok-line)}
.msg:empty,.msg-err:empty,.msg-ok:empty,.cf-err:empty,.am-msg:empty,.err:empty{display:none}
.msg[hidden],.msg-err[hidden],.msg-ok[hidden]{display:none}
.field[aria-invalid=true],.cf-i[aria-invalid=true],.am-input[aria-invalid=true],.cc textarea[aria-invalid=true],.cc input[aria-invalid=true]{border-color:var(--danger)!important;box-shadow:0 0 0 3px var(--danger-ring)!important}
.msg.in,.msg-err.in,.msg-ok.in{animation:msgIn var(--dur-base) var(--ease-out) both}
@keyframes msgIn{from{opacity:0;transform:translateY(-4px);filter:blur(var(--rise-blur))}}
.nudge{animation:nudge 320ms var(--ease-out)}
@keyframes nudge{20%{transform:translateX(-4px)}45%{transform:translateX(3px)}70%{transform:translateX(-2px)}100%{transform:none}}
@media (prefers-reduced-motion:reduce){.msg.in,.msg-err.in,.msg-ok.in,.nudge{animation:none}.msg[data-tone=wait]::before{animation-duration:2.4s}}

/* ---- Dialogs and switches: one box for every pop-up (share, invite, settings) ----
   <dialog class="dlg"> with a .dlg-x close button in its top right; .switch is the on/off toggle inside one
   (role="switch" aria-checked, with an <i> for the knob). Page scripts add only their own rows. */
.dlg{margin:auto;border:0;padding:24px;width:min(440px,calc(100vw - 32px));border-radius:var(--r-lg);background:var(--paper);color:var(--ink);box-shadow:var(--sh-dialog)}
.dlg::backdrop{background:var(--scrim);backdrop-filter:var(--blur-soft);-webkit-backdrop-filter:var(--blur-soft)}
.dlg[open]{animation:dlgIn var(--dur-base) var(--ease-out) both}
@keyframes dlgIn{from{opacity:0;transform:translateY(8px) scale(.98)}}
.dlg-x{all:unset;cursor:pointer;position:absolute;top:18px;right:18px;width:32px;height:32px;border-radius:50%;display:grid;place-items:center;color:var(--grey);transition:background-color var(--dur-base) ease,color var(--dur-base) ease}
.dlg-x svg{width:14px;height:14px;fill:none;stroke:currentColor;stroke-width:1.6;stroke-linecap:round}
@media (hover:hover){.dlg-x:hover{background:var(--fill);color:var(--ink)}}
@media (prefers-reduced-motion:reduce){.dlg[open]{animation:none}}
.switch{all:unset;cursor:pointer;flex-shrink:0;position:relative;width:36px;height:22px;border-radius:var(--r-pill);background:var(--fill-3);transition:background-color var(--dur-base) ease}
.switch i{position:absolute;top:3px;left:3px;width:16px;height:16px;border-radius:50%;background:var(--paper);box-shadow:0 1px 2px rgba(0,0,0,.2);transition:transform var(--dur-base) var(--ease-out)}
.switch[aria-checked=true]{background:var(--ink)}
.switch[aria-checked=true] i{transform:translateX(14px)}
.switch:focus-visible{box-shadow:var(--btn-focus)}
