/* ==========================================================================
   BlissPOP Star Mascot — bliss-mascot.css
   Pairs with /js/bliss-mascot.js. All tunables are CSS variables on .bm-layer
   so a page can restyle without touching JS.
   ========================================================================== */

.bm-layer {
  --bm-size: 84px;
  --bm-gold: #ffcc33;
  --bm-pink: #ff4fb8;
  --bm-purple: #8a2be2;
  --bm-bubble-bg: #ffffff;
  --bm-bubble-fg: #3b1457;
  --bm-bubble-border: #f3c94b;
  --bm-chip-bg: #f6ecff;
  --bm-chip-fg: #5b1f8f;
  --bm-font: "Nunito Sans", "Nunito", system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
  --bm-z: 900;

  position: fixed;
  inset: 0;
  pointer-events: none;
  z-index: var(--bm-z);
  overflow: hidden;
  contain: layout style;
}

/* ---- The mascot -------------------------------------------------------- */
.bm {
  position: absolute;
  left: 0;
  top: 0;
  width: var(--bm-size);
  height: var(--bm-size);
  pointer-events: auto;
  touch-action: none;            /* we own the gesture while touching her */
  user-select: none;
  -webkit-user-select: none;
  -webkit-touch-callout: none;
  -webkit-tap-highlight-color: transparent;
  cursor: grab;
  will-change: transform;
  outline: none;
}
.bm:focus-visible .bm-body { filter: drop-shadow(0 0 0 #fff) drop-shadow(0 0 6px var(--bm-gold)); }
.bm.is-dragging { cursor: grabbing; }

.bm-body {                        /* flip + tilt live here */
  width: 100%;
  height: 100%;
  transform-origin: 50% 60%;
  transition: transform .18s ease-out;
}
.bm.is-flying .bm-body,
.bm.is-dragging .bm-body,
.bm.is-falling .bm-body { transition: none; }

.bm-bob { width: 100%; height: 100%; transform-origin: 50% 70%; }
.bm-img {
  width: 100%;
  height: 100%;
  display: block;
  pointer-events: none;
  filter: drop-shadow(0 4px 6px rgba(60, 10, 90, .28));
  -webkit-user-drag: none;
}
.bm-fallback {
  width: 100%; height: 100%;
  display: grid; place-items: center;
  font-size: calc(var(--bm-size) * .7);
  line-height: 1;
}

/* idle float */
.bm.is-idle .bm-bob    { animation: bm-bob 2.6s ease-in-out infinite; }
.bm.is-sleeping .bm-bob { animation: bm-breathe 3.6s ease-in-out infinite; }
.bm.is-sleeping .bm-img { filter: drop-shadow(0 3px 4px rgba(60,10,90,.22)) saturate(.85) brightness(.92); }

@keyframes bm-bob     { 0%,100% { transform: translateY(0) }   50% { transform: translateY(-5px) } }
@keyframes bm-breathe { 0%,100% { transform: scale(1, 1) }     50% { transform: scale(1.03, .97) } }

/* one-shot moves (class added, then removed by JS on animationend) */
/* .bm prefix keeps these at the same specificity as the idle float, and later in the file, so they win */
.bm .bm-bob.do-land   { animation: bm-land .42s cubic-bezier(.3,1.6,.5,1); }
.bm .bm-bob.do-hop    { animation: bm-hop .62s cubic-bezier(.3,.9,.4,1); }
.bm .bm-bob.do-twirl  { animation: bm-twirl .8s cubic-bezier(.45,.05,.3,1); }
.bm .bm-bob.do-shake  { animation: bm-shake .45s ease-in-out; }
.bm .bm-bob.do-pop    { animation: bm-pop .5s cubic-bezier(.3,1.7,.5,1); }

/* tucked away while the phone keyboard is open */
.bm { transition: opacity .2s ease; }
.bm.is-tucked { opacity: 0; pointer-events: none; }

@keyframes bm-land  { 0% { transform: scale(1.18,.78) } 55% { transform: scale(.94,1.08) } 100% { transform: scale(1,1) } }
@keyframes bm-hop   { 0% { transform: translateY(0) scale(1.08,.9) } 40% { transform: translateY(-34%) scale(.94,1.06) }
                      75% { transform: translateY(0) scale(1.1,.88) } 100% { transform: translateY(0) scale(1) } }
@keyframes bm-twirl { 0% { transform: rotate(0) scale(1) } 50% { transform: rotate(200deg) scale(1.12) } 100% { transform: rotate(360deg) scale(1) } }
@keyframes bm-shake { 0%,100% { transform: rotate(0) } 25% { transform: rotate(-9deg) } 75% { transform: rotate(9deg) } }
@keyframes bm-pop   { 0% { transform: scale(.4) } 100% { transform: scale(1) } }

/* Zzz while sleeping */
.bm-zzz {
  position: absolute;
  right: -2px;
  top: -6px;
  font: 800 13px/1 var(--bm-font);
  color: var(--bm-purple);
  text-shadow: 0 0 3px #fff, 0 0 2px #fff;
  pointer-events: none;
  display: none;
}
.bm.is-sleeping .bm-zzz { display: block; }
.bm-zzz span { position: absolute; opacity: 0; animation: bm-z 2.4s ease-out infinite; }
.bm-zzz span:nth-child(2) { animation-delay: .8s; font-size: 11px; }
.bm-zzz span:nth-child(3) { animation-delay: 1.6s; font-size: 9px; }
@keyframes bm-z { 0% { transform: translate(0,0); opacity: 0 } 20% { opacity: 1 } 100% { transform: translate(10px,-22px); opacity: 0 } }

/* ---- Peek (hidden) state: a little star tucked at the screen edge -------- */
.bm-peek {
  position: absolute;
  right: 0;
  bottom: calc(96px + env(safe-area-inset-bottom, 0px));
  width: 44px;
  height: 44px;
  transform: translateX(46%) rotate(-18deg);
  pointer-events: auto;
  cursor: pointer;
  border: 0;
  padding: 0;
  background: none;
  transition: transform .25s ease;
  -webkit-tap-highlight-color: transparent;
}
.bm-peek:hover, .bm-peek:focus-visible { transform: translateX(28%) rotate(-8deg); outline: none; }
.bm-peek img { width: 100%; height: 100%; display: block; filter: drop-shadow(0 2px 4px rgba(60,10,90,.3)); }

/* ---- Speech bubble ------------------------------------------------------ */
.bm-bubble {
  position: absolute;
  left: 0;
  top: 0;
  max-width: min(240px, calc(100vw - 32px));
  padding: 10px 13px;
  border-radius: 16px;
  background: var(--bm-bubble-bg);
  color: var(--bm-bubble-fg);
  border: 2px solid var(--bm-bubble-border);
  box-shadow: 0 6px 18px rgba(59, 20, 87, .22);
  font: 700 14px/1.35 var(--bm-font);
  pointer-events: auto;
  opacity: 0;
  transform: translateY(6px) scale(.96);
  transition: opacity .18s ease, transform .22s cubic-bezier(.3,1.5,.5,1);
  visibility: hidden;
}
.bm-bubble.is-on { opacity: 1; transform: none; visibility: visible; }
.bm-bubble::after {               /* the little tail, positioned by --tail-x */
  content: "";
  position: absolute;
  left: var(--tail-x, 50%);
  width: 12px;
  height: 12px;
  background: var(--bm-bubble-bg);
  border: 2px solid var(--bm-bubble-border);
  border-top: 0;
  border-left: 0;
  transform: translateX(-50%) rotate(45deg);
  bottom: -8px;
}
.bm-bubble.is-below::after { bottom: auto; top: -8px; transform: translateX(-50%) rotate(225deg); }
.bm-bubble-actions { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 8px; }
.bm-chip {
  font: 700 12.5px/1 var(--bm-font);
  padding: 8px 11px;
  min-height: 32px;
  border-radius: 999px;
  border: 0;
  background: var(--bm-chip-bg);
  color: var(--bm-chip-fg);
  cursor: pointer;
}
.bm-chip:focus-visible { outline: 2px solid var(--bm-purple); outline-offset: 2px; }

/* ---- Particles (sparkle trail, bursts, hearts) --------------------------- */
.bm-fx {
  position: absolute;
  left: 0;
  top: 0;
  pointer-events: none;
  font-size: 14px;
  line-height: 1;
  will-change: transform, opacity;
  animation: bm-fx var(--d, .9s) cubic-bezier(.2,.7,.3,1) forwards;
}
@keyframes bm-fx {
  0%   { transform: translate(var(--x0), var(--y0)) scale(var(--s0, .4)) rotate(0); opacity: 1; }
  100% { transform: translate(var(--x1), var(--y1)) scale(var(--s1, 1)) rotate(var(--r, 90deg)); opacity: 0; }
}
.bm-fx.is-star::before  { content: "\2726"; color: var(--c, var(--bm-gold)); text-shadow: 0 0 4px rgba(255,255,255,.8); }
.bm-fx.is-heart::before { content: "\2665"; color: var(--c, var(--bm-pink)); }
.bm-fx.is-dot { width: 6px; height: 6px; border-radius: 50%; background: var(--c, var(--bm-gold)); box-shadow: 0 0 6px var(--c, var(--bm-gold)); }

/* ---- Reduced motion: she stays put, no floating, no trails --------------- */
@media (prefers-reduced-motion: reduce) {
  .bm.is-idle .bm-bob,
  .bm.is-sleeping .bm-bob,
  .bm-zzz span { animation: none; }
  .bm .bm-bob[class*="do-"] { animation-duration: .01s; }
  .bm-fx { display: none; }
}

/* Print: never print the mascot */
@media print { .bm-layer { display: none !important; } }
