friend-assistant 0.1.39 → 0.1.40

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/BUILD.json CHANGED
@@ -1,5 +1,5 @@
1
1
  {
2
2
  "name": "friend-assistant",
3
- "version": "0.1.39",
4
- "builtAt": "2026-10-13T01:19:00.862Z"
3
+ "version": "0.1.40",
4
+ "builtAt": "2026-10-13T02:23:53.362Z"
5
5
  }
package/dist/friend.mjs CHANGED
@@ -6237,15 +6237,16 @@ function youtubeId(raw) {
6237
6237
  }
6238
6238
  var clean = (v, max) => typeof v === "string" ? v.replace(/[\u0000-\u001f\u007f]/g, " ").replace(/\s+/g, " ").trim().slice(0, max) : "";
6239
6239
  async function titleOfYoutube(id2, d = {}) {
6240
- const fallback = { title: "YouTube video", uploader: "" };
6240
+ const fallback = { title: "YouTube video", uploader: "", embeddable: true };
6241
6241
  const ctl = new AbortController();
6242
6242
  const timer = setTimeout(() => ctl.abort(), d.timeoutMs ?? 5e3);
6243
6243
  try {
6244
6244
  const url = `https://www.youtube.com/oembed?url=${encodeURIComponent(`https://www.youtube.com/watch?v=${id2}`)}&format=json`;
6245
6245
  const res = await (d.fetch ?? fetch)(url, { signal: ctl.signal });
6246
+ if (res.status === 401 || res.status === 403) return { ...fallback, embeddable: false };
6246
6247
  if (!res.ok) return fallback;
6247
6248
  const j = await res.json();
6248
- return { title: clean(j.title, 200) || fallback.title, uploader: clean(j.author_name, 100) };
6249
+ return { title: clean(j.title, 200) || fallback.title, uploader: clean(j.author_name, 100), embeddable: true };
6249
6250
  } catch {
6250
6251
  return fallback;
6251
6252
  } finally {
@@ -6386,7 +6387,9 @@ var VideoHub = class {
6386
6387
  const v = await vetVideoUrl(args.url, { allowedSites: cfg.allowedSites, ...this.d.resolve ? { resolve: this.d.resolve } : {} });
6387
6388
  if (!v.ok) return { ok: false, text: v.error };
6388
6389
  id2 = linkId;
6389
- ({ title: title2, uploader } = await titleOfYoutube(id2, { fetch: this.d.fetch }));
6390
+ const t = await titleOfYoutube(id2, { fetch: this.d.fetch });
6391
+ if (!t.embeddable) return null;
6392
+ ({ title: title2, uploader } = t);
6390
6393
  } else {
6391
6394
  const sites = cfg.allowedSites;
6392
6395
  if (sites.length && !sites.some((s) => s === "youtube.com" || s.endsWith(".youtube.com"))) return { ok: false, text: `A search uses YouTube, which is not on your allowed list (${sites.join(", ")}).` };
@@ -6408,7 +6411,10 @@ var VideoHub = class {
6408
6411
  const output = args.output ?? cfg.output;
6409
6412
  if (output === "screen" && (args.mode ?? cfg.youtube) === "embed") {
6410
6413
  const ytId = args.url ? youtubeId(args.url) : null;
6411
- if (ytId || !args.url && args.query && args.query.trim()) return this.playEmbedded(args, ytId, cfg);
6414
+ if (ytId || !args.url && args.query && args.query.trim()) {
6415
+ const emb = await this.playEmbedded(args, ytId, cfg);
6416
+ if (emb) return emb;
6417
+ }
6412
6418
  }
6413
6419
  let status2 = await this.ensureStatus();
6414
6420
  const got = await this.ensureTools(this.missing(status2, this.wanted(output, status2)), cfg);
@@ -17798,7 +17804,7 @@ async function daemonCommand(args, io2, deps = realDeps) {
17798
17804
  import crossSpawn5 from "cross-spawn";
17799
17805
  var PACKAGE = "friend-assistant";
17800
17806
  var real = {
17801
- current: () => true ? "0.1.39" : "development",
17807
+ current: () => true ? "0.1.40" : "development",
17802
17808
  latest: () => new Promise((resolve13) => {
17803
17809
  const child = crossSpawn5("npm", ["view", PACKAGE, "version", "--prefer-online"], { stdio: ["ignore", "pipe", "ignore"] });
17804
17810
  let out = "";
@@ -18086,7 +18092,7 @@ async function run(argv, io2) {
18086
18092
  case "version":
18087
18093
  case "--version":
18088
18094
  case "-v":
18089
- io2.out(true ? "0.1.39" : "development");
18095
+ io2.out(true ? "0.1.40" : "development");
18090
18096
  return 0;
18091
18097
  case "lan":
18092
18098
  return await lanCommand(rest, io2);
@@ -1 +1 @@
1
- :root{--accent:#3fd8ff;--warn:#ffb454;--bad:#ff6b7a;--ok:#5ef0b0;--ink:#d4ecf7;--muted:#7fa3b6;--glass:#06141c9e;--edge:color-mix(in srgb, var(--accent) 48%, transparent);--ui:"Segoe UI", system-ui, -apple-system, "Helvetica Neue", Arial, sans-serif;--mono:"Cascadia Mono", "SF Mono", Consolas, ui-monospace, monospace;--lightningcss-light: ;--lightningcss-dark:initial;color-scheme:dark}*{box-sizing:border-box}html,body,#root{height:100%;margin:0}body{color:var(--ink);font:16px/1.5 var(--ui);-webkit-tap-highlight-color:transparent;background:#000;overflow:hidden}button,input{font:inherit;color:inherit}button{cursor:pointer}:focus-visible{outline:2px solid var(--accent);outline-offset:2px}.stage{touch-action:manipulation;background:#000;position:fixed;inset:0;overflow:hidden}.ambient{pointer-events:none;background:radial-gradient(ellipse at 50% 55%, color-mix(in srgb, var(--accent) 10%, transparent), transparent 62%), linear-gradient(#3fd8ff0b 1px, transparent 1px) 0 0 / 64px 64px, linear-gradient(90deg, #3fd8ff0b 1px, transparent 1px) 0 0 / 64px 64px;position:absolute;inset:0;-webkit-mask-image:radial-gradient(#000 30%,#0000 78%);mask-image:radial-gradient(#000 30%,#0000 78%)}.presence{z-index:1;transition:inset .7s cubic-bezier(.2,.7,.2,1),width .7s,height .7s,opacity .5s;position:absolute}.presence-full{inset:0}.presence-corner{left:max(10px, env(safe-area-inset-left));bottom:max(52px, calc(env(safe-area-inset-bottom) + 42px));width:clamp(96px,16vw,190px);height:clamp(96px,16vw,190px)}.objects{pointer-events:none;position:absolute;inset:0}.objects-stack{pointer-events:auto;padding:max(56px, env(safe-area-inset-top)) 14px 140px;flex-direction:column;gap:12px;display:flex;overflow-y:auto}.auto-grid{pointer-events:none;padding:max(24px, env(safe-area-inset-top)) 24px 24px clamp(120px, 20vw, 230px);grid-template-columns:repeat(auto-fit,minmax(min(280px,100%),1fr));align-content:safe center;align-items:start;gap:12px;display:grid;position:absolute;inset:0;overflow-y:auto}.auto-grid>.obj{pointer-events:auto}.objects-stack>.auto-grid{flex-direction:column;padding:0;display:flex;position:static;overflow:visible}.obj.leaving{pointer-events:none;animation:.35s forwards leave}@keyframes leave{to{opacity:0;transform:scale(.96)translateY(-6px)}}@media (prefers-reduced-motion:reduce){.obj.leaving{animation:none}}.glass{background:var(--glass);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);border:1px solid var(--edge);box-shadow:0 0 22px color-mix(in srgb, var(--accent) 16%, transparent), inset 0 0 28px #3fd8ff0d;clip-path:polygon(0 0,calc(100% - 14px) 0,100% 14px,100% 100%,14px 100%,0 calc(100% - 14px))}.obj{pointer-events:auto;min-width:0;padding:16px 18px;animation:.45s both appear;overflow:auto}.obj.alert{border-color:var(--warn)}.overlay-layer{z-index:40;pointer-events:none;place-items:center;padding:16px;display:grid;position:fixed;inset:0}.overlay-backdrop{-webkit-backdrop-filter:blur(3px);backdrop-filter:blur(3px);pointer-events:auto;background:#02080ca8;animation:.3s both appear;position:absolute;inset:0}.obj.overlay{z-index:1;width:min(760px,94vw);max-height:80vh;box-shadow:0 0 40px color-mix(in srgb, var(--accent) 30%, transparent);position:relative}@keyframes appear{0%{opacity:0;transform:translateY(8px)scale(.985)}}.obj-close{width:44px;height:44px;color:var(--muted);background:0 0;border:0;font-size:1.5rem;line-height:1;position:absolute;top:2px;right:6px}.obj-close:hover{color:var(--accent)}.obj-title{letter-spacing:.16em;text-transform:uppercase;color:var(--accent);margin:0 36px 8px 0;font-size:.78rem;font-weight:600}.obj-md>:first-child{margin-top:0}.obj-md>:last-child{margin-bottom:0}.obj-md a{color:var(--accent)}.obj-md code{font-family:var(--mono);background:#3fd8ff1a;padding:0 4px;font-size:.9em}.obj-stat{gap:2px;display:grid}.obj-label{letter-spacing:.16em;text-transform:uppercase;color:var(--muted);font-size:.78rem}.obj-value{font-variant-numeric:tabular-nums;font-size:clamp(2rem,6vw,3.6rem);font-weight:300;line-height:1.05}.obj-value small{color:var(--muted);margin-left:4px;font-size:.4em}.obj-delta{color:var(--ok);font-size:.9rem}.obj-list{gap:4px;margin:0;padding-left:1.1rem;display:grid}.obj-list .done{color:var(--muted);text-decoration:line-through}.obj-table-wrap{overflow-x:auto}.obj-table{border-collapse:collapse;width:100%;font-size:.92rem}.obj-table th{text-align:left;letter-spacing:.14em;text-transform:uppercase;color:var(--accent);font-size:.72rem;font-weight:600}.obj-table th,.obj-table td{font-variant-numeric:tabular-nums;border-bottom:1px solid #3fd8ff2e;padding:6px 10px}.obj-code{font:.86rem/1.5 var(--mono);margin:0;overflow:auto}.obj-empty{color:var(--muted);margin:0}.integration-steps{color:var(--muted);gap:4px;margin:4px 0 10px;padding-left:1.2rem;font-size:.86rem;display:grid}.integration-steps li.done{color:var(--ok)}.obj-doc{max-height:70vh;overflow:auto}.obj-doc h1,.obj-doc h2,.obj-doc h3,.obj-doc h4{color:var(--accent);letter-spacing:.06em;font-weight:500}.obj-doc table{border-collapse:collapse;width:100%;font-size:.92rem}.obj-doc th,.obj-doc td{border:1px solid color-mix(in srgb, var(--accent) 22%, transparent);text-align:left;padding:5px 9px}.obj-doc th{color:var(--accent);letter-spacing:.14em;text-transform:uppercase;font-size:.72rem;font-weight:500}.obj-doc pre{border:1px solid color-mix(in srgb, var(--accent) 22%, transparent);font:.86rem/1.5 var(--mono);background:#3fd8ff0d;padding:8px 10px;overflow:auto}.obj-doc blockquote{border-left:2px solid var(--edge);color:var(--muted);margin:.6em 0;padding-left:12px}.obj-progress{gap:6px;min-width:0;display:grid}.obj-progress-head{justify-content:space-between;align-items:baseline;gap:12px;display:flex}.obj-progress-pct{font:1.1rem var(--mono);font-variant-numeric:tabular-nums}.obj-progress-bar{border:1px solid var(--edge);background:#3fd8ff12;height:8px}.obj-progress-bar i{background:var(--accent);height:100%;box-shadow:0 0 10px var(--accent);transition:width .4s;display:block}.obj-progress-detail{color:var(--muted);font-size:.82rem}.obj-checklist{gap:6px;margin:0;padding:0;list-style:none;display:grid}.obj-checklist li{align-items:center;gap:10px;display:flex}.obj-checklist .box{border:1px solid var(--accent);width:16px;height:16px;color:var(--accent);flex:none;place-items:center;font-size:.8rem;display:inline-grid}.obj-checklist .done{color:var(--muted)}.obj-checklist .done span:last-child{text-decoration:line-through}.obj-kv{gap:4px;margin:0;display:grid}.obj-kv>div{border-bottom:1px solid color-mix(in srgb, var(--accent) 16%, transparent);justify-content:space-between;gap:18px;padding:3px 0;display:flex}.obj-kv dt{color:var(--muted);letter-spacing:.14em;text-transform:uppercase;font-size:.78rem}.obj-kv dd{font-family:var(--mono);font-variant-numeric:tabular-nums;text-align:right;margin:0}.obj-countdown{justify-items:center;gap:2px;display:grid}.obj-countdown-time{font:300 clamp(2rem, 6vw, 3.4rem) var(--mono);font-variant-numeric:tabular-nums;text-shadow:0 0 14px var(--accent)}.obj-countdown.done .obj-countdown-time{color:var(--warn);text-shadow:0 0 14px var(--warn)}.obj-media{flex-direction:column;gap:6px;width:100%;max-height:100%;display:flex}.obj-media img,.obj-media video{object-fit:contain;border:1px solid var(--edge);background:#050b10;max-width:100%;max-height:50vh;margin:0 auto;display:block}.obj-pdf iframe{border:1px solid var(--edge);background:#050b10;width:100%;min-width:0;height:min(520px,62vh)}.obj-open{color:var(--accent);letter-spacing:.1em;text-transform:uppercase;font-size:.82rem}.obj-gallery-bar{justify-content:space-between;align-items:center;gap:10px;display:flex}.obj-gallery-bar span{color:var(--ink);justify-items:center;font-size:.86rem;display:grid}.obj-gallery-bar small{color:var(--muted);font-family:var(--mono)}.obj-gallery-bar button{border:1px solid var(--edge);min-width:44px;min-height:44px;color:var(--accent);cursor:pointer;background:0 0;font-size:1.3rem}.obj-gallery-bar button:disabled{opacity:.3;cursor:default}.obj-group{align-items:start;gap:14px;display:grid}.obj-group-grid{grid-template-columns:repeat(auto-fit,minmax(170px,1fr))}.obj-group-row{grid-auto-columns:minmax(150px,1fr);grid-auto-flow:column;overflow-x:auto}.obj-group-column{grid-template-columns:1fr}.obj-part{border:1px solid color-mix(in srgb, var(--accent) 20%, transparent);background:#3fd8ff0a;min-width:0;padding:8px 10px}.obj-tabs{border-bottom:1px solid var(--edge);gap:2px;margin-bottom:8px;display:flex;overflow-x:auto}.obj-tabs button{min-height:40px;color:var(--muted);letter-spacing:.14em;text-transform:uppercase;cursor:pointer;white-space:nowrap;background:0 0;border:0;padding:8px 14px;font-size:.78rem}.obj-tabs button.on{color:var(--accent);box-shadow:inset 0 -2px 0 var(--accent);text-shadow:0 0 8px var(--accent)}.obj-chart{width:100%;height:auto;display:block}.obj-chart .grid{stroke:#3fd8ff24;stroke-width:1px}.obj-chart .tick{fill:var(--muted);font:10px var(--mono);font-variant-numeric:tabular-nums}.legend{color:var(--muted);flex-wrap:wrap;gap:6px 14px;margin:6px 0 0;padding:0;font-size:.8rem;list-style:none;display:flex}.legend i{width:10px;height:10px;margin-right:6px;display:inline-block}.obj-gauge{justify-items:center;display:grid}.obj-gauge svg{width:min(100%,260px);height:auto}.obj-gauge .track{stroke:#3fd8ff26}.obj-gauge .value{stroke:var(--accent);filter:drop-shadow(0 0 6px var(--accent))}.obj-gauge.gauge-warn .value{stroke:var(--warn);filter:drop-shadow(0 0 6px var(--warn))}.obj-gauge.gauge-crit .value{stroke:var(--bad);filter:drop-shadow(0 0 6px var(--bad))}.gauge-read{align-items:baseline;gap:4px;margin-top:-62px;display:flex}.gauge-value{font-variant-numeric:tabular-nums;font-size:clamp(1.8rem,5vw,2.8rem);font-weight:300}.gauge-unit{color:var(--muted)}.obj-gauge .obj-label{margin-top:18px}.obj-timeline{border-left:1px solid var(--edge);gap:14px;margin:8px 0 0;padding:0 0 0 20px;list-style:none;display:grid}.obj-timeline li{gap:2px;display:grid;position:relative}.obj-timeline li:before{content:"";background:var(--accent);width:9px;height:9px;box-shadow:0 0 8px var(--accent);border-radius:50%;position:absolute;top:.5em;left:-25px}.obj-timeline time{font:.75rem/1.3 var(--mono);color:var(--accent)}.obj-timeline span{color:var(--muted);font-size:.9rem}.obj-graph{width:100%;height:auto;max-height:70vh;margin:0 auto;display:block}.obj[style*=" height:"] .obj-graph{max-height:calc(100% - 32px)}.obj-graph .edge{stroke:color-mix(in srgb, var(--accent) 55%, transparent);stroke-width:1.4px}.obj-graph .arrow{fill:var(--accent)}.obj-graph .node{fill:#3fd8ff26;stroke:var(--accent);stroke-width:1.5px}.obj-graph .node-label{fill:var(--ink);font:10px var(--ui)}.obj-graph .edge-label{fill:var(--muted);font:9px var(--ui)}.captions{z-index:20;left:50%;bottom:max(7%, env(safe-area-inset-bottom));text-align:center;pointer-events:none;text-shadow:0 0 18px #000,0 0 4px #000;text-wrap:balance;width:min(780px,100% - 32px);margin:0;font-size:clamp(1.1rem,2.6vw,1.6rem);font-weight:300;position:absolute;transform:translate(-50%)}.captions.done{animation:1.4s 8s forwards fadeOut}@keyframes fadeOut{to{opacity:0}}.command-bar{z-index:30;left:50%;bottom:max(14px, env(safe-area-inset-bottom));background:var(--glass);border:1px solid var(--edge);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);gap:8px;width:min(640px,100% - 24px);padding:8px;display:flex;position:absolute;transform:translate(-50%)}.command-bar input{background:0 0;border:0;outline:none;flex:1;min-height:44px;padding:0 10px;font-size:1.05rem}.command-bar button{border:1px solid var(--edge);background:0 0;min-width:44px;min-height:44px}.conn-badge{top:max(10px, env(safe-area-inset-top));font:500 .78rem var(--mono);letter-spacing:.08em;color:var(--warn);border:1px solid var(--warn);background:#0009;padding:6px 12px;position:absolute;right:12px}.mic-indicator{left:50%;top:max(12px, env(safe-area-inset-top));font:500 .82rem var(--mono);letter-spacing:.1em;text-transform:uppercase;color:#ffd9a0;border:1px solid var(--warn);background:#000000c7;align-items:center;gap:10px;padding:8px 16px;display:flex;position:absolute;transform:translate(-50%)}.mic-indicator i{background:var(--bad);width:10px;height:10px;box-shadow:0 0 10px var(--bad);border-radius:50%;animation:1s ease-in-out infinite mic-pulse}.mic-transcribing i{background:var(--warn);box-shadow:0 0 10px var(--warn)}@keyframes mic-pulse{50%{opacity:.35}}@media (prefers-reduced-motion:reduce){.mic-indicator i{animation:none}}.toasts{top:max(48px, env(safe-area-inset-top));gap:6px;width:min(420px,100% - 24px);display:grid;position:absolute;left:50%;transform:translate(-50%)}.toast{border:1px solid var(--edge);background:#000000d1;padding:10px 14px;font-size:.92rem}.toast-warn{border-color:var(--warn);color:#ffd9a0}.toast-error{border-color:var(--bad);color:#ffc2c9}.approval{border-color:var(--warn);background:#020c12eb;width:min(460px,100% - 24px);max-height:calc(100% - 24px);padding:20px;position:absolute;top:50%;left:50%;overflow:auto;transform:translate(-50%,-50%);box-shadow:0 0 0 100vmax #0000008c,0 0 30px #ffb45440}.plugins{flex-direction:column;width:min(560px,100% - 24px);display:flex;overflow:hidden}.plugins-body{min-height:0;padding-right:4px;overflow-y:auto}.plugins-heading{letter-spacing:.14em;text-transform:uppercase;color:var(--muted);margin:14px 0 6px;font-size:.78rem}.plugin-list{gap:8px;margin:0;padding:0;list-style:none;display:grid}.plugin-list li{background:#ffffff0a;flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 10px;padding:8px 10px;display:flex}.plugin-info{flex:180px;min-width:0}.plugin-info .auth-note{font-size:.82rem}.plugin-actions{flex-wrap:wrap;gap:6px;display:flex}.plugin-actions button{border:1px solid var(--edge);background:0 0;padding:0 12px}.obj-sandbox{flex-direction:column;gap:6px;width:100%;min-width:min(560px,80vw);height:min(420px,60vh);display:flex}.obj-sandbox iframe{border:1px solid var(--edge);background:#050b10;flex:1;width:100%;min-height:200px}.camera-indicator{border-color:var(--bad);color:#ffc2c9;letter-spacing:.12em;text-transform:uppercase;background:#020c12e6;align-items:center;gap:10px;padding:6px 12px 6px 6px;font-size:.8rem;display:flex;position:absolute;bottom:12px;right:12px}.camera-indicator video{object-fit:cover;background:#000;width:72px;height:54px}.camera-indicator span:before{content:"";background:var(--bad);border-radius:50%;width:8px;height:8px;margin-right:8px;display:inline-block}.challenge,.enroll{border-color:var(--accent);box-shadow:0 0 0 100vmax #0000008c,0 0 30px #3fd8ff40}.challenge .approval-title,.enroll .approval-title{color:var(--accent)}.approval-head{align-items:center;gap:10px;display:flex}.approval-title{letter-spacing:.18em;text-transform:uppercase;color:var(--warn);font-size:.8rem}.tier{font:600 .74rem var(--mono);border:1px solid;padding:2px 8px}.tier-T2{color:var(--warn)}.tier-T3{color:var(--bad)}.approval-summary{font:.95rem/1.5 var(--mono);word-break:break-all;background:#ffffff0a;max-height:40vh;margin:14px 0;padding:10px 12px;overflow:auto}.approval-actions{flex-wrap:wrap;gap:8px;margin-top:14px;display:flex}.approval-actions button,.owner-menu button,.auth button{border:1px solid var(--edge);letter-spacing:.04em;background:0 0;padding:0 16px}button.primary{background:color-mix(in srgb, var(--accent) 22%, transparent);border-color:var(--accent)}button.danger{border-color:var(--bad);color:#ffc2c9}button:disabled{opacity:.4;cursor:not-allowed}.pinpad{justify-items:center;gap:8px;display:grid}.pin-dots{letter-spacing:.4em;min-height:1.6em;color:var(--accent);font-size:1.6rem}.pin-keys{grid-template-columns:repeat(3,64px);gap:8px;display:grid}.pin-keys button{border:1px solid var(--edge);background:#3fd8ff0d;font-size:1.2rem}.owner-menu{top:max(60px, env(safe-area-inset-top));background:#020c12f0;gap:8px;width:220px;padding:12px;display:grid;left:12px}.boot{background:#000;height:100%}.auth{gap:8px;width:min(380px,100% - 28px);padding:24px;display:grid;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%)}.auth h1{letter-spacing:.3em;text-transform:uppercase;color:var(--accent);margin:0 0 6px;font-size:1.1rem;font-weight:300}.auth label{letter-spacing:.12em;text-transform:uppercase;color:var(--muted);margin-top:6px;font-size:.78rem}.auth input{border:1px solid var(--edge);background:#ffffff0a;padding:0 12px}.auth button{margin-top:12px}.auth-note{color:var(--muted);margin:0;font-size:.9rem}.auth-error{color:#ffc2c9;margin:4px 0 0;font-size:.9rem}@media (width<=599px){.presence-full{inset:0}.captions{bottom:max(11%, env(safe-area-inset-bottom))}}@media (prefers-reduced-motion:reduce){.obj,.presence{transition:none;animation:none}}.status-badge{left:12px;bottom:max(12px, env(safe-area-inset-bottom));font:500 .78rem var(--mono);letter-spacing:.08em;color:var(--ink);border:1px solid var(--edge);background:#0000008c;align-items:center;gap:9px;max-width:min(60vw,360px);padding:6px 12px;display:flex;position:absolute}.status-badge span{text-overflow:ellipsis;white-space:nowrap;overflow:hidden}.status-badge i{background:var(--muted);border-radius:50%;flex:none;width:9px;height:9px}.status-idle i{background:var(--ok);box-shadow:0 0 8px var(--ok)}.status-working i,.status-speaking i{background:var(--accent);box-shadow:0 0 10px var(--accent);animation:1s ease-in-out infinite mic-pulse}.status-listening i{background:var(--bad);box-shadow:0 0 10px var(--bad);animation:1s ease-in-out infinite mic-pulse}.status-waiting{border-color:var(--warn);color:#ffd9a0}.status-waiting i{background:var(--warn);box-shadow:0 0 10px var(--warn);animation:1s ease-in-out infinite mic-pulse}.status-offline{border-color:var(--warn);color:var(--warn)}.status-offline i{background:var(--warn)}@media (prefers-reduced-motion:reduce){.status-badge i{animation:none!important}}.clock{right:12px;bottom:max(12px, env(safe-area-inset-bottom));text-align:right;color:var(--muted);line-height:1.15;font-family:var(--mono);pointer-events:none;position:absolute}.clock b{color:var(--ink);letter-spacing:.06em;font-size:1.15rem;font-weight:500;display:block}.clock span{letter-spacing:.1em;text-transform:uppercase;font-size:.7rem}.settings{flex-direction:column;width:min(520px,100% - 24px);max-height:calc(100% - 24px);display:flex}.settings-body{gap:6px;min-height:0;padding-right:4px;display:grid;overflow-y:auto}.settings-field{gap:3px;display:grid}.settings-field>span{letter-spacing:.1em;text-transform:uppercase;color:var(--muted);font-size:.74rem}.settings-field input:not([type=range]):not([type=checkbox]),.settings-field select{border:1px solid var(--edge);color:var(--ink);min-height:40px;font:inherit;background:#ffffff0a;padding:0 10px}.settings-field select option{background:#06141c}.settings-check{align-items:center;gap:10px;min-height:40px;display:flex}.slash-list{border:1px solid var(--edge);background:#020c12f5;max-height:40vh;margin:0;padding:4px;list-style:none;position:absolute;bottom:calc(100% + 6px);left:0;right:0;overflow-y:auto}.slash-list li{cursor:pointer;align-items:baseline;gap:10px;padding:7px 10px;display:flex}.slash-list li.on,.slash-list li:hover{background:color-mix(in srgb, var(--accent) 18%, transparent)}.slash-list b{font:600 .9rem var(--mono);color:var(--accent)}.slash-list i{font:.78rem var(--mono);color:var(--warn);font-style:normal}.slash-list span{color:var(--muted);font-size:.82rem}.movable{position:absolute}.movable[data-panel=status],.movable[data-panel=clock]{cursor:grab;touch-action:none;pointer-events:auto}.movable:focus-visible{outline:2px solid var(--accent);outline-offset:2px}.panel{resize:both;flex-direction:column;width:clamp(260px,28vw,420px);min-width:220px;min-height:140px;max-height:80vh;padding:0;display:flex;overflow:hidden}.panel-chat{height:62vh}.panel-tasks{width:clamp(240px,26vw,360px);height:40vh}.panel-head{cursor:grab;touch-action:none;border-bottom:1px solid var(--edge);-webkit-user-select:none;user-select:none;justify-content:space-between;align-items:center;gap:10px;padding:8px 12px;display:flex}.panel-head .obj-close{position:static}.chat-lines{flex:1;align-content:start;gap:8px;min-height:0;padding:10px 12px;display:grid;overflow-y:auto}.chat-line{white-space:pre-wrap;overflow-wrap:anywhere;max-width:92%;margin:0;padding:7px 10px;font-size:.9rem}.chat-user{background:color-mix(in srgb, var(--accent) 18%, transparent);border:1px solid var(--edge);justify-self:end}.chat-assistant{background:#ffffff0d;justify-self:start}.chat-form{border-top:1px solid var(--edge);gap:6px;padding:8px;display:flex}.chat-form input{border:1px solid var(--edge);min-width:0;color:var(--ink);min-height:40px;font:inherit;background:#ffffff0a;flex:1;padding:0 10px}.chat-form button{border:1px solid var(--edge);color:var(--ink);background:0 0;min-height:40px;padding:0 14px}.task-body{flex:1;min-height:0;padding:10px 12px;overflow-y:auto}.task-list{gap:8px;margin:0;padding:0;list-style:none;display:grid}.task-list li{border-left:3px solid var(--accent);background:#ffffff0a;gap:2px;padding:8px 10px;display:grid}.task-list li.overdue{border-left-color:var(--bad)}.task-title{overflow-wrap:anywhere;font-size:.95rem}.task-due{font:.75rem var(--mono);color:var(--muted)}.task-list li.overdue .task-due{color:var(--bad)}@media (width<=600px){.panel{resize:none;width:calc(100% - 24px);left:12px!important}.panel-chat{height:52vh;bottom:56px;top:auto!important}.panel-tasks{height:30vh;top:56px!important}}.help{flex-direction:column;width:min(560px,100% - 24px);max-height:calc(100% - 24px);display:flex}.help-list{gap:4px;min-height:0;margin:8px 0;display:grid;overflow-y:auto}.help-row{border-bottom:1px solid #ffffff0f;grid-template-columns:minmax(130px,38%) 1fr;gap:12px;padding:6px 4px;display:grid}.help-row dt{font:600 .9rem var(--mono);color:var(--accent);overflow-wrap:anywhere}.help-row dt i{color:var(--warn);font-style:normal;font-weight:400}.help-row dd{color:var(--ink);margin:0;font-size:.9rem}@media (width<=600px){.help-row{grid-template-columns:1fr;gap:2px}}.connectors{width:min(600px,100% - 24px);max-height:calc(100% - 24px);overflow-y:auto}.connector-form{gap:8px;display:grid}.connector-form textarea,.settings-field textarea{border:1px solid var(--edge);color:var(--ink);font:.85rem var(--mono);resize:vertical;background:#ffffff0a;padding:8px 10px}.connector-steps{color:var(--muted);gap:4px;margin:0;padding-left:20px;font-size:.88rem;display:grid}.connector-warning{border-left:3px solid var(--warn);color:#ffd9a0;padding-left:10px}.conn-status{font:.74rem var(--mono)}.conn-ready{color:var(--ok)}.conn-error{color:var(--bad)}.conn-connecting{color:var(--warn)}.conn-off{color:var(--muted)}.settings-wide{width:min(980px,100% - 24px);height:min(720px,100% - 24px)}.settings-layout{flex:1;grid-template-columns:190px 1fr;gap:16px;min-height:0;margin-top:8px;display:grid}.settings-tabs{align-content:start;gap:6px;display:grid}.settings-tab{text-align:left;color:var(--ink);background:0 0;border:1px solid #0000;gap:2px;padding:10px 12px;display:grid}.settings-tab small{color:var(--muted);font-size:.74rem}.settings-tab:hover{background:#ffffff0d}.settings-tab.on{border-color:var(--accent);background:color-mix(in srgb, var(--accent) 16%, transparent)}.settings-wide .settings-body{align-content:start;padding-right:8px}@media (width<=700px){.settings-wide{height:calc(100% - 24px)}.settings-layout{grid-template-columns:1fr;gap:8px}.settings-tabs{grid-auto-columns:1fr;grid-auto-flow:column;overflow-x:auto}.settings-tab small{display:none}}.look-tab{grid-template-columns:minmax(220px,300px) 1fr;align-items:start;gap:18px;display:grid}.look-side{gap:10px;display:grid;position:sticky;top:0}.look-controls{gap:6px;min-width:0;display:grid}@media (width<=860px){.look-tab{grid-template-columns:1fr}.look-side{position:static}}.look-preview{border:1px solid var(--edge);background:#000;height:230px;position:relative;overflow:hidden}.look-preview-glow{background:radial-gradient(ellipse at 50% 55%, color-mix(in srgb, var(--accent) 22%, transparent), transparent 65%);position:absolute;inset:0}.look-preview-stage{position:absolute;inset:0}.look-preview-caption{text-align:center;text-shadow:0 0 10px #000;margin:0;position:absolute;bottom:8px;left:8px;right:8px}.look-preview .presence-full{inset:0}.theme-grid{grid-template-columns:repeat(auto-fill,minmax(118px,1fr));gap:8px;display:grid}.theme-card{border:1px solid var(--edge);color:var(--ink);text-align:left;background:#ffffff08;justify-items:start;gap:1px;padding:10px;display:grid}.theme-card i{background:var(--swatch);width:22px;height:22px;box-shadow:0 0 12px var(--swatch);border-radius:50%;margin-bottom:4px}.theme-card small{color:var(--muted);font-size:.72rem}.theme-card.on,.style-choice.on{border-color:var(--accent);background:color-mix(in srgb, var(--accent) 18%, transparent)}.style-row{grid-template-columns:repeat(3,1fr);gap:8px;display:grid}.style-choice{border:1px solid var(--edge);color:var(--ink);text-align:left;background:#ffffff08;gap:2px;padding:10px;display:grid}.style-choice small{color:var(--muted);font-size:.72rem}.swatch-row{flex-wrap:wrap;align-items:center;gap:8px;display:flex}.swatch{border:2px solid #0000;border-radius:50%;width:32px;height:32px;min-height:32px;padding:0}.swatch.on{box-shadow:0 0 0 2px var(--accent);border-color:#fff}.swatch-custom{color:var(--muted);align-items:center;gap:6px;font-size:.8rem;display:flex}.swatch-custom input[type=color]{border:1px solid var(--edge);background:0 0;width:40px;height:32px;padding:0}.captions-small{font-size:clamp(.9rem,2vw,1.15rem)}.captions-medium{font-size:clamp(1.1rem,2.6vw,1.6rem)}.captions-large{font-size:clamp(1.4rem,3.6vw,2.3rem)}.voice-hear{flex-wrap:wrap;align-items:center;gap:12px;display:flex}.connector-command{border:1px solid var(--edge);font:.85rem var(--mono);-webkit-user-select:all;user-select:all;background:#ffffff0d;margin:0;padding:8px 10px;overflow-x:auto}html,body{overscroll-behavior:none}@media (pointer:coarse){.stage{-webkit-touch-callout:none;-webkit-user-select:none;user-select:none}}input,textarea,select,.connector-command{-webkit-user-select:text;user-select:text}.owner-menu{max-height:calc(100dvh - 80px);overflow-y:auto}.touch-controls{z-index:25;left:0;right:0;bottom:max(14px, env(safe-area-inset-bottom));pointer-events:none;justify-content:center;align-items:flex-end;gap:26px;display:flex;position:absolute}.touch-controls>*{pointer-events:auto}.touch-talk{justify-items:center;gap:6px;display:grid}.touch-hint{max-width:70vw;font:500 .74rem var(--mono);letter-spacing:.06em;color:var(--muted);text-align:center;text-shadow:0 0 6px #000,0 0 2px #000;padding:2px 10px}.touch-mic,.touch-side{border:1px solid var(--edge);color:var(--ink);background:var(--glass);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);touch-action:none;-webkit-user-select:none;user-select:none;-webkit-touch-callout:none;-webkit-tap-highlight-color:transparent;border-radius:50%;place-items:center;padding:0;display:grid}.touch-mic{border-color:var(--accent);width:76px;height:76px;box-shadow:0 0 22px color-mix(in srgb, var(--accent) 30%, transparent)}.touch-mic.on{background:color-mix(in srgb, var(--bad) 40%, transparent);border-color:var(--bad);box-shadow:0 0 28px var(--bad);animation:1s ease-in-out infinite mic-pulse}.touch-side{touch-action:manipulation;width:52px;height:52px;margin-bottom:12px}@media (prefers-reduced-motion:reduce){.touch-mic.on{animation:none}}@media (pointer:coarse){.captions{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 150px)}.status-badge,.clock{bottom:max(8px, env(safe-area-inset-bottom))}.presence-corner{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 70px)}}@media (width<=600px) and (pointer:coarse){.panel-chat{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 150px);height:min(48vh,100dvh - 260px)}.objects-stack{padding-bottom:190px}}.elsewhere{z-index:3000;-webkit-backdrop-filter:blur(6px);backdrop-filter:blur(6px);background:#000000c7;place-items:center;padding:16px;display:grid;position:fixed;inset:0}.elsewhere-card{border:1px solid var(--edge);background:var(--glass);max-width:380px;color:var(--ink);text-align:center;border-radius:16px;padding:24px}.elsewhere-card h2{margin:0 0 10px;font-size:1.15rem}.elsewhere-card p{color:var(--muted);margin:0 0 18px;line-height:1.45}.elsewhere-btn{border:1px solid var(--accent);background:color-mix(in srgb, var(--accent) 25%, transparent);min-height:48px;color:var(--ink);font:600 1rem var(--mono);cursor:pointer;border-radius:24px;padding:0 28px}.obj-grip{cursor:grab;touch-action:none;border-radius:8px 8px 0 0;height:22px;position:absolute;top:0;left:0;right:92px}.obj-grip:before{content:"";background:var(--muted);opacity:.35;border-radius:2px;width:34px;height:3px;margin-left:-17px;transition:opacity .15s;position:absolute;top:8px;left:50%}.obj:hover .obj-grip:before,.obj-grip:focus-visible:before{opacity:.9}.obj-grip:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}.obj.dragging{cursor:grabbing;box-shadow:0 0 0 1px var(--accent), 0 8px 30px #00000080;-webkit-user-select:none;user-select:none;transition:none;animation:none}.obj-pin{width:44px;height:44px;color:var(--muted);opacity:.55;background:0 0;border:0;place-items:center;display:grid;position:absolute;top:2px;right:50px}.obj:hover .obj-pin,.obj-pin.on,.obj-pin:focus-visible{opacity:1}.obj-pin.on,.obj-pin:hover{color:var(--accent)}.obj.pinned{border-color:color-mix(in srgb, var(--accent) 55%, transparent)}.obj-resize{cursor:nwse-resize;touch-action:none;opacity:0;background:linear-gradient(135deg, transparent 55%, var(--accent) 56%, var(--accent) 64%, transparent 65%, transparent 76%, var(--accent) 77%, var(--accent) 85%, transparent 86%);width:22px;height:22px;transition:opacity .15s;position:absolute;bottom:0;right:0}.obj:hover .obj-resize,.obj.dragging .obj-resize{opacity:.7}@media (pointer:coarse){.obj-pin{opacity:1}.obj-resize{opacity:.7;width:30px;height:30px}.obj-grip{height:30px}.obj-grip:before{opacity:.7;top:12px}}.profile-badge{top:max(56px, calc(env(safe-area-inset-top) + 48px));border:1px solid var(--edge);background:var(--glass);-webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);color:var(--ink);cursor:grab;touch-action:none;-webkit-user-select:none;user-select:none;border-radius:12px;align-items:center;gap:8px;padding:6px 12px 6px 8px;display:flex;position:fixed;left:12px}.profile-shield{color:var(--accent);flex:none}.profile-shield.member{color:#8ff0b0}.profile-shield.guest{color:var(--warn)}.profile-text{min-width:0;line-height:1.15;display:grid}.profile-text b{text-overflow:ellipsis;white-space:nowrap;max-width:130px;font-size:.86rem;font-weight:600;overflow:hidden}.profile-text small{font:500 .64rem var(--mono);letter-spacing:.1em;text-transform:uppercase;color:var(--muted)}@media (width<=600px){.profile-text{display:none}.profile-badge{padding:4px 6px}}.hud{--hud-line:color-mix(in srgb, var(--accent) 62%, transparent);--hud-line-dim:color-mix(in srgb, var(--accent) 26%, transparent);--hud-glow:color-mix(in srgb, var(--accent) 42%, transparent);--hud-bg:#030d14d1;--hud-bg-hi:#081e2ae6;--cut:10px;color:var(--ink);font-family:var(--mono);-webkit-user-select:none;user-select:none}.hud-cut{background:var(--hud-line);clip-path:polygon(0 0, calc(100% - var(--cut)) 0, 100% var(--cut), 100% 100%, var(--cut) 100%, 0 calc(100% - var(--cut)));position:relative}.hud-cut:before{content:"";background:var(--hud-bg);clip-path:polygon(0 0, calc(100% - var(--cut) + 1px) 0, 100% calc(var(--cut) - 1px), 100% 100%, calc(var(--cut) - 1px) 100%, 0 calc(100% - var(--cut) + 1px));z-index:0;transition:background .14s ease-out;position:absolute;inset:1px}.hud-cut>*{z-index:1;position:relative}.hud-kicker{letter-spacing:.22em;text-transform:uppercase;color:var(--muted);margin:0 0 6px 2px;font-size:.62rem}.hud-profile{top:max(56px, calc(env(safe-area-inset-top) + 48px));cursor:grab;touch-action:none;align-items:center;display:flex;position:fixed;left:12px}.hud-emblem{z-index:2;background:radial-gradient(circle, var(--hud-bg-hi), var(--hud-bg));width:64px;height:64px;box-shadow:0 0 18px var(--hud-glow), inset 0 0 12px var(--hud-line-dim);border-radius:50%;flex:none;place-items:center;display:grid;position:relative}.hud-emblem-svg{color:var(--accent)}.hud-emblem-svg.member{color:#8ff0b0}.hud-emblem-svg.guest{color:var(--warn)}.hud-ring-chase{opacity:0;transform-origin:32px 32px}.hud-tag{--cut:9px;gap:1px;min-width:176px;margin-left:-14px;padding:6px 18px 7px 24px;line-height:1.15;display:grid}.hud-tag b{letter-spacing:.02em;text-overflow:ellipsis;white-space:nowrap;max-width:190px;font-size:.95rem;font-weight:600;overflow:hidden}.hud-tag small{letter-spacing:.16em;text-transform:uppercase;color:var(--muted);font-size:.62rem}.hud-tag .hud-tag-top{color:var(--accent);letter-spacing:.2em}.hud-tag:after{content:"";background:var(--accent);width:2px;box-shadow:0 0 8px var(--hud-glow);z-index:1;position:absolute;top:8px;bottom:8px;left:10px}.hud-profile.member .hud-tag:after{background:#8ff0b0}.hud-profile.guest .hud-tag:after{background:var(--warn)}.hud-clock{top:max(56px, calc(env(safe-area-inset-top) + 48px));cursor:grab;touch-action:none;text-align:left;position:fixed;left:332px}.hud-clock time{align-items:flex-end;gap:14px;display:flex}.hud-date{justify-items:start;line-height:1;display:grid}.hud-day{letter-spacing:.02em;text-shadow:0 0 14px var(--hud-glow);font-size:3.1rem;font-weight:700;display:flex}.hud-month{background:var(--accent);color:#031018;letter-spacing:.22em;text-transform:uppercase;clip-path:polygon(0 0,100% 0,calc(100% - 6px) 100%,0 100%);margin-top:2px;padding:1px 8px 1px 6px;font-size:.7rem;font-weight:700}.hud-weekday{letter-spacing:.2em;text-transform:uppercase;color:var(--muted);margin-top:3px;font-size:.64rem}.hud-time-block{gap:5px;min-width:150px;padding-bottom:4px;display:grid}.hud-clock-time{letter-spacing:.06em;align-items:baseline;font-size:1.55rem;display:flex}.hud-colon{color:var(--accent);margin:0 1px;font-style:normal}.hud-period{letter-spacing:.2em;color:var(--muted);margin-left:6px;font-size:.62rem}.hud-line{background:linear-gradient(90deg, var(--hud-line), transparent);height:1px;position:relative}.hud-line:after{content:"";border:1px solid var(--accent);background:var(--hud-bg);border-radius:50%;width:7px;height:7px;position:absolute;top:-3px;left:-3px}.hud-dot{background:var(--accent);width:5px;height:5px;box-shadow:0 0 8px var(--accent);border-radius:50%;position:absolute;top:-2px;left:0}.hud-digit{display:inline-block}.hud-launcher{left:12px;top:calc(max(56px, env(safe-area-inset-top) + 48px) + 86px);cursor:grab;touch-action:none;position:fixed}.hud-stack{gap:6px;margin:0;padding:0;list-style:none;display:grid}.hud-tab{--cut:9px;align-items:stretch;min-width:176px;transition:transform .14s ease-out,filter .14s ease-out;display:flex}.hud-tab-main{color:var(--ink);font:inherit;letter-spacing:.06em;text-align:left;cursor:pointer;background:0 0;border:0;flex:1;grid-template-columns:26px 1fr;align-items:center;gap:10px;min-height:40px;padding:7px 18px 9px 10px;font-size:.82rem;display:grid;position:relative;overflow:hidden}.hud-tab-main:focus-visible{outline:1px dashed var(--accent);outline-offset:-3px}.hud-icon{background:var(--hud-line-dim);width:26px;height:26px;color:var(--accent);place-items:center;font-size:.95rem;transition:background .14s ease-out,color .14s;display:grid}.hud-tab-label{text-transform:uppercase;letter-spacing:.14em;font-size:.74rem}.hud-tab-engaged{letter-spacing:.2em;color:var(--accent);opacity:0;font-size:.74rem;position:absolute;top:50%;left:46px;transform:translateY(-50%)}.hud-tab:after{content:"";background:var(--accent);width:26%;height:2px;box-shadow:0 0 6px var(--hud-glow);z-index:2;transition:width .22s ease-out;position:absolute;bottom:4px;left:12px}.hud-sweep,.hud-scan{pointer-events:none;opacity:0;position:absolute;inset:0}.hud-sweep{background:linear-gradient(100deg, transparent 30%, color-mix(in srgb, var(--accent) 38%, transparent) 50%, transparent 70%);transform:translate(-100%)}.hud-scan{background:linear-gradient(180deg, transparent, color-mix(in srgb, var(--accent) 55%, transparent) 50%, transparent);height:14px;inset:-14px 0 auto}.hud-ripple{background:radial-gradient(circle, color-mix(in srgb, var(--accent) 55%, transparent), transparent 62%);opacity:.9;pointer-events:none;border-radius:50%;animation:.6s ease-out forwards hud-ripple;position:absolute;transform:scale(0)}@media (hover:hover){.hud-tab:hover{filter:brightness(1.22);transform:translate(6px)}.hud-tab:hover:after{width:calc(100% - 24px)}.hud-tab:hover:before{background:var(--hud-bg-hi)}.hud-tab:hover .hud-icon{background:var(--accent);color:#031018}.hud-tab:hover .hud-sweep{opacity:1;animation:.6s ease-out hud-sweep}}.hud-tab:active{transform:translate(3px)scale(.97)}.hud-tab:active:before{background:color-mix(in srgb, var(--accent) 18%, var(--hud-bg))}.hud-tab.engaged .hud-tab-label{opacity:0}.hud-tab.engaged .hud-tab-engaged{opacity:1;animation:.65s steps(2,end) hud-flicker}.hud-tab.engaged .hud-scan{opacity:1;animation:.45s linear hud-scan}.hud-tab.current:before{background:var(--hud-bg-hi)}.hud-tab.current:after{width:calc(100% - 24px)}.hud-tab.current .hud-tab-title{color:var(--accent)}.hud-btn{background:var(--hud-line-dim);width:36px;height:32px;color:var(--ink);cursor:pointer;clip-path:polygon(7px 0,100% 0,calc(100% - 7px) 100%,0 100%);border:0;place-items:center;padding:0;transition:background .14s ease-out,color .14s,transform .1s;display:inline-grid;position:relative;overflow:hidden}.hud-btn sup{color:var(--accent);font-size:.55rem;position:absolute;top:3px;right:6px}.hud-btn.on,.hud-btn[aria-pressed=true]{color:var(--accent);background:color-mix(in srgb, var(--accent) 24%, transparent)}.hud-btn-main{background:var(--accent);color:#031018;width:52px;height:36px}.hud-btn:focus-visible{outline:1px dashed var(--accent);outline-offset:2px}@media (hover:hover){.hud-btn:hover{background:color-mix(in srgb, var(--accent) 44%, transparent);color:#fff}.hud-btn-main:hover{background:color-mix(in srgb, var(--accent) 78%, #fff);color:#031018}}.hud-btn:active{transform:scale(.94)}.hud-range{appearance:none;cursor:pointer;--fill:0%;background:0 0;width:100%;height:14px;margin:0}.hud-range::-webkit-slider-runnable-track{background:linear-gradient(90deg, var(--accent) var(--fill), var(--hud-line-dim) var(--fill));height:2px}.hud-range::-moz-range-track{background:var(--hud-line-dim);height:2px}.hud-range::-moz-range-progress{background:var(--accent);height:2px}.hud-range::-webkit-slider-thumb{-webkit-appearance:none;background:var(--accent);clip-path:polygon(0 0,100% 0,100% 70%,50% 100%,0 70%);width:9px;height:13px;box-shadow:0 0 8px var(--hud-glow);border:0;margin-top:-5.5px}.hud-range::-moz-range-thumb{background:var(--accent);border:0;border-radius:0;width:9px;height:13px}.hud-range:disabled{opacity:.4;cursor:default}.hud-chip{border:1px solid var(--hud-line-dim);color:var(--muted);font:inherit;letter-spacing:.16em;text-transform:uppercase;cursor:pointer;background:0 0;padding:4px 12px;font-size:.66rem;transition:color .14s,border-color .14s,background .14s}.hud-chip.on{color:var(--accent);border-color:var(--accent);background:color-mix(in srgb, var(--accent) 12%, transparent)}@media (hover:hover){.hud-chip:hover{color:var(--ink);border-color:var(--hud-line)}}.hud-mini{border:1px solid var(--hud-line-dim);width:30px;height:30px;color:var(--accent);font:inherit;cursor:pointer;background:0 0;align-self:center;margin-right:8px;font-size:1.05rem;transition:background .14s,color .14s}@media (hover:hover){.hud-mini:hover{background:var(--accent);color:#031018}}.hud-music{--cut:14px;cursor:grab;touch-action:none;padding:10px 14px 12px;position:fixed;bottom:12px;right:12px}.hud-music.mini{width:min(560px,100vw - 24px)}.hud-music.full{width:min(1000px,100vw - 24px);max-height:calc(100vh - 24px);padding:12px 16px 16px;overflow:auto}.hud-music-head{justify-content:space-between;align-items:center;margin-bottom:6px;display:flex}.hud-music-head .hud-kicker{margin:0}.hud-head-actions{gap:4px;display:flex}.hud-head-actions .hud-btn{width:30px;height:24px}.hud-music-body{align-items:center;gap:16px;display:flex}.hud-music.full .hud-music-body{align-items:stretch;gap:22px}.hud-music-left{flex:none;align-items:center;gap:12px;display:flex}.hud-music-main{flex:1;align-content:center;gap:8px;min-width:0;display:grid}.hud-now{gap:2px;min-width:0;display:grid}.hud-title{letter-spacing:.02em;white-space:nowrap;text-overflow:ellipsis;font-variant-ligatures:none;font-size:1rem;font-weight:600;overflow:hidden}.hud-music.full .hud-title{white-space:normal;font-size:1.35rem}.hud-sub{letter-spacing:.1em;text-transform:uppercase;color:var(--muted);white-space:nowrap;text-overflow:ellipsis;font-size:.7rem;overflow:hidden}.hud-timeline{grid-template-columns:auto 1fr auto;align-items:center;gap:10px;display:grid}.hud-time{letter-spacing:.1em;color:var(--muted);font-variant-numeric:tabular-nums;font-size:.7rem}.hud-controls{align-items:center;gap:6px;display:flex}.hud-controls .hud-btn:first-child{margin-right:6px}.hud-controls .hud-btn:last-child{margin-left:6px}.hud-volume{grid-template-columns:auto 1fr;align-items:center;gap:8px;max-width:260px;display:grid}.hud-unlock{border:1px solid var(--warn);color:var(--warn);font:inherit;letter-spacing:.16em;text-transform:uppercase;cursor:pointer;background:0 0;justify-self:start;padding:4px 12px;font-size:.66rem;animation:1.4s ease-in-out infinite hud-pulse}.hud-dial{--bass:0;flex:none;position:relative}.hud-dial-svg{width:100%;height:100%;position:absolute;inset:0;overflow:visible}.hud-dial-ticks{fill:none;stroke:var(--hud-line);stroke-width:3px;stroke-dasharray:1 5.02}.hud-dial-track{fill:none;stroke:var(--hud-line-dim);stroke-width:2px}.hud-dial-arc{fill:none;stroke:var(--accent);stroke-width:3px;stroke-linecap:butt;filter:drop-shadow(0 0 4px var(--hud-glow));transition:stroke-dasharray .25s linear}.hud-dial-inner{fill:none;stroke:var(--hud-line-dim);stroke-width:1px}.hud-needle{transform-origin:100px 100px;opacity:.85}.hud-needle line{stroke:var(--accent);stroke-width:1.4px;stroke-linecap:round}.hud-needle circle{fill:var(--accent);filter:drop-shadow(0 0 4px var(--accent))}.hud-spectrum{pointer-events:none;position:absolute;inset:0}.hud-cover{color:var(--hud-line);background:var(--hud-bg-hi) center / cover no-repeat;box-shadow:0 0 16px var(--hud-line-dim), inset 0 0 14px #0000008c;border:1px solid var(--hud-line);transform:scale(calc(1 + var(--bass) * .045));border-radius:50%;place-items:center;display:grid;position:absolute;inset:20%}.hud-levels{flex-direction:column-reverse;gap:3px;width:9px;height:220px;display:flex}.hud-levels i{background:var(--hud-line-dim);flex:1;transition:background 80ms linear,box-shadow 80ms linear;display:block}.hud-levels i.on{background:var(--accent);box-shadow:0 0 6px var(--hud-glow)}.hud-levels i:nth-child(n+10).on{background:var(--warn);box-shadow:0 0 6px color-mix(in srgb, var(--warn) 50%, transparent)}.hud-playlist{grid-template-rows:auto auto minmax(0,1fr);gap:8px;width:300px;min-width:0;max-height:340px;display:grid}.hud-tabs{flex-wrap:wrap;gap:6px;display:flex}.hud-search{border:1px solid var(--hud-line-dim);width:100%;color:var(--ink);font:inherit;background:#0000004d;padding:6px 10px;font-size:.8rem}.hud-search:focus{border-color:var(--accent);outline:none}.hud-list{align-content:start;gap:5px;min-height:0;margin:0;padding:0 4px 0 0;list-style:none;display:grid;overflow-y:auto}.hud-list .hud-tab{--cut:7px;min-width:0}.hud-list .hud-tab-main{grid-template-columns:1fr;gap:1px;min-height:0;padding:6px 12px 8px 14px;display:grid}.hud-tab-title{letter-spacing:.03em;white-space:nowrap;text-overflow:ellipsis;font-size:.8rem;overflow:hidden}.hud-list small{letter-spacing:.12em;text-transform:uppercase;color:var(--muted);white-space:nowrap;text-overflow:ellipsis;font-size:.62rem;overflow:hidden}.hud-source{letter-spacing:.18em;color:#031018;background:var(--accent);clip-path:polygon(0 0,100% 0,calc(100% - 4px) 100%,0 100%);vertical-align:1px;margin-left:8px;padding:0 5px;font-size:.56rem;font-style:normal}.hud-notice{border-left:2px solid var(--warn);letter-spacing:.06em;color:var(--warn);margin:0;padding:4px 10px;font-size:.7rem}.hud-empty{color:var(--muted);padding:10px 4px;font-size:.75rem}@keyframes hud-spin{to{transform:rotate(360deg)}}@keyframes hud-sweep{0%{transform:translate(-100%)}to{transform:translate(100%)}}@keyframes hud-scan{0%{top:-14px}to{top:calc(100% + 14px)}}@keyframes hud-ripple{to{opacity:0;transform:scale(1)}}@keyframes hud-flicker{0%,to{opacity:1}25%{opacity:.2}50%{opacity:1}75%{opacity:.45}}@keyframes hud-pulse{0%,to{opacity:1}50%{opacity:.45}}@keyframes hud-boot{0%{opacity:0;filter:brightness(2.2);transform:translate(-14px)}30%{opacity:1}42%{opacity:.35}56%{opacity:1}70%{opacity:.7}to{opacity:1;filter:none;transform:none}}@keyframes hud-roll{0%{opacity:0;transform:translateY(60%)}to{opacity:1;transform:none}}@keyframes hud-blink{0%,49%{opacity:1}50%,to{opacity:.25}}@keyframes hud-travel{0%{left:0}to{left:calc(100% - 5px)}}@keyframes hud-flare{0%{box-shadow:0 0 18px var(--hud-glow), 0 0 0 0 var(--accent)}60%{box-shadow:0 0 30px var(--accent), 0 0 0 14px transparent}to{box-shadow:0 0 18px var(--hud-glow), 0 0 0 0 transparent}}[data-hud-anim=full] .hud-boot{animation:.55s ease-out both hud-boot;animation-delay:calc(var(--i,0) * 80ms)}[data-hud-anim=full] .hud-ring-turn{transform-origin:32px 32px;animation:40s linear infinite hud-spin}[data-hud-anim=full] .hud-profile.speaking .hud-ring-turn{animation-duration:7s}[data-hud-anim=full] .hud-profile.speaking .hud-emblem{animation:.9s ease-out hud-flare}[data-hud-anim=full] .hud-profile.busy .hud-ring-chase{opacity:1;animation:1.5s linear infinite hud-spin}[data-hud-anim=full] .hud-profile.listening .hud-emblem{box-shadow:0 0 26px var(--accent), inset 0 0 14px var(--hud-line-dim)}[data-hud-anim=full] .hud-digit{animation:.35s ease-out hud-roll}[data-hud-anim=full] .hud-colon{animation:1s step-end infinite hud-blink}[data-hud-anim=full] .hud-dot{animation:1s linear infinite hud-travel}[data-hud-anim=full] .hud-dial.playing .hud-needle{animation:3s linear infinite hud-spin}[data-hud-anim=full] .hud-dial.playing .hud-cover{animation:22s linear infinite hud-spin-keep}@keyframes hud-spin-keep{to{rotate:360deg}}[data-hud-anim=full] .hud-tab-main:focus-visible{animation:1.6s ease-in-out infinite hud-pulse}[data-hud-anim=reduced] .hud-boot,[data-hud-anim=reduced] .hud-digit,[data-hud-anim=reduced] .hud-colon,[data-hud-anim=reduced] .hud-dot{animation:none}[data-hud-anim=reduced] .hud-needle{display:none}[data-hud-anim=off] .hud *,[data-hud-anim=off] .hud{transition:none!important;animation:none!important}[data-hud-anim=off] .hud-tab:hover{transform:none}[data-hud-anim=off] .hud-needle{display:none}@media (prefers-reduced-motion:reduce){.hud *,.hud{transition:none!important;animation:none!important}.hud-tab:hover{transform:none}}@media (width<=900px){.hud-clock{left:12px;top:calc(max(56px, env(safe-area-inset-top) + 48px) + 76px)}.hud-launcher{top:calc(max(56px, env(safe-area-inset-top) + 48px) + 180px)}}@media (width<=640px){.hud-tag{min-width:120px}.hud-tag b{max-width:110px}.hud-day{font-size:2.2rem}.hud-launcher .hud-tab{min-width:0}.hud-launcher .hud-tab-main{grid-template-columns:26px;padding:7px 8px 9px}.hud-launcher .hud-tab-label,.hud-launcher .hud-tab-engaged,.hud-launcher .hud-kicker{display:none}.hud-music.mini{bottom:56px}.hud-music.full .hud-music-body{flex-direction:column;align-items:center}.hud-music.full .hud-music-left{flex-wrap:wrap;justify-content:center}.hud-playlist{width:100%;max-height:220px}.hud-levels{height:120px}}
1
+ :root{--accent:#3fd8ff;--warn:#ffb454;--bad:#ff6b7a;--ok:#5ef0b0;--ink:#d4ecf7;--muted:#7fa3b6;--glass:#06141c9e;--edge:color-mix(in srgb, var(--accent) 48%, transparent);--ui:"Segoe UI", system-ui, -apple-system, "Helvetica Neue", Arial, sans-serif;--mono:"Cascadia Mono", "SF Mono", Consolas, ui-monospace, monospace;--lightningcss-light: ;--lightningcss-dark:initial;color-scheme:dark}*{box-sizing:border-box}html,body,#root{height:100%;margin:0}body{color:var(--ink);font:16px/1.5 var(--ui);-webkit-tap-highlight-color:transparent;background:#000;overflow:hidden}button,input{font:inherit;color:inherit}button{cursor:pointer}:focus-visible{outline:2px solid var(--accent);outline-offset:2px}.stage{touch-action:manipulation;background:#000;position:fixed;inset:0;overflow:hidden}.ambient{pointer-events:none;background:radial-gradient(ellipse at 50% 55%, color-mix(in srgb, var(--accent) 10%, transparent), transparent 62%), linear-gradient(#3fd8ff0b 1px, transparent 1px) 0 0 / 64px 64px, linear-gradient(90deg, #3fd8ff0b 1px, transparent 1px) 0 0 / 64px 64px;position:absolute;inset:0;-webkit-mask-image:radial-gradient(#000 30%,#0000 78%);mask-image:radial-gradient(#000 30%,#0000 78%)}.presence{z-index:1;transition:inset .7s cubic-bezier(.2,.7,.2,1),width .7s,height .7s,opacity .5s;position:absolute}.presence-full{inset:0}.presence-corner{left:max(10px, env(safe-area-inset-left));bottom:max(52px, calc(env(safe-area-inset-bottom) + 42px));width:clamp(96px,16vw,190px);height:clamp(96px,16vw,190px)}.objects{pointer-events:none;position:absolute;inset:0}.objects-stack{pointer-events:auto;padding:max(56px, env(safe-area-inset-top)) 14px 140px;flex-direction:column;gap:12px;display:flex;overflow-y:auto}.auto-grid{pointer-events:none;padding:max(24px, env(safe-area-inset-top)) 24px 24px clamp(120px, 20vw, 230px);grid-template-columns:repeat(auto-fit,minmax(min(280px,100%),1fr));align-content:safe center;align-items:start;gap:12px;display:grid;position:absolute;inset:0;overflow-y:auto}.auto-grid>.obj{pointer-events:auto}.objects-stack>.auto-grid{flex-direction:column;padding:0;display:flex;position:static;overflow:visible}.obj.leaving{pointer-events:none;animation:.35s forwards leave}@keyframes leave{to{opacity:0;transform:scale(.96)translateY(-6px)}}@media (prefers-reduced-motion:reduce){.obj.leaving{animation:none}}.glass{background:var(--glass);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);border:1px solid var(--edge);box-shadow:0 0 22px color-mix(in srgb, var(--accent) 16%, transparent), inset 0 0 28px #3fd8ff0d;clip-path:polygon(0 0,calc(100% - 14px) 0,100% 14px,100% 100%,14px 100%,0 calc(100% - 14px))}.obj{pointer-events:auto;min-width:0;padding:16px 18px;animation:.45s both appear;overflow:auto}.obj.alert{border-color:var(--warn)}.overlay-layer{z-index:40;pointer-events:none;place-items:center;padding:16px;display:grid;position:fixed;inset:0}.overlay-backdrop{-webkit-backdrop-filter:blur(3px);backdrop-filter:blur(3px);pointer-events:auto;background:#02080ca8;animation:.3s both appear;position:absolute;inset:0}.obj.overlay{z-index:1;width:min(760px,94vw);max-height:80vh;box-shadow:0 0 40px color-mix(in srgb, var(--accent) 30%, transparent);position:relative}@keyframes appear{0%{opacity:0;transform:translateY(8px)scale(.985)}}.obj-close{width:44px;height:44px;color:var(--muted);background:0 0;border:0;font-size:1.5rem;line-height:1;position:absolute;top:2px;right:6px}.obj-close:hover{color:var(--accent)}.obj-title{letter-spacing:.16em;text-transform:uppercase;color:var(--accent);margin:0 36px 8px 0;font-size:.78rem;font-weight:600}.obj-md>:first-child{margin-top:0}.obj-md>:last-child{margin-bottom:0}.obj-md a{color:var(--accent)}.obj-md code{font-family:var(--mono);background:#3fd8ff1a;padding:0 4px;font-size:.9em}.obj-stat{gap:2px;display:grid}.obj-label{letter-spacing:.16em;text-transform:uppercase;color:var(--muted);font-size:.78rem}.obj-value{font-variant-numeric:tabular-nums;font-size:clamp(2rem,6vw,3.6rem);font-weight:300;line-height:1.05}.obj-value small{color:var(--muted);margin-left:4px;font-size:.4em}.obj-delta{color:var(--ok);font-size:.9rem}.obj-list{gap:4px;margin:0;padding-left:1.1rem;display:grid}.obj-list .done{color:var(--muted);text-decoration:line-through}.obj-table-wrap{overflow-x:auto}.obj-table{border-collapse:collapse;width:100%;font-size:.92rem}.obj-table th{text-align:left;letter-spacing:.14em;text-transform:uppercase;color:var(--accent);font-size:.72rem;font-weight:600}.obj-table th,.obj-table td{font-variant-numeric:tabular-nums;border-bottom:1px solid #3fd8ff2e;padding:6px 10px}.obj-code{font:.86rem/1.5 var(--mono);margin:0;overflow:auto}.obj-empty{color:var(--muted);margin:0}.integration-steps{color:var(--muted);gap:4px;margin:4px 0 10px;padding-left:1.2rem;font-size:.86rem;display:grid}.integration-steps li.done{color:var(--ok)}.obj-doc{max-height:70vh;overflow:auto}.obj-doc h1,.obj-doc h2,.obj-doc h3,.obj-doc h4{color:var(--accent);letter-spacing:.06em;font-weight:500}.obj-doc table{border-collapse:collapse;width:100%;font-size:.92rem}.obj-doc th,.obj-doc td{border:1px solid color-mix(in srgb, var(--accent) 22%, transparent);text-align:left;padding:5px 9px}.obj-doc th{color:var(--accent);letter-spacing:.14em;text-transform:uppercase;font-size:.72rem;font-weight:500}.obj-doc pre{border:1px solid color-mix(in srgb, var(--accent) 22%, transparent);font:.86rem/1.5 var(--mono);background:#3fd8ff0d;padding:8px 10px;overflow:auto}.obj-doc blockquote{border-left:2px solid var(--edge);color:var(--muted);margin:.6em 0;padding-left:12px}.obj-progress{gap:6px;min-width:0;display:grid}.obj-progress-head{justify-content:space-between;align-items:baseline;gap:12px;display:flex}.obj-progress-pct{font:1.1rem var(--mono);font-variant-numeric:tabular-nums}.obj-progress-bar{border:1px solid var(--edge);background:#3fd8ff12;height:8px}.obj-progress-bar i{background:var(--accent);height:100%;box-shadow:0 0 10px var(--accent);transition:width .4s;display:block}.obj-progress-detail{color:var(--muted);font-size:.82rem}.obj-checklist{gap:6px;margin:0;padding:0;list-style:none;display:grid}.obj-checklist li{align-items:center;gap:10px;display:flex}.obj-checklist .box{border:1px solid var(--accent);width:16px;height:16px;color:var(--accent);flex:none;place-items:center;font-size:.8rem;display:inline-grid}.obj-checklist .done{color:var(--muted)}.obj-checklist .done span:last-child{text-decoration:line-through}.obj-kv{gap:4px;margin:0;display:grid}.obj-kv>div{border-bottom:1px solid color-mix(in srgb, var(--accent) 16%, transparent);justify-content:space-between;gap:18px;padding:3px 0;display:flex}.obj-kv dt{color:var(--muted);letter-spacing:.14em;text-transform:uppercase;font-size:.78rem}.obj-kv dd{font-family:var(--mono);font-variant-numeric:tabular-nums;text-align:right;margin:0}.obj-countdown{justify-items:center;gap:2px;display:grid}.obj-countdown-time{font:300 clamp(2rem, 6vw, 3.4rem) var(--mono);font-variant-numeric:tabular-nums;text-shadow:0 0 14px var(--accent)}.obj-countdown.done .obj-countdown-time{color:var(--warn);text-shadow:0 0 14px var(--warn)}.obj-media{flex-direction:column;gap:6px;width:100%;max-height:100%;display:flex}.obj-media img,.obj-media video{object-fit:contain;border:1px solid var(--edge);background:#050b10;max-width:100%;max-height:50vh;margin:0 auto;display:block}.obj-pdf iframe{border:1px solid var(--edge);background:#050b10;width:100%;min-width:0;height:min(520px,62vh)}.obj-open{color:var(--accent);letter-spacing:.1em;text-transform:uppercase;font-size:.82rem}.obj-gallery-bar{justify-content:space-between;align-items:center;gap:10px;display:flex}.obj-gallery-bar span{color:var(--ink);justify-items:center;font-size:.86rem;display:grid}.obj-gallery-bar small{color:var(--muted);font-family:var(--mono)}.obj-gallery-bar button{border:1px solid var(--edge);min-width:44px;min-height:44px;color:var(--accent);cursor:pointer;background:0 0;font-size:1.3rem}.obj-gallery-bar button:disabled{opacity:.3;cursor:default}.obj-group{align-items:start;gap:14px;display:grid}.obj-group-grid{grid-template-columns:repeat(auto-fit,minmax(170px,1fr))}.obj-group-row{grid-auto-columns:minmax(150px,1fr);grid-auto-flow:column;overflow-x:auto}.obj-group-column{grid-template-columns:1fr}.obj-part{border:1px solid color-mix(in srgb, var(--accent) 20%, transparent);background:#3fd8ff0a;min-width:0;padding:8px 10px}.obj-tabs{border-bottom:1px solid var(--edge);gap:2px;margin-bottom:8px;display:flex;overflow-x:auto}.obj-tabs button{min-height:40px;color:var(--muted);letter-spacing:.14em;text-transform:uppercase;cursor:pointer;white-space:nowrap;background:0 0;border:0;padding:8px 14px;font-size:.78rem}.obj-tabs button.on{color:var(--accent);box-shadow:inset 0 -2px 0 var(--accent);text-shadow:0 0 8px var(--accent)}.obj-chart{width:100%;height:auto;display:block}.obj-chart .grid{stroke:#3fd8ff24;stroke-width:1px}.obj-chart .tick{fill:var(--muted);font:10px var(--mono);font-variant-numeric:tabular-nums}.legend{color:var(--muted);flex-wrap:wrap;gap:6px 14px;margin:6px 0 0;padding:0;font-size:.8rem;list-style:none;display:flex}.legend i{width:10px;height:10px;margin-right:6px;display:inline-block}.obj-gauge{justify-items:center;display:grid}.obj-gauge svg{width:min(100%,260px);height:auto}.obj-gauge .track{stroke:#3fd8ff26}.obj-gauge .value{stroke:var(--accent);filter:drop-shadow(0 0 6px var(--accent))}.obj-gauge.gauge-warn .value{stroke:var(--warn);filter:drop-shadow(0 0 6px var(--warn))}.obj-gauge.gauge-crit .value{stroke:var(--bad);filter:drop-shadow(0 0 6px var(--bad))}.gauge-read{align-items:baseline;gap:4px;margin-top:-62px;display:flex}.gauge-value{font-variant-numeric:tabular-nums;font-size:clamp(1.8rem,5vw,2.8rem);font-weight:300}.gauge-unit{color:var(--muted)}.obj-gauge .obj-label{margin-top:18px}.obj-timeline{border-left:1px solid var(--edge);gap:14px;margin:8px 0 0;padding:0 0 0 20px;list-style:none;display:grid}.obj-timeline li{gap:2px;display:grid;position:relative}.obj-timeline li:before{content:"";background:var(--accent);width:9px;height:9px;box-shadow:0 0 8px var(--accent);border-radius:50%;position:absolute;top:.5em;left:-25px}.obj-timeline time{font:.75rem/1.3 var(--mono);color:var(--accent)}.obj-timeline span{color:var(--muted);font-size:.9rem}.obj-graph{width:100%;height:auto;max-height:70vh;margin:0 auto;display:block}.obj[style*=" height:"] .obj-graph{max-height:calc(100% - 32px)}.obj-graph .edge{stroke:color-mix(in srgb, var(--accent) 55%, transparent);stroke-width:1.4px}.obj-graph .arrow{fill:var(--accent)}.obj-graph .node{fill:#3fd8ff26;stroke:var(--accent);stroke-width:1.5px}.obj-graph .node-label{fill:var(--ink);font:10px var(--ui)}.obj-graph .edge-label{fill:var(--muted);font:9px var(--ui)}.captions{z-index:20;left:50%;bottom:max(7%, env(safe-area-inset-bottom));text-align:center;pointer-events:none;text-shadow:0 0 18px #000,0 0 4px #000;text-wrap:balance;width:min(780px,100% - 32px);margin:0;font-size:clamp(1.1rem,2.6vw,1.6rem);font-weight:300;position:absolute;transform:translate(-50%)}.captions.done{animation:1.4s 8s forwards fadeOut}@keyframes fadeOut{to{opacity:0}}.command-bar{z-index:30;left:50%;bottom:max(14px, env(safe-area-inset-bottom));background:var(--glass);border:1px solid var(--edge);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);gap:8px;width:min(640px,100% - 24px);padding:8px;display:flex;position:absolute;transform:translate(-50%)}.command-bar input{background:0 0;border:0;outline:none;flex:1;min-height:44px;padding:0 10px;font-size:1.05rem}.command-bar button{border:1px solid var(--edge);background:0 0;min-width:44px;min-height:44px}.conn-badge{top:max(10px, env(safe-area-inset-top));font:500 .78rem var(--mono);letter-spacing:.08em;color:var(--warn);border:1px solid var(--warn);background:#0009;padding:6px 12px;position:absolute;right:12px}.mic-indicator{left:50%;top:max(12px, env(safe-area-inset-top));font:500 .82rem var(--mono);letter-spacing:.1em;text-transform:uppercase;color:#ffd9a0;border:1px solid var(--warn);background:#000000c7;align-items:center;gap:10px;padding:8px 16px;display:flex;position:absolute;transform:translate(-50%)}.mic-indicator i{background:var(--bad);width:10px;height:10px;box-shadow:0 0 10px var(--bad);border-radius:50%;animation:1s ease-in-out infinite mic-pulse}.mic-transcribing i{background:var(--warn);box-shadow:0 0 10px var(--warn)}@keyframes mic-pulse{50%{opacity:.35}}@media (prefers-reduced-motion:reduce){.mic-indicator i{animation:none}}.toasts{top:max(48px, env(safe-area-inset-top));gap:6px;width:min(420px,100% - 24px);display:grid;position:absolute;left:50%;transform:translate(-50%)}.toast{border:1px solid var(--edge);background:#000000d1;padding:10px 14px;font-size:.92rem}.toast-warn{border-color:var(--warn);color:#ffd9a0}.toast-error{border-color:var(--bad);color:#ffc2c9}.approval{border-color:var(--warn);background:#020c12eb;width:min(460px,100% - 24px);max-height:calc(100% - 24px);padding:20px;position:absolute;top:50%;left:50%;overflow:auto;transform:translate(-50%,-50%);box-shadow:0 0 0 100vmax #0000008c,0 0 30px #ffb45440}.plugins{flex-direction:column;width:min(560px,100% - 24px);display:flex;overflow:hidden}.plugins-body{min-height:0;padding-right:4px;overflow-y:auto}.plugins-heading{letter-spacing:.14em;text-transform:uppercase;color:var(--muted);margin:14px 0 6px;font-size:.78rem}.plugin-list{gap:8px;margin:0;padding:0;list-style:none;display:grid}.plugin-list li{background:#ffffff0a;flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 10px;padding:8px 10px;display:flex}.plugin-info{flex:180px;min-width:0}.plugin-info .auth-note{font-size:.82rem}.plugin-actions{flex-wrap:wrap;gap:6px;display:flex}.plugin-actions button{border:1px solid var(--edge);background:0 0;padding:0 12px}.obj-sandbox{flex-direction:column;gap:6px;width:100%;min-width:min(560px,80vw);height:min(420px,60vh);display:flex}.obj-sandbox iframe{border:1px solid var(--edge);background:#050b10;flex:1;width:100%;min-height:200px}.camera-indicator{border-color:var(--bad);color:#ffc2c9;letter-spacing:.12em;text-transform:uppercase;background:#020c12e6;align-items:center;gap:10px;padding:6px 12px 6px 6px;font-size:.8rem;display:flex;position:absolute;bottom:12px;right:12px}.camera-indicator video{object-fit:cover;background:#000;width:72px;height:54px}.camera-indicator span:before{content:"";background:var(--bad);border-radius:50%;width:8px;height:8px;margin-right:8px;display:inline-block}.challenge,.enroll{border-color:var(--accent);box-shadow:0 0 0 100vmax #0000008c,0 0 30px #3fd8ff40}.challenge .approval-title,.enroll .approval-title{color:var(--accent)}.approval-head{align-items:center;gap:10px;display:flex}.approval-title{letter-spacing:.18em;text-transform:uppercase;color:var(--warn);font-size:.8rem}.tier{font:600 .74rem var(--mono);border:1px solid;padding:2px 8px}.tier-T2{color:var(--warn)}.tier-T3{color:var(--bad)}.approval-summary{font:.95rem/1.5 var(--mono);word-break:break-all;background:#ffffff0a;max-height:40vh;margin:14px 0;padding:10px 12px;overflow:auto}.approval-actions{flex-wrap:wrap;gap:8px;margin-top:14px;display:flex}.approval-actions button,.owner-menu button,.auth button{border:1px solid var(--edge);letter-spacing:.04em;background:0 0;padding:0 16px}button.primary{background:color-mix(in srgb, var(--accent) 22%, transparent);border-color:var(--accent)}button.danger{border-color:var(--bad);color:#ffc2c9}button:disabled{opacity:.4;cursor:not-allowed}.pinpad{justify-items:center;gap:8px;display:grid}.pin-dots{letter-spacing:.4em;min-height:1.6em;color:var(--accent);font-size:1.6rem}.pin-keys{grid-template-columns:repeat(3,64px);gap:8px;display:grid}.pin-keys button{border:1px solid var(--edge);background:#3fd8ff0d;font-size:1.2rem}.owner-menu{top:max(60px, env(safe-area-inset-top));background:#020c12f0;gap:8px;width:220px;padding:12px;display:grid;left:12px}.boot{background:#000;height:100%}.auth{gap:8px;width:min(380px,100% - 28px);padding:24px;display:grid;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%)}.auth h1{letter-spacing:.3em;text-transform:uppercase;color:var(--accent);margin:0 0 6px;font-size:1.1rem;font-weight:300}.auth label{letter-spacing:.12em;text-transform:uppercase;color:var(--muted);margin-top:6px;font-size:.78rem}.auth input{border:1px solid var(--edge);background:#ffffff0a;padding:0 12px}.auth button{margin-top:12px}.auth-note{color:var(--muted);margin:0;font-size:.9rem}.auth-error{color:#ffc2c9;margin:4px 0 0;font-size:.9rem}@media (width<=599px){.presence-full{inset:0}.captions{bottom:max(11%, env(safe-area-inset-bottom))}}@media (prefers-reduced-motion:reduce){.obj,.presence{transition:none;animation:none}}.status-badge{left:12px;bottom:max(12px, env(safe-area-inset-bottom));font:500 .78rem var(--mono);letter-spacing:.08em;color:var(--ink);border:1px solid var(--edge);background:#0000008c;align-items:center;gap:9px;max-width:min(60vw,360px);padding:6px 12px;display:flex;position:absolute}.status-badge span{text-overflow:ellipsis;white-space:nowrap;overflow:hidden}.status-badge i{background:var(--muted);border-radius:50%;flex:none;width:9px;height:9px}.status-idle i{background:var(--ok);box-shadow:0 0 8px var(--ok)}.status-working i,.status-speaking i{background:var(--accent);box-shadow:0 0 10px var(--accent);animation:1s ease-in-out infinite mic-pulse}.status-listening i{background:var(--bad);box-shadow:0 0 10px var(--bad);animation:1s ease-in-out infinite mic-pulse}.status-waiting{border-color:var(--warn);color:#ffd9a0}.status-waiting i{background:var(--warn);box-shadow:0 0 10px var(--warn);animation:1s ease-in-out infinite mic-pulse}.status-offline{border-color:var(--warn);color:var(--warn)}.status-offline i{background:var(--warn)}@media (prefers-reduced-motion:reduce){.status-badge i{animation:none!important}}.clock{right:12px;bottom:max(12px, env(safe-area-inset-bottom));text-align:right;color:var(--muted);line-height:1.15;font-family:var(--mono);pointer-events:none;position:absolute}.clock b{color:var(--ink);letter-spacing:.06em;font-size:1.15rem;font-weight:500;display:block}.clock span{letter-spacing:.1em;text-transform:uppercase;font-size:.7rem}.settings{flex-direction:column;width:min(520px,100% - 24px);max-height:calc(100% - 24px);display:flex}.settings-body{gap:6px;min-height:0;padding-right:4px;display:grid;overflow-y:auto}.settings-field{gap:3px;display:grid}.settings-field>span{letter-spacing:.1em;text-transform:uppercase;color:var(--muted);font-size:.74rem}.settings-field input:not([type=range]):not([type=checkbox]),.settings-field select{border:1px solid var(--edge);color:var(--ink);min-height:40px;font:inherit;background:#ffffff0a;padding:0 10px}.settings-field select option{background:#06141c}.settings-check{align-items:center;gap:10px;min-height:40px;display:flex}.slash-list{border:1px solid var(--edge);background:#020c12f5;max-height:40vh;margin:0;padding:4px;list-style:none;position:absolute;bottom:calc(100% + 6px);left:0;right:0;overflow-y:auto}.slash-list li{cursor:pointer;align-items:baseline;gap:10px;padding:7px 10px;display:flex}.slash-list li.on,.slash-list li:hover{background:color-mix(in srgb, var(--accent) 18%, transparent)}.slash-list b{font:600 .9rem var(--mono);color:var(--accent)}.slash-list i{font:.78rem var(--mono);color:var(--warn);font-style:normal}.slash-list span{color:var(--muted);font-size:.82rem}.movable{position:absolute}.movable[data-panel=status],.movable[data-panel=clock]{cursor:grab;touch-action:none;pointer-events:auto}.movable:focus-visible{outline:2px solid var(--accent);outline-offset:2px}.panel{resize:both;flex-direction:column;width:clamp(260px,28vw,420px);min-width:220px;min-height:140px;max-height:80vh;padding:0;display:flex;overflow:hidden}.panel-chat{height:62vh}.panel-tasks{width:clamp(240px,26vw,360px);height:40vh}.panel-head{cursor:grab;touch-action:none;border-bottom:1px solid var(--edge);-webkit-user-select:none;user-select:none;justify-content:space-between;align-items:center;gap:10px;padding:8px 12px;display:flex}.panel-head .obj-close{position:static}.chat-lines{flex:1;align-content:start;gap:8px;min-height:0;padding:10px 12px;display:grid;overflow-y:auto}.chat-line{white-space:pre-wrap;overflow-wrap:anywhere;max-width:92%;margin:0;padding:7px 10px;font-size:.9rem}.chat-user{background:color-mix(in srgb, var(--accent) 18%, transparent);border:1px solid var(--edge);justify-self:end}.chat-assistant{background:#ffffff0d;justify-self:start}.chat-form{border-top:1px solid var(--edge);gap:6px;padding:8px;display:flex}.chat-form input{border:1px solid var(--edge);min-width:0;color:var(--ink);min-height:40px;font:inherit;background:#ffffff0a;flex:1;padding:0 10px}.chat-form button{border:1px solid var(--edge);color:var(--ink);background:0 0;min-height:40px;padding:0 14px}.task-body{flex:1;min-height:0;padding:10px 12px;overflow-y:auto}.task-list{gap:8px;margin:0;padding:0;list-style:none;display:grid}.task-list li{border-left:3px solid var(--accent);background:#ffffff0a;gap:2px;padding:8px 10px;display:grid}.task-list li.overdue{border-left-color:var(--bad)}.task-title{overflow-wrap:anywhere;font-size:.95rem}.task-due{font:.75rem var(--mono);color:var(--muted)}.task-list li.overdue .task-due{color:var(--bad)}@media (width<=600px){.panel{resize:none;width:calc(100% - 24px);left:12px!important}.panel-chat{height:52vh;bottom:56px;top:auto!important}.panel-tasks{height:30vh;top:56px!important}}.help{flex-direction:column;width:min(560px,100% - 24px);max-height:calc(100% - 24px);display:flex}.help-list{gap:4px;min-height:0;margin:8px 0;display:grid;overflow-y:auto}.help-row{border-bottom:1px solid #ffffff0f;grid-template-columns:minmax(130px,38%) 1fr;gap:12px;padding:6px 4px;display:grid}.help-row dt{font:600 .9rem var(--mono);color:var(--accent);overflow-wrap:anywhere}.help-row dt i{color:var(--warn);font-style:normal;font-weight:400}.help-row dd{color:var(--ink);margin:0;font-size:.9rem}@media (width<=600px){.help-row{grid-template-columns:1fr;gap:2px}}.connectors{width:min(600px,100% - 24px);max-height:calc(100% - 24px);overflow-y:auto}.connector-form{gap:8px;display:grid}.connector-form textarea,.settings-field textarea{border:1px solid var(--edge);color:var(--ink);font:.85rem var(--mono);resize:vertical;background:#ffffff0a;padding:8px 10px}.connector-steps{color:var(--muted);gap:4px;margin:0;padding-left:20px;font-size:.88rem;display:grid}.connector-warning{border-left:3px solid var(--warn);color:#ffd9a0;padding-left:10px}.conn-status{font:.74rem var(--mono)}.conn-ready{color:var(--ok)}.conn-error{color:var(--bad)}.conn-connecting{color:var(--warn)}.conn-off{color:var(--muted)}.settings-wide{width:min(980px,100% - 24px);height:min(720px,100% - 24px)}.settings-layout{flex:1;grid-template-columns:190px 1fr;gap:16px;min-height:0;margin-top:8px;display:grid}.settings-tabs{align-content:start;gap:6px;display:grid}.settings-tab{text-align:left;color:var(--ink);background:0 0;border:1px solid #0000;gap:2px;padding:10px 12px;display:grid}.settings-tab small{color:var(--muted);font-size:.74rem}.settings-tab:hover{background:#ffffff0d}.settings-tab.on{border-color:var(--accent);background:color-mix(in srgb, var(--accent) 16%, transparent)}.settings-wide .settings-body{align-content:start;padding-right:8px}@media (width<=700px){.settings-wide{height:calc(100% - 24px)}.settings-layout{grid-template-columns:1fr;gap:8px}.settings-tabs{grid-auto-columns:1fr;grid-auto-flow:column;overflow-x:auto}.settings-tab small{display:none}}.look-tab{grid-template-columns:minmax(220px,300px) 1fr;align-items:start;gap:18px;display:grid}.look-side{gap:10px;display:grid;position:sticky;top:0}.look-controls{gap:6px;min-width:0;display:grid}@media (width<=860px){.look-tab{grid-template-columns:1fr}.look-side{position:static}}.look-preview{border:1px solid var(--edge);background:#000;height:230px;position:relative;overflow:hidden}.look-preview-glow{background:radial-gradient(ellipse at 50% 55%, color-mix(in srgb, var(--accent) 22%, transparent), transparent 65%);position:absolute;inset:0}.look-preview-stage{position:absolute;inset:0}.look-preview-caption{text-align:center;text-shadow:0 0 10px #000;margin:0;position:absolute;bottom:8px;left:8px;right:8px}.look-preview .presence-full{inset:0}.theme-grid{grid-template-columns:repeat(auto-fill,minmax(118px,1fr));gap:8px;display:grid}.theme-card{border:1px solid var(--edge);color:var(--ink);text-align:left;background:#ffffff08;justify-items:start;gap:1px;padding:10px;display:grid}.theme-card i{background:var(--swatch);width:22px;height:22px;box-shadow:0 0 12px var(--swatch);border-radius:50%;margin-bottom:4px}.theme-card small{color:var(--muted);font-size:.72rem}.theme-card.on,.style-choice.on{border-color:var(--accent);background:color-mix(in srgb, var(--accent) 18%, transparent)}.style-row{grid-template-columns:repeat(3,1fr);gap:8px;display:grid}.style-choice{border:1px solid var(--edge);color:var(--ink);text-align:left;background:#ffffff08;gap:2px;padding:10px;display:grid}.style-choice small{color:var(--muted);font-size:.72rem}.swatch-row{flex-wrap:wrap;align-items:center;gap:8px;display:flex}.swatch{border:2px solid #0000;border-radius:50%;width:32px;height:32px;min-height:32px;padding:0}.swatch.on{box-shadow:0 0 0 2px var(--accent);border-color:#fff}.swatch-custom{color:var(--muted);align-items:center;gap:6px;font-size:.8rem;display:flex}.swatch-custom input[type=color]{border:1px solid var(--edge);background:0 0;width:40px;height:32px;padding:0}.captions-small{font-size:clamp(.9rem,2vw,1.15rem)}.captions-medium{font-size:clamp(1.1rem,2.6vw,1.6rem)}.captions-large{font-size:clamp(1.4rem,3.6vw,2.3rem)}.voice-hear{flex-wrap:wrap;align-items:center;gap:12px;display:flex}.connector-command{border:1px solid var(--edge);font:.85rem var(--mono);-webkit-user-select:all;user-select:all;background:#ffffff0d;margin:0;padding:8px 10px;overflow-x:auto}html,body{overscroll-behavior:none}@media (pointer:coarse){.stage{-webkit-touch-callout:none;-webkit-user-select:none;user-select:none}}input,textarea,select,.connector-command{-webkit-user-select:text;user-select:text}.owner-menu{max-height:calc(100dvh - 80px);overflow-y:auto}.touch-controls{z-index:25;left:0;right:0;bottom:max(14px, env(safe-area-inset-bottom));pointer-events:none;justify-content:center;align-items:flex-end;gap:26px;display:flex;position:absolute}.touch-controls>*{pointer-events:auto}.touch-talk{justify-items:center;gap:6px;display:grid}.touch-hint{max-width:70vw;font:500 .74rem var(--mono);letter-spacing:.06em;color:var(--muted);text-align:center;text-shadow:0 0 6px #000,0 0 2px #000;padding:2px 10px}.touch-mic,.touch-side{border:1px solid var(--edge);color:var(--ink);background:var(--glass);-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);touch-action:none;-webkit-user-select:none;user-select:none;-webkit-touch-callout:none;-webkit-tap-highlight-color:transparent;border-radius:50%;place-items:center;padding:0;display:grid}.touch-mic{border-color:var(--accent);width:76px;height:76px;box-shadow:0 0 22px color-mix(in srgb, var(--accent) 30%, transparent)}.touch-mic.on{background:color-mix(in srgb, var(--bad) 40%, transparent);border-color:var(--bad);box-shadow:0 0 28px var(--bad);animation:1s ease-in-out infinite mic-pulse}.touch-side{touch-action:manipulation;width:52px;height:52px;margin-bottom:12px}@media (prefers-reduced-motion:reduce){.touch-mic.on{animation:none}}@media (pointer:coarse){.captions{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 150px)}.status-badge,.clock{bottom:max(8px, env(safe-area-inset-bottom))}.presence-corner{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 70px)}}@media (width<=600px) and (pointer:coarse){.panel-chat{bottom:calc(max(14px, env(safe-area-inset-bottom)) + 150px);height:min(48vh,100dvh - 260px)}.objects-stack{padding-bottom:190px}}.elsewhere{z-index:3000;-webkit-backdrop-filter:blur(6px);backdrop-filter:blur(6px);background:#000000c7;place-items:center;padding:16px;display:grid;position:fixed;inset:0}.elsewhere-card{border:1px solid var(--edge);background:var(--glass);max-width:380px;color:var(--ink);text-align:center;border-radius:16px;padding:24px}.elsewhere-card h2{margin:0 0 10px;font-size:1.15rem}.elsewhere-card p{color:var(--muted);margin:0 0 18px;line-height:1.45}.elsewhere-btn{border:1px solid var(--accent);background:color-mix(in srgb, var(--accent) 25%, transparent);min-height:48px;color:var(--ink);font:600 1rem var(--mono);cursor:pointer;border-radius:24px;padding:0 28px}.obj-grip{cursor:grab;touch-action:none;border-radius:8px 8px 0 0;height:22px;position:absolute;top:0;left:0;right:92px}.obj-grip:before{content:"";background:var(--muted);opacity:.35;border-radius:2px;width:34px;height:3px;margin-left:-17px;transition:opacity .15s;position:absolute;top:8px;left:50%}.obj:hover .obj-grip:before,.obj-grip:focus-visible:before{opacity:.9}.obj-grip:focus-visible{outline:2px solid var(--accent);outline-offset:-2px}.obj.dragging{cursor:grabbing;box-shadow:0 0 0 1px var(--accent), 0 8px 30px #00000080;-webkit-user-select:none;user-select:none;transition:none;animation:none}.obj-pin{width:44px;height:44px;color:var(--muted);opacity:.55;background:0 0;border:0;place-items:center;display:grid;position:absolute;top:2px;right:50px}.obj:hover .obj-pin,.obj-pin.on,.obj-pin:focus-visible{opacity:1}.obj-pin.on,.obj-pin:hover{color:var(--accent)}.obj.pinned{border-color:color-mix(in srgb, var(--accent) 55%, transparent)}.obj-resize{cursor:nwse-resize;touch-action:none;opacity:0;background:linear-gradient(135deg, transparent 55%, var(--accent) 56%, var(--accent) 64%, transparent 65%, transparent 76%, var(--accent) 77%, var(--accent) 85%, transparent 86%);width:22px;height:22px;transition:opacity .15s;position:absolute;bottom:0;right:0}.obj:hover .obj-resize,.obj.dragging .obj-resize{opacity:.7}@media (pointer:coarse){.obj-pin{opacity:1}.obj-resize{opacity:.7;width:30px;height:30px}.obj-grip{height:30px}.obj-grip:before{opacity:.7;top:12px}}.obj-media.obj-media-fill{height:100%;min-height:min(360px,60vh)}.obj-media-fill .obj-youtube{border:1px solid var(--edge);background:#000;flex:auto;width:100%;height:100%;min-height:0;display:block}.profile-badge{top:max(56px, calc(env(safe-area-inset-top) + 48px));border:1px solid var(--edge);background:var(--glass);-webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);color:var(--ink);cursor:grab;touch-action:none;-webkit-user-select:none;user-select:none;border-radius:12px;align-items:center;gap:8px;padding:6px 12px 6px 8px;display:flex;position:fixed;left:12px}.profile-shield{color:var(--accent);flex:none}.profile-shield.member{color:#8ff0b0}.profile-shield.guest{color:var(--warn)}.profile-text{min-width:0;line-height:1.15;display:grid}.profile-text b{text-overflow:ellipsis;white-space:nowrap;max-width:130px;font-size:.86rem;font-weight:600;overflow:hidden}.profile-text small{font:500 .64rem var(--mono);letter-spacing:.1em;text-transform:uppercase;color:var(--muted)}@media (width<=600px){.profile-text{display:none}.profile-badge{padding:4px 6px}}.hud{--hud-line:color-mix(in srgb, var(--accent) 62%, transparent);--hud-line-dim:color-mix(in srgb, var(--accent) 26%, transparent);--hud-glow:color-mix(in srgb, var(--accent) 42%, transparent);--hud-bg:#030d14d1;--hud-bg-hi:#081e2ae6;--cut:10px;color:var(--ink);font-family:var(--mono);-webkit-user-select:none;user-select:none}.hud-cut{background:var(--hud-line);clip-path:polygon(0 0, calc(100% - var(--cut)) 0, 100% var(--cut), 100% 100%, var(--cut) 100%, 0 calc(100% - var(--cut)));position:relative}.hud-cut:before{content:"";background:var(--hud-bg);clip-path:polygon(0 0, calc(100% - var(--cut) + 1px) 0, 100% calc(var(--cut) - 1px), 100% 100%, calc(var(--cut) - 1px) 100%, 0 calc(100% - var(--cut) + 1px));z-index:0;transition:background .14s ease-out;position:absolute;inset:1px}.hud-cut>*{z-index:1;position:relative}.hud-kicker{letter-spacing:.22em;text-transform:uppercase;color:var(--muted);margin:0 0 6px 2px;font-size:.62rem}.hud-profile{top:max(56px, calc(env(safe-area-inset-top) + 48px));cursor:grab;touch-action:none;align-items:center;display:flex;position:fixed;left:12px}.hud-emblem{z-index:2;background:radial-gradient(circle, var(--hud-bg-hi), var(--hud-bg));width:64px;height:64px;box-shadow:0 0 18px var(--hud-glow), inset 0 0 12px var(--hud-line-dim);border-radius:50%;flex:none;place-items:center;display:grid;position:relative}.hud-emblem-svg{color:var(--accent)}.hud-emblem-svg.member{color:#8ff0b0}.hud-emblem-svg.guest{color:var(--warn)}.hud-ring-chase{opacity:0;transform-origin:32px 32px}.hud-tag{--cut:9px;gap:1px;min-width:176px;margin-left:-14px;padding:6px 18px 7px 24px;line-height:1.15;display:grid}.hud-tag b{letter-spacing:.02em;text-overflow:ellipsis;white-space:nowrap;max-width:190px;font-size:.95rem;font-weight:600;overflow:hidden}.hud-tag small{letter-spacing:.16em;text-transform:uppercase;color:var(--muted);font-size:.62rem}.hud-tag .hud-tag-top{color:var(--accent);letter-spacing:.2em}.hud-tag:after{content:"";background:var(--accent);width:2px;box-shadow:0 0 8px var(--hud-glow);z-index:1;position:absolute;top:8px;bottom:8px;left:10px}.hud-profile.member .hud-tag:after{background:#8ff0b0}.hud-profile.guest .hud-tag:after{background:var(--warn)}.hud-clock{top:max(56px, calc(env(safe-area-inset-top) + 48px));cursor:grab;touch-action:none;text-align:left;position:fixed;left:332px}.hud-clock time{align-items:flex-end;gap:14px;display:flex}.hud-date{justify-items:start;line-height:1;display:grid}.hud-day{letter-spacing:.02em;text-shadow:0 0 14px var(--hud-glow);font-size:3.1rem;font-weight:700;display:flex}.hud-month{background:var(--accent);color:#031018;letter-spacing:.22em;text-transform:uppercase;clip-path:polygon(0 0,100% 0,calc(100% - 6px) 100%,0 100%);margin-top:2px;padding:1px 8px 1px 6px;font-size:.7rem;font-weight:700}.hud-weekday{letter-spacing:.2em;text-transform:uppercase;color:var(--muted);margin-top:3px;font-size:.64rem}.hud-time-block{gap:5px;min-width:150px;padding-bottom:4px;display:grid}.hud-clock-time{letter-spacing:.06em;align-items:baseline;font-size:1.55rem;display:flex}.hud-colon{color:var(--accent);margin:0 1px;font-style:normal}.hud-period{letter-spacing:.2em;color:var(--muted);margin-left:6px;font-size:.62rem}.hud-line{background:linear-gradient(90deg, var(--hud-line), transparent);height:1px;position:relative}.hud-line:after{content:"";border:1px solid var(--accent);background:var(--hud-bg);border-radius:50%;width:7px;height:7px;position:absolute;top:-3px;left:-3px}.hud-dot{background:var(--accent);width:5px;height:5px;box-shadow:0 0 8px var(--accent);border-radius:50%;position:absolute;top:-2px;left:0}.hud-digit{display:inline-block}.hud-launcher{left:12px;top:calc(max(56px, env(safe-area-inset-top) + 48px) + 86px);cursor:grab;touch-action:none;position:fixed}.hud-stack{gap:6px;margin:0;padding:0;list-style:none;display:grid}.hud-tab{--cut:9px;align-items:stretch;min-width:176px;transition:transform .14s ease-out,filter .14s ease-out;display:flex}.hud-tab-main{color:var(--ink);font:inherit;letter-spacing:.06em;text-align:left;cursor:pointer;background:0 0;border:0;flex:1;grid-template-columns:26px 1fr;align-items:center;gap:10px;min-height:40px;padding:7px 18px 9px 10px;font-size:.82rem;display:grid;position:relative;overflow:hidden}.hud-tab-main:focus-visible{outline:1px dashed var(--accent);outline-offset:-3px}.hud-icon{background:var(--hud-line-dim);width:26px;height:26px;color:var(--accent);place-items:center;font-size:.95rem;transition:background .14s ease-out,color .14s;display:grid}.hud-tab-label{text-transform:uppercase;letter-spacing:.14em;font-size:.74rem}.hud-tab-engaged{letter-spacing:.2em;color:var(--accent);opacity:0;font-size:.74rem;position:absolute;top:50%;left:46px;transform:translateY(-50%)}.hud-tab:after{content:"";background:var(--accent);width:26%;height:2px;box-shadow:0 0 6px var(--hud-glow);z-index:2;transition:width .22s ease-out;position:absolute;bottom:4px;left:12px}.hud-sweep,.hud-scan{pointer-events:none;opacity:0;position:absolute;inset:0}.hud-sweep{background:linear-gradient(100deg, transparent 30%, color-mix(in srgb, var(--accent) 38%, transparent) 50%, transparent 70%);transform:translate(-100%)}.hud-scan{background:linear-gradient(180deg, transparent, color-mix(in srgb, var(--accent) 55%, transparent) 50%, transparent);height:14px;inset:-14px 0 auto}.hud-ripple{background:radial-gradient(circle, color-mix(in srgb, var(--accent) 55%, transparent), transparent 62%);opacity:.9;pointer-events:none;border-radius:50%;animation:.6s ease-out forwards hud-ripple;position:absolute;transform:scale(0)}@media (hover:hover){.hud-tab:hover{filter:brightness(1.22);transform:translate(6px)}.hud-tab:hover:after{width:calc(100% - 24px)}.hud-tab:hover:before{background:var(--hud-bg-hi)}.hud-tab:hover .hud-icon{background:var(--accent);color:#031018}.hud-tab:hover .hud-sweep{opacity:1;animation:.6s ease-out hud-sweep}}.hud-tab:active{transform:translate(3px)scale(.97)}.hud-tab:active:before{background:color-mix(in srgb, var(--accent) 18%, var(--hud-bg))}.hud-tab.engaged .hud-tab-label{opacity:0}.hud-tab.engaged .hud-tab-engaged{opacity:1;animation:.65s steps(2,end) hud-flicker}.hud-tab.engaged .hud-scan{opacity:1;animation:.45s linear hud-scan}.hud-tab.current:before{background:var(--hud-bg-hi)}.hud-tab.current:after{width:calc(100% - 24px)}.hud-tab.current .hud-tab-title{color:var(--accent)}.hud-btn{background:var(--hud-line-dim);width:36px;height:32px;color:var(--ink);cursor:pointer;clip-path:polygon(7px 0,100% 0,calc(100% - 7px) 100%,0 100%);border:0;place-items:center;padding:0;transition:background .14s ease-out,color .14s,transform .1s;display:inline-grid;position:relative;overflow:hidden}.hud-btn sup{color:var(--accent);font-size:.55rem;position:absolute;top:3px;right:6px}.hud-btn.on,.hud-btn[aria-pressed=true]{color:var(--accent);background:color-mix(in srgb, var(--accent) 24%, transparent)}.hud-btn-main{background:var(--accent);color:#031018;width:52px;height:36px}.hud-btn:focus-visible{outline:1px dashed var(--accent);outline-offset:2px}@media (hover:hover){.hud-btn:hover{background:color-mix(in srgb, var(--accent) 44%, transparent);color:#fff}.hud-btn-main:hover{background:color-mix(in srgb, var(--accent) 78%, #fff);color:#031018}}.hud-btn:active{transform:scale(.94)}.hud-range{appearance:none;cursor:pointer;--fill:0%;background:0 0;width:100%;height:14px;margin:0}.hud-range::-webkit-slider-runnable-track{background:linear-gradient(90deg, var(--accent) var(--fill), var(--hud-line-dim) var(--fill));height:2px}.hud-range::-moz-range-track{background:var(--hud-line-dim);height:2px}.hud-range::-moz-range-progress{background:var(--accent);height:2px}.hud-range::-webkit-slider-thumb{-webkit-appearance:none;background:var(--accent);clip-path:polygon(0 0,100% 0,100% 70%,50% 100%,0 70%);width:9px;height:13px;box-shadow:0 0 8px var(--hud-glow);border:0;margin-top:-5.5px}.hud-range::-moz-range-thumb{background:var(--accent);border:0;border-radius:0;width:9px;height:13px}.hud-range:disabled{opacity:.4;cursor:default}.hud-chip{border:1px solid var(--hud-line-dim);color:var(--muted);font:inherit;letter-spacing:.16em;text-transform:uppercase;cursor:pointer;background:0 0;padding:4px 12px;font-size:.66rem;transition:color .14s,border-color .14s,background .14s}.hud-chip.on{color:var(--accent);border-color:var(--accent);background:color-mix(in srgb, var(--accent) 12%, transparent)}@media (hover:hover){.hud-chip:hover{color:var(--ink);border-color:var(--hud-line)}}.hud-mini{border:1px solid var(--hud-line-dim);width:30px;height:30px;color:var(--accent);font:inherit;cursor:pointer;background:0 0;align-self:center;margin-right:8px;font-size:1.05rem;transition:background .14s,color .14s}@media (hover:hover){.hud-mini:hover{background:var(--accent);color:#031018}}.hud-music{--cut:14px;cursor:grab;touch-action:none;padding:10px 14px 12px;position:fixed;bottom:12px;right:12px}.hud-music.mini{width:min(560px,100vw - 24px)}.hud-music.full{width:min(1000px,100vw - 24px);max-height:calc(100vh - 24px);padding:12px 16px 16px;overflow:auto}.hud-music-head{justify-content:space-between;align-items:center;margin-bottom:6px;display:flex}.hud-music-head .hud-kicker{margin:0}.hud-head-actions{gap:4px;display:flex}.hud-head-actions .hud-btn{width:30px;height:24px}.hud-music-body{align-items:center;gap:16px;display:flex}.hud-music.full .hud-music-body{align-items:stretch;gap:22px}.hud-music-left{flex:none;align-items:center;gap:12px;display:flex}.hud-music-main{flex:1;align-content:center;gap:8px;min-width:0;display:grid}.hud-now{gap:2px;min-width:0;display:grid}.hud-title{letter-spacing:.02em;white-space:nowrap;text-overflow:ellipsis;font-variant-ligatures:none;font-size:1rem;font-weight:600;overflow:hidden}.hud-music.full .hud-title{white-space:normal;font-size:1.35rem}.hud-sub{letter-spacing:.1em;text-transform:uppercase;color:var(--muted);white-space:nowrap;text-overflow:ellipsis;font-size:.7rem;overflow:hidden}.hud-timeline{grid-template-columns:auto 1fr auto;align-items:center;gap:10px;display:grid}.hud-time{letter-spacing:.1em;color:var(--muted);font-variant-numeric:tabular-nums;font-size:.7rem}.hud-controls{align-items:center;gap:6px;display:flex}.hud-controls .hud-btn:first-child{margin-right:6px}.hud-controls .hud-btn:last-child{margin-left:6px}.hud-volume{grid-template-columns:auto 1fr;align-items:center;gap:8px;max-width:260px;display:grid}.hud-unlock{border:1px solid var(--warn);color:var(--warn);font:inherit;letter-spacing:.16em;text-transform:uppercase;cursor:pointer;background:0 0;justify-self:start;padding:4px 12px;font-size:.66rem;animation:1.4s ease-in-out infinite hud-pulse}.hud-dial{--bass:0;flex:none;position:relative}.hud-dial-svg{width:100%;height:100%;position:absolute;inset:0;overflow:visible}.hud-dial-ticks{fill:none;stroke:var(--hud-line);stroke-width:3px;stroke-dasharray:1 5.02}.hud-dial-track{fill:none;stroke:var(--hud-line-dim);stroke-width:2px}.hud-dial-arc{fill:none;stroke:var(--accent);stroke-width:3px;stroke-linecap:butt;filter:drop-shadow(0 0 4px var(--hud-glow));transition:stroke-dasharray .25s linear}.hud-dial-inner{fill:none;stroke:var(--hud-line-dim);stroke-width:1px}.hud-needle{transform-origin:100px 100px;opacity:.85}.hud-needle line{stroke:var(--accent);stroke-width:1.4px;stroke-linecap:round}.hud-needle circle{fill:var(--accent);filter:drop-shadow(0 0 4px var(--accent))}.hud-spectrum{pointer-events:none;position:absolute;inset:0}.hud-cover{color:var(--hud-line);background:var(--hud-bg-hi) center / cover no-repeat;box-shadow:0 0 16px var(--hud-line-dim), inset 0 0 14px #0000008c;border:1px solid var(--hud-line);transform:scale(calc(1 + var(--bass) * .045));border-radius:50%;place-items:center;display:grid;position:absolute;inset:20%}.hud-levels{flex-direction:column-reverse;gap:3px;width:9px;height:220px;display:flex}.hud-levels i{background:var(--hud-line-dim);flex:1;transition:background 80ms linear,box-shadow 80ms linear;display:block}.hud-levels i.on{background:var(--accent);box-shadow:0 0 6px var(--hud-glow)}.hud-levels i:nth-child(n+10).on{background:var(--warn);box-shadow:0 0 6px color-mix(in srgb, var(--warn) 50%, transparent)}.hud-playlist{grid-template-rows:auto auto minmax(0,1fr);gap:8px;width:300px;min-width:0;max-height:340px;display:grid}.hud-tabs{flex-wrap:wrap;gap:6px;display:flex}.hud-search{border:1px solid var(--hud-line-dim);width:100%;color:var(--ink);font:inherit;background:#0000004d;padding:6px 10px;font-size:.8rem}.hud-search:focus{border-color:var(--accent);outline:none}.hud-list{align-content:start;gap:5px;min-height:0;margin:0;padding:0 4px 0 0;list-style:none;display:grid;overflow-y:auto}.hud-list .hud-tab{--cut:7px;min-width:0}.hud-list .hud-tab-main{grid-template-columns:1fr;gap:1px;min-height:0;padding:6px 12px 8px 14px;display:grid}.hud-tab-title{letter-spacing:.03em;white-space:nowrap;text-overflow:ellipsis;font-size:.8rem;overflow:hidden}.hud-list small{letter-spacing:.12em;text-transform:uppercase;color:var(--muted);white-space:nowrap;text-overflow:ellipsis;font-size:.62rem;overflow:hidden}.hud-source{letter-spacing:.18em;color:#031018;background:var(--accent);clip-path:polygon(0 0,100% 0,calc(100% - 4px) 100%,0 100%);vertical-align:1px;margin-left:8px;padding:0 5px;font-size:.56rem;font-style:normal}.hud-notice{border-left:2px solid var(--warn);letter-spacing:.06em;color:var(--warn);margin:0;padding:4px 10px;font-size:.7rem}.hud-empty{color:var(--muted);padding:10px 4px;font-size:.75rem}@keyframes hud-spin{to{transform:rotate(360deg)}}@keyframes hud-sweep{0%{transform:translate(-100%)}to{transform:translate(100%)}}@keyframes hud-scan{0%{top:-14px}to{top:calc(100% + 14px)}}@keyframes hud-ripple{to{opacity:0;transform:scale(1)}}@keyframes hud-flicker{0%,to{opacity:1}25%{opacity:.2}50%{opacity:1}75%{opacity:.45}}@keyframes hud-pulse{0%,to{opacity:1}50%{opacity:.45}}@keyframes hud-boot{0%{opacity:0;filter:brightness(2.2);transform:translate(-14px)}30%{opacity:1}42%{opacity:.35}56%{opacity:1}70%{opacity:.7}to{opacity:1;filter:none;transform:none}}@keyframes hud-roll{0%{opacity:0;transform:translateY(60%)}to{opacity:1;transform:none}}@keyframes hud-blink{0%,49%{opacity:1}50%,to{opacity:.25}}@keyframes hud-travel{0%{left:0}to{left:calc(100% - 5px)}}@keyframes hud-flare{0%{box-shadow:0 0 18px var(--hud-glow), 0 0 0 0 var(--accent)}60%{box-shadow:0 0 30px var(--accent), 0 0 0 14px transparent}to{box-shadow:0 0 18px var(--hud-glow), 0 0 0 0 transparent}}[data-hud-anim=full] .hud-boot{animation:.55s ease-out both hud-boot;animation-delay:calc(var(--i,0) * 80ms)}[data-hud-anim=full] .hud-ring-turn{transform-origin:32px 32px;animation:40s linear infinite hud-spin}[data-hud-anim=full] .hud-profile.speaking .hud-ring-turn{animation-duration:7s}[data-hud-anim=full] .hud-profile.speaking .hud-emblem{animation:.9s ease-out hud-flare}[data-hud-anim=full] .hud-profile.busy .hud-ring-chase{opacity:1;animation:1.5s linear infinite hud-spin}[data-hud-anim=full] .hud-profile.listening .hud-emblem{box-shadow:0 0 26px var(--accent), inset 0 0 14px var(--hud-line-dim)}[data-hud-anim=full] .hud-digit{animation:.35s ease-out hud-roll}[data-hud-anim=full] .hud-colon{animation:1s step-end infinite hud-blink}[data-hud-anim=full] .hud-dot{animation:1s linear infinite hud-travel}[data-hud-anim=full] .hud-dial.playing .hud-needle{animation:3s linear infinite hud-spin}[data-hud-anim=full] .hud-dial.playing .hud-cover{animation:22s linear infinite hud-spin-keep}@keyframes hud-spin-keep{to{rotate:360deg}}[data-hud-anim=full] .hud-tab-main:focus-visible{animation:1.6s ease-in-out infinite hud-pulse}[data-hud-anim=reduced] .hud-boot,[data-hud-anim=reduced] .hud-digit,[data-hud-anim=reduced] .hud-colon,[data-hud-anim=reduced] .hud-dot{animation:none}[data-hud-anim=reduced] .hud-needle{display:none}[data-hud-anim=off] .hud *,[data-hud-anim=off] .hud{transition:none!important;animation:none!important}[data-hud-anim=off] .hud-tab:hover{transform:none}[data-hud-anim=off] .hud-needle{display:none}@media (prefers-reduced-motion:reduce){.hud *,.hud{transition:none!important;animation:none!important}.hud-tab:hover{transform:none}}@media (width<=900px){.hud-clock{left:12px;top:calc(max(56px, env(safe-area-inset-top) + 48px) + 76px)}.hud-launcher{top:calc(max(56px, env(safe-area-inset-top) + 48px) + 180px)}}@media (width<=640px){.hud-tag{min-width:120px}.hud-tag b{max-width:110px}.hud-day{font-size:2.2rem}.hud-launcher .hud-tab{min-width:0}.hud-launcher .hud-tab-main{grid-template-columns:26px;padding:7px 8px 9px}.hud-launcher .hud-tab-label,.hud-launcher .hud-tab-engaged,.hud-launcher .hud-kicker{display:none}.hud-music.mini{bottom:56px}.hud-music.full .hud-music-body{flex-direction:column;align-items:center}.hud-music.full .hud-music-left{flex-wrap:wrap;justify-content:center}.hud-playlist{width:100%;max-height:220px}.hud-levels{height:120px}}
@@ -4452,5 +4452,5 @@ ${this.parser.parse(e)}</blockquote>
4452
4452
  ${e}</tr>
4453
4453
  `}tablecell(e){let t=this.parser.parseInline(e.tokens),n=e.header?`th`:`td`;return(e.align?`<${n} align="${e.align}">`:`<${n}>`)+t+`</${n}>
4454
4454
  `}strong({tokens:e}){return`<strong>${this.parser.parseInline(e)}</strong>`}em({tokens:e}){return`<em>${this.parser.parseInline(e)}</em>`}codespan({text:e}){return`<code>${Sw(e,!0)}</code>`}br(e){return`<br>`}del({tokens:e}){return`<del>${this.parser.parseInline(e)}</del>`}link({href:e,title:t,text:n,tokens:r,autolink:i}){let a=i?Sw(n,!0):this.parser.parseInline(r),o=ww(e);if(o===null)return a;e=Sw(o,i);let s=`<a href="`+e+`"`;return t&&(s+=` title="`+Sw(t)+`"`),s+=`>`+a+`</a>`,s}image({href:e,title:t,text:n,tokens:r}){r&&(n=this.parser.parseInline(r,this.parser.textRenderer));let i=ww(e);if(i===null)return Sw(n);e=i;let a=`<img src="${Sw(e)}" alt="${Sw(n)}"`;return t&&(a+=` title="${Sw(t)}"`),a+=`>`,a}text(e){return`tokens`in e&&e.tokens?this.parser.parseInline(e.tokens):`escaped`in e&&e.escaped?e.text:Sw(e.text)}},Lw=class{strong({text:e}){return e}em({text:e}){return e}codespan({text:e}){return e}del({text:e}){return e}html({text:e}){return e}text({text:e}){return e}link({text:e}){return``+e}image({text:e}){return``+e}br(){return``}checkbox({raw:e}){return e}},Rw=class e{options;renderer;textRenderer;constructor(e){this.options=e||QS,this.options.renderer=this.options.renderer||new Iw,this.renderer=this.options.renderer,this.renderer.options=this.options,this.renderer.parser=this,this.textRenderer=new Lw}static parse(t,n){return new e(n).parse(t)}static parseInline(t,n){return new e(n).parseInline(t)}parse(e){this.renderer.parser=this;let t=``;for(let n=0;n<e.length;n++){let r=e[n];if(this.options.extensions?.renderers?.[r.type]){let e=r,n=this.options.extensions.renderers[e.type].call({parser:this},e);if(n!==!1||![`space`,`hr`,`heading`,`code`,`table`,`blockquote`,`list`,`checkbox`,`html`,`def`,`paragraph`,`text`].includes(e.type)){t+=n||``;continue}}let i=r;switch(i.type){case`space`:t+=this.renderer.space(i);break;case`hr`:t+=this.renderer.hr(i);break;case`heading`:t+=this.renderer.heading(i);break;case`code`:t+=this.renderer.code(i);break;case`table`:t+=this.renderer.table(i);break;case`blockquote`:t+=this.renderer.blockquote(i);break;case`list`:t+=this.renderer.list(i);break;case`checkbox`:t+=this.renderer.checkbox(i);break;case`html`:t+=this.renderer.html(i);break;case`def`:t+=this.renderer.def(i);break;case`paragraph`:t+=this.renderer.paragraph(i);break;case`text`:t+=this.renderer.text(i);break;default:{let e=`Token with "`+i.type+`" type was not found.`;if(this.options.silent)return console.error(e),``;throw Error(e)}}}return t}parseInline(e,t=this.renderer){this.renderer.parser=this;let n=``;for(let r=0;r<e.length;r++){let i=e[r];if(this.options.extensions?.renderers?.[i.type]){let e=this.options.extensions.renderers[i.type].call({parser:this},i);if(e!==!1||![`escape`,`html`,`link`,`image`,`checkbox`,`strong`,`em`,`codespan`,`br`,`del`,`text`].includes(i.type)){n+=e||``;continue}}let a=i;switch(a.type){case`escape`:n+=t.text(a);break;case`html`:n+=t.html(a);break;case`link`:n+=t.link(a);break;case`image`:n+=t.image(a);break;case`checkbox`:n+=t.checkbox(a);break;case`strong`:n+=t.strong(a);break;case`em`:n+=t.em(a);break;case`codespan`:n+=t.codespan(a);break;case`br`:n+=t.br(a);break;case`del`:n+=t.del(a);break;case`text`:n+=t.text(a);break;default:{let e=`Token with "`+a.type+`" type was not found.`;if(this.options.silent)return console.error(e),``;throw Error(e)}}}return n}},zw=class{options;block;constructor(e){this.options=e||QS}static passThroughHooks=new Set([`preprocess`,`postprocess`,`processAllTokens`,`emStrongMask`]);static passThroughHooksRespectAsync=new Set([`preprocess`,`postprocess`,`processAllTokens`]);preprocess(e){return e}postprocess(e){return e}processAllTokens(e){return e}emStrongMask(e){return e}provideLexer(e=this.block){return e?Fw.lex:Fw.lexInline}provideParser(e=this.block){return e?Rw.parse:Rw.parseInline}},Bw=new class{defaults=ZS();options=this.setOptions;parse=this.parseMarkdown(!0);parseInline=this.parseMarkdown(!1);Parser=Rw;Renderer=Iw;TextRenderer=Lw;Lexer=Fw;Tokenizer=Pw;Hooks=zw;constructor(...e){this.use(...e)}walkTokens(e,t){let n=[];for(let r of e)switch(n=n.concat(t.call(this,r)),r.type){case`table`:{let e=r;for(let r of e.header)n=n.concat(this.walkTokens(r.tokens,t));for(let r of e.rows)for(let e of r)n=n.concat(this.walkTokens(e.tokens,t));break}case`list`:{let e=r;n=n.concat(this.walkTokens(e.items,t));break}default:{let e=r;this.defaults.extensions?.childTokens?.[e.type]?this.defaults.extensions.childTokens[e.type].forEach(r=>{let i=e[r].flat(1/0);n=n.concat(this.walkTokens(i,t))}):e.tokens&&(n=n.concat(this.walkTokens(e.tokens,t)))}}return n}use(...e){let t=this.defaults.extensions||{renderers:{},childTokens:{}};return e.forEach(e=>{let n={...e};if(n.async=this.defaults.async||n.async||!1,e.extensions&&(e.extensions.forEach(e=>{if(!e.name)throw Error(`extension name required`);if(`renderer`in e){let n=t.renderers[e.name];n?t.renderers[e.name]=function(...t){let r=e.renderer.apply(this,t);return r===!1&&(r=n.apply(this,t)),r}:t.renderers[e.name]=e.renderer}if(`tokenizer`in e){if(!e.level||e.level!==`block`&&e.level!==`inline`)throw Error(`extension level must be 'block' or 'inline'`);let n=t[e.level];n?n.unshift(e.tokenizer):t[e.level]=[e.tokenizer],e.start&&(e.level===`block`?t.startBlock?t.startBlock.push(e.start):t.startBlock=[e.start]:e.level===`inline`&&(t.startInline?t.startInline.push(e.start):t.startInline=[e.start]))}`childTokens`in e&&e.childTokens&&(t.childTokens[e.name]=e.childTokens)}),n.extensions=t),e.renderer){let t=this.defaults.renderer||new Iw(this.defaults);for(let n in e.renderer){if(!(n in t))throw Error(`renderer '${n}' does not exist`);if([`options`,`parser`].includes(n))continue;let r=n,i=e.renderer[r],a=t[r];t[r]=(...e)=>{let n=i.apply(t,e);return n===!1&&(n=a.apply(t,e)),n||``}}n.renderer=t}if(e.tokenizer){let t=this.defaults.tokenizer||new Pw(this.defaults);for(let n in e.tokenizer){if(!(n in t))throw Error(`tokenizer '${n}' does not exist`);if([`options`,`rules`,`lexer`].includes(n))continue;let r=n,i=e.tokenizer[r],a=t[r];t[r]=(...e)=>{let n=i.apply(t,e);return n===!1&&(n=a.apply(t,e)),n}}n.tokenizer=t}if(e.hooks){let t=this.defaults.hooks||new zw;for(let n in e.hooks){if(!(n in t))throw Error(`hook '${n}' does not exist`);if([`options`,`block`].includes(n))continue;let r=n,i=e.hooks[r],a=t[r];t[r]=zw.passThroughHooks.has(n)?e=>{if(this.defaults.async&&zw.passThroughHooksRespectAsync.has(n))return(async()=>{let n=await i.call(t,e);return a.call(t,n)})();let r=i.call(t,e);return a.call(t,r)}:(...e)=>{if(this.defaults.async)return(async()=>{let n=await i.apply(t,e);return n===!1&&(n=await a.apply(t,e)),n})();let n=i.apply(t,e);return n===!1&&(n=a.apply(t,e)),n}}n.hooks=t}if(e.walkTokens){let t=this.defaults.walkTokens,r=e.walkTokens;n.walkTokens=function(e){let n=[];return n.push(r.call(this,e)),t&&(n=n.concat(t.call(this,e))),n}}this.defaults={...this.defaults,...n}}),this}setOptions(e){return this.defaults={...this.defaults,...e},this}lexer(e,t){return Fw.lex(e,t??this.defaults)}parser(e,t){return Rw.parse(e,t??this.defaults)}parseMarkdown(e){return(t,n)=>{let r={...n},i={...this.defaults,...r},a=this.onError(!!i.silent,!!i.async);if(this.defaults.async===!0&&r.async===!1)return a(Error(`marked(): The async option was set to true by an extension. Remove async: false from the parse options object to return a Promise.`));if(typeof t>`u`||t===null)return a(Error(`marked(): input parameter is undefined or null`));if(typeof t!=`string`)return a(Error(`marked(): input parameter is of type `+Object.prototype.toString.call(t)+`, string expected`));if(i.hooks&&(i.hooks.options=i,i.hooks.block=e),i.async)return(async()=>{let n=i.hooks?await i.hooks.preprocess(t):t,r=await(i.hooks?await i.hooks.provideLexer(e):e?Fw.lex:Fw.lexInline)(n,i),a=i.hooks?await i.hooks.processAllTokens(r):r;i.walkTokens&&await Promise.all(this.walkTokens(a,i.walkTokens));let o=await(i.hooks?await i.hooks.provideParser(e):e?Rw.parse:Rw.parseInline)(a,i);return i.hooks?await i.hooks.postprocess(o):o})().catch(a);try{i.hooks&&(t=i.hooks.preprocess(t));let n=(i.hooks?i.hooks.provideLexer(e):e?Fw.lex:Fw.lexInline)(t,i);i.hooks&&(n=i.hooks.processAllTokens(n)),i.walkTokens&&this.walkTokens(n,i.walkTokens);let r=(i.hooks?i.hooks.provideParser(e):e?Rw.parse:Rw.parseInline)(n,i);return i.hooks&&(r=i.hooks.postprocess(r)),r}catch(e){return a(e)}}}onError(e,t){return n=>{if(n.message+=`
4455
- Please report this to https://github.com/markedjs/marked.`,e){let e=`<p>An error occurred:</p><pre>`+Sw(n.message+``,!0)+`</pre>`;return t?Promise.resolve(e):e}if(t)return Promise.reject(n);throw n}}};function Vw(e,t){return Bw.parse(e,t)}Vw.options=Vw.setOptions=function(e){return Bw.setOptions(e),Vw.defaults=Bw.defaults,$S(Vw.defaults),Vw},Vw.getDefaults=ZS,Vw.defaults=QS;function Hw(...e){return Bw.use(...e),Vw.defaults=Bw.defaults,$S(Vw.defaults),Vw}Vw.use=Hw,Vw.walkTokens=function(e,t){return Bw.walkTokens(e,t)},Vw.parseInline=Bw.parseInline,Vw.Parser=Rw,Vw.parser=Rw.parse,Vw.Renderer=Iw,Vw.TextRenderer=Lw,Vw.Lexer=Fw,Vw.lexer=Fw.lex,Vw.Tokenizer=Pw,Vw.Hooks=zw,Vw.parse=Vw,Vw.options,Vw.setOptions,Vw.walkTokens,Vw.parseInline,Rw.parse,Fw.lex;var Uw=!1;function Ww(){Uw||(Uw=!0,XS.addHook(`afterSanitizeAttributes`,e=>{e instanceof Element&&e.tagName===`A`&&(e.setAttribute(`rel`,`noopener noreferrer`),e.setAttribute(`target`,`_blank`))}))}function Gw(e){Ww();let t=Vw.parse(e,{async:!1,breaks:!0});return XS.sanitize(t,{ALLOWED_TAGS:[`p`,`br`,`strong`,`em`,`code`,`pre`,`ul`,`ol`,`li`,`a`,`h1`,`h2`,`h3`,`h4`,`h5`,`h6`,`blockquote`,`hr`,`del`,`table`,`thead`,`tbody`,`tr`,`th`,`td`],ALLOWED_ATTR:[`href`,`rel`,`target`],ALLOWED_URI_REGEXP:/^(?:https?:|mailto:)/i})}var Kw=e=>Number.isFinite(e);function qw(e){let t=Math.floor(Math.log10(e)),n=e/10**t;return(n<=1?1:n<=2?2:n<=2.5?2.5:n<=5?5:10)*10**t}function Jw(e,t,n=5){let r=Kw(e)?e:0,i=Kw(t)?t:r+1;r>i&&([r,i]=[i,r]),r===i&&(i=r+(Math.abs(r)||1));let a=qw((i-r)/Math.max(1,n-1)),o=Math.floor(r/a)*a,s=Math.ceil(i/a)*a,c=[];for(let e=o;e<=s+a/2;e+=a)c.push(Math.round(e*1e9)/1e9);return{min:o,max:s,ticks:c}}function Yw(e,t){let[n,r]=e,[i,a]=t;return r===n?()=>i:e=>i+(e-n)/(r-n)*(a-i)}function Xw(e){return e.map(([e,t],n)=>`${n===0?`M`:`L`}${e.toFixed(2)} ${t.toFixed(2)}`).join(` `)}function Zw(e,t,n,r,i){let a=r=>{let i=r*Math.PI/180;return`${(e+n*Math.cos(i)).toFixed(2)} ${(t+n*Math.sin(i)).toFixed(2)}`},o=+(Math.abs(i-r)>180);return`M ${a(r)} A ${n} ${n} 0 ${o} 1 ${a(i)}`}function Qw(e,t,n){return!Kw(e)||!Kw(t)||!Kw(n)||n<=t?0:Math.min(1,Math.max(0,(e-t)/(n-t)))*240}function $w(e,t,n,r){let i=t.x-e.x,a=t.y-e.y,o=Math.hypot(i,a);if(o===0||o<=n+r)return{from:{...e},to:{...t}};let s=i/o,c=a/o;return{from:{x:e.x+s*n,y:e.y+c*n},to:{x:t.x-s*r,y:t.y-c*r}}}function eT(e,t,n){if(e<=0)return[];if(e===1)return[{x:t/2,y:n/2}];let r=Math.min(t,n)*.36;return Array.from({length:e},(i,a)=>{let o=-Math.PI/2+a*2*Math.PI/e;return{x:t/2+r*Math.cos(o),y:n/2+r*Math.sin(o)}})}var tT=e=>typeof e==`object`&&!!e&&!Array.isArray(e),nT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,rT=e=>Array.isArray(e)?e:[],iT=e=>typeof e==`number`?Number.isFinite(e)?e:null:typeof e==`string`&&e.trim()!==``&&Number.isFinite(Number(e))?Number(e):null,aT=(e,t)=>e.length>t?e.slice(0,t)+`…`:e,oT=[`var(--accent)`,`#ffb454`,`#7b8cff`,`#5ef0b0`,`#ff6b7a`,`#c792ea`],sT=({text:e})=>e?(0,p.jsx)(`h3`,{className:`obj-title`,children:e}):null,cT=({text:e=`No data`})=>(0,p.jsx)(`p`,{className:`obj-empty`,children:e}),lT=400,uT=220,dT={l:44,r:12,t:10,b:28};function fT({props:e}){let t=e.kind===`bar`||e.kind===`area`?e.kind:`line`,n=rT(e.labels).slice(0,120).map(nT),r=rT(e.series).slice(0,6).map((e,t)=>{let n=tT(e)?e:{},r=rT(n.values).slice(0,120).map((e,t)=>({idx:t,v:iT(e)})).filter(e=>e.v!==null);return{name:nT(n.name)||`series ${t+1}`,points:r}}).filter(e=>e.points.length>0);if(r.length===0)return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{})]});let i=r.flatMap(e=>e.points.map(e=>e.v)),a=Math.min(...i),o=Math.max(...i),s=Jw(t===`line`?a:Math.min(0,a),t===`line`?o:Math.max(0,o),5),c=Math.max(n.length,...r.map(e=>e.points[e.points.length-1].idx+1),2),l=Yw([s.min,s.max],[uT-dT.b,dT.t]),u=Yw([0,c-1],[dT.l,lT-dT.r]),d=(lT-dT.l-dT.r)/c,f=Math.max(1,d*.7/r.length),m=(e,t)=>dT.l+e*d+d*.15+t*f,h=Math.max(1,Math.ceil(c/6)),g=nT(e.unit);return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsxs)(`svg`,{className:`obj-chart`,viewBox:`0 0 ${lT} ${uT}`,role:`img`,"aria-label":nT(e.title)||`chart`,children:[s.ticks.map(e=>(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`line`,{className:`grid`,x1:dT.l,x2:lT-dT.r,y1:l(e),y2:l(e)}),(0,p.jsxs)(`text`,{className:`tick`,x:dT.l-6,y:l(e)+3,textAnchor:`end`,children:[e,g&&e===s.max?g:``]})]},e)),Array.from({length:c},(e,t)=>t).filter(e=>e%h===0&&n[e]).map(e=>(0,p.jsx)(`text`,{className:`tick`,x:t===`bar`?m(e,0)+f*r.length/2:u(e),y:212,textAnchor:`middle`,children:aT(n[e],8)},e)),r.map((e,n)=>{let r=oT[n%oT.length];if(t===`bar`)return(0,p.jsx)(`g`,{children:e.points.map(e=>(0,p.jsx)(`rect`,{className:`bar`,x:m(e.idx,n),y:Math.min(l(e.v),l(0)),width:f,height:Math.abs(l(e.v)-l(0)),fill:r},e.idx))},n);let i=e.points.map(e=>[u(e.idx),l(e.v)]),a=Xw(i),o=`${a} L${i[i.length-1][0].toFixed(2)} ${l(s.min).toFixed(2)} L${i[0][0].toFixed(2)} ${l(s.min).toFixed(2)} Z`;return(0,p.jsxs)(`g`,{children:[t===`area`&&(0,p.jsx)(`path`,{className:`series-area`,d:o,fill:r,opacity:.18}),(0,p.jsx)(`path`,{className:`series-line`,d:a,fill:`none`,stroke:r,strokeWidth:2,strokeLinejoin:`round`})]},n)})]}),r.length>1&&(0,p.jsx)(`ul`,{className:`legend`,children:r.map((e,t)=>(0,p.jsxs)(`li`,{children:[(0,p.jsx)(`i`,{style:{background:oT[t%oT.length]}}),(0,p.jsx)(`span`,{children:e.name})]},t))})]})}function pT({props:e}){let t=iT(e.min)??0,n=iT(e.max)??100,r=iT(e.value)??t,i=Qw(r,t,n),a=i/240;return(0,p.jsxs)(`div`,{className:`obj-gauge ${a>.95?`gauge-crit`:a>.8?`gauge-warn`:``}`,children:[(0,p.jsxs)(`svg`,{viewBox:`0 0 200 150`,role:`img`,"aria-label":`${nT(e.label)} ${r}`,children:[(0,p.jsx)(`path`,{className:`track`,d:Zw(100,100,70,150,390),fill:`none`,strokeWidth:12,strokeLinecap:`round`}),i>0&&(0,p.jsx)(`path`,{className:`value`,d:Zw(100,100,70,150,150+i),fill:`none`,strokeWidth:12,strokeLinecap:`round`})]}),(0,p.jsxs)(`div`,{className:`gauge-read`,children:[(0,p.jsx)(`span`,{className:`gauge-value`,children:String(Math.round(r*100)/100)}),nT(e.unit)&&(0,p.jsx)(`small`,{className:`gauge-unit`,children:nT(e.unit)})]}),(0,p.jsx)(`span`,{className:`obj-label`,children:nT(e.label)})]})}function mT({props:e}){let t=rT(e.items).slice(0,30).map(e=>tT(e)?e:{}).map(e=>({time:nT(e.time),title:nT(e.title),detail:nT(e.detail)})).filter(e=>e.title||e.time);return t.length===0?(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{text:`Nothing to show`})]}):(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(`ol`,{className:`obj-timeline`,children:t.map((e,t)=>(0,p.jsxs)(`li`,{children:[(0,p.jsx)(`time`,{children:e.time}),(0,p.jsx)(`strong`,{children:e.title}),e.detail&&(0,p.jsx)(`span`,{children:e.detail})]},t))})]})}var hT=400,gT=300,_T=12;function vT({props:e}){let t=(0,l.useId)(),n=new Set,r=[];for(let t of rT(e.nodes)){let e=tT(t)?t:{},i=nT(e.id);if(i&&!n.has(i)&&(n.add(i),r.push({id:i,label:nT(e.label)||i}),r.length>=40))break}if(r.length===0)return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{text:`Nothing to show`})]});let i=new Map(r.map((e,t)=>[e.id,eT(r.length,hT,gT)[t]])),a=[];for(let t of rT(e.edges)){let e=tT(t)?t:{},n=nT(e.from),r=nT(e.to);if(i.has(n)&&i.has(r)&&n!==r&&(a.push({from:n,to:r,label:nT(e.label)}),a.length>=80))break}return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsxs)(`svg`,{className:`obj-graph`,viewBox:`0 0 ${hT} ${gT}`,role:`img`,"aria-label":nT(e.title)||`graph`,children:[(0,p.jsx)(`defs`,{children:(0,p.jsx)(`marker`,{id:t,viewBox:`0 0 10 10`,refX:`9`,refY:`5`,markerWidth:`6`,markerHeight:`6`,orient:`auto-start-reverse`,children:(0,p.jsx)(`path`,{d:`M0 0 L10 5 L0 10 z`,className:`arrow`})})}),a.map((e,n)=>{let{from:r,to:a}=$w(i.get(e.from),i.get(e.to),14,17),o=(r.x+a.x)/2+(hT/2-(r.x+a.x)/2)*.25,s=(r.y+a.y)/2+(gT/2-(r.y+a.y)/2)*.25;return(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`path`,{className:`edge`,d:`M ${r.x.toFixed(1)} ${r.y.toFixed(1)} Q ${o.toFixed(1)} ${s.toFixed(1)} ${a.x.toFixed(1)} ${a.y.toFixed(1)}`,fill:`none`,markerEnd:`url(#${t})`}),e.label&&(0,p.jsx)(`text`,{className:`edge-label`,x:o,y:s,textAnchor:`middle`,children:aT(e.label,12)})]},n)}),r.map(e=>{let t=i.get(e.id);return(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`circle`,{className:`node`,cx:t.x,cy:t.y,r:_T}),(0,p.jsx)(`text`,{className:`node-label`,x:t.x,y:t.y+26,textAnchor:`middle`,children:aT(e.label,18)})]},e.id)})]})]})}var yT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,bT=e=>Array.isArray(e)?e:[],xT=e=>typeof e==`object`&&e?e:{},ST=/^\/api\/media\/[0-9a-f]{32}$/,CT=e=>typeof e==`string`&&ST.test(e)?e:null,wT=/^\/api\/video\/[0-9a-f]{32}$/,TT=e=>typeof e==`string`&&wT.test(e)?e:null,ET=({props:e})=>yT(e.title)?(0,p.jsx)(`h3`,{className:`obj-title`,children:yT(e.title)}):null;function DT({props:e}){let t=(0,l.useMemo)(()=>Gw(yT(e.text)),[e.text]);return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`div`,{className:`obj-md obj-doc`,dangerouslySetInnerHTML:{__html:t}})]})}function OT({props:e}){let t=Math.min(100,Math.max(0,Number(e.value)||0));return(0,p.jsxs)(`div`,{className:`obj-progress`,children:[(0,p.jsxs)(`div`,{className:`obj-progress-head`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:yT(e.label)}),(0,p.jsxs)(`span`,{className:`obj-progress-pct`,children:[Math.round(t),`%`]})]}),(0,p.jsx)(`div`,{className:`obj-progress-bar`,role:`progressbar`,"aria-valuemin":0,"aria-valuemax":100,"aria-valuenow":Math.round(t),"aria-label":yT(e.label)||`Progress`,children:(0,p.jsx)(`i`,{style:{width:`${t}%`}})}),yT(e.detail)&&(0,p.jsx)(`span`,{className:`obj-progress-detail`,children:yT(e.detail)})]})}function kT({props:e}){let t=bT(e.items).map(e=>xT(typeof e==`object`&&e?e:{text:e})),n=t.filter(e=>e.done===!0).length;return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`ul`,{className:`obj-checklist`,children:t.map((e,t)=>(0,p.jsxs)(`li`,{className:e.done===!0?`done`:void 0,children:[(0,p.jsx)(`span`,{className:`box`,"aria-hidden":`true`,children:e.done===!0?`✓`:``}),(0,p.jsx)(`span`,{children:yT(e.text)})]},t))}),t.length>0&&(0,p.jsxs)(`small`,{className:`obj-progress-detail`,children:[n,` of `,t.length,` done`]})]})}function AT({props:e}){return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`dl`,{className:`obj-kv`,children:bT(e.rows).map((e,t)=>{let n=xT(e);return(0,p.jsxs)(`div`,{children:[(0,p.jsx)(`dt`,{children:yT(n.key)}),(0,p.jsx)(`dd`,{children:yT(n.value)})]},t)})})]})}var jT=e=>String(Math.floor(e)).padStart(2,`0`);function MT(e){let t=Math.max(0,Math.ceil(e));return`${jT(t/3600)}:${jT(t%3600/60)}:${jT(t%60)}`}function NT({props:e}){let t=(0,l.useRef)(null);if(t.current===null){let n=typeof e.to==`string`?Date.parse(e.to):NaN,r=Number(e.seconds);t.current=Number.isFinite(n)?n:Date.now()+(Number.isFinite(r)?r:0)*1e3}let[n,r]=(0,l.useState)(Date.now());(0,l.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),250);return()=>clearInterval(e)},[]);let i=(t.current-n)/1e3;return(0,p.jsxs)(`div`,{className:`obj-countdown${i<=0?` done`:``}`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:yT(e.title)||yT(e.label)}),(0,p.jsx)(`span`,{className:`obj-countdown-time`,role:`timer`,children:MT(i)})]})}function PT({props:e}){let t=CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsx)(`img`,{src:t,alt:yT(e.title)||`Picture`,loading:`lazy`}):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This picture is not available.`})]})}function FT({src:e,web:t,title:n}){let[r,i]=(0,l.useState)(t?`loading`:`ready`);return r===`failed`?(0,p.jsx)(`p`,{className:`obj-empty`,children:`This video could not be played. Ask Friend to try again, or to play it in a window on the PC.`}):(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`video`,{src:e,controls:!0,playsInline:!0,autoPlay:t,preload:t?`auto`:`metadata`,"aria-label":n,onLoadedData:()=>i(`ready`),onError:()=>i(`failed`)}),t&&r===`loading`&&(0,p.jsx)(`p`,{className:`obj-empty`,children:`Preparing the video…`})]})}var IT=/^[A-Za-z0-9_-]{11}$/;function LT({id:e,start:t,title:n}){let[r,i]=(0,l.useState)(!1),a=new URLSearchParams({autoplay:`1`,rel:`0`,playsinline:`1`,modestbranding:`1`});return t>0&&a.set(`start`,String(t)),(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`iframe`,{className:`obj-youtube`,src:`https://www.youtube-nocookie.com/embed/${e}?${a.toString()}`,title:n,allow:`autoplay; encrypted-media; fullscreen; picture-in-picture`,allowFullScreen:!0,referrerPolicy:`strict-origin-when-cross-origin`,onLoad:()=>i(!0)}),!r&&(0,p.jsx)(`p`,{className:`obj-empty`,children:`Loading the player…`})]})}function RT({props:e}){if(e.embed!==void 0){let t=typeof e.embed==`string`&&IT.test(e.embed)?e.embed:null,n=typeof e.start==`number`&&e.start>0&&e.start<=86400?Math.floor(e.start):0;return(0,p.jsxs)(`div`,{className:`obj-media`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsx)(LT,{id:t,start:n,title:yT(e.title)||`YouTube video`},`${t}-${n}`):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This clip is not available.`})]})}let t=TT(e.src),n=t??CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media`,children:[(0,p.jsx)(ET,{props:e}),n?(0,p.jsx)(FT,{src:n,web:t!==null,title:yT(e.title)||`Video`},n):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This clip is not available.`})]})}function zT({props:e}){let t=CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media obj-pdf`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`iframe`,{src:t,title:yT(e.title)||`Document`}),(0,p.jsx)(`a`,{className:`obj-open`,href:t,target:`_blank`,rel:`noopener noreferrer`,children:`Open in a new tab`})]}):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This document is not available.`})]})}function BT({props:e}){let t=bT(e.items).map(xT).filter(e=>CT(e.src)),[n,r]=(0,l.useState)(0),i=Math.min(n,Math.max(0,t.length-1)),a=t[i];if(!a)return(0,p.jsx)(`p`,{className:`obj-empty`,children:`Nothing to show.`});let o=CT(a.src),s=a.kind===`video`;return(0,p.jsxs)(`div`,{className:`obj-media obj-gallery`,children:[(0,p.jsx)(ET,{props:e}),s?(0,p.jsx)(`video`,{src:o,controls:!0,playsInline:!0,preload:`metadata`},o):(0,p.jsx)(`img`,{src:o,alt:yT(a.caption)||`Picture ${i+1}`},o),(0,p.jsxs)(`div`,{className:`obj-gallery-bar`,children:[(0,p.jsx)(`button`,{type:`button`,"aria-label":`Previous`,disabled:t.length<2,onClick:()=>r((i+t.length-1)%t.length),children:`‹`}),(0,p.jsxs)(`span`,{children:[yT(a.caption),(0,p.jsxs)(`small`,{children:[i+1,` / `,t.length]})]}),(0,p.jsx)(`button`,{type:`button`,"aria-label":`Next`,disabled:t.length<2,onClick:()=>r((i+1)%t.length),children:`›`})]})]})}var VT=[`default-src 'none'`,`script-src 'unsafe-inline'`,`style-src 'unsafe-inline'`,`img-src data: blob:`,`form-action 'none'`,`base-uri 'none'`].join(`; `),HT=`html,body{margin:0;min-height:100%;background:#050b10;color:var(--ink,#d8f6ff);font:15px/1.5 var(--ui,system-ui,sans-serif)}`,UT=[`--accent`,`--ink`,`--muted`,`--ok`,`--warn`,`--bad`,`--glass`,`--edge`,`--ui`,`--mono`],WT=/^[\w\s#().,%'"/-]+$/;function GT(){if(typeof document>`u`)return``;let e=getComputedStyle(document.documentElement),t=UT.map(t=>[t,e.getPropertyValue(t).trim()]).filter(([,e])=>e&&WT.test(e));return t.length?`:root{${t.map(([e,t])=>`${e}:${t}`).join(`;`)}}`:``}function KT(e,t=``){return`<!doctype html><html><head><meta charset="utf-8"><meta http-equiv="Content-Security-Policy" content="${VT}"><meta name="viewport" content="width=device-width,initial-scale=1"><style>${t}${HT}</style></head><body>${e}</body></html>`}function qT({props:e}){let t=typeof e.html==`string`?e.html:``,n=typeof e.title==`string`?e.title:``,r=(0,l.useMemo)(()=>KT(t,GT()),[t]);return(0,p.jsxs)(`div`,{className:`obj-sandbox`,children:[n&&(0,p.jsx)(`h3`,{className:`obj-title`,children:n}),(0,p.jsx)(`iframe`,{title:n||`Page made by Friend`,sandbox:`allow-scripts`,referrerPolicy:`no-referrer`,allow:``,srcDoc:r})]})}var JT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,YT=e=>Array.isArray(e)?e:[];function XT({props:e}){let t=(0,l.useMemo)(()=>Gw(JT(e.text)),[e.text]);return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-md`,dangerouslySetInnerHTML:{__html:t}})]})}function ZT({props:e}){return(0,p.jsxs)(`div`,{className:`obj-stat`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:JT(e.label)}),(0,p.jsxs)(`span`,{className:`obj-value`,children:[(0,p.jsx)(`span`,{children:JT(e.value)}),JT(e.unit)&&(0,p.jsx)(`small`,{children:JT(e.unit)})]}),JT(e.delta)&&(0,p.jsx)(`span`,{className:`obj-delta`,children:JT(e.delta)})]})}function QT({props:e}){return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`ul`,{className:`obj-list`,children:YT(e.items).map((e,t)=>{let n=typeof e==`object`&&e?e:{text:e};return(0,p.jsx)(`li`,{className:n.done?`done`:void 0,children:JT(n.text)},t)})})]})}function $T({props:e}){let t=YT(e.columns),n=YT(e.rows);return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-table-wrap`,children:(0,p.jsxs)(`table`,{className:`obj-table`,children:[(0,p.jsx)(`thead`,{children:(0,p.jsx)(`tr`,{children:t.map((e,t)=>(0,p.jsx)(`th`,{children:JT(e)},t))})}),(0,p.jsx)(`tbody`,{children:n.map((e,t)=>(0,p.jsx)(`tr`,{children:YT(e).map((e,t)=>(0,p.jsx)(`td`,{children:JT(e)},t))},t))})]})})]})}function eE({props:e}){return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`pre`,{className:`obj-code`,"data-lang":JT(e.language),children:(0,p.jsx)(`code`,{children:JT(e.code)})})]})}function tE({part:e}){let t=typeof e==`object`&&e?e:{},n=typeof t.type==`string`?t.type:``;if(n===`group`||n===`tabs`||n===`sandbox`)return null;let r=iE[n];return r?(0,p.jsx)(`div`,{className:`obj-part obj-part-${n}`,children:(0,p.jsx)(r,{props:typeof t.props==`object`&&t.props!==null?t.props:{}})}):null}function nE({props:e}){let t=e.layout===`row`||e.layout===`column`?e.layout:`grid`;return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-group obj-group-${t}`,children:YT(e.items).map((e,t)=>(0,p.jsx)(tE,{part:e},t))})]})}function rE({props:e}){let t=YT(e.tabs).map(e=>typeof e==`object`&&e?e:{}),[n,r]=(0,l.useState)(0),i=Math.min(n,Math.max(0,t.length-1));return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-tabs`,role:`tablist`,children:t.map((e,t)=>(0,p.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":t===i,className:t===i?`on`:void 0,onClick:()=>r(t),children:JT(e.title)||`Tab ${t+1}`},t))}),t[i]&&(0,p.jsx)(tE,{part:t[i]})]})}var iE={card:XT,stat:ZT,list:QT,table:$T,code:eE,chart:fT,gauge:pT,timeline:mT,graph:vT,sandbox:qT,markdown:DT,image:PT,video:RT,pdf:zT,gallery:BT,group:nE,tabs:rE,progress:OT,checklist:kT,countdown:NT,kv:AT};function aE(e,t){let n=new Map(t.map(e=>[e.id,e])),r=[],i=new Set;for(let t of e){if(i.has(t.object.id))continue;i.add(t.object.id);let e=n.get(t.object.id);r.push(e?{object:e,leaving:!1}:{object:t.object,leaving:!0})}for(let e of t)i.has(e.id)||(i.add(e.id),r.push({object:e,leaving:!1}));return r}function oE(e,t){let[n,r]=(0,l.useState)(()=>e.map(e=>({object:e,leaving:!1}))),i=(0,l.useRef)(new Map);return(0,l.useEffect)(()=>{r(n=>{let a=aE(n,e),o=new Set(n.filter(e=>e.leaving).map(e=>e.object.id));for(let e of a){let n=i.current.get(e.object.id);if(!e.leaving)n&&clearTimeout(n),i.current.delete(e.object.id);else if(!o.has(e.object.id)&&!n){let n=e.object.id;i.current.set(n,setTimeout(()=>{i.current.delete(n),r(e=>e.filter(e=>!(e.object.id===n&&e.leaving)))},Math.max(t,0)))}}return t<=0?a.filter(e=>!e.leaving):a})},[e,t]),(0,l.useEffect)(()=>()=>{for(let e of i.current.values())clearTimeout(e);i.current.clear()},[]),n}var sE=.12,cE=.1,lE=.02,uE=(e,t,n)=>Math.min(Math.max(e,t),n);function dE(e){let t=uE(e.w,sE,1),n=uE(e.h,cE,1);return{x:uE(e.x,0,1-t),y:uE(e.y,0,1-n),w:t,h:n}}function fE(e,t){let n=t.getBoundingClientRect(),r=e.getBoundingClientRect();return n.width<=0||n.height<=0?null:dE({x:(r.left-n.left)/n.width,y:(r.top-n.top)/n.height,w:r.width/n.width,h:r.height/n.height})}function pE(e,t,n){let r=(0,l.useRef)(null),[i,a]=(0,l.useState)(null),o=(0,l.useCallback)((n,r)=>{let i=dE(r);t({type:`object.place`,id:n,placement:{x:i.x,y:i.y,w:i.w,h:i.h}}),e({type:`stage.move`,objectId:n,rect:i})},[e,t]),s=(0,l.useCallback)((e,t,i)=>{if(e.pointerType===`mouse`&&e.button!==0)return;let o=n(),s=e.currentTarget.closest(`[data-object]`);if(!o||!s||r.current)return;let c=fE(s,o);if(!c)return;let l=o.getBoundingClientRect();r.current={id:t.id,mode:i,pointer:e.pointerId,startX:e.clientX,startY:e.clientY,from:c,stageW:l.width,stageH:l.height};try{e.currentTarget.setPointerCapture(e.pointerId)}catch{}e.stopPropagation(),e.preventDefault(),a({id:t.id,box:c})},[n]),c=(e,t)=>{let n=(t.clientX-e.startX)/e.stageW,r=(t.clientY-e.startY)/e.stageH;return e.mode===`move`?dE({...e.from,x:e.from.x+n,y:e.from.y+r}):dE({...e.from,w:e.from.w+n,h:e.from.h+r})};return{preview:i,begin:s,move:(0,l.useCallback)(e=>{let t=r.current;t&&t.pointer===e.pointerId&&a({id:t.id,box:c(t,e)})},[]),end:(0,l.useCallback)((e,t)=>{let n=r.current;n&&n.pointer===e.pointerId&&(r.current=null,a(null),t||o(n.id,c(n,e)))},[o]),key:(0,l.useCallback)((e,t)=>{let r={ArrowLeft:[-.02,0],ArrowRight:[lE,0],ArrowUp:[0,-.02],ArrowDown:[0,lE]}[e.key],i=n(),a=e.currentTarget.closest(`[data-object]`);if(!r||!i||!a)return;let s=fE(a,i);s&&(e.preventDefault(),o(t.id,e.shiftKey?{...s,w:s.w+r[0],h:s.h+r[1]}:{...s,x:s.x+r[0],y:s.y+r[1]}))},[o,n])}}function mE(e,t){if(e===`auto`)return{position:`relative`};if(t.w<600)return{position:`relative`,width:`100%`};let[n,r,i,a]=typeof e==`string`?Nl[e]:[e.x*100,e.y*100,e.w*100,e.h*100],o={position:`absolute`,left:`${n}%`,top:`${r}%`,width:`${i}%`};return e===`top`||e===`bottom`?{...o,maxHeight:`${a}%`}:{...o,height:`${a}%`}}var hE=350,gE=()=>typeof matchMedia==`function`&&matchMedia(`(prefers-reduced-motion: reduce)`).matches,_E=class extends l.Component{state={failed:!1};static getDerivedStateFromError(){return{failed:!0}}render(){return this.state.failed?null:this.props.children}};function vE(){let e=()=>({w:window.innerWidth,h:window.innerHeight}),[t,n]=(0,l.useState)(e);return(0,l.useEffect)(()=>{let t=()=>n(e());return window.addEventListener(`resize`,t),()=>window.removeEventListener(`resize`,t)},[]),t}var yE=350;function bE({state:e,send:t,dispatch:n,voice:r,slash:i,onMenu:a}){let o=vE(),[s,c]=(0,l.useState)(0),[u,d]=(0,l.useState)(!1),f=ne(),m=o.w<600,h=e.scene===`focus`||e.scene===`multi`,g={"--accent":e.mood.accent,"--intensity":e.mood.intensity},_=e.voice.mode,v=_===`listening`?`listening`:_===`speaking`?`speaking`:_===`transcribing`?`thinking`:e.presence.state,y=Qb(e.look.reactivity),b=Math.min(1,(_===`listening`||_===`speaking`?e.voice.level:e.presence.amplitude)*y),x=(0,l.useRef)({timer:null,down:!1,talking:!1,id:null}),S=e=>{if(!(e.target===e.currentTarget||e.target.closest(`[data-presence]`))||e.pointerType===`mouse`&&e.button!==0)return;let t=x.current;if(!(t.down&&t.id!==null&&e.pointerId!==t.id)){t.timer&&clearTimeout(t.timer),t.down=!0,t.talking=!1,t.id=typeof e.pointerId==`number`?e.pointerId:null;try{t.id!==null&&e.currentTarget.setPointerCapture?.(t.id)}catch{}t.timer=r?setTimeout(()=>{t.down&&(t.talking=!0,r.pressStart())},yE):null}},C=(e,t)=>{let n=x.current;n.down&&(n.id===null||typeof e.pointerId!=`number`||e.pointerId===n.id)&&(n.down=!1,n.id=null,n.timer&&clearTimeout(n.timer),n.timer=null,n.talking?(n.talking=!1,t?r?.blur?.():r?.pressEnd()):t||c(e=>e+1))},w=(0,l.useRef)(null),T=pE(t,n,()=>w.current),E=oE(e.objects,gE()?0:hE),D=E.filter(e=>e.object.layer===`overlay`),O=E.filter(e=>e.object.layer!==`overlay`&&e.object.placement===`auto`),k=E.filter(e=>e.object.layer!==`overlay`&&e.object.placement!==`auto`),A=({object:e,leaving:r})=>{let i=iE[e.type];if(!i)return null;let a=e.layer===`overlay`,s=!m&&!r&&!a,c=T.preview?.id===e.id?T.preview.box:null,l=c?{x:c.x,y:c.y,w:c.w,h:c.h}:e.placement;return(0,p.jsxs)(`section`,{"data-object":e.id,className:`obj glass${e.style===`alert`?` alert`:``}${a?` overlay`:``}${e.pinned?` pinned`:``}${c?` dragging`:``}${r?` leaving`:``}`,style:a?void 0:mE(l,o),children:[s&&(0,p.jsx)(`div`,{className:`obj-grip`,role:`button`,tabIndex:0,"aria-label":`Move ${e.id}. Drag, or use the arrow keys; hold Shift to resize.`,onPointerDown:t=>T.begin(t,e,`move`),onPointerMove:T.move,onPointerUp:e=>T.end(e,!1),onPointerCancel:e=>T.end(e,!0),onKeyDown:t=>T.key(t,e)}),!a&&(0,p.jsx)(`button`,{className:`obj-pin${e.pinned?` on`:``}`,"aria-label":e.pinned?`Unpin ${e.id}`:`Pin ${e.id} to the screen`,"aria-pressed":!!e.pinned,title:e.pinned?`Pinned: stays on the screen. Click to unpin.`:`Pin: keep this on the screen.`,disabled:r,onClick:()=>t({type:`stage.pin`,objectId:e.id,pinned:!e.pinned}),children:(0,p.jsx)(`svg`,{width:`14`,height:`14`,viewBox:`0 0 24 24`,fill:e.pinned?`currentColor`:`none`,stroke:`currentColor`,strokeWidth:`2`,strokeLinecap:`round`,strokeLinejoin:`round`,"aria-hidden":`true`,children:(0,p.jsx)(`path`,{d:`M12 17v5M9 3h6l-1 7 3 3H7l3-3-1-7z`})})}),(0,p.jsx)(`button`,{className:`obj-close`,"aria-label":`Dismiss ${e.id}`,title:e.pinned?`Remove this widget`:`Dismiss`,disabled:r,onClick:()=>{t({type:`stage.event`,objectId:e.id,event:`dismiss`}),n({type:`object.dismiss`,id:e.id})},children:`×`}),s&&(0,p.jsx)(`div`,{className:`obj-resize`,"aria-hidden":`true`,onPointerDown:t=>T.begin(t,e,`resize`),onPointerMove:T.move,onPointerUp:e=>T.end(e,!1),onPointerCancel:e=>T.end(e,!0)}),(0,p.jsx)(_E,{children:(0,p.jsx)(i,{props:e.props})})]},e.id)};return(0,p.jsxs)(`div`,{ref:w,"data-testid":`stage`,className:`stage`,style:g,onPointerDown:S,onPointerUp:e=>C(e,!1),onPointerCancel:e=>C(e,!0),onContextMenu:e=>r&&e.preventDefault(),children:[e.look.ambient&&(0,p.jsx)(`div`,{className:`ambient`,"aria-hidden":`true`,style:{opacity:.35+.65*e.mood.intensity}}),(0,p.jsx)(Zb,{state:v,amplitude:b,pulse:e.presence.pulse,mode:h?`corner`:`full`,accent:e.mood.accent,style:e.presence.style,intensity:e.mood.intensity,scale:e.look.size}),(0,p.jsxs)(`div`,{className:m?`objects objects-stack`:`objects`,style:{zIndex:10},children:[O.length>0&&(0,p.jsx)(`div`,{className:`auto-grid`,children:O.map(A)}),k.map(A)]}),D.length>0&&(0,p.jsxs)(`div`,{className:`overlay-layer`,"data-testid":`overlay`,children:[(0,p.jsx)(`div`,{className:`overlay-backdrop`,onClick:()=>D.forEach(({object:e})=>{t({type:`stage.event`,objectId:e.id,event:`dismiss`}),n({type:`object.dismiss`,id:e.id})})}),D.map(A)]}),e.look.captions&&e.captions&&(0,p.jsx)(`p`,{className:`captions captions-${e.look.captionSize}${e.captionDone?` done`:``}`,"aria-live":`polite`,children:e.captions}),f&&r&&!u&&(0,p.jsx)(xx,{voice:r,mode:_,onType:()=>c(e=>e+1),onMenu:()=>a?.()}),(0,p.jsx)(vx,{requestOpen:s,slash:i,onOpenChange:d,onSend:e=>t({type:`chat.send`,text:e})})]})}function xE(){let e=()=>Math.random().toString(36).slice(2,12)+Date.now().toString(36);try{let t=sessionStorage.getItem(`friend.tab`);return t||(t=e(),sessionStorage.setItem(`friend.tab`,t)),t}catch{return e()}}function SE(){return`${location.protocol===`https:`?`wss`:`ws`}://${location.host}/ws`}function CE(e=SE()){let t=null,n=`connecting`,r=!1,i=0,a=!1,o=xE(),s=null,c=new Set,l=new Set,u=e=>{n=e,l.forEach(t=>t(e))};function d(){if(r)return;u(`connecting`);let n=new WebSocket(`${e}${e.includes(`?`)?`&`:`?`}tab=${o}${a?`&takeover=1`:``}`);t=n,n.onopen=()=>{i=0,a=!1,u(`open`)},n.onmessage=e=>{try{let t=JSON.parse(String(e.data));c.forEach(e=>e(t))}catch{}},n.onclose=e=>{if(!r){if(e.code===4401)return u(`unauthorized`);if(e.code===4409||e.code===4410)return u(`elsewhere`);u(`closed`),s=setTimeout(d,Math.min(500*2**i++,8e3))}},n.onerror=()=>{}}return d(),{send(e){t?.readyState===WebSocket.OPEN&&t.send(JSON.stringify(e))},onMessage(e){return c.add(e),()=>c.delete(e)},onState(e){return l.add(e),()=>l.delete(e)},state:()=>n,takeOver(){r||n!==`elsewhere`||(a=!0,i=0,d())},close(){r=!0,s&&clearTimeout(s),t?.close()}}}var wE={scene:`conversation`,objects:[],captions:``,captionDone:!0,presence:{state:`idle`,style:`sphere`,amplitude:0,pulse:0},mood:{accent:`#3fd8ff`,intensity:.6},approval:null,alerts:[],connection:`connecting`,chat:[],chatLive:!1,view:`companion`,look:{size:1,reactivity:.7,ambient:!0,captions:!0,captionSize:`medium`},viewKnown:!1,busy:!1,activity:null,deviceOnline:!1,voice:{mode:`idle`,level:0,available:!1,enrolled:!1},challenge:null,camera:{enabled:!1,stream:null},speaker:null,ownerName:``,assistantName:``,hud:null,music:null,hostMusic:null,musicCmd:null,uiOpen:null},TE=200,EE=e=>e.length>TE?e.slice(-200):e,DE=0,OE=e=>Math.min(1,Math.max(0,e));function kE(e,t){switch(t.cmd){case`scene`:return{...e,scene:t.mode};case`show`:{let n=e.objects.findIndex(e=>e.id===t.object.id),r=n===-1?[...e.objects,t.object]:e.objects.map((e,r)=>r===n?t.object:e);return{...e,objects:r}}case`update`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,props:{...e.props,...t.props}}:e)};case`hide`:return{...e,objects:e.objects.filter(e=>e.id!==t.id)};case`clear`:return{...e,objects:e.objects.filter(e=>e.pinned),scene:`conversation`};case`pin`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,pinned:!0}:e)};case`unpin`:return{...e,objects:e.objects.map(e=>e.id===t.id?(({pinned:e,...t})=>t)(e):e)};case`place`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,placement:t.placement}:e)};case`presence`:return{...e,presence:{...e.presence,state:t.state??e.presence.state,style:t.style??e.presence.style}};case`mood`:return{...e,mood:{accent:t.accent??e.mood.accent,intensity:t.intensity??e.mood.intensity}}}}function AE(e,t){let n=t;if(n&&typeof n==`object`){if(n.type===`conn`)return{...e,connection:n.value};if(n.type===`chat.seed`){let t=Array.isArray(n.lines)?n.lines:[];return e.chat.length===0?{...e,chat:EE(t)}:{...e,chat:EE([...t,...e.chat])}}if(n.type===`alert.add`)return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:n.level,text:n.text}]};if(n.type===`camera.enable`)return{...e,camera:{enabled:n.value,stream:n.value?e.camera.stream:null}};if(n.type===`camera.open`)return{...e,camera:{...e.camera,stream:n.stream}};if(n.type===`camera.closed`)return{...e,camera:{...e.camera,stream:null}};if(n.type===`challenge.dismiss`)return e.challenge?.id===n.id?{...e,challenge:null}:e;if(n.type===`voice.mode`)return{...e,voice:{...e.voice,mode:n.mode,level:n.mode===`idle`?0:e.voice.level}};if(n.type===`voice.level`){let t=Number.isFinite(n.level)?Math.min(1,Math.max(0,n.level)):0;return{...e,voice:{...e.voice,level:t}}}if(n.type===`object.dismiss`)return{...e,objects:e.objects.filter(e=>e.id!==n.id)};if(n.type===`object.place`)return{...e,objects:e.objects.map(e=>e.id===n.id?{...e,placement:n.placement}:e)};if(n.type===`alert.dismiss`)return{...e,alerts:e.alerts.filter(e=>e.id!==n.id)}}let r=eu.safeParse(t);if(!r.success)return e;let i=r.data;switch(i.type){case`snapshot`:return{...e,scene:i.stage.scene,objects:i.stage.objects,presence:{...e.presence,state:i.stage.presence.state,style:i.stage.presence.style},mood:i.stage.mood,approval:i.pendingApproval??null};case`stage`:return kE(e,i.command);case`chat.user`:return{...e,chat:EE([...e.chat,{role:`user`,text:i.text}]),chatLive:!1};case`ui.open`:return{...e,uiOpen:{n:(e.uiOpen?.n??0)+1,...i.integration?{integration:i.integration}:{}}};case`ui`:return{...e,view:i.view,look:i.look??e.look,ownerName:i.ownerName??e.ownerName,assistantName:i.assistantName??e.assistantName,hud:i.hud??e.hud,music:i.music??e.music,viewKnown:!0};case`music.host`:return{...e,hostMusic:i.state};case`music.command`:{let{type:t,...n}=i;return{...e,musicCmd:{n:(e.musicCmd?.n??0)+1,command:n}}}case`caption.delta`:{let t=e.captionDone,n=e.chat.at(-1),r=e.chatLive&&n?.role===`assistant`?[...e.chat.slice(0,-1),{role:`assistant`,text:n.text+i.text}]:EE([...e.chat,{role:`assistant`,text:i.text}]);return{...e,chat:r,chatLive:!0,captions:(t?``:e.captions)+i.text,captionDone:!1,presence:{...e.presence,amplitude:OE(.3+i.text.length*.04),pulse:e.presence.pulse+1}}}case`caption.end`:return{...e,chatLive:!1,captionDone:!0,presence:{...e.presence,amplitude:0}};case`approval.request`:{let{type:t,...n}=i;return{...e,approval:n}}case`approval.resolved`:return e.approval?.id===i.id?{...e,approval:null}:e;case`alert`:return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:i.level,text:i.text}]};case`activity`:return{...e,activity:i.text};case`status`:return{...e,busy:i.busy,activity:i.busy?e.activity:null,deviceOnline:i.deviceOnline,voice:{...e.voice,available:i.voiceAvailable??e.voice.available,enrolled:i.voiceEnrolled??e.voice.enrolled}};case`error`:return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:`error`,text:i.message}]};case`voice.heard`:return{...e,captions:i.trust===`guest`?`Guest: ${i.text}`:i.trust===`member`&&i.speaker?`${i.speaker}: ${i.text}`:i.text,captionDone:!0,speaker:{name:i.trust===`member`?i.speaker??null:null,trust:i.trust??`unverified`,seq:(e.speaker?.seq??0)+1}};case`voice.challenge`:return{...e,challenge:{id:i.id,text:i.text}};case`voice.challenge.end`:return e.challenge?.id===i.id?{...e,challenge:null}:e;case`audio.chunk`:case`audio.stop`:return e;case`camera.request`:case`camera.cancel`:case`screen.request`:case`screen.cancel`:return e}}var jE=1024,ME=.8,NE=300;function PE(e,t){let n=Math.min(1,jE/Math.max(e,t));return{width:Math.round(e*n),height:Math.round(t*n)}}function FE(e){let t=e?.name;return t===`NotAllowedError`||t===`SecurityError`?`permission`:t===`NotFoundError`||t===`OverconstrainedError`?`no-camera`:`busy`}async function IE(){if(!navigator.mediaDevices?.getUserMedia)throw Object.assign(Error(`This browser cannot use the camera here (use localhost or HTTPS).`),{name:`NotFoundError`});return navigator.mediaDevices.getUserMedia({video:{width:{ideal:1280}},audio:!1})}async function LE(e,t=NE){let n=document.createElement(`video`);n.muted=!0,n.playsInline=!0,n.srcObject=e,await n.play(),await new Promise(e=>setTimeout(e,t));let{width:r,height:i}=PE(n.videoWidth||640,n.videoHeight||480),a=document.createElement(`canvas`);return a.width=r,a.height=i,a.getContext(`2d`).drawImage(n,0,0,r,i),n.srcObject=null,new Promise((e,t)=>a.toBlob(n=>n?e(n):t(Error(`Could not encode the picture.`)),`image/jpeg`,ME))}var RE=class{opts;active=null;constructor(e){this.opts=e}async handle(e){if(e.type===`camera.cancel`){let t=this.active;t&&t.id===e.id&&(t.cancelled=!0,this.release(t));return}if(!this.opts.enabled())return this.opts.send({type:`camera.denied`,id:e.id,reason:`off`});if(this.active)return this.opts.send({type:`camera.denied`,id:e.id,reason:`busy`});let t={id:e.id,cancelled:!1,stream:null,opened:!1,released:!1};this.active=t;try{let n=await(this.opts.open??IE)();if(t.stream=n,t.cancelled){n.getTracks().forEach(e=>e.stop());return}t.opened=!0,this.opts.dispatch({type:`camera.open`,stream:n});let r=await(this.opts.frame??(e=>LE(e)))(n);if(t.cancelled)return;this.release(t);try{await this.opts.upload(e.id,r)}catch{this.opts.dispatch({type:`alert.add`,level:`warn`,text:`Could not send the camera picture to Friend.`})}}catch(n){t.cancelled||this.opts.send({type:`camera.denied`,id:e.id,reason:FE(n)})}finally{this.release(t),this.active===t&&(this.active=null)}}dispose(){let e=this.active;e&&(e.cancelled=!0,this.release(e))}release(e){e.released||(e.released=!0,e.stream?.getTracks().forEach(e=>e.stop()),e.opened&&this.opts.dispatch({type:`camera.closed`}))}};function zE(e,t){if(e.match(/^[a-z]+:\/\//i))return e;if(e.match(/^\/\//))return window.location.protocol+e;if(e.match(/^[a-z]+:/i))return e;let n=document.implementation.createHTMLDocument(),r=n.createElement(`base`),i=n.createElement(`a`);return n.head.appendChild(r),n.body.appendChild(i),t&&(r.href=t),i.href=e,i.href}var BE=(()=>{let e=0,t=()=>`0000${(Math.random()*36**4<<0).toString(36)}`.slice(-4);return()=>(e+=1,`u${t()}${e}`)})();function VE(e){let t=[];for(let n=0,r=e.length;n<r;n++)t.push(e[n]);return t}var HE=null;function UE(e={}){return HE||(e.includeStyleProperties?(HE=e.includeStyleProperties,HE):(HE=VE(window.getComputedStyle(document.documentElement)),HE))}function WE(e,t){let n=(e.ownerDocument.defaultView||window).getComputedStyle(e).getPropertyValue(t);return n?parseFloat(n.replace(`px`,``)):0}function GE(e){let t=WE(e,`border-left-width`),n=WE(e,`border-right-width`);return e.clientWidth+t+n}function KE(e){let t=WE(e,`border-top-width`),n=WE(e,`border-bottom-width`);return e.clientHeight+t+n}function qE(e,t={}){return{width:t.width||GE(e),height:t.height||KE(e)}}function JE(){let e,t;try{t=process}catch{}let n=t&&t.env?t.env.devicePixelRatio:null;return n&&(e=parseInt(n,10),Number.isNaN(e)&&(e=1)),e||window.devicePixelRatio||1}var YE=16384;function XE(e){(e.width>YE||e.height>YE)&&(e.width>YE&&e.height>YE?e.width>e.height?(e.height*=YE/e.width,e.width=YE):(e.width*=YE/e.height,e.height=YE):e.width>YE?(e.height*=YE/e.width,e.width=YE):(e.width*=YE/e.height,e.height=YE))}function ZE(e){return new Promise((t,n)=>{let r=new Image;r.onload=()=>{r.decode().then(()=>{requestAnimationFrame(()=>t(r))})},r.onerror=n,r.crossOrigin=`anonymous`,r.decoding=`async`,r.src=e})}async function QE(e){return Promise.resolve().then(()=>new XMLSerializer().serializeToString(e)).then(encodeURIComponent).then(e=>`data:image/svg+xml;charset=utf-8,${e}`)}async function $E(e,t,n){let r=`http://www.w3.org/2000/svg`,i=document.createElementNS(r,`svg`),a=document.createElementNS(r,`foreignObject`);return i.setAttribute(`width`,`${t}`),i.setAttribute(`height`,`${n}`),i.setAttribute(`viewBox`,`0 0 ${t} ${n}`),a.setAttribute(`width`,`100%`),a.setAttribute(`height`,`100%`),a.setAttribute(`x`,`0`),a.setAttribute(`y`,`0`),a.setAttribute(`externalResourcesRequired`,`true`),i.appendChild(a),a.appendChild(e),QE(i)}var eD=(e,t)=>{if(e instanceof t)return!0;let n=Object.getPrototypeOf(e);return n===null?!1:n.constructor.name===t.name||eD(n,t)};function tD(e){let t=e.getPropertyValue(`content`);return`${e.cssText} content: '${t.replace(/'|"/g,``)}';`}function nD(e,t){return UE(t).map(t=>`${t}: ${e.getPropertyValue(t)}${e.getPropertyPriority(t)?` !important`:``};`).join(` `)}function rD(e,t,n,r){let i=`.${e}:${t}`,a=n.cssText?tD(n):nD(n,r);return document.createTextNode(`${i}{${a}}`)}function iD(e,t,n,r){let i=window.getComputedStyle(e,n),a=i.getPropertyValue(`content`);if(a===``||a===`none`)return;let o=BE();try{t.className=`${t.className} ${o}`}catch{return}let s=document.createElement(`style`);s.appendChild(rD(o,n,i,r)),t.appendChild(s)}function aD(e,t,n){iD(e,t,`:before`,n),iD(e,t,`:after`,n)}var oD=`application/font-woff`,sD=`image/jpeg`,cD={woff:oD,woff2:oD,ttf:`application/font-truetype`,eot:`application/vnd.ms-fontobject`,png:`image/png`,jpg:sD,jpeg:sD,gif:`image/gif`,tiff:`image/tiff`,svg:`image/svg+xml`,webp:`image/webp`};function lD(e){let t=/\.([^./]*?)$/g.exec(e);return t?t[1]:``}function uD(e){return cD[lD(e).toLowerCase()]||``}function dD(e){return e.split(/,/)[1]}function fD(e){return e.search(/^(data:)/)!==-1}function pD(e,t){return`data:${t};base64,${e}`}async function mD(e,t,n){let r=await fetch(e,t);if(r.status===404)throw Error(`Resource "${r.url}" not found`);let i=await r.blob();return new Promise((e,t)=>{let a=new FileReader;a.onerror=t,a.onloadend=()=>{try{e(n({res:r,result:a.result}))}catch(e){t(e)}},a.readAsDataURL(i)})}var hD={};function gD(e,t,n){let r=e.replace(/\?.*/,``);return n&&(r=e),/ttf|otf|eot|woff2?/i.test(r)&&(r=r.replace(/.*\//,``)),t?`[${t}]${r}`:r}async function _D(e,t,n){let r=gD(e,t,n.includeQueryParams);if(hD[r]!=null)return hD[r];n.cacheBust&&(e+=(/\?/.test(e)?`&`:`?`)+new Date().getTime());let i;try{i=pD(await mD(e,n.fetchRequestInit,({res:e,result:n})=>(t||=e.headers.get(`Content-Type`)||``,dD(n))),t)}catch(t){i=n.imagePlaceholder||``;let r=`Failed to fetch resource: ${e}`;t&&(r=typeof t==`string`?t:t.message),r&&console.warn(r)}return hD[r]=i,i}async function vD(e){let t=e.toDataURL();return t===`data:,`?e.cloneNode(!1):ZE(t)}async function yD(e,t){if(e.currentSrc){let t=document.createElement(`canvas`),n=t.getContext(`2d`);return t.width=e.clientWidth,t.height=e.clientHeight,n?.drawImage(e,0,0,t.width,t.height),ZE(t.toDataURL())}let n=e.poster;return ZE(await _D(n,uD(n),t))}async function bD(e,t){try{if(e?.contentDocument?.body)return await AD(e.contentDocument.body,t,!0)}catch{}return e.cloneNode(!1)}async function xD(e,t){return eD(e,HTMLCanvasElement)?vD(e):eD(e,HTMLVideoElement)?yD(e,t):eD(e,HTMLIFrameElement)?bD(e,t):e.cloneNode(CD(e))}var SD=e=>e.tagName!=null&&e.tagName.toUpperCase()===`SLOT`,CD=e=>e.tagName!=null&&e.tagName.toUpperCase()===`SVG`;async function wD(e,t,n){if(CD(t))return t;let r=[];return r=SD(e)&&e.assignedNodes?VE(e.assignedNodes()):eD(e,HTMLIFrameElement)&&e.contentDocument?.body?VE(e.contentDocument.body.childNodes):VE((e.shadowRoot??e).childNodes),r.length===0||eD(e,HTMLVideoElement)||await r.reduce((e,r)=>e.then(()=>AD(r,n)).then(e=>{e&&t.appendChild(e)}),Promise.resolve()),t}function TD(e,t,n){let r=t.style;if(!r)return;let i=window.getComputedStyle(e);i.cssText?(r.cssText=i.cssText,r.transformOrigin=i.transformOrigin):UE(n).forEach(n=>{let a=i.getPropertyValue(n);n===`font-size`&&a.endsWith(`px`)&&(a=`${Math.floor(parseFloat(a.substring(0,a.length-2)))-.1}px`),eD(e,HTMLIFrameElement)&&n===`display`&&a===`inline`&&(a=`block`),n===`d`&&t.getAttribute(`d`)&&(a=`path(${t.getAttribute(`d`)})`),r.setProperty(n,a,i.getPropertyPriority(n))})}function ED(e,t){eD(e,HTMLTextAreaElement)&&(t.innerHTML=e.value),eD(e,HTMLInputElement)&&t.setAttribute(`value`,e.value)}function DD(e,t){if(eD(e,HTMLSelectElement)){let n=t,r=Array.from(n.children).find(t=>e.value===t.getAttribute(`value`));r&&r.setAttribute(`selected`,``)}}function OD(e,t,n){return eD(t,Element)&&(TD(e,t,n),aD(e,t,n),ED(e,t),DD(e,t)),t}async function kD(e,t){let n=e.querySelectorAll?e.querySelectorAll(`use`):[];if(n.length===0)return e;let r={};for(let i=0;i<n.length;i++){let a=n[i].getAttribute(`xlink:href`);if(a){let n=e.querySelector(a),i=document.querySelector(a);!n&&i&&!r[a]&&(r[a]=await AD(i,t,!0))}}let i=Object.values(r);if(i.length){let t=`http://www.w3.org/1999/xhtml`,n=document.createElementNS(t,`svg`);n.setAttribute(`xmlns`,t),n.style.position=`absolute`,n.style.width=`0`,n.style.height=`0`,n.style.overflow=`hidden`,n.style.display=`none`;let r=document.createElementNS(t,`defs`);n.appendChild(r);for(let e=0;e<i.length;e++)r.appendChild(i[e]);e.appendChild(n)}return e}async function AD(e,t,n){return!n&&t.filter&&!t.filter(e)?null:Promise.resolve(e).then(e=>xD(e,t)).then(n=>wD(e,n,t)).then(n=>OD(e,n,t)).then(e=>kD(e,t))}var jD=/url\((['"]?)([^'"]+?)\1\)/g,MD=/url\([^)]+\)\s*format\((["']?)([^"']+)\1\)/g,ND=/src:\s*(?:url\([^)]+\)\s*format\([^)]+\)[,;]\s*)+/g;function PD(e){let t=e.replace(/([.*+?^${}()|\[\]\/\\])/g,`\\$1`);return RegExp(`(url\\(['"]?)(${t})(['"]?\\))`,`g`)}function FD(e){let t=[];return e.replace(jD,(e,n,r)=>(t.push(r),e)),t.filter(e=>!fD(e))}async function ID(e,t,n,r,i){try{let a=n?zE(t,n):t,o=uD(t),s;return s=i?pD(await i(a),o):await _D(a,o,r),e.replace(PD(t),`$1${s}$3`)}catch{}return e}function LD(e,{preferredFontFormat:t}){return t?e.replace(ND,e=>{for(;;){let[n,,r]=MD.exec(e)||[];if(!r)return``;if(r===t)return`src: ${n};`}}):e}function RD(e){return e.search(jD)!==-1}async function zD(e,t,n){if(!RD(e))return e;let r=LD(e,n);return FD(r).reduce((e,r)=>e.then(e=>ID(e,r,t,n)),Promise.resolve(r))}async function BD(e,t,n){let r=t.style?.getPropertyValue(e);if(r){let i=await zD(r,null,n);return t.style.setProperty(e,i,t.style.getPropertyPriority(e)),!0}return!1}async function VD(e,t){await BD(`background`,e,t)||await BD(`background-image`,e,t),await BD(`mask`,e,t)||await BD(`-webkit-mask`,e,t)||await BD(`mask-image`,e,t)||await BD(`-webkit-mask-image`,e,t)}async function HD(e,t){let n=eD(e,HTMLImageElement);if((!n||fD(e.src))&&(!eD(e,SVGImageElement)||fD(e.href.baseVal)))return;let r=n?e.src:e.href.baseVal,i=await _D(r,uD(r),t);await new Promise((r,a)=>{e.onload=r,e.onerror=t.onImageErrorHandler?(...e)=>{try{r(t.onImageErrorHandler(...e))}catch(e){a(e)}}:a;let o=e;o.decode&&=r,o.loading===`lazy`&&(o.loading=`eager`),n?(e.srcset=``,e.src=i):e.href.baseVal=i})}async function UD(e,t){let n=VE(e.childNodes).map(e=>WD(e,t));await Promise.all(n).then(()=>e)}async function WD(e,t){eD(e,Element)&&(await VD(e,t),await HD(e,t),await UD(e,t))}function GD(e,t){let{style:n}=e;t.backgroundColor&&(n.backgroundColor=t.backgroundColor),t.width&&(n.width=`${t.width}px`),t.height&&(n.height=`${t.height}px`);let r=t.style;return r!=null&&Object.keys(r).forEach(e=>{n[e]=r[e]}),e}var KD={};async function qD(e){let t=KD[e];return t??(t={url:e,cssText:await(await fetch(e)).text()},KD[e]=t,t)}async function JD(e,t){let n=e.cssText,r=/url\(["']?([^"')]+)["']?\)/g,i=(n.match(/url\([^)]+\)/g)||[]).map(async i=>{let a=i.replace(r,`$1`);return a.startsWith(`https://`)||(a=new URL(a,e.url).href),mD(a,t.fetchRequestInit,({result:e})=>(n=n.replace(i,`url(${e})`),[i,e]))});return Promise.all(i).then(()=>n)}function YD(e){if(e==null)return[];let t=[],n=e.replace(/(\/\*[\s\S]*?\*\/)/gi,``),r=RegExp(`((@.*?keyframes [\\s\\S]*?){([\\s\\S]*?}\\s*?)})`,`gi`);for(;;){let e=r.exec(n);if(e===null)break;t.push(e[0])}n=n.replace(r,``);let i=/@import[\s\S]*?url\([^)]*\)[\s\S]*?;/gi,a=RegExp(`((\\s*?(?:\\/\\*[\\s\\S]*?\\*\\/)?\\s*?@media[\\s\\S]*?){([\\s\\S]*?)}\\s*?})|(([\\s\\S]*?){([\\s\\S]*?)})`,`gi`);for(;;){let e=i.exec(n);if(e===null){if(e=a.exec(n),e===null)break;i.lastIndex=a.lastIndex}else a.lastIndex=i.lastIndex;t.push(e[0])}return t}async function XD(e,t){let n=[],r=[];return e.forEach(n=>{if(`cssRules`in n)try{VE(n.cssRules||[]).forEach((e,i)=>{if(e.type===CSSRule.IMPORT_RULE){let a=i+1,o=e.href,s=qD(o).then(e=>JD(e,t)).then(e=>YD(e).forEach(e=>{try{n.insertRule(e,e.startsWith(`@import`)?a+=1:n.cssRules.length)}catch(t){console.error(`Error inserting rule from remote css`,{rule:e,error:t})}})).catch(e=>{console.error(`Error loading remote css`,e.toString())});r.push(s)}})}catch(i){let a=e.find(e=>e.href==null)||document.styleSheets[0];n.href!=null&&r.push(qD(n.href).then(e=>JD(e,t)).then(e=>YD(e).forEach(e=>{a.insertRule(e,a.cssRules.length)})).catch(e=>{console.error(`Error loading remote stylesheet`,e)})),console.error(`Error inlining remote css file`,i)}}),Promise.all(r).then(()=>(e.forEach(e=>{if(`cssRules`in e)try{VE(e.cssRules||[]).forEach(e=>{n.push(e)})}catch(t){console.error(`Error while reading CSS rules from ${e.href}`,t)}}),n))}function ZD(e){return e.filter(e=>e.type===CSSRule.FONT_FACE_RULE).filter(e=>RD(e.style.getPropertyValue(`src`)))}async function QD(e,t){if(e.ownerDocument==null)throw Error(`Provided element is not within a Document`);return ZD(await XD(VE(e.ownerDocument.styleSheets),t))}function $D(e){return e.trim().replace(/["']/g,``)}function eO(e){let t=new Set;function n(e){(e.style.fontFamily||getComputedStyle(e).fontFamily).split(`,`).forEach(e=>{t.add($D(e))}),Array.from(e.children).forEach(e=>{e instanceof HTMLElement&&n(e)})}return n(e),t}async function tO(e,t){let n=await QD(e,t),r=eO(e);return(await Promise.all(n.filter(e=>r.has($D(e.style.fontFamily))).map(e=>{let n=e.parentStyleSheet?e.parentStyleSheet.href:null;return zD(e.cssText,n,t)}))).join(`
4455
+ Please report this to https://github.com/markedjs/marked.`,e){let e=`<p>An error occurred:</p><pre>`+Sw(n.message+``,!0)+`</pre>`;return t?Promise.resolve(e):e}if(t)return Promise.reject(n);throw n}}};function Vw(e,t){return Bw.parse(e,t)}Vw.options=Vw.setOptions=function(e){return Bw.setOptions(e),Vw.defaults=Bw.defaults,$S(Vw.defaults),Vw},Vw.getDefaults=ZS,Vw.defaults=QS;function Hw(...e){return Bw.use(...e),Vw.defaults=Bw.defaults,$S(Vw.defaults),Vw}Vw.use=Hw,Vw.walkTokens=function(e,t){return Bw.walkTokens(e,t)},Vw.parseInline=Bw.parseInline,Vw.Parser=Rw,Vw.parser=Rw.parse,Vw.Renderer=Iw,Vw.TextRenderer=Lw,Vw.Lexer=Fw,Vw.lexer=Fw.lex,Vw.Tokenizer=Pw,Vw.Hooks=zw,Vw.parse=Vw,Vw.options,Vw.setOptions,Vw.walkTokens,Vw.parseInline,Rw.parse,Fw.lex;var Uw=!1;function Ww(){Uw||(Uw=!0,XS.addHook(`afterSanitizeAttributes`,e=>{e instanceof Element&&e.tagName===`A`&&(e.setAttribute(`rel`,`noopener noreferrer`),e.setAttribute(`target`,`_blank`))}))}function Gw(e){Ww();let t=Vw.parse(e,{async:!1,breaks:!0});return XS.sanitize(t,{ALLOWED_TAGS:[`p`,`br`,`strong`,`em`,`code`,`pre`,`ul`,`ol`,`li`,`a`,`h1`,`h2`,`h3`,`h4`,`h5`,`h6`,`blockquote`,`hr`,`del`,`table`,`thead`,`tbody`,`tr`,`th`,`td`],ALLOWED_ATTR:[`href`,`rel`,`target`],ALLOWED_URI_REGEXP:/^(?:https?:|mailto:)/i})}var Kw=e=>Number.isFinite(e);function qw(e){let t=Math.floor(Math.log10(e)),n=e/10**t;return(n<=1?1:n<=2?2:n<=2.5?2.5:n<=5?5:10)*10**t}function Jw(e,t,n=5){let r=Kw(e)?e:0,i=Kw(t)?t:r+1;r>i&&([r,i]=[i,r]),r===i&&(i=r+(Math.abs(r)||1));let a=qw((i-r)/Math.max(1,n-1)),o=Math.floor(r/a)*a,s=Math.ceil(i/a)*a,c=[];for(let e=o;e<=s+a/2;e+=a)c.push(Math.round(e*1e9)/1e9);return{min:o,max:s,ticks:c}}function Yw(e,t){let[n,r]=e,[i,a]=t;return r===n?()=>i:e=>i+(e-n)/(r-n)*(a-i)}function Xw(e){return e.map(([e,t],n)=>`${n===0?`M`:`L`}${e.toFixed(2)} ${t.toFixed(2)}`).join(` `)}function Zw(e,t,n,r,i){let a=r=>{let i=r*Math.PI/180;return`${(e+n*Math.cos(i)).toFixed(2)} ${(t+n*Math.sin(i)).toFixed(2)}`},o=+(Math.abs(i-r)>180);return`M ${a(r)} A ${n} ${n} 0 ${o} 1 ${a(i)}`}function Qw(e,t,n){return!Kw(e)||!Kw(t)||!Kw(n)||n<=t?0:Math.min(1,Math.max(0,(e-t)/(n-t)))*240}function $w(e,t,n,r){let i=t.x-e.x,a=t.y-e.y,o=Math.hypot(i,a);if(o===0||o<=n+r)return{from:{...e},to:{...t}};let s=i/o,c=a/o;return{from:{x:e.x+s*n,y:e.y+c*n},to:{x:t.x-s*r,y:t.y-c*r}}}function eT(e,t,n){if(e<=0)return[];if(e===1)return[{x:t/2,y:n/2}];let r=Math.min(t,n)*.36;return Array.from({length:e},(i,a)=>{let o=-Math.PI/2+a*2*Math.PI/e;return{x:t/2+r*Math.cos(o),y:n/2+r*Math.sin(o)}})}var tT=e=>typeof e==`object`&&!!e&&!Array.isArray(e),nT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,rT=e=>Array.isArray(e)?e:[],iT=e=>typeof e==`number`?Number.isFinite(e)?e:null:typeof e==`string`&&e.trim()!==``&&Number.isFinite(Number(e))?Number(e):null,aT=(e,t)=>e.length>t?e.slice(0,t)+`…`:e,oT=[`var(--accent)`,`#ffb454`,`#7b8cff`,`#5ef0b0`,`#ff6b7a`,`#c792ea`],sT=({text:e})=>e?(0,p.jsx)(`h3`,{className:`obj-title`,children:e}):null,cT=({text:e=`No data`})=>(0,p.jsx)(`p`,{className:`obj-empty`,children:e}),lT=400,uT=220,dT={l:44,r:12,t:10,b:28};function fT({props:e}){let t=e.kind===`bar`||e.kind===`area`?e.kind:`line`,n=rT(e.labels).slice(0,120).map(nT),r=rT(e.series).slice(0,6).map((e,t)=>{let n=tT(e)?e:{},r=rT(n.values).slice(0,120).map((e,t)=>({idx:t,v:iT(e)})).filter(e=>e.v!==null);return{name:nT(n.name)||`series ${t+1}`,points:r}}).filter(e=>e.points.length>0);if(r.length===0)return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{})]});let i=r.flatMap(e=>e.points.map(e=>e.v)),a=Math.min(...i),o=Math.max(...i),s=Jw(t===`line`?a:Math.min(0,a),t===`line`?o:Math.max(0,o),5),c=Math.max(n.length,...r.map(e=>e.points[e.points.length-1].idx+1),2),l=Yw([s.min,s.max],[uT-dT.b,dT.t]),u=Yw([0,c-1],[dT.l,lT-dT.r]),d=(lT-dT.l-dT.r)/c,f=Math.max(1,d*.7/r.length),m=(e,t)=>dT.l+e*d+d*.15+t*f,h=Math.max(1,Math.ceil(c/6)),g=nT(e.unit);return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsxs)(`svg`,{className:`obj-chart`,viewBox:`0 0 ${lT} ${uT}`,role:`img`,"aria-label":nT(e.title)||`chart`,children:[s.ticks.map(e=>(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`line`,{className:`grid`,x1:dT.l,x2:lT-dT.r,y1:l(e),y2:l(e)}),(0,p.jsxs)(`text`,{className:`tick`,x:dT.l-6,y:l(e)+3,textAnchor:`end`,children:[e,g&&e===s.max?g:``]})]},e)),Array.from({length:c},(e,t)=>t).filter(e=>e%h===0&&n[e]).map(e=>(0,p.jsx)(`text`,{className:`tick`,x:t===`bar`?m(e,0)+f*r.length/2:u(e),y:212,textAnchor:`middle`,children:aT(n[e],8)},e)),r.map((e,n)=>{let r=oT[n%oT.length];if(t===`bar`)return(0,p.jsx)(`g`,{children:e.points.map(e=>(0,p.jsx)(`rect`,{className:`bar`,x:m(e.idx,n),y:Math.min(l(e.v),l(0)),width:f,height:Math.abs(l(e.v)-l(0)),fill:r},e.idx))},n);let i=e.points.map(e=>[u(e.idx),l(e.v)]),a=Xw(i),o=`${a} L${i[i.length-1][0].toFixed(2)} ${l(s.min).toFixed(2)} L${i[0][0].toFixed(2)} ${l(s.min).toFixed(2)} Z`;return(0,p.jsxs)(`g`,{children:[t===`area`&&(0,p.jsx)(`path`,{className:`series-area`,d:o,fill:r,opacity:.18}),(0,p.jsx)(`path`,{className:`series-line`,d:a,fill:`none`,stroke:r,strokeWidth:2,strokeLinejoin:`round`})]},n)})]}),r.length>1&&(0,p.jsx)(`ul`,{className:`legend`,children:r.map((e,t)=>(0,p.jsxs)(`li`,{children:[(0,p.jsx)(`i`,{style:{background:oT[t%oT.length]}}),(0,p.jsx)(`span`,{children:e.name})]},t))})]})}function pT({props:e}){let t=iT(e.min)??0,n=iT(e.max)??100,r=iT(e.value)??t,i=Qw(r,t,n),a=i/240;return(0,p.jsxs)(`div`,{className:`obj-gauge ${a>.95?`gauge-crit`:a>.8?`gauge-warn`:``}`,children:[(0,p.jsxs)(`svg`,{viewBox:`0 0 200 150`,role:`img`,"aria-label":`${nT(e.label)} ${r}`,children:[(0,p.jsx)(`path`,{className:`track`,d:Zw(100,100,70,150,390),fill:`none`,strokeWidth:12,strokeLinecap:`round`}),i>0&&(0,p.jsx)(`path`,{className:`value`,d:Zw(100,100,70,150,150+i),fill:`none`,strokeWidth:12,strokeLinecap:`round`})]}),(0,p.jsxs)(`div`,{className:`gauge-read`,children:[(0,p.jsx)(`span`,{className:`gauge-value`,children:String(Math.round(r*100)/100)}),nT(e.unit)&&(0,p.jsx)(`small`,{className:`gauge-unit`,children:nT(e.unit)})]}),(0,p.jsx)(`span`,{className:`obj-label`,children:nT(e.label)})]})}function mT({props:e}){let t=rT(e.items).slice(0,30).map(e=>tT(e)?e:{}).map(e=>({time:nT(e.time),title:nT(e.title),detail:nT(e.detail)})).filter(e=>e.title||e.time);return t.length===0?(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{text:`Nothing to show`})]}):(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(`ol`,{className:`obj-timeline`,children:t.map((e,t)=>(0,p.jsxs)(`li`,{children:[(0,p.jsx)(`time`,{children:e.time}),(0,p.jsx)(`strong`,{children:e.title}),e.detail&&(0,p.jsx)(`span`,{children:e.detail})]},t))})]})}var hT=400,gT=300,_T=12;function vT({props:e}){let t=(0,l.useId)(),n=new Set,r=[];for(let t of rT(e.nodes)){let e=tT(t)?t:{},i=nT(e.id);if(i&&!n.has(i)&&(n.add(i),r.push({id:i,label:nT(e.label)||i}),r.length>=40))break}if(r.length===0)return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsx)(cT,{text:`Nothing to show`})]});let i=new Map(r.map((e,t)=>[e.id,eT(r.length,hT,gT)[t]])),a=[];for(let t of rT(e.edges)){let e=tT(t)?t:{},n=nT(e.from),r=nT(e.to);if(i.has(n)&&i.has(r)&&n!==r&&(a.push({from:n,to:r,label:nT(e.label)}),a.length>=80))break}return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(sT,{text:nT(e.title)}),(0,p.jsxs)(`svg`,{className:`obj-graph`,viewBox:`0 0 ${hT} ${gT}`,role:`img`,"aria-label":nT(e.title)||`graph`,children:[(0,p.jsx)(`defs`,{children:(0,p.jsx)(`marker`,{id:t,viewBox:`0 0 10 10`,refX:`9`,refY:`5`,markerWidth:`6`,markerHeight:`6`,orient:`auto-start-reverse`,children:(0,p.jsx)(`path`,{d:`M0 0 L10 5 L0 10 z`,className:`arrow`})})}),a.map((e,n)=>{let{from:r,to:a}=$w(i.get(e.from),i.get(e.to),14,17),o=(r.x+a.x)/2+(hT/2-(r.x+a.x)/2)*.25,s=(r.y+a.y)/2+(gT/2-(r.y+a.y)/2)*.25;return(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`path`,{className:`edge`,d:`M ${r.x.toFixed(1)} ${r.y.toFixed(1)} Q ${o.toFixed(1)} ${s.toFixed(1)} ${a.x.toFixed(1)} ${a.y.toFixed(1)}`,fill:`none`,markerEnd:`url(#${t})`}),e.label&&(0,p.jsx)(`text`,{className:`edge-label`,x:o,y:s,textAnchor:`middle`,children:aT(e.label,12)})]},n)}),r.map(e=>{let t=i.get(e.id);return(0,p.jsxs)(`g`,{children:[(0,p.jsx)(`circle`,{className:`node`,cx:t.x,cy:t.y,r:_T}),(0,p.jsx)(`text`,{className:`node-label`,x:t.x,y:t.y+26,textAnchor:`middle`,children:aT(e.label,18)})]},e.id)})]})]})}var yT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,bT=e=>Array.isArray(e)?e:[],xT=e=>typeof e==`object`&&e?e:{},ST=/^\/api\/media\/[0-9a-f]{32}$/,CT=e=>typeof e==`string`&&ST.test(e)?e:null,wT=/^\/api\/video\/[0-9a-f]{32}$/,TT=e=>typeof e==`string`&&wT.test(e)?e:null,ET=({props:e})=>yT(e.title)?(0,p.jsx)(`h3`,{className:`obj-title`,children:yT(e.title)}):null;function DT({props:e}){let t=(0,l.useMemo)(()=>Gw(yT(e.text)),[e.text]);return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`div`,{className:`obj-md obj-doc`,dangerouslySetInnerHTML:{__html:t}})]})}function OT({props:e}){let t=Math.min(100,Math.max(0,Number(e.value)||0));return(0,p.jsxs)(`div`,{className:`obj-progress`,children:[(0,p.jsxs)(`div`,{className:`obj-progress-head`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:yT(e.label)}),(0,p.jsxs)(`span`,{className:`obj-progress-pct`,children:[Math.round(t),`%`]})]}),(0,p.jsx)(`div`,{className:`obj-progress-bar`,role:`progressbar`,"aria-valuemin":0,"aria-valuemax":100,"aria-valuenow":Math.round(t),"aria-label":yT(e.label)||`Progress`,children:(0,p.jsx)(`i`,{style:{width:`${t}%`}})}),yT(e.detail)&&(0,p.jsx)(`span`,{className:`obj-progress-detail`,children:yT(e.detail)})]})}function kT({props:e}){let t=bT(e.items).map(e=>xT(typeof e==`object`&&e?e:{text:e})),n=t.filter(e=>e.done===!0).length;return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`ul`,{className:`obj-checklist`,children:t.map((e,t)=>(0,p.jsxs)(`li`,{className:e.done===!0?`done`:void 0,children:[(0,p.jsx)(`span`,{className:`box`,"aria-hidden":`true`,children:e.done===!0?`✓`:``}),(0,p.jsx)(`span`,{children:yT(e.text)})]},t))}),t.length>0&&(0,p.jsxs)(`small`,{className:`obj-progress-detail`,children:[n,` of `,t.length,` done`]})]})}function AT({props:e}){return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(ET,{props:e}),(0,p.jsx)(`dl`,{className:`obj-kv`,children:bT(e.rows).map((e,t)=>{let n=xT(e);return(0,p.jsxs)(`div`,{children:[(0,p.jsx)(`dt`,{children:yT(n.key)}),(0,p.jsx)(`dd`,{children:yT(n.value)})]},t)})})]})}var jT=e=>String(Math.floor(e)).padStart(2,`0`);function MT(e){let t=Math.max(0,Math.ceil(e));return`${jT(t/3600)}:${jT(t%3600/60)}:${jT(t%60)}`}function NT({props:e}){let t=(0,l.useRef)(null);if(t.current===null){let n=typeof e.to==`string`?Date.parse(e.to):NaN,r=Number(e.seconds);t.current=Number.isFinite(n)?n:Date.now()+(Number.isFinite(r)?r:0)*1e3}let[n,r]=(0,l.useState)(Date.now());(0,l.useEffect)(()=>{let e=setInterval(()=>r(Date.now()),250);return()=>clearInterval(e)},[]);let i=(t.current-n)/1e3;return(0,p.jsxs)(`div`,{className:`obj-countdown${i<=0?` done`:``}`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:yT(e.title)||yT(e.label)}),(0,p.jsx)(`span`,{className:`obj-countdown-time`,role:`timer`,children:MT(i)})]})}function PT({props:e}){let t=CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsx)(`img`,{src:t,alt:yT(e.title)||`Picture`,loading:`lazy`}):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This picture is not available.`})]})}function FT({src:e,web:t,title:n}){let[r,i]=(0,l.useState)(t?`loading`:`ready`);return r===`failed`?(0,p.jsx)(`p`,{className:`obj-empty`,children:`This video could not be played. Ask Friend to try again, or to play it in a window on the PC.`}):(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`video`,{src:e,controls:!0,playsInline:!0,autoPlay:t,preload:t?`auto`:`metadata`,"aria-label":n,onLoadedData:()=>i(`ready`),onError:()=>i(`failed`)}),t&&r===`loading`&&(0,p.jsx)(`p`,{className:`obj-empty`,children:`Preparing the video…`})]})}var IT=/^[A-Za-z0-9_-]{11}$/;function LT({id:e,start:t,title:n}){let[r,i]=(0,l.useState)(!1),a=new URLSearchParams({autoplay:`1`,rel:`0`,playsinline:`1`,modestbranding:`1`});return t>0&&a.set(`start`,String(t)),(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`iframe`,{className:`obj-youtube`,src:`https://www.youtube-nocookie.com/embed/${e}?${a.toString()}`,title:n,allow:`autoplay; encrypted-media; fullscreen; picture-in-picture`,allowFullScreen:!0,referrerPolicy:`strict-origin-when-cross-origin`,onLoad:()=>i(!0)}),!r&&(0,p.jsx)(`p`,{className:`obj-empty`,children:`Loading the player…`})]})}function RT({props:e}){if(e.embed!==void 0){let t=typeof e.embed==`string`&&IT.test(e.embed)?e.embed:null,n=typeof e.start==`number`&&e.start>0&&e.start<=86400?Math.floor(e.start):0;return(0,p.jsxs)(`div`,{className:`obj-media obj-media-fill`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsx)(LT,{id:t,start:n,title:yT(e.title)||`YouTube video`},`${t}-${n}`):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This clip is not available.`})]})}let t=TT(e.src),n=t??CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media`,children:[(0,p.jsx)(ET,{props:e}),n?(0,p.jsx)(FT,{src:n,web:t!==null,title:yT(e.title)||`Video`},n):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This clip is not available.`})]})}function zT({props:e}){let t=CT(e.src);return(0,p.jsxs)(`div`,{className:`obj-media obj-pdf`,children:[(0,p.jsx)(ET,{props:e}),t?(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`iframe`,{src:t,title:yT(e.title)||`Document`}),(0,p.jsx)(`a`,{className:`obj-open`,href:t,target:`_blank`,rel:`noopener noreferrer`,children:`Open in a new tab`})]}):(0,p.jsx)(`p`,{className:`obj-empty`,children:`This document is not available.`})]})}function BT({props:e}){let t=bT(e.items).map(xT).filter(e=>CT(e.src)),[n,r]=(0,l.useState)(0),i=Math.min(n,Math.max(0,t.length-1)),a=t[i];if(!a)return(0,p.jsx)(`p`,{className:`obj-empty`,children:`Nothing to show.`});let o=CT(a.src),s=a.kind===`video`;return(0,p.jsxs)(`div`,{className:`obj-media obj-gallery`,children:[(0,p.jsx)(ET,{props:e}),s?(0,p.jsx)(`video`,{src:o,controls:!0,playsInline:!0,preload:`metadata`},o):(0,p.jsx)(`img`,{src:o,alt:yT(a.caption)||`Picture ${i+1}`},o),(0,p.jsxs)(`div`,{className:`obj-gallery-bar`,children:[(0,p.jsx)(`button`,{type:`button`,"aria-label":`Previous`,disabled:t.length<2,onClick:()=>r((i+t.length-1)%t.length),children:`‹`}),(0,p.jsxs)(`span`,{children:[yT(a.caption),(0,p.jsxs)(`small`,{children:[i+1,` / `,t.length]})]}),(0,p.jsx)(`button`,{type:`button`,"aria-label":`Next`,disabled:t.length<2,onClick:()=>r((i+1)%t.length),children:`›`})]})]})}var VT=[`default-src 'none'`,`script-src 'unsafe-inline'`,`style-src 'unsafe-inline'`,`img-src data: blob:`,`form-action 'none'`,`base-uri 'none'`].join(`; `),HT=`html,body{margin:0;min-height:100%;background:#050b10;color:var(--ink,#d8f6ff);font:15px/1.5 var(--ui,system-ui,sans-serif)}`,UT=[`--accent`,`--ink`,`--muted`,`--ok`,`--warn`,`--bad`,`--glass`,`--edge`,`--ui`,`--mono`],WT=/^[\w\s#().,%'"/-]+$/;function GT(){if(typeof document>`u`)return``;let e=getComputedStyle(document.documentElement),t=UT.map(t=>[t,e.getPropertyValue(t).trim()]).filter(([,e])=>e&&WT.test(e));return t.length?`:root{${t.map(([e,t])=>`${e}:${t}`).join(`;`)}}`:``}function KT(e,t=``){return`<!doctype html><html><head><meta charset="utf-8"><meta http-equiv="Content-Security-Policy" content="${VT}"><meta name="viewport" content="width=device-width,initial-scale=1"><style>${t}${HT}</style></head><body>${e}</body></html>`}function qT({props:e}){let t=typeof e.html==`string`?e.html:``,n=typeof e.title==`string`?e.title:``,r=(0,l.useMemo)(()=>KT(t,GT()),[t]);return(0,p.jsxs)(`div`,{className:`obj-sandbox`,children:[n&&(0,p.jsx)(`h3`,{className:`obj-title`,children:n}),(0,p.jsx)(`iframe`,{title:n||`Page made by Friend`,sandbox:`allow-scripts`,referrerPolicy:`no-referrer`,allow:``,srcDoc:r})]})}var JT=e=>typeof e==`string`?e:typeof e==`number`?String(e):``,YT=e=>Array.isArray(e)?e:[];function XT({props:e}){let t=(0,l.useMemo)(()=>Gw(JT(e.text)),[e.text]);return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-md`,dangerouslySetInnerHTML:{__html:t}})]})}function ZT({props:e}){return(0,p.jsxs)(`div`,{className:`obj-stat`,children:[(0,p.jsx)(`span`,{className:`obj-label`,children:JT(e.label)}),(0,p.jsxs)(`span`,{className:`obj-value`,children:[(0,p.jsx)(`span`,{children:JT(e.value)}),JT(e.unit)&&(0,p.jsx)(`small`,{children:JT(e.unit)})]}),JT(e.delta)&&(0,p.jsx)(`span`,{className:`obj-delta`,children:JT(e.delta)})]})}function QT({props:e}){return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`ul`,{className:`obj-list`,children:YT(e.items).map((e,t)=>{let n=typeof e==`object`&&e?e:{text:e};return(0,p.jsx)(`li`,{className:n.done?`done`:void 0,children:JT(n.text)},t)})})]})}function $T({props:e}){let t=YT(e.columns),n=YT(e.rows);return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-table-wrap`,children:(0,p.jsxs)(`table`,{className:`obj-table`,children:[(0,p.jsx)(`thead`,{children:(0,p.jsx)(`tr`,{children:t.map((e,t)=>(0,p.jsx)(`th`,{children:JT(e)},t))})}),(0,p.jsx)(`tbody`,{children:n.map((e,t)=>(0,p.jsx)(`tr`,{children:YT(e).map((e,t)=>(0,p.jsx)(`td`,{children:JT(e)},t))},t))})]})})]})}function eE({props:e}){return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`pre`,{className:`obj-code`,"data-lang":JT(e.language),children:(0,p.jsx)(`code`,{children:JT(e.code)})})]})}function tE({part:e}){let t=typeof e==`object`&&e?e:{},n=typeof t.type==`string`?t.type:``;if(n===`group`||n===`tabs`||n===`sandbox`)return null;let r=iE[n];return r?(0,p.jsx)(`div`,{className:`obj-part obj-part-${n}`,children:(0,p.jsx)(r,{props:typeof t.props==`object`&&t.props!==null?t.props:{}})}):null}function nE({props:e}){let t=e.layout===`row`||e.layout===`column`?e.layout:`grid`;return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-group obj-group-${t}`,children:YT(e.items).map((e,t)=>(0,p.jsx)(tE,{part:e},t))})]})}function rE({props:e}){let t=YT(e.tabs).map(e=>typeof e==`object`&&e?e:{}),[n,r]=(0,l.useState)(0),i=Math.min(n,Math.max(0,t.length-1));return(0,p.jsxs)(p.Fragment,{children:[JT(e.title)&&(0,p.jsx)(`h3`,{className:`obj-title`,children:JT(e.title)}),(0,p.jsx)(`div`,{className:`obj-tabs`,role:`tablist`,children:t.map((e,t)=>(0,p.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":t===i,className:t===i?`on`:void 0,onClick:()=>r(t),children:JT(e.title)||`Tab ${t+1}`},t))}),t[i]&&(0,p.jsx)(tE,{part:t[i]})]})}var iE={card:XT,stat:ZT,list:QT,table:$T,code:eE,chart:fT,gauge:pT,timeline:mT,graph:vT,sandbox:qT,markdown:DT,image:PT,video:RT,pdf:zT,gallery:BT,group:nE,tabs:rE,progress:OT,checklist:kT,countdown:NT,kv:AT};function aE(e,t){let n=new Map(t.map(e=>[e.id,e])),r=[],i=new Set;for(let t of e){if(i.has(t.object.id))continue;i.add(t.object.id);let e=n.get(t.object.id);r.push(e?{object:e,leaving:!1}:{object:t.object,leaving:!0})}for(let e of t)i.has(e.id)||(i.add(e.id),r.push({object:e,leaving:!1}));return r}function oE(e,t){let[n,r]=(0,l.useState)(()=>e.map(e=>({object:e,leaving:!1}))),i=(0,l.useRef)(new Map);return(0,l.useEffect)(()=>{r(n=>{let a=aE(n,e),o=new Set(n.filter(e=>e.leaving).map(e=>e.object.id));for(let e of a){let n=i.current.get(e.object.id);if(!e.leaving)n&&clearTimeout(n),i.current.delete(e.object.id);else if(!o.has(e.object.id)&&!n){let n=e.object.id;i.current.set(n,setTimeout(()=>{i.current.delete(n),r(e=>e.filter(e=>!(e.object.id===n&&e.leaving)))},Math.max(t,0)))}}return t<=0?a.filter(e=>!e.leaving):a})},[e,t]),(0,l.useEffect)(()=>()=>{for(let e of i.current.values())clearTimeout(e);i.current.clear()},[]),n}var sE=.12,cE=.1,lE=.02,uE=(e,t,n)=>Math.min(Math.max(e,t),n);function dE(e){let t=uE(e.w,sE,1),n=uE(e.h,cE,1);return{x:uE(e.x,0,1-t),y:uE(e.y,0,1-n),w:t,h:n}}function fE(e,t){let n=t.getBoundingClientRect(),r=e.getBoundingClientRect();return n.width<=0||n.height<=0?null:dE({x:(r.left-n.left)/n.width,y:(r.top-n.top)/n.height,w:r.width/n.width,h:r.height/n.height})}function pE(e,t,n){let r=(0,l.useRef)(null),[i,a]=(0,l.useState)(null),o=(0,l.useCallback)((n,r)=>{let i=dE(r);t({type:`object.place`,id:n,placement:{x:i.x,y:i.y,w:i.w,h:i.h}}),e({type:`stage.move`,objectId:n,rect:i})},[e,t]),s=(0,l.useCallback)((e,t,i)=>{if(e.pointerType===`mouse`&&e.button!==0)return;let o=n(),s=e.currentTarget.closest(`[data-object]`);if(!o||!s||r.current)return;let c=fE(s,o);if(!c)return;let l=o.getBoundingClientRect();r.current={id:t.id,mode:i,pointer:e.pointerId,startX:e.clientX,startY:e.clientY,from:c,stageW:l.width,stageH:l.height};try{e.currentTarget.setPointerCapture(e.pointerId)}catch{}e.stopPropagation(),e.preventDefault(),a({id:t.id,box:c})},[n]),c=(e,t)=>{let n=(t.clientX-e.startX)/e.stageW,r=(t.clientY-e.startY)/e.stageH;return e.mode===`move`?dE({...e.from,x:e.from.x+n,y:e.from.y+r}):dE({...e.from,w:e.from.w+n,h:e.from.h+r})};return{preview:i,begin:s,move:(0,l.useCallback)(e=>{let t=r.current;t&&t.pointer===e.pointerId&&a({id:t.id,box:c(t,e)})},[]),end:(0,l.useCallback)((e,t)=>{let n=r.current;n&&n.pointer===e.pointerId&&(r.current=null,a(null),t||o(n.id,c(n,e)))},[o]),key:(0,l.useCallback)((e,t)=>{let r={ArrowLeft:[-.02,0],ArrowRight:[lE,0],ArrowUp:[0,-.02],ArrowDown:[0,lE]}[e.key],i=n(),a=e.currentTarget.closest(`[data-object]`);if(!r||!i||!a)return;let s=fE(a,i);s&&(e.preventDefault(),o(t.id,e.shiftKey?{...s,w:s.w+r[0],h:s.h+r[1]}:{...s,x:s.x+r[0],y:s.y+r[1]}))},[o,n])}}function mE(e,t){if(e===`auto`)return{position:`relative`};if(t.w<600)return{position:`relative`,width:`100%`};let[n,r,i,a]=typeof e==`string`?Nl[e]:[e.x*100,e.y*100,e.w*100,e.h*100],o={position:`absolute`,left:`${n}%`,top:`${r}%`,width:`${i}%`};return e===`top`||e===`bottom`?{...o,maxHeight:`${a}%`}:{...o,height:`${a}%`}}var hE=350,gE=()=>typeof matchMedia==`function`&&matchMedia(`(prefers-reduced-motion: reduce)`).matches,_E=class extends l.Component{state={failed:!1};static getDerivedStateFromError(){return{failed:!0}}render(){return this.state.failed?null:this.props.children}};function vE(){let e=()=>({w:window.innerWidth,h:window.innerHeight}),[t,n]=(0,l.useState)(e);return(0,l.useEffect)(()=>{let t=()=>n(e());return window.addEventListener(`resize`,t),()=>window.removeEventListener(`resize`,t)},[]),t}var yE=350;function bE({state:e,send:t,dispatch:n,voice:r,slash:i,onMenu:a}){let o=vE(),[s,c]=(0,l.useState)(0),[u,d]=(0,l.useState)(!1),f=ne(),m=o.w<600,h=e.scene===`focus`||e.scene===`multi`,g={"--accent":e.mood.accent,"--intensity":e.mood.intensity},_=e.voice.mode,v=_===`listening`?`listening`:_===`speaking`?`speaking`:_===`transcribing`?`thinking`:e.presence.state,y=Qb(e.look.reactivity),b=Math.min(1,(_===`listening`||_===`speaking`?e.voice.level:e.presence.amplitude)*y),x=(0,l.useRef)({timer:null,down:!1,talking:!1,id:null}),S=e=>{if(!(e.target===e.currentTarget||e.target.closest(`[data-presence]`))||e.pointerType===`mouse`&&e.button!==0)return;let t=x.current;if(!(t.down&&t.id!==null&&e.pointerId!==t.id)){t.timer&&clearTimeout(t.timer),t.down=!0,t.talking=!1,t.id=typeof e.pointerId==`number`?e.pointerId:null;try{t.id!==null&&e.currentTarget.setPointerCapture?.(t.id)}catch{}t.timer=r?setTimeout(()=>{t.down&&(t.talking=!0,r.pressStart())},yE):null}},C=(e,t)=>{let n=x.current;n.down&&(n.id===null||typeof e.pointerId!=`number`||e.pointerId===n.id)&&(n.down=!1,n.id=null,n.timer&&clearTimeout(n.timer),n.timer=null,n.talking?(n.talking=!1,t?r?.blur?.():r?.pressEnd()):t||c(e=>e+1))},w=(0,l.useRef)(null),T=pE(t,n,()=>w.current),E=oE(e.objects,gE()?0:hE),D=E.filter(e=>e.object.layer===`overlay`),O=E.filter(e=>e.object.layer!==`overlay`&&e.object.placement===`auto`),k=E.filter(e=>e.object.layer!==`overlay`&&e.object.placement!==`auto`),A=({object:e,leaving:r})=>{let i=iE[e.type];if(!i)return null;let a=e.layer===`overlay`,s=!m&&!r&&!a,c=T.preview?.id===e.id?T.preview.box:null,l=c?{x:c.x,y:c.y,w:c.w,h:c.h}:e.placement;return(0,p.jsxs)(`section`,{"data-object":e.id,className:`obj glass${e.style===`alert`?` alert`:``}${a?` overlay`:``}${e.pinned?` pinned`:``}${c?` dragging`:``}${r?` leaving`:``}`,style:a?void 0:mE(l,o),children:[s&&(0,p.jsx)(`div`,{className:`obj-grip`,role:`button`,tabIndex:0,"aria-label":`Move ${e.id}. Drag, or use the arrow keys; hold Shift to resize.`,onPointerDown:t=>T.begin(t,e,`move`),onPointerMove:T.move,onPointerUp:e=>T.end(e,!1),onPointerCancel:e=>T.end(e,!0),onKeyDown:t=>T.key(t,e)}),!a&&(0,p.jsx)(`button`,{className:`obj-pin${e.pinned?` on`:``}`,"aria-label":e.pinned?`Unpin ${e.id}`:`Pin ${e.id} to the screen`,"aria-pressed":!!e.pinned,title:e.pinned?`Pinned: stays on the screen. Click to unpin.`:`Pin: keep this on the screen.`,disabled:r,onClick:()=>t({type:`stage.pin`,objectId:e.id,pinned:!e.pinned}),children:(0,p.jsx)(`svg`,{width:`14`,height:`14`,viewBox:`0 0 24 24`,fill:e.pinned?`currentColor`:`none`,stroke:`currentColor`,strokeWidth:`2`,strokeLinecap:`round`,strokeLinejoin:`round`,"aria-hidden":`true`,children:(0,p.jsx)(`path`,{d:`M12 17v5M9 3h6l-1 7 3 3H7l3-3-1-7z`})})}),(0,p.jsx)(`button`,{className:`obj-close`,"aria-label":`Dismiss ${e.id}`,title:e.pinned?`Remove this widget`:`Dismiss`,disabled:r,onClick:()=>{t({type:`stage.event`,objectId:e.id,event:`dismiss`}),n({type:`object.dismiss`,id:e.id})},children:`×`}),s&&(0,p.jsx)(`div`,{className:`obj-resize`,"aria-hidden":`true`,onPointerDown:t=>T.begin(t,e,`resize`),onPointerMove:T.move,onPointerUp:e=>T.end(e,!1),onPointerCancel:e=>T.end(e,!0)}),(0,p.jsx)(_E,{children:(0,p.jsx)(i,{props:e.props})})]},e.id)};return(0,p.jsxs)(`div`,{ref:w,"data-testid":`stage`,className:`stage`,style:g,onPointerDown:S,onPointerUp:e=>C(e,!1),onPointerCancel:e=>C(e,!0),onContextMenu:e=>r&&e.preventDefault(),children:[e.look.ambient&&(0,p.jsx)(`div`,{className:`ambient`,"aria-hidden":`true`,style:{opacity:.35+.65*e.mood.intensity}}),(0,p.jsx)(Zb,{state:v,amplitude:b,pulse:e.presence.pulse,mode:h?`corner`:`full`,accent:e.mood.accent,style:e.presence.style,intensity:e.mood.intensity,scale:e.look.size}),(0,p.jsxs)(`div`,{className:m?`objects objects-stack`:`objects`,style:{zIndex:10},children:[O.length>0&&(0,p.jsx)(`div`,{className:`auto-grid`,children:O.map(A)}),k.map(A)]}),D.length>0&&(0,p.jsxs)(`div`,{className:`overlay-layer`,"data-testid":`overlay`,children:[(0,p.jsx)(`div`,{className:`overlay-backdrop`,onClick:()=>D.forEach(({object:e})=>{t({type:`stage.event`,objectId:e.id,event:`dismiss`}),n({type:`object.dismiss`,id:e.id})})}),D.map(A)]}),e.look.captions&&e.captions&&(0,p.jsx)(`p`,{className:`captions captions-${e.look.captionSize}${e.captionDone?` done`:``}`,"aria-live":`polite`,children:e.captions}),f&&r&&!u&&(0,p.jsx)(xx,{voice:r,mode:_,onType:()=>c(e=>e+1),onMenu:()=>a?.()}),(0,p.jsx)(vx,{requestOpen:s,slash:i,onOpenChange:d,onSend:e=>t({type:`chat.send`,text:e})})]})}function xE(){let e=()=>Math.random().toString(36).slice(2,12)+Date.now().toString(36);try{let t=sessionStorage.getItem(`friend.tab`);return t||(t=e(),sessionStorage.setItem(`friend.tab`,t)),t}catch{return e()}}function SE(){return`${location.protocol===`https:`?`wss`:`ws`}://${location.host}/ws`}function CE(e=SE()){let t=null,n=`connecting`,r=!1,i=0,a=!1,o=xE(),s=null,c=new Set,l=new Set,u=e=>{n=e,l.forEach(t=>t(e))};function d(){if(r)return;u(`connecting`);let n=new WebSocket(`${e}${e.includes(`?`)?`&`:`?`}tab=${o}${a?`&takeover=1`:``}`);t=n,n.onopen=()=>{i=0,a=!1,u(`open`)},n.onmessage=e=>{try{let t=JSON.parse(String(e.data));c.forEach(e=>e(t))}catch{}},n.onclose=e=>{if(!r){if(e.code===4401)return u(`unauthorized`);if(e.code===4409||e.code===4410)return u(`elsewhere`);u(`closed`),s=setTimeout(d,Math.min(500*2**i++,8e3))}},n.onerror=()=>{}}return d(),{send(e){t?.readyState===WebSocket.OPEN&&t.send(JSON.stringify(e))},onMessage(e){return c.add(e),()=>c.delete(e)},onState(e){return l.add(e),()=>l.delete(e)},state:()=>n,takeOver(){r||n!==`elsewhere`||(a=!0,i=0,d())},close(){r=!0,s&&clearTimeout(s),t?.close()}}}var wE={scene:`conversation`,objects:[],captions:``,captionDone:!0,presence:{state:`idle`,style:`sphere`,amplitude:0,pulse:0},mood:{accent:`#3fd8ff`,intensity:.6},approval:null,alerts:[],connection:`connecting`,chat:[],chatLive:!1,view:`companion`,look:{size:1,reactivity:.7,ambient:!0,captions:!0,captionSize:`medium`},viewKnown:!1,busy:!1,activity:null,deviceOnline:!1,voice:{mode:`idle`,level:0,available:!1,enrolled:!1},challenge:null,camera:{enabled:!1,stream:null},speaker:null,ownerName:``,assistantName:``,hud:null,music:null,hostMusic:null,musicCmd:null,uiOpen:null},TE=200,EE=e=>e.length>TE?e.slice(-200):e,DE=0,OE=e=>Math.min(1,Math.max(0,e));function kE(e,t){switch(t.cmd){case`scene`:return{...e,scene:t.mode};case`show`:{let n=e.objects.findIndex(e=>e.id===t.object.id),r=n===-1?[...e.objects,t.object]:e.objects.map((e,r)=>r===n?t.object:e);return{...e,objects:r}}case`update`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,props:{...e.props,...t.props}}:e)};case`hide`:return{...e,objects:e.objects.filter(e=>e.id!==t.id)};case`clear`:return{...e,objects:e.objects.filter(e=>e.pinned),scene:`conversation`};case`pin`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,pinned:!0}:e)};case`unpin`:return{...e,objects:e.objects.map(e=>e.id===t.id?(({pinned:e,...t})=>t)(e):e)};case`place`:return{...e,objects:e.objects.map(e=>e.id===t.id?{...e,placement:t.placement}:e)};case`presence`:return{...e,presence:{...e.presence,state:t.state??e.presence.state,style:t.style??e.presence.style}};case`mood`:return{...e,mood:{accent:t.accent??e.mood.accent,intensity:t.intensity??e.mood.intensity}}}}function AE(e,t){let n=t;if(n&&typeof n==`object`){if(n.type===`conn`)return{...e,connection:n.value};if(n.type===`chat.seed`){let t=Array.isArray(n.lines)?n.lines:[];return e.chat.length===0?{...e,chat:EE(t)}:{...e,chat:EE([...t,...e.chat])}}if(n.type===`alert.add`)return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:n.level,text:n.text}]};if(n.type===`camera.enable`)return{...e,camera:{enabled:n.value,stream:n.value?e.camera.stream:null}};if(n.type===`camera.open`)return{...e,camera:{...e.camera,stream:n.stream}};if(n.type===`camera.closed`)return{...e,camera:{...e.camera,stream:null}};if(n.type===`challenge.dismiss`)return e.challenge?.id===n.id?{...e,challenge:null}:e;if(n.type===`voice.mode`)return{...e,voice:{...e.voice,mode:n.mode,level:n.mode===`idle`?0:e.voice.level}};if(n.type===`voice.level`){let t=Number.isFinite(n.level)?Math.min(1,Math.max(0,n.level)):0;return{...e,voice:{...e.voice,level:t}}}if(n.type===`object.dismiss`)return{...e,objects:e.objects.filter(e=>e.id!==n.id)};if(n.type===`object.place`)return{...e,objects:e.objects.map(e=>e.id===n.id?{...e,placement:n.placement}:e)};if(n.type===`alert.dismiss`)return{...e,alerts:e.alerts.filter(e=>e.id!==n.id)}}let r=eu.safeParse(t);if(!r.success)return e;let i=r.data;switch(i.type){case`snapshot`:return{...e,scene:i.stage.scene,objects:i.stage.objects,presence:{...e.presence,state:i.stage.presence.state,style:i.stage.presence.style},mood:i.stage.mood,approval:i.pendingApproval??null};case`stage`:return kE(e,i.command);case`chat.user`:return{...e,chat:EE([...e.chat,{role:`user`,text:i.text}]),chatLive:!1};case`ui.open`:return{...e,uiOpen:{n:(e.uiOpen?.n??0)+1,...i.integration?{integration:i.integration}:{}}};case`ui`:return{...e,view:i.view,look:i.look??e.look,ownerName:i.ownerName??e.ownerName,assistantName:i.assistantName??e.assistantName,hud:i.hud??e.hud,music:i.music??e.music,viewKnown:!0};case`music.host`:return{...e,hostMusic:i.state};case`music.command`:{let{type:t,...n}=i;return{...e,musicCmd:{n:(e.musicCmd?.n??0)+1,command:n}}}case`caption.delta`:{let t=e.captionDone,n=e.chat.at(-1),r=e.chatLive&&n?.role===`assistant`?[...e.chat.slice(0,-1),{role:`assistant`,text:n.text+i.text}]:EE([...e.chat,{role:`assistant`,text:i.text}]);return{...e,chat:r,chatLive:!0,captions:(t?``:e.captions)+i.text,captionDone:!1,presence:{...e.presence,amplitude:OE(.3+i.text.length*.04),pulse:e.presence.pulse+1}}}case`caption.end`:return{...e,chatLive:!1,captionDone:!0,presence:{...e.presence,amplitude:0}};case`approval.request`:{let{type:t,...n}=i;return{...e,approval:n}}case`approval.resolved`:return e.approval?.id===i.id?{...e,approval:null}:e;case`alert`:return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:i.level,text:i.text}]};case`activity`:return{...e,activity:i.text};case`status`:return{...e,busy:i.busy,activity:i.busy?e.activity:null,deviceOnline:i.deviceOnline,voice:{...e.voice,available:i.voiceAvailable??e.voice.available,enrolled:i.voiceEnrolled??e.voice.enrolled}};case`error`:return{...e,alerts:[...e.alerts.slice(-3),{id:++DE,level:`error`,text:i.message}]};case`voice.heard`:return{...e,captions:i.trust===`guest`?`Guest: ${i.text}`:i.trust===`member`&&i.speaker?`${i.speaker}: ${i.text}`:i.text,captionDone:!0,speaker:{name:i.trust===`member`?i.speaker??null:null,trust:i.trust??`unverified`,seq:(e.speaker?.seq??0)+1}};case`voice.challenge`:return{...e,challenge:{id:i.id,text:i.text}};case`voice.challenge.end`:return e.challenge?.id===i.id?{...e,challenge:null}:e;case`audio.chunk`:case`audio.stop`:return e;case`camera.request`:case`camera.cancel`:case`screen.request`:case`screen.cancel`:return e}}var jE=1024,ME=.8,NE=300;function PE(e,t){let n=Math.min(1,jE/Math.max(e,t));return{width:Math.round(e*n),height:Math.round(t*n)}}function FE(e){let t=e?.name;return t===`NotAllowedError`||t===`SecurityError`?`permission`:t===`NotFoundError`||t===`OverconstrainedError`?`no-camera`:`busy`}async function IE(){if(!navigator.mediaDevices?.getUserMedia)throw Object.assign(Error(`This browser cannot use the camera here (use localhost or HTTPS).`),{name:`NotFoundError`});return navigator.mediaDevices.getUserMedia({video:{width:{ideal:1280}},audio:!1})}async function LE(e,t=NE){let n=document.createElement(`video`);n.muted=!0,n.playsInline=!0,n.srcObject=e,await n.play(),await new Promise(e=>setTimeout(e,t));let{width:r,height:i}=PE(n.videoWidth||640,n.videoHeight||480),a=document.createElement(`canvas`);return a.width=r,a.height=i,a.getContext(`2d`).drawImage(n,0,0,r,i),n.srcObject=null,new Promise((e,t)=>a.toBlob(n=>n?e(n):t(Error(`Could not encode the picture.`)),`image/jpeg`,ME))}var RE=class{opts;active=null;constructor(e){this.opts=e}async handle(e){if(e.type===`camera.cancel`){let t=this.active;t&&t.id===e.id&&(t.cancelled=!0,this.release(t));return}if(!this.opts.enabled())return this.opts.send({type:`camera.denied`,id:e.id,reason:`off`});if(this.active)return this.opts.send({type:`camera.denied`,id:e.id,reason:`busy`});let t={id:e.id,cancelled:!1,stream:null,opened:!1,released:!1};this.active=t;try{let n=await(this.opts.open??IE)();if(t.stream=n,t.cancelled){n.getTracks().forEach(e=>e.stop());return}t.opened=!0,this.opts.dispatch({type:`camera.open`,stream:n});let r=await(this.opts.frame??(e=>LE(e)))(n);if(t.cancelled)return;this.release(t);try{await this.opts.upload(e.id,r)}catch{this.opts.dispatch({type:`alert.add`,level:`warn`,text:`Could not send the camera picture to Friend.`})}}catch(n){t.cancelled||this.opts.send({type:`camera.denied`,id:e.id,reason:FE(n)})}finally{this.release(t),this.active===t&&(this.active=null)}}dispose(){let e=this.active;e&&(e.cancelled=!0,this.release(e))}release(e){e.released||(e.released=!0,e.stream?.getTracks().forEach(e=>e.stop()),e.opened&&this.opts.dispatch({type:`camera.closed`}))}};function zE(e,t){if(e.match(/^[a-z]+:\/\//i))return e;if(e.match(/^\/\//))return window.location.protocol+e;if(e.match(/^[a-z]+:/i))return e;let n=document.implementation.createHTMLDocument(),r=n.createElement(`base`),i=n.createElement(`a`);return n.head.appendChild(r),n.body.appendChild(i),t&&(r.href=t),i.href=e,i.href}var BE=(()=>{let e=0,t=()=>`0000${(Math.random()*36**4<<0).toString(36)}`.slice(-4);return()=>(e+=1,`u${t()}${e}`)})();function VE(e){let t=[];for(let n=0,r=e.length;n<r;n++)t.push(e[n]);return t}var HE=null;function UE(e={}){return HE||(e.includeStyleProperties?(HE=e.includeStyleProperties,HE):(HE=VE(window.getComputedStyle(document.documentElement)),HE))}function WE(e,t){let n=(e.ownerDocument.defaultView||window).getComputedStyle(e).getPropertyValue(t);return n?parseFloat(n.replace(`px`,``)):0}function GE(e){let t=WE(e,`border-left-width`),n=WE(e,`border-right-width`);return e.clientWidth+t+n}function KE(e){let t=WE(e,`border-top-width`),n=WE(e,`border-bottom-width`);return e.clientHeight+t+n}function qE(e,t={}){return{width:t.width||GE(e),height:t.height||KE(e)}}function JE(){let e,t;try{t=process}catch{}let n=t&&t.env?t.env.devicePixelRatio:null;return n&&(e=parseInt(n,10),Number.isNaN(e)&&(e=1)),e||window.devicePixelRatio||1}var YE=16384;function XE(e){(e.width>YE||e.height>YE)&&(e.width>YE&&e.height>YE?e.width>e.height?(e.height*=YE/e.width,e.width=YE):(e.width*=YE/e.height,e.height=YE):e.width>YE?(e.height*=YE/e.width,e.width=YE):(e.width*=YE/e.height,e.height=YE))}function ZE(e){return new Promise((t,n)=>{let r=new Image;r.onload=()=>{r.decode().then(()=>{requestAnimationFrame(()=>t(r))})},r.onerror=n,r.crossOrigin=`anonymous`,r.decoding=`async`,r.src=e})}async function QE(e){return Promise.resolve().then(()=>new XMLSerializer().serializeToString(e)).then(encodeURIComponent).then(e=>`data:image/svg+xml;charset=utf-8,${e}`)}async function $E(e,t,n){let r=`http://www.w3.org/2000/svg`,i=document.createElementNS(r,`svg`),a=document.createElementNS(r,`foreignObject`);return i.setAttribute(`width`,`${t}`),i.setAttribute(`height`,`${n}`),i.setAttribute(`viewBox`,`0 0 ${t} ${n}`),a.setAttribute(`width`,`100%`),a.setAttribute(`height`,`100%`),a.setAttribute(`x`,`0`),a.setAttribute(`y`,`0`),a.setAttribute(`externalResourcesRequired`,`true`),i.appendChild(a),a.appendChild(e),QE(i)}var eD=(e,t)=>{if(e instanceof t)return!0;let n=Object.getPrototypeOf(e);return n===null?!1:n.constructor.name===t.name||eD(n,t)};function tD(e){let t=e.getPropertyValue(`content`);return`${e.cssText} content: '${t.replace(/'|"/g,``)}';`}function nD(e,t){return UE(t).map(t=>`${t}: ${e.getPropertyValue(t)}${e.getPropertyPriority(t)?` !important`:``};`).join(` `)}function rD(e,t,n,r){let i=`.${e}:${t}`,a=n.cssText?tD(n):nD(n,r);return document.createTextNode(`${i}{${a}}`)}function iD(e,t,n,r){let i=window.getComputedStyle(e,n),a=i.getPropertyValue(`content`);if(a===``||a===`none`)return;let o=BE();try{t.className=`${t.className} ${o}`}catch{return}let s=document.createElement(`style`);s.appendChild(rD(o,n,i,r)),t.appendChild(s)}function aD(e,t,n){iD(e,t,`:before`,n),iD(e,t,`:after`,n)}var oD=`application/font-woff`,sD=`image/jpeg`,cD={woff:oD,woff2:oD,ttf:`application/font-truetype`,eot:`application/vnd.ms-fontobject`,png:`image/png`,jpg:sD,jpeg:sD,gif:`image/gif`,tiff:`image/tiff`,svg:`image/svg+xml`,webp:`image/webp`};function lD(e){let t=/\.([^./]*?)$/g.exec(e);return t?t[1]:``}function uD(e){return cD[lD(e).toLowerCase()]||``}function dD(e){return e.split(/,/)[1]}function fD(e){return e.search(/^(data:)/)!==-1}function pD(e,t){return`data:${t};base64,${e}`}async function mD(e,t,n){let r=await fetch(e,t);if(r.status===404)throw Error(`Resource "${r.url}" not found`);let i=await r.blob();return new Promise((e,t)=>{let a=new FileReader;a.onerror=t,a.onloadend=()=>{try{e(n({res:r,result:a.result}))}catch(e){t(e)}},a.readAsDataURL(i)})}var hD={};function gD(e,t,n){let r=e.replace(/\?.*/,``);return n&&(r=e),/ttf|otf|eot|woff2?/i.test(r)&&(r=r.replace(/.*\//,``)),t?`[${t}]${r}`:r}async function _D(e,t,n){let r=gD(e,t,n.includeQueryParams);if(hD[r]!=null)return hD[r];n.cacheBust&&(e+=(/\?/.test(e)?`&`:`?`)+new Date().getTime());let i;try{i=pD(await mD(e,n.fetchRequestInit,({res:e,result:n})=>(t||=e.headers.get(`Content-Type`)||``,dD(n))),t)}catch(t){i=n.imagePlaceholder||``;let r=`Failed to fetch resource: ${e}`;t&&(r=typeof t==`string`?t:t.message),r&&console.warn(r)}return hD[r]=i,i}async function vD(e){let t=e.toDataURL();return t===`data:,`?e.cloneNode(!1):ZE(t)}async function yD(e,t){if(e.currentSrc){let t=document.createElement(`canvas`),n=t.getContext(`2d`);return t.width=e.clientWidth,t.height=e.clientHeight,n?.drawImage(e,0,0,t.width,t.height),ZE(t.toDataURL())}let n=e.poster;return ZE(await _D(n,uD(n),t))}async function bD(e,t){try{if(e?.contentDocument?.body)return await AD(e.contentDocument.body,t,!0)}catch{}return e.cloneNode(!1)}async function xD(e,t){return eD(e,HTMLCanvasElement)?vD(e):eD(e,HTMLVideoElement)?yD(e,t):eD(e,HTMLIFrameElement)?bD(e,t):e.cloneNode(CD(e))}var SD=e=>e.tagName!=null&&e.tagName.toUpperCase()===`SLOT`,CD=e=>e.tagName!=null&&e.tagName.toUpperCase()===`SVG`;async function wD(e,t,n){if(CD(t))return t;let r=[];return r=SD(e)&&e.assignedNodes?VE(e.assignedNodes()):eD(e,HTMLIFrameElement)&&e.contentDocument?.body?VE(e.contentDocument.body.childNodes):VE((e.shadowRoot??e).childNodes),r.length===0||eD(e,HTMLVideoElement)||await r.reduce((e,r)=>e.then(()=>AD(r,n)).then(e=>{e&&t.appendChild(e)}),Promise.resolve()),t}function TD(e,t,n){let r=t.style;if(!r)return;let i=window.getComputedStyle(e);i.cssText?(r.cssText=i.cssText,r.transformOrigin=i.transformOrigin):UE(n).forEach(n=>{let a=i.getPropertyValue(n);n===`font-size`&&a.endsWith(`px`)&&(a=`${Math.floor(parseFloat(a.substring(0,a.length-2)))-.1}px`),eD(e,HTMLIFrameElement)&&n===`display`&&a===`inline`&&(a=`block`),n===`d`&&t.getAttribute(`d`)&&(a=`path(${t.getAttribute(`d`)})`),r.setProperty(n,a,i.getPropertyPriority(n))})}function ED(e,t){eD(e,HTMLTextAreaElement)&&(t.innerHTML=e.value),eD(e,HTMLInputElement)&&t.setAttribute(`value`,e.value)}function DD(e,t){if(eD(e,HTMLSelectElement)){let n=t,r=Array.from(n.children).find(t=>e.value===t.getAttribute(`value`));r&&r.setAttribute(`selected`,``)}}function OD(e,t,n){return eD(t,Element)&&(TD(e,t,n),aD(e,t,n),ED(e,t),DD(e,t)),t}async function kD(e,t){let n=e.querySelectorAll?e.querySelectorAll(`use`):[];if(n.length===0)return e;let r={};for(let i=0;i<n.length;i++){let a=n[i].getAttribute(`xlink:href`);if(a){let n=e.querySelector(a),i=document.querySelector(a);!n&&i&&!r[a]&&(r[a]=await AD(i,t,!0))}}let i=Object.values(r);if(i.length){let t=`http://www.w3.org/1999/xhtml`,n=document.createElementNS(t,`svg`);n.setAttribute(`xmlns`,t),n.style.position=`absolute`,n.style.width=`0`,n.style.height=`0`,n.style.overflow=`hidden`,n.style.display=`none`;let r=document.createElementNS(t,`defs`);n.appendChild(r);for(let e=0;e<i.length;e++)r.appendChild(i[e]);e.appendChild(n)}return e}async function AD(e,t,n){return!n&&t.filter&&!t.filter(e)?null:Promise.resolve(e).then(e=>xD(e,t)).then(n=>wD(e,n,t)).then(n=>OD(e,n,t)).then(e=>kD(e,t))}var jD=/url\((['"]?)([^'"]+?)\1\)/g,MD=/url\([^)]+\)\s*format\((["']?)([^"']+)\1\)/g,ND=/src:\s*(?:url\([^)]+\)\s*format\([^)]+\)[,;]\s*)+/g;function PD(e){let t=e.replace(/([.*+?^${}()|\[\]\/\\])/g,`\\$1`);return RegExp(`(url\\(['"]?)(${t})(['"]?\\))`,`g`)}function FD(e){let t=[];return e.replace(jD,(e,n,r)=>(t.push(r),e)),t.filter(e=>!fD(e))}async function ID(e,t,n,r,i){try{let a=n?zE(t,n):t,o=uD(t),s;return s=i?pD(await i(a),o):await _D(a,o,r),e.replace(PD(t),`$1${s}$3`)}catch{}return e}function LD(e,{preferredFontFormat:t}){return t?e.replace(ND,e=>{for(;;){let[n,,r]=MD.exec(e)||[];if(!r)return``;if(r===t)return`src: ${n};`}}):e}function RD(e){return e.search(jD)!==-1}async function zD(e,t,n){if(!RD(e))return e;let r=LD(e,n);return FD(r).reduce((e,r)=>e.then(e=>ID(e,r,t,n)),Promise.resolve(r))}async function BD(e,t,n){let r=t.style?.getPropertyValue(e);if(r){let i=await zD(r,null,n);return t.style.setProperty(e,i,t.style.getPropertyPriority(e)),!0}return!1}async function VD(e,t){await BD(`background`,e,t)||await BD(`background-image`,e,t),await BD(`mask`,e,t)||await BD(`-webkit-mask`,e,t)||await BD(`mask-image`,e,t)||await BD(`-webkit-mask-image`,e,t)}async function HD(e,t){let n=eD(e,HTMLImageElement);if((!n||fD(e.src))&&(!eD(e,SVGImageElement)||fD(e.href.baseVal)))return;let r=n?e.src:e.href.baseVal,i=await _D(r,uD(r),t);await new Promise((r,a)=>{e.onload=r,e.onerror=t.onImageErrorHandler?(...e)=>{try{r(t.onImageErrorHandler(...e))}catch(e){a(e)}}:a;let o=e;o.decode&&=r,o.loading===`lazy`&&(o.loading=`eager`),n?(e.srcset=``,e.src=i):e.href.baseVal=i})}async function UD(e,t){let n=VE(e.childNodes).map(e=>WD(e,t));await Promise.all(n).then(()=>e)}async function WD(e,t){eD(e,Element)&&(await VD(e,t),await HD(e,t),await UD(e,t))}function GD(e,t){let{style:n}=e;t.backgroundColor&&(n.backgroundColor=t.backgroundColor),t.width&&(n.width=`${t.width}px`),t.height&&(n.height=`${t.height}px`);let r=t.style;return r!=null&&Object.keys(r).forEach(e=>{n[e]=r[e]}),e}var KD={};async function qD(e){let t=KD[e];return t??(t={url:e,cssText:await(await fetch(e)).text()},KD[e]=t,t)}async function JD(e,t){let n=e.cssText,r=/url\(["']?([^"')]+)["']?\)/g,i=(n.match(/url\([^)]+\)/g)||[]).map(async i=>{let a=i.replace(r,`$1`);return a.startsWith(`https://`)||(a=new URL(a,e.url).href),mD(a,t.fetchRequestInit,({result:e})=>(n=n.replace(i,`url(${e})`),[i,e]))});return Promise.all(i).then(()=>n)}function YD(e){if(e==null)return[];let t=[],n=e.replace(/(\/\*[\s\S]*?\*\/)/gi,``),r=RegExp(`((@.*?keyframes [\\s\\S]*?){([\\s\\S]*?}\\s*?)})`,`gi`);for(;;){let e=r.exec(n);if(e===null)break;t.push(e[0])}n=n.replace(r,``);let i=/@import[\s\S]*?url\([^)]*\)[\s\S]*?;/gi,a=RegExp(`((\\s*?(?:\\/\\*[\\s\\S]*?\\*\\/)?\\s*?@media[\\s\\S]*?){([\\s\\S]*?)}\\s*?})|(([\\s\\S]*?){([\\s\\S]*?)})`,`gi`);for(;;){let e=i.exec(n);if(e===null){if(e=a.exec(n),e===null)break;i.lastIndex=a.lastIndex}else a.lastIndex=i.lastIndex;t.push(e[0])}return t}async function XD(e,t){let n=[],r=[];return e.forEach(n=>{if(`cssRules`in n)try{VE(n.cssRules||[]).forEach((e,i)=>{if(e.type===CSSRule.IMPORT_RULE){let a=i+1,o=e.href,s=qD(o).then(e=>JD(e,t)).then(e=>YD(e).forEach(e=>{try{n.insertRule(e,e.startsWith(`@import`)?a+=1:n.cssRules.length)}catch(t){console.error(`Error inserting rule from remote css`,{rule:e,error:t})}})).catch(e=>{console.error(`Error loading remote css`,e.toString())});r.push(s)}})}catch(i){let a=e.find(e=>e.href==null)||document.styleSheets[0];n.href!=null&&r.push(qD(n.href).then(e=>JD(e,t)).then(e=>YD(e).forEach(e=>{a.insertRule(e,a.cssRules.length)})).catch(e=>{console.error(`Error loading remote stylesheet`,e)})),console.error(`Error inlining remote css file`,i)}}),Promise.all(r).then(()=>(e.forEach(e=>{if(`cssRules`in e)try{VE(e.cssRules||[]).forEach(e=>{n.push(e)})}catch(t){console.error(`Error while reading CSS rules from ${e.href}`,t)}}),n))}function ZD(e){return e.filter(e=>e.type===CSSRule.FONT_FACE_RULE).filter(e=>RD(e.style.getPropertyValue(`src`)))}async function QD(e,t){if(e.ownerDocument==null)throw Error(`Provided element is not within a Document`);return ZD(await XD(VE(e.ownerDocument.styleSheets),t))}function $D(e){return e.trim().replace(/["']/g,``)}function eO(e){let t=new Set;function n(e){(e.style.fontFamily||getComputedStyle(e).fontFamily).split(`,`).forEach(e=>{t.add($D(e))}),Array.from(e.children).forEach(e=>{e instanceof HTMLElement&&n(e)})}return n(e),t}async function tO(e,t){let n=await QD(e,t),r=eO(e);return(await Promise.all(n.filter(e=>r.has($D(e.style.fontFamily))).map(e=>{let n=e.parentStyleSheet?e.parentStyleSheet.href:null;return zD(e.cssText,n,t)}))).join(`
4456
4456
  `)}async function nO(e,t){let n=t.fontEmbedCSS==null?t.skipFonts?null:await tO(e,t):t.fontEmbedCSS;if(n){let t=document.createElement(`style`),r=document.createTextNode(n);t.appendChild(r),e.firstChild?e.insertBefore(t,e.firstChild):e.appendChild(t)}}async function rO(e,t={}){let{width:n,height:r}=qE(e,t),i=await AD(e,t,!0);return await nO(i,t),await WD(i,t),GD(i,t),await $E(i,n,r)}async function iO(e,t={}){let{width:n,height:r}=qE(e,t),i=await ZE(await rO(e,t)),a=document.createElement(`canvas`),o=a.getContext(`2d`),s=t.pixelRatio||JE(),c=t.canvasWidth||n,l=t.canvasHeight||r;return a.width=c*s,a.height=l*s,t.skipAutoScale||XE(a),a.style.width=`${c}`,a.style.height=`${l}`,t.backgroundColor&&(o.fillStyle=t.backgroundColor,o.fillRect(0,0,a.width,a.height)),o.drawImage(i,0,0,a.width,a.height),a}var aO=1600,oO=.85;function sO(e,t){let n=Math.min(1,aO/Math.max(e,t,1));return{width:Math.max(1,Math.round(e*n)),height:Math.max(1,Math.round(t*n))}}async function cO(){let e=document.documentElement.getBoundingClientRect(),t=await iO(document.body,{width:Math.round(e.width),height:Math.round(e.height),pixelRatio:1,backgroundColor:`#050b10`,filter:e=>!(e instanceof HTMLElement&&e.dataset.noCapture!==void 0)}),n=sO(t.width,t.height),r=document.createElement(`canvas`);return r.width=n.width,r.height=n.height,r.getContext(`2d`).drawImage(t,0,0,n.width,n.height),new Promise((e,t)=>r.toBlob(n=>n?e(n):t(Error(`Could not encode the picture.`)),`image/jpeg`,oO))}var lO=class{opts;active=null;constructor(e){this.opts=e}async handle(e){if(e.type===`screen.cancel`){this.active&&this.active.id===e.id&&(this.active.cancelled=!0);return}if(this.active)return this.opts.send({type:`screen.denied`,id:e.id,reason:`busy`});let t={id:e.id,cancelled:!1};this.active=t;try{let n=await(this.opts.capture??cO)();if(t.cancelled)return;try{await this.opts.upload(e.id,n)}catch{this.opts.dispatch({type:`alert.add`,level:`warn`,text:`Could not send the picture of the screen to Friend.`})}}catch(n){t.cancelled||this.opts.send({type:`screen.denied`,id:e.id,reason:uO(n)})}finally{this.active===t&&(this.active=null)}}dispose(){this.active&&(this.active.cancelled=!0)}};function uO(e){return e?.name===`NotSupportedError`?`unsupported`:`failed`}var dO={401:`Please sign in again.`,413:`That recording was too long.`,409:`Friend is busy with the last request. Try again in a moment.`,429:`You're talking too fast. Wait a moment.`,503:`Voice is not available. Run: friend voice setup`};async function fO(e,t){let n;try{n=await fetch(`/api/voice/utterance`,{method:`POST`,headers:{"content-type":e.type||`audio/webm`},body:e,signal:t})}catch(e){throw e.name===`AbortError`?e:Error(`Could not reach Friend. Check the connection.`)}if(!n.ok){let e=``;try{e=(await n.json()).error??``}catch{}throw Error(e||dO[n.status]||`The voice request failed (${n.status}).`)}let r=await n.json();return{text:typeof r.text==`string`?r.text:``}}var pO=0,mO=new Set;function hO(e){return mO.add(e),()=>mO.delete(e)}var gO=e=>mO.forEach(t=>{try{t(e)}catch{}}),_O=e=>/not compatible|audio capture|audiosession/i.test(String(e?.message??e));function vO(e){try{let t=navigator.audioSession;t&&t.type!==e&&(t.type=e)}catch{}}function yO(){pO===0&&vO(`playback`)}function bO(){pO++,pO===1&&gO(!0),vO(`play-and-record`);let e=!1;return()=>{e||(e=!0,pO=Math.max(0,pO-1),pO===0&&(vO(`playback`),gO(!1)))}}var xO=4096,SO=8,CO=20,wO=6e6;function TO(e){try{let t=atob(e),n=new Uint8Array(t.length);for(let e=0;e<t.length;e++)n[e]=t.charCodeAt(e);return n}catch{return null}}var EO=class{ctx=null;analyser=null;pending=new Map;queue=[];current=null;busy=!1;gen=0;isPlaying=!1;unwatch=null;listeners=new Set;unlock(){yO();let e=this.ensureContext();e.state!==`running`&&e.resume().catch(()=>{})}locked(){return!this.ctx||this.ctx.state!==`running`}enqueue(e){if(!Number.isInteger(e.seq)||e.seq<0||e.seq>xO)return;let t=TO(e.data);if(!t)return;let n=this.pending.get(e.id);if(n||(this.pending.size>=SO&&this.pending.delete(this.pending.keys().next().value),n={parts:new Map,lastSeq:null,bytes:0},this.pending.set(e.id,n)),n.bytes+=t.length,n.bytes>wO){this.pending.delete(e.id);return}if(n.parts.set(e.seq,t),e.last&&(n.lastSeq=e.seq),n.lastSeq===null||n.parts.size!==n.lastSeq+1)return;this.pending.delete(e.id);let r=new Uint8Array([...n.parts.values()].reduce((e,t)=>e+t.length,0)),i=0;for(let e=0;e<=n.lastSeq;e++){let t=n.parts.get(e);if(!t)return;r.set(t,i),i+=t.length}for(this.queue.push(r.buffer);this.queue.length>CO;)this.queue.shift();this.pump()}stop(){this.gen++,this.queue=[],this.pending.clear(),this.busy=!1;let e=this.current;if(this.current=null,e){e.onended=null;try{e.stop()}catch{}}this.setPlaying(!1)}dispose(){this.stop(),this.ctx?.close().catch(()=>{}),this.unwatch?.(),this.unwatch=null,this.ctx=null,this.analyser=null}playing(){return this.isPlaying}onChange(e){return this.listeners.add(e),()=>this.listeners.delete(e)}level(){if(!this.analyser||!this.isPlaying)return 0;let e=new Uint8Array(this.analyser.fftSize);this.analyser.getByteTimeDomainData(e);let t=0;for(let n of e)t+=((n-128)/128)**2;return Math.min(1,Math.sqrt(t/e.length)*4)}ensureContext(){if(!this.ctx){let e=window.AudioContext??window.webkitAudioContext;this.ctx=new e,this.analyser=this.ctx.createAnalyser(),this.analyser.fftSize=1024,this.analyser.connect(this.ctx.destination);let t=this.ctx;this.unwatch?.(),this.unwatch=hO(e=>{e&&t.state===`running`?t.suspend().catch(()=>{}):!e&&t.state!==`running`&&t.state!==`closed`&&t.resume().catch(()=>{})})}return this.ctx}setPlaying(e){this.isPlaying!==e&&(this.isPlaying=e,this.listeners.forEach(t=>t(e)))}async pump(){if(this.busy)return;let e=this.queue.shift();if(!e){this.setPlaying(!1);return}this.busy=!0;let t=this.gen;try{let n=this.ensureContext();if(n.state!==`running`){try{await n.resume()}catch{}if(t!==this.gen)return;if(n.state!==`running`){this.queue.unshift(e),this.busy=!1;return}}let r=await n.decodeAudioData(e);if(t!==this.gen)return;let i=n.createBufferSource();i.buffer=r,i.connect(this.analyser),i.onended=()=>{this.current===i&&(this.current=null,this.busy=!1,this.pump())},this.current=i,this.setPlaying(!0),i.start()}catch{if(t!==this.gen)return;this.busy=!1,this.pump()}}},DO=e=>new Promise(t=>setTimeout(t,e)),OO=[`audio/webm;codecs=opus`,`audio/webm`,`audio/mp4`,`audio/ogg;codecs=opus`],kO=3e3;function AO(e){let t=e;return t?.name===`NotAllowedError`||t?.name===`SecurityError`?Error(`Microphone permission was denied. Allow it in the browser to talk.`):t?.name===`NotFoundError`||t?.name===`OverconstrainedError`?Error(`No microphone was found.`):Error(t?.message||`Could not open the microphone.`)}var jO=class e{opts;stream=null;rec=null;chunks=[];ctx=null;analyser=null;timer=null;starting=!1;leaveSession=null;constructor(e={}){this.opts=e}static supported(){return typeof navigator<`u`&&!!navigator.mediaDevices?.getUserMedia&&typeof MediaRecorder<`u`}get active(){return this.rec!==null}async start(){if(!(this.rec||this.starting)){if(!e.supported())throw Error(`This browser cannot record audio here (use localhost or HTTPS).`);this.starting=!0;try{this.leaveSession=bO();try{let e=()=>navigator.mediaDevices.getUserMedia({audio:{echoCancellation:!0,noiseSuppression:!0}});try{this.stream=await e()}catch(t){if(!_O(t))throw t;await DO(250),this.leaveSession?.(),this.leaveSession=bO(),this.stream=await e()}}catch(e){throw this.leaveSession?.(),this.leaveSession=null,AO(e)}try{let e=OO.find(e=>MediaRecorder.isTypeSupported(e));this.chunks=[];let t=new MediaRecorder(this.stream,e?{mimeType:e}:void 0);t.ondataavailable=e=>{e.data&&e.data.size>0&&this.chunks.push(e.data)},t.onerror=()=>this.failed();for(let e of this.stream.getTracks())e.onended=()=>this.failed();this.openMeter(this.stream),t.start(250),this.rec=t,this.opts.maxMs&&(this.timer=setTimeout(()=>{this.timer=null,this.opts.onLimit?.()},this.opts.maxMs))}catch(e){throw this.release(),AO(e)}}finally{this.starting=!1}}}stop(){let e=this.rec;return e?new Promise(t=>{let n=!1,r=null,i=()=>{if(n)return;n=!0,r&&clearTimeout(r);let i=new Blob(this.chunks,{type:e.mimeType||`audio/webm`});this.release(),t(i)};if(r=setTimeout(i,kO),e.onstop=i,e.state===`inactive`)return i();try{e.stop()}catch{i()}}):Promise.reject(Error(`Not recording.`))}cancel(){let e=this.rec;if(e){e.ondataavailable=null,e.onstop=null,e.onerror=null;try{e.state!==`inactive`&&e.stop()}catch{}}this.release()}level(){if(!this.analyser||!this.rec)return 0;let e=new Uint8Array(this.analyser.fftSize);this.analyser.getByteTimeDomainData(e);let t=0;for(let n of e)t+=((n-128)/128)**2;return Math.min(1,Math.sqrt(t/e.length)*4)}failed(){this.rec&&(this.cancel(),this.opts.onError?.())}openMeter(e){try{this.ctx=new AudioContext,this.analyser=this.ctx.createAnalyser(),this.analyser.fftSize=1024,this.ctx.createMediaStreamSource(e).connect(this.analyser)}catch{this.analyser=null}}release(){this.timer&&clearTimeout(this.timer),this.timer=null,this.stream?.getTracks().forEach(e=>{e.onended=null,e.stop()}),this.ctx?.close().catch(()=>{}),this.stream=null,this.rec=null,this.ctx=null,this.analyser=null,this.chunks=[],this.leaveSession?.(),this.leaveSession=null}},MO=2e3,NO=()=>typeof window<`u`&&window.isSecureContext===!1,PO=50,FO=class{deps;recorder;player;mode=`idle`;pressed=!1;disposed=!1;uploads=0;toldAboutSound=!1;abort=null;poll=null;unsubscribe;constructor(e){this.deps=e;let t=()=>this.recorderFailed();this.recorder=e.recorder??e.makeRecorder?.(t)??new jO({maxMs:6e4,onLimit:()=>void this.pressEnd(),onError:t}),this.player=e.player??new EO,this.unsubscribe=this.player.onChange(e=>{this.mode!==`listening`&&this.mode!==`transcribing`&&this.setMode(e?`speaking`:`idle`)})}async pressStart(){if(!(this.pressed||this.disposed)){if(!this.deps.available()){this.alert(`warn`,`Voice is not available. Run: friend voice setup`);return}if(!(this.deps.supported?.()??jO.supported())){this.alert(`warn`,NO()?`This page is not secure, so the browser blocks the microphone. On the PC run: friend lan https on, restart Friend, and open the https:// address.`:`This browser cannot record audio here (use localhost or HTTPS).`);return}this.pressed=!0,this.player.unlock(),this.player.playing()&&(this.deps.send({type:`voice.interrupt`}),this.player.stop());try{await this.recorder.start()}catch(e){this.pressed=!1,this.alert(`error`,e.message),this.setMode(`idle`);return}if(!this.pressed){this.recorder.cancel(),this.setMode(`idle`);return}this.setMode(`listening`)}}async pressEnd(){if(!this.pressed||(this.pressed=!1,!this.recorder.active))return;let e=await this.recorder.stop();if(e.size<MO){this.alert(`info`,`Hold the key a little longer while you speak.`),this.setMode(`idle`);return}this.setMode(`transcribing`);let t=new AbortController;this.abort=t,this.uploads++;try{let{text:n}=await this.deps.post(e,t.signal);n.trim()||this.alert(`info`,`I didn't catch that.`)}catch(e){e.name!==`AbortError`&&this.alert(`error`,e.message)}finally{this.uploads--,this.abort===t&&(this.abort=null),this.settle()}}blur(){this.pressed&&(this.pressed=!1,this.recorder.cancel(),this.setMode(`idle`))}handleServer(e){if(e.type!==`audio.chunk`)return this.player.stop();this.player.enqueue(e),!this.toldAboutSound&&this.player.locked?.()&&(this.toldAboutSound=!0,this.deps.dispatch({type:`alert.add`,level:`info`,text:`Sound is blocked by the browser. Click or press a key once anywhere on the page to hear me.`}))}unlock(){this.player.unlock()}dispose(){this.disposed=!0,this.pressed=!1,this.stopPolling(),this.abort?.abort(),this.recorder.cancel(),this.player.stop(),this.player.dispose?.(),this.unsubscribe()}recorderFailed(){this.pressed=!1,this.recorder.cancel(),this.alert(`error`,`The microphone stopped working.`),this.setMode(`idle`)}settle(){this.uploads>0||this.mode!==`transcribing`||this.setMode(this.player.playing()?`speaking`:`idle`)}setMode(e){this.disposed||(this.mode=e,this.deps.dispatch({type:`voice.mode`,mode:e}),e===`listening`||e===`speaking`?this.startPolling():this.stopPolling())}startPolling(){this.stopPolling(),this.poll=setInterval(()=>{let e=this.mode===`listening`?this.recorder.level():this.player.level();this.deps.dispatch({type:`voice.level`,level:e})},PO)}stopPolling(){this.poll&&clearInterval(this.poll),this.poll=null}alert(e,t){this.disposed||this.deps.dispatch({type:`alert.add`,level:e,text:t})}};function IO(e){let[t,n]=(0,l.useReducer)(AE,wE),r=(0,l.useRef)(null),i=(0,l.useRef)(null),a=(0,l.useRef)(null),o=(0,l.useRef)(e);o.current=e;let s=(0,l.useRef)(t);return s.current=t,(0,l.useEffect)(()=>{let e=CE();r.current=e;let t=new FO({send:t=>e.send(t),dispatch:e=>n(e),post:fO,available:()=>s.current.voice.available});i.current=t;let c=new RE({send:t=>e.send(t),dispatch:e=>n(e),enabled:()=>s.current.camera.enabled,upload:async(e,t)=>{let n=await fetch(`/api/camera/frame/${encodeURIComponent(e)}`,{method:`POST`,headers:{"content-type":`image/jpeg`},body:t});if(!n.ok)throw Error(`upload failed (${n.status})`)}});a.current=c;let l=new lO({send:t=>e.send(t),dispatch:e=>n(e),upload:async(e,t)=>{let n=await fetch(`/api/screen/frame/${encodeURIComponent(e)}`,{method:`POST`,headers:{"content-type":`image/jpeg`},body:t});if(!n.ok)throw Error(`upload failed (${n.status})`)}}),u=e.onMessage(e=>{n(e);let r=e?.type,i=e?.id;(r===`camera.request`||r===`camera.cancel`)&&typeof i==`string`&&c.handle({type:r,id:i}),(r===`screen.request`||r===`screen.cancel`)&&typeof i==`string`&&l.handle({type:r,id:i}),(r===`audio.chunk`||r===`audio.stop`)&&t.handleServer(e)}),d=e.onState(e=>{n({type:`conn`,value:e}),e===`unauthorized`&&o.current(),e===`elsewhere`&&(t.blur(),c.dispose(),l.dispose())});return()=>{u(),d(),t.dispose(),c.dispose(),l.dispose(),e.close(),i.current=null,a.current=null,r.current=null}},[]),(0,l.useEffect)(()=>{t.camera.enabled||a.current?.dispose()},[t.camera.enabled]),{state:t,send:(0,l.useCallback)(e=>r.current?.send(e),[]),dispatch:(0,l.useCallback)(e=>n(e),[]),voice:(0,l.useMemo)(()=>({pressStart:()=>void i.current?.pressStart(),pressEnd:()=>void i.current?.pressEnd(),blur:()=>i.current?.blur(),unlock:()=>i.current?.unlock()}),[]),useHere:(0,l.useCallback)(()=>r.current?.takeOver(),[])}}var LO={401:`Please sign in again.`,403:`Incorrect PIN.`,413:`That recording was too long.`,429:`Too many attempts. Wait a moment.`,503:`Voice is not available. Run: friend voice setup`};async function RO(e,t){let n;try{n=await fetch(e,t)}catch{throw Error(`Could not reach Friend. Check the connection.`)}if(!n.ok){let e=``;try{e=(await n.json()).error??``}catch{}throw Error(e||LO[n.status]||`The request failed (${n.status}).`)}return await n.json()}var zO=(e,t)=>({method:e,headers:{"content-type":`application/json`},body:JSON.stringify(t)}),BO={state:()=>RO(`/api/voice/enroll`,{}),sample:e=>RO(`/api/voice/enroll/sample`,{method:`POST`,headers:{"content-type":e.type||`audio/webm`},body:e}),finish:e=>RO(`/api/voice/enroll/finish`,zO(`POST`,{pin:e})),cancel:async()=>{await RO(`/api/voice/enroll/cancel`,zO(`POST`,{}))},remove:async e=>{await RO(`/api/voice/enroll`,zO(`DELETE`,{pin:e}))}},VO=[`Friend, good evening. It is a pleasant day to get things done.`,`Open my projects and show me what changed today.`,`My voice is my key, so please remember it well.`,`Check the weather and read me the latest headlines.`,`Always protect the boss, and never trust a stranger.`],HO=15e3;function UO({api:e=BO,createRecorder:t=e=>new jO(e),onClose:n,who:r}){let[i,a]=(0,l.useState)(null),[o,s]=(0,l.useState)(0),[c,u]=(0,l.useState)(null),[f,m]=(0,l.useState)(`record`),[h,g]=(0,l.useState)(!1),[_,v]=(0,l.useState)(!1),[y,b]=(0,l.useState)(null),[S,C]=(0,l.useState)(``),w=(0,l.useRef)(!0),T=(0,l.useRef)(null);(0,l.useEffect)(()=>(w.current=!0,e.state().then(e=>{w.current&&(a(e),s(e.samples))}).catch(e=>w.current&&b(e.message)),()=>{w.current=!1,T.current?.cancel(),T.current=null}),[e]);let E=(0,l.useCallback)(async()=>{let t=T.current;if(t){T.current=null,g(!1),v(!0);try{let n=await t.stop(),r=await e.sample(n);if(!w.current)return;s(r.count),u(r.note)}catch(e){w.current&&b(e.message)}finally{w.current&&v(!1)}}},[e]),D=async()=>{b(null),u(null);let e=t({maxMs:HO,onLimit:()=>void E(),onError:()=>{T.current=null,w.current&&(g(!1),b(`The microphone stopped working. Try again.`))}});try{await e.start()}catch(e){w.current&&b(e.message);return}if(!w.current)return e.cancel();T.current=e,g(!0)},O=async e=>{b(null),v(!0);try{await e()}catch(e){w.current&&b(e.message)}finally{w.current&&(v(!1),C(``))}},k=async()=>{T.current?.cancel(),T.current=null,await e.cancel().catch(()=>{}),n()},A=i?.min??3,j=o%VO.length,ee=o<VO.length?`Phrase ${o+1} of ${VO.length}`:`Extra recording (${o} so far)`;return(0,p.jsxs)(`div`,{className:`approval enroll glass`,role:`dialog`,"aria-label":`Voice enrollment`,style:{pointerEvents:`auto`},children:[(0,p.jsx)(`div`,{className:`approval-head`,children:(0,p.jsx)(`span`,{className:`approval-title`,children:r?`Teach Friend ${r}'s voice`:`Teach Friend your voice`})}),f===`record`&&(0,p.jsxs)(p.Fragment,{children:[!r&&i?.enrolled&&(0,p.jsx)(`p`,{className:`auth-note`,children:`Your voice is already saved. Saving a new one replaces it.`}),r&&(0,p.jsxs)(`p`,{className:`auth-note`,children:[`Hand the device to `,r,`. `,r,` reads each sentence aloud, close to the microphone, in a quiet room.`]}),(0,p.jsxs)(`p`,{className:`auth-note`,children:[ee,`. Press Record, read this aloud in a quiet room, then press Stop.`]}),(0,p.jsx)(`pre`,{className:`approval-summary`,"data-testid":`enroll-phrase`,style:{whiteSpace:`pre-wrap`},children:VO[j]}),(0,p.jsxs)(`div`,{role:`status`,className:`auth-note`,children:[o,` recorded`,o>=A?` — enough to save`:` — at least ${A} needed`,`.`,c?` ${c}`:``]}),y&&(0,p.jsx)(`p`,{role:`alert`,className:`auth-error`,children:y}),(0,p.jsxs)(`div`,{className:`approval-actions`,children:[h?(0,p.jsx)(`button`,{type:`button`,style:d,className:`danger`,onClick:()=>void E(),children:`Stop`}):(0,p.jsx)(`button`,{type:`button`,style:d,className:`primary`,disabled:_||!i||o>=(i?.max??8),onClick:()=>void D(),children:_?`Uploading…`:`Record`}),(0,p.jsx)(`button`,{type:`button`,style:d,disabled:h||_||o<A,onClick:()=>m(`pin-save`),children:r?`Save ${r}'s voice`:`Save my voice`}),!r&&i?.enrolled&&(0,p.jsx)(`button`,{type:`button`,style:d,className:`danger`,disabled:h||_,onClick:()=>m(`pin-delete`),children:`Delete my voice`}),(0,p.jsx)(`button`,{type:`button`,style:d,onClick:()=>void k(),children:`Cancel`})]})]}),(f===`pin-save`||f===`pin-delete`)&&(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`p`,{className:`auth-note`,children:f===`pin-save`?r?`Enter your PIN to save ${r}'s voice.`:`Enter your PIN to save your voice.`:`Enter your PIN to delete your saved voice.`}),(0,p.jsx)(x,{pin:S,onChange:C,onSubmit:f===`pin-save`?()=>!_&&void O(async()=>{await e.finish(S),w.current&&m(`saved`)}):void 0}),y&&(0,p.jsx)(`p`,{role:`alert`,className:`auth-error`,children:y}),(0,p.jsxs)(`div`,{className:`approval-actions`,children:[f===`pin-save`?(0,p.jsx)(`button`,{type:`button`,style:d,className:`primary`,disabled:_||S.length<6,onClick:()=>void O(async()=>{await e.finish(S),w.current&&m(`saved`)}),children:`Save`}):(0,p.jsx)(`button`,{type:`button`,style:d,className:`danger`,disabled:_||S.length<6,onClick:()=>void O(async()=>{await e.remove(S),w.current&&m(`deleted`)}),children:`Delete`}),(0,p.jsx)(`button`,{type:`button`,style:d,onClick:()=>{C(``),b(null),m(`record`)},children:`Back`})]})]}),(f===`saved`||f===`deleted`)&&(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`p`,{className:`auth-note`,children:f===`saved`?r?`${r}'s voice is saved. From now on I will know when ${r} is talking.`:`Your voice is saved. From now on I will tell you apart from other speakers.`:`Your voice was deleted. Every voice is treated as yours until you enroll again.`}),(0,p.jsx)(`div`,{className:`approval-actions`,children:(0,p.jsx)(`button`,{type:`button`,style:d,className:`primary`,onClick:n,children:`Done`})})]})]})}var WO=new Set([`INPUT`,`TEXTAREA`,`SELECT`,`BUTTON`,`A`,`SUMMARY`]),GO=new Set([`button`,`checkbox`,`switch`,`tab`,`menuitem`,`link`,`radio`,`option`,`textbox`,`combobox`,`slider`]),KO=e=>e instanceof HTMLElement&&(WO.has(e.tagName)||e.isContentEditable||GO.has(e.getAttribute(`role`)??``)),qO=e=>e.code===`Space`||e.key===` `;function JO(e){let t=(0,l.useRef)(e);t.current=e,(0,l.useEffect)(()=>{let e=!1,n=n=>{!qO(n)||n.ctrlKey||n.metaKey||n.altKey||KO(n.target)||KO(document.activeElement)||(n.preventDefault(),!(n.repeat||e)&&(e=!0,t.current.pressStart()))},r=n=>{qO(n)&&e&&(e=!1,n.preventDefault(),t.current.pressEnd())},i=()=>{e=!1,t.current.blur()},a=()=>{document.hidden&&i()};return window.addEventListener(`keydown`,n),window.addEventListener(`keyup`,r),window.addEventListener(`blur`,i),document.addEventListener(`visibilitychange`,a),()=>{window.removeEventListener(`keydown`,n),window.removeEventListener(`keyup`,r),window.removeEventListener(`blur`,i),document.removeEventListener(`visibilitychange`,a)}},[])}function YO(e){let t=(0,l.useRef)(e);t.current=e,(0,l.useEffect)(()=>{let e=()=>t.current.unlock(),n=[`pointerdown`,`keydown`,`touchend`];for(let t of n)window.addEventListener(t,e,{passive:!0});return()=>{for(let t of n)window.removeEventListener(t,e)}},[])}function XO({onUseHere:e}){return(0,p.jsx)(`div`,{className:`elsewhere`,role:`alertdialog`,"aria-labelledby":`elsewhere-title`,"data-testid":`elsewhere`,children:(0,p.jsxs)(`div`,{className:`elsewhere-card`,children:[(0,p.jsx)(`h2`,{id:`elsewhere-title`,children:`Friend is open in another window`}),(0,p.jsx)(`p`,{children:`Friend works in one window at a time. Click “Use here” to use it in this window instead; the other one will stop.`}),(0,p.jsx)(`button`,{type:`button`,className:`elsewhere-btn`,onClick:e,autoFocus:!0,children:`Use here`})]})})}function ZO(e,t,n){let r=Math.max(100,Math.round(e)),i=Math.max(100,Math.round(t));return{width:r,height:i,kind:r<=599?`phone`:n||r<1024?`tablet`:`desktop`,orientation:i>r?`portrait`:`landscape`,touch:n}}var QO=()=>typeof matchMedia==`function`&&matchMedia(`(pointer: coarse)`).matches;function $O(){return ZO(window.innerWidth,window.innerHeight,QO())}var ek=(e,t)=>!!e&&e.width===t.width&&e.height===t.height&&e.kind===t.kind&&e.orientation===t.orientation&&e.touch===t.touch;function tk(e,t){let n=(0,l.useRef)(null),r=(0,l.useRef)(e);r.current=e,(0,l.useEffect)(()=>{if(t!==`open`){n.current=null;return}let e=()=>{let e=$O();ek(n.current,e)||(n.current=e,r.current({type:`ui.screen`,...e}))};e();let i=null,a=()=>{i&&clearTimeout(i),i=setTimeout(e,400)};return window.addEventListener(`resize`,a),window.addEventListener(`orientationchange`,a),()=>{i&&clearTimeout(i),window.removeEventListener(`resize`,a),window.removeEventListener(`orientationchange`,a)}},[t])}var nk={401:`Please sign in again.`,403:`Incorrect PIN.`,413:`That recording was too long.`,429:`Too many attempts. Wait a moment.`,503:`Voice is not available. Run: friend voice setup`};async function rk(e,t={}){let n;try{n=await fetch(e,t)}catch{throw Error(`Could not reach Friend. Check the connection.`)}if(!n.ok){let e=``;try{e=(await n.json()).error??``}catch{}throw Error(e||nk[n.status]||`The request failed (${n.status}).`)}return await n.json()}var ik=(e,t)=>({method:e,headers:{"content-type":`application/json`},body:JSON.stringify(t)}),ak={overview:()=>rk(`/api/voice/people`),begin:e=>rk(`/api/voice/people/begin`,ik(`POST`,{name:e})),recording:{state:async()=>(await rk(`/api/voice/people`)).enrolling??{enrolled:!1,samples:0,min:3,max:8},sample:e=>rk(`/api/voice/people/sample`,{method:`POST`,headers:{"content-type":e.type||`audio/webm`},body:e}),finish:e=>rk(`/api/voice/people/finish`,ik(`POST`,{pin:e})),cancel:async()=>{await rk(`/api/voice/people/cancel`,ik(`POST`,{}))},remove:async()=>{}},removePerson:async(e,t)=>{await rk(`/api/voice/people/${e}`,ik(`DELETE`,{pin:t}))}};function ok({api:e=ak,createRecorder:t,onClose:n}){let[r,i]=(0,l.useState)(null),[a,o]=(0,l.useState)({kind:`list`}),[s,c]=(0,l.useState)(``),[u,f]=(0,l.useState)(``),[m,h]=(0,l.useState)(!1),[g,_]=(0,l.useState)(null),v=(0,l.useRef)(!0),y=(0,l.useCallback)(()=>{e.overview().then(e=>v.current&&i(e)).catch(e=>v.current&&_(e.message))},[e]);(0,l.useEffect)(()=>(v.current=!0,y(),()=>{v.current=!1}),[y]);let b=async()=>{_(null),h(!0);try{let t=await e.begin(s.trim());v.current&&o({kind:`record`,name:t.name})}catch(e){v.current&&_(e.message)}finally{v.current&&h(!1)}},S=async t=>{_(null),h(!0);try{if(await e.removePerson(t.id,u),!v.current)return;o({kind:`list`}),y()}catch(e){v.current&&_(e.message)}finally{v.current&&(h(!1),f(``))}};return a.kind===`record`?(0,p.jsx)(UO,{api:e.recording,who:a.name,...t?{createRecorder:t}:{},onClose:()=>{c(``),o({kind:`list`}),y()}}):(0,p.jsxs)(`div`,{className:`approval enroll glass`,role:`dialog`,"aria-label":`Family voices`,style:{pointerEvents:`auto`},children:[(0,p.jsx)(`div`,{className:`approval-head`,children:(0,p.jsx)(`span`,{className:`approval-title`,children:`Family voices`})}),a.kind===`list`&&(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`p`,{className:`auth-note`,children:`Friend knows your voice. Add the people at home, so it knows who is talking and answers them by name. They can chat and ask for the weather, but cannot use your PC or see your private things.`}),r&&!r.ownerEnrolled&&(0,p.jsx)(`p`,{className:`auth-note`,children:`First teach Friend your own voice (Esc, then Enroll my voice).`}),r&&r.people.length===0&&r.ownerEnrolled&&(0,p.jsx)(`p`,{className:`auth-note`,children:`Nobody added yet.`}),r&&r.people.length>0&&(0,p.jsx)(`ul`,{className:`household-list`,"aria-label":`People Friend knows`,children:r.people.map(e=>(0,p.jsxs)(`li`,{className:`household-row`,children:[(0,p.jsx)(`span`,{children:e.name}),(0,p.jsx)(`button`,{type:`button`,style:d,className:`danger`,onClick:()=>o({kind:`remove`,person:e}),"aria-label":`Remove ${e.name}`,children:`Remove`})]},e.id))}),r&&r.ownerEnrolled&&r.people.length<r.max&&(0,p.jsxs)(`label`,{className:`settings-field`,children:[(0,p.jsx)(`span`,{children:`Add a person`}),(0,p.jsx)(`input`,{value:s,maxLength:40,placeholder:`Name, for example Priya`,onChange:e=>c(e.target.value),onKeyDown:e=>e.key===`Enter`&&s.trim()&&!m&&void b()})]}),g&&(0,p.jsx)(`p`,{role:`alert`,className:`auth-error`,children:g}),(0,p.jsxs)(`div`,{className:`approval-actions`,children:[r&&r.ownerEnrolled&&r.people.length<r.max&&(0,p.jsx)(`button`,{type:`button`,style:d,className:`primary`,disabled:m||!s.trim(),onClick:()=>void b(),children:`Record their voice`}),(0,p.jsx)(`button`,{type:`button`,style:d,onClick:n,children:`Close`})]})]}),a.kind===`remove`&&(0,p.jsxs)(p.Fragment,{children:[(0,p.jsxs)(`p`,{className:`auth-note`,children:[`Enter your PIN to remove `,a.person.name,`’s voice. Friend will treat their voice as a stranger’s.`]}),(0,p.jsx)(x,{pin:u,onChange:f}),g&&(0,p.jsx)(`p`,{role:`alert`,className:`auth-error`,children:g}),(0,p.jsxs)(`div`,{className:`approval-actions`,children:[(0,p.jsx)(`button`,{type:`button`,style:d,className:`danger`,disabled:m||u.length<6,onClick:()=>void S(a.person),children:`Remove`}),(0,p.jsx)(`button`,{type:`button`,style:d,onClick:()=>{f(``),_(null),o({kind:`list`})},children:`Back`})]})]})]})}var sk=`▌▍▎▏█▓▒░<>/\\|+-=*#%&0123456789ABCDEF`;function ck(e,t,n=Math.random){let r=[...e];if(t>=1)return e;let i=Math.floor(r.length*Math.max(0,t));return r.map((e,t)=>t<i||e===` `?e:sk[Math.floor(n()*36)]).join(``)}var lk=e=>e.length===0?0:Math.min(24,Math.max(6,Math.ceil([...e].length/2)));function uk(e,t){let[n,r]=(0,l.useState)(e),i=(0,l.useRef)(e);return(0,l.useEffect)(()=>{if(!t||e===i.current){i.current=e,r(e);return}i.current=e;let n=lk(e);if(n===0){r(e);return}let a=0,o=setInterval(()=>{a++,r(ck(e,a/n)),a>=n&&clearInterval(o)},320/n);return()=>clearInterval(o)},[e,t]),n}function dk(e){let t=e.currentTarget,n=t.getBoundingClientRect(),r=document.createElement(`span`);r.className=`hud-ripple`;let i=Math.max(n.width,n.height)*2;r.style.width=r.style.height=`${i}px`,r.style.left=`${e.clientX-n.left-i/2}px`,r.style.top=`${e.clientY-n.top-i/2}px`,t.appendChild(r),r.addEventListener(`animationend`,()=>r.remove(),{once:!0}),setTimeout(()=>r.remove(),900)}function fk({items:e,animations:t,onAction:n}){let[r,i]=(0,l.useState)(null),a=(0,l.useRef)(void 0);if((0,l.useEffect)(()=>()=>clearTimeout(a.current),[]),e.length===0)return null;let o=e=>{t!==`off`&&(i(e.id),clearTimeout(a.current),a.current=setTimeout(()=>i(null),650)),n(e)};return(0,p.jsxs)(B,{id:`launcher`,label:`Quick launch`,wholeBox:!0,testId:`launcher`,className:`hud hud-launcher${t===`full`?` hud-boot`:``}`,children:[(0,p.jsx)(`div`,{className:`hud-kicker`,children:`Quick launch`}),(0,p.jsx)(`ul`,{className:`hud-stack`,children:e.map((e,n)=>(0,p.jsx)(`li`,{className:`hud-tab hud-cut${r===e.id?` engaged`:``}${t===`full`?` hud-boot`:``}`,style:{"--i":n+1},children:(0,p.jsxs)(`button`,{type:`button`,className:`hud-tab-main`,"aria-label":e.label,onPointerDown:t===`off`?void 0:dk,onClick:()=>o(e),children:[(0,p.jsx)(`span`,{className:`hud-icon`,"aria-hidden":`true`,children:e.icon}),(0,p.jsx)(`span`,{className:`hud-tab-label`,children:e.label}),(0,p.jsx)(`span`,{className:`hud-tab-engaged`,"aria-hidden":`true`,children:`ENGAGED`}),(0,p.jsx)(`span`,{className:`hud-sweep`,"aria-hidden":`true`}),(0,p.jsx)(`span`,{className:`hud-scan`,"aria-hidden":`true`})]})},e.id))})]})}var pk=(e,t=18)=>(0,p.jsx)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.8`,strokeLinecap:`round`,strokeLinejoin:`round`,"aria-hidden":`true`,children:e}),mk=()=>pk((0,p.jsx)(`path`,{d:`M7 4.5v15l12-7.5z`,fill:`currentColor`})),hk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`rect`,{x:`6`,y:`4.5`,width:`4`,height:`15`,fill:`currentColor`}),(0,p.jsx)(`rect`,{x:`14`,y:`4.5`,width:`4`,height:`15`,fill:`currentColor`})]})),gk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M5 5v14l10-7z`,fill:`currentColor`}),(0,p.jsx)(`path`,{d:`M18 5v14`})]})),_k=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M19 5v14L9 12z`,fill:`currentColor`}),(0,p.jsx)(`path`,{d:`M6 5v14`})]})),vk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M3 7h3.5c3 0 4 2 5.5 5s2.500 5 5.500 5H21`}),(0,p.jsx)(`path`,{d:`M3 17h3.5c1.500 0 2.500-.6 3.400-1.800M13.500 8.800C14.500 7.600 15.500 7 17 7h4`}),(0,p.jsx)(`path`,{d:`m18.500 4.500 2.500 2.500-2.500 2.500M18.500 14.500l2.500 2.500-2.500 2.500`})]})),yk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M17 3l3 3-3 3`}),(0,p.jsx)(`path`,{d:`M4 11V9a3 3 0 0 1 3-3h13M7 21l-3-3 3-3`}),(0,p.jsx)(`path`,{d:`M20 13v2a3 3 0 0 1-3 3H4`})]})),bk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M4 9.500v5h3.500L12 18.500v-13L7.500 9.500z`,fill:`currentColor`}),(0,p.jsx)(`path`,{d:`M15.500 9a4 4 0 0 1 0 6M18 6.500a7.500 7.500 0 0 1 0 11`})]})),xk=()=>pk((0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(`path`,{d:`M4 9.500v5h3.500L12 18.500v-13L7.500 9.500z`,fill:`currentColor`}),(0,p.jsx)(`path`,{d:`m16 9 5 6M21 9l-5 6`})]})),Sk=()=>pk((0,p.jsx)(`path`,{d:`M4 9V4h5M20 9V4h-5M4 15v5h5M20 15v5h-5`})),Ck=()=>pk((0,p.jsx)(`path`,{d:`M9 4v5H4M15 4v5h5M9 20v-5H4M15 20v-5h5`})),wk=()=>pk((0,p.jsx)(`path`,{d:`M6 6l12 12M18 6 6 18`})),Tk=()=>pk((0,p.jsx)(`path`,{d:`M9 18V6l10-2v12`}),22),Ek=56,Dk=()=>({bars:new Float32Array(Ek),bass:0,left:0,right:0});function Ok(e,t,n,r,i){let a=n?.82:.9;if(t&&n){t.getByteFrequencyData(i);let n=Math.min(i.length,96);for(let t=0;t<Ek;t++){let r=Math.min(n-1,Math.floor((t/Ek)**1.6*n));e.bars[t]=Math.max((i[r]??0)/255,e.bars[t]*a)}}else if(n)for(let t=0;t<Ek;t++)e.bars[t]=Math.max(.12+.28*Math.abs(Math.sin(r/420+t*.55)*Math.cos(r/900+t*.21)),e.bars[t]*a);else for(let t=0;t<Ek;t++)e.bars[t]=e.bars[t]*a;let o=0;for(let t=0;t<6;t++)o+=e.bars[t];e.bass=Math.min(1,o/6*1.15);let s=0,c=0;for(let t=0;t<Ek/2;t++)s+=e.bars[t],c+=e.bars[t+Ek/2];e.left=Math.min(1,s/(Ek/2)*1.6),e.right=Math.min(1,c/(Ek/2)*3.2)}function kk({progress:e,playing:t,cover:n,analyser:r,levels:i,visualizer:a,animate:o,size:s}){let c=(0,l.useRef)(null),u=(0,l.useRef)(null),d=(0,l.useRef)(new Uint8Array(new ArrayBuffer(128)));(0,l.useEffect)(()=>{let e=c.current,n=e?.getContext(`2d`);if(!e||!n||!o)return;let l=0,f=Math.min(2,window.devicePixelRatio||1);e.width=e.height=Math.round(s*f);let p=getComputedStyle(e).getPropertyValue(`--accent`).trim()||`#3fd8ff`,m=e=>{if(Ok(i,r,t,e,d.current),u.current?.style.setProperty(`--bass`,i.bass.toFixed(3)),n.setTransform(f,0,0,f,0,0),n.clearRect(0,0,s,s),a){let e=s/2,t=s*.335,r=s*.135;n.lineCap=`round`,n.lineWidth=Math.max(1.5,s/90);for(let a=0;a<Ek;a++){let o=a/Ek*Math.PI*2-Math.PI/2,s=i.bars[a],c=2+s*r;n.strokeStyle=p,n.globalAlpha=.35+s*.65,n.beginPath(),n.moveTo(e+Math.cos(o)*t,e+Math.sin(o)*t),n.lineTo(e+Math.cos(o)*(t+c),e+Math.sin(o)*(t+c)),n.stroke()}n.globalAlpha=1}(t||!i.bars.every(e=>e<.01)||a)&&(l=requestAnimationFrame(m))};return l=requestAnimationFrame(m),()=>cancelAnimationFrame(l)},[r,t,a,o,s,i]);let f=Math.max(0,Math.min(1,e))*100;return(0,p.jsxs)(`div`,{ref:u,className:`hud-dial${t?` playing`:``}`,style:{width:s,height:s},role:`img`,"aria-label":`Playback dial`,children:[(0,p.jsxs)(`svg`,{className:`hud-dial-svg`,viewBox:`0 0 200 200`,"aria-hidden":`true`,children:[(0,p.jsx)(`circle`,{className:`hud-dial-ticks`,cx:`100`,cy:`100`,r:`96`}),(0,p.jsx)(`circle`,{className:`hud-dial-track`,cx:`100`,cy:`100`,r:`88`}),(0,p.jsx)(`circle`,{className:`hud-dial-arc`,cx:`100`,cy:`100`,r:`88`,pathLength:`100`,strokeDasharray:`${f} 100`,transform:`rotate(-90 100 100)`}),(0,p.jsx)(`circle`,{className:`hud-dial-inner`,cx:`100`,cy:`100`,r:`62`}),(0,p.jsxs)(`g`,{className:`hud-needle`,children:[(0,p.jsx)(`line`,{x1:`100`,y1:`100`,x2:`100`,y2:`14`}),(0,p.jsx)(`circle`,{cx:`100`,cy:`14`,r:`2.500`})]})]}),(0,p.jsx)(`canvas`,{ref:c,className:`hud-spectrum`,style:{width:s,height:s},"aria-hidden":`true`}),(0,p.jsx)(`div`,{className:`hud-cover`,style:n?{backgroundImage:`url("${n}")`}:void 0,children:!n&&(0,p.jsx)(Tk,{})})]})}var Ak=e=>{let t=Math.max(0,Math.floor(Number.isFinite(e)?e:0));return`${Math.floor(t/60)}:${String(t%60).padStart(2,`0`)}`},jk=new Map,Mk=e=>{let t=Wl(e);return t&&t.source===`local`?t.id:null},Nk=e=>Wl(e)?.source===`spotify`,Pk=e=>Wl(e)?.source===`soundcloud`,Fk=e=>Wl(e)?.source===`audius`,Ik={spotify:`Spotify`,soundcloud:`SoundCloud`,audius:`Audius`};function Lk(e){let[t,n]=(0,l.useState)(e?jk.get(e)??!1:!1);return(0,l.useEffect)(()=>{if(!e)return n(!1);if(jk.has(e))return n(jk.get(e));let t=!0,r=new Image;r.onload=()=>{jk.set(e,!0),t&&n(!0)},r.onerror=()=>{jk.set(e,!1),t&&n(!1)};let i=Mk(e);return i?(r.src=`/api/music/cover/${i}`,()=>{t=!1}):n(!1)},[e]),e&&t?`/api/music/cover/${Mk(e)}`:null}async function Rk(e,t){let n=await fetch(`/api/music/library?q=${encodeURIComponent(e)}&limit=${t}`);return n.ok?await n.json():{tracks:[],total:0}}function zk(){let[e,t]=(0,l.useState)(null);return(0,l.useEffect)(()=>{let e=!0;return fetch(`/api/music/sources`).then(e=>e.ok?e.json():null).then(n=>{let r={};for(let e of[`spotify`,`soundcloud`,`audius`]){let t=n?.sources?.find(t=>t.id===e)?.status;t&&(r[e]={connected:t.connected,needs:t.needs})}e&&n&&t(r)}).catch(()=>{}),()=>{e=!1}},[]),e}async function Bk(e,t,n){let r=await fetch(`/api/music/search?q=${encodeURIComponent(t)}&source=${e}&limit=${n}`);if(!r.ok)return{tracks:[],total:0};let i=((await r.json()).tracks??[]).map(e=>({id:e.ref,title:e.title,artist:e.artist,album:e.album,durationSec:e.durationSec}));return{tracks:i,total:i.length}}var Vk=e=>({id:e.id,title:e.title,artist:e.artist,album:e.album,durationSec:e.durationSec});function Hk({levels:e,animate:t,side:n}){let r=(0,l.useRef)(null);return(0,l.useEffect)(()=>{if(!t)return;let i=0,a=r.current,o=()=>{if(a){let t=n===`left`?e.left:e.right,r=Math.round(t*12);a.querySelectorAll(`i`).forEach((e,t)=>e.classList.toggle(`on`,t<r))}i=requestAnimationFrame(o)};return i=requestAnimationFrame(o),()=>cancelAnimationFrame(i)},[e,t,n]),(0,p.jsx)(`div`,{ref:r,className:`hud-levels ${n}`,"aria-hidden":`true`,children:Array.from({length:12},(e,t)=>(0,p.jsx)(`i`,{},t))})}function Uk({player:e,anim:t}){let{state:n,dispatch:r}=e,i=(0,l.useCallback)(async()=>{if(n.queue.length>0)return r({type:`resume`});let e=await Rk(``,500);r({type:`play`,tracks:e.tracks.map(Vk),mode:`replace`,...n.shuffle?{shuffle:!0}:{}})},[n.queue.length,n.shuffle,r]),a=e=>n=>{t!==`off`&&dk(n),e()};return(0,p.jsxs)(`div`,{className:`hud-controls`,role:`group`,"aria-label":`Player controls`,children:[(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":`Shuffle`,"aria-pressed":n.shuffle,title:`Shuffle`,onClick:()=>r({type:`shuffle`}),children:(0,p.jsx)(vk,{})}),(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":`Previous track`,title:`Previous`,onPointerDown:a(()=>{}),onClick:()=>r({type:`previous`}),children:(0,p.jsx)(_k,{})}),(0,p.jsx)(`button`,{type:`button`,className:`hud-btn hud-btn-main`,"aria-label":n.playing?`Pause`:`Play`,title:n.playing?`Pause`:`Play`,onPointerDown:a(()=>{}),onClick:()=>n.playing?r({type:`pause`}):void i(),children:n.playing?(0,p.jsx)(hk,{}):(0,p.jsx)(mk,{})}),(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":`Next track`,title:`Next`,onPointerDown:a(()=>{}),onClick:()=>r({type:`next`}),children:(0,p.jsx)(gk,{})}),(0,p.jsxs)(`button`,{type:`button`,className:`hud-btn${n.repeat===`off`?``:` on`}`,"aria-label":`Repeat: ${n.repeat}`,title:`Repeat: ${n.repeat}`,onClick:()=>r({type:`repeat`,mode:n.repeat===`off`?`all`:n.repeat===`all`?`one`:`off`}),children:[(0,p.jsx)(yk,{}),n.repeat===`one`&&(0,p.jsx)(`sup`,{children:`1`})]})]})}function Wk({player:e}){let{state:t,dispatch:n}=e,r=t.duration>0?t.position/t.duration*100:0;return(0,p.jsxs)(`div`,{className:`hud-timeline`,children:[(0,p.jsx)(`span`,{className:`hud-time`,children:Ak(t.position)}),(0,p.jsx)(`input`,{type:`range`,className:`hud-range`,"aria-label":`Position`,min:0,max:Math.max(1,Math.floor(t.duration)),step:1,value:Math.min(Math.floor(t.position),Math.max(1,Math.floor(t.duration))),style:{"--fill":`${r}%`},disabled:t.duration<=0,onChange:e=>n({type:`seek`,seconds:Number(e.target.value)})}),(0,p.jsxs)(`span`,{className:`hud-time`,children:[`-`,Ak(Math.max(0,t.duration-t.position))]})]})}function Gk({player:e}){let{state:t,dispatch:n}=e;return(0,p.jsxs)(`div`,{className:`hud-volume`,children:[(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":t.muted?`Unmute`:`Mute`,onClick:()=>n({type:`mute`}),children:t.muted||t.volume===0?(0,p.jsx)(xk,{}):(0,p.jsx)(bk,{})}),(0,p.jsx)(`input`,{type:`range`,className:`hud-range`,"aria-label":`Volume`,min:0,max:100,value:t.muted?0:t.volume,style:{"--fill":`${t.muted?0:t.volume}%`},onChange:e=>n({type:`volume`,level:Number(e.target.value)})})]})}function Kk({player:e,anim:t}){let{state:n,dispatch:r}=e,[i,a]=(0,l.useState)(n.queue.length?`queue`:`library`),[o,s]=(0,l.useState)(``),[c,u]=(0,l.useState)(`folder`),[d,f]=(0,l.useState)(null),m=zk(),h=[`spotify`,`soundcloud`,`audius`].filter(e=>m?.[e]?.connected),g=c!==`folder`&&h.includes(c)?c:null,_=g?m?.[g]?.needs:null;(0,l.useEffect)(()=>{if(i!==`library`)return;let e=!0;if(g&&!o.trim()){f(null);return}let t=()=>g?Bk(g,o.trim(),30):Rk(o,100),n=setTimeout(()=>void t().then(t=>e&&f(t)),o?250:0);return()=>{e=!1,clearTimeout(n)}},[i,o,g]);let v=i===`queue`?n.queue.map((e,t)=>({track:e,index:t})):(d?.tracks??[]).map((e,t)=>({track:Vk(e),index:t}));return(0,p.jsxs)(`div`,{className:`hud-playlist`,children:[(0,p.jsxs)(`div`,{className:`hud-tabs`,role:`tablist`,children:[[`queue`,`library`].map(e=>(0,p.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":i===e,className:`hud-chip${i===e?` on`:``}`,onClick:()=>a(e),children:e===`queue`?`Queue (${n.queue.length})`:`Library`},e)),i===`queue`&&n.queue.length>0&&(0,p.jsx)(`button`,{type:`button`,className:`hud-chip`,onClick:()=>r({type:`clear`}),children:`Clear`})]}),i===`library`&&h.length>0&&(0,p.jsx)(`div`,{className:`hud-tabs`,role:`tablist`,"aria-label":`Where to look`,children:[`folder`,...h].map(e=>(0,p.jsx)(`button`,{type:`button`,role:`tab`,"aria-selected":c===e,className:`hud-chip${c===e?` on`:``}`,onClick:()=>{u(e),f(null)},children:e===`folder`?`Folder`:Ik[e]},e))}),i===`library`&&(0,p.jsx)(`input`,{className:`hud-search`,type:`search`,placeholder:`Search title, artist or album`,"aria-label":`Search the music`,value:o,onChange:e=>s(e.target.value)}),(0,p.jsxs)(`ul`,{className:`hud-list`,children:[v.length===0&&(0,p.jsx)(`li`,{className:`hud-empty`,children:i===`queue`?`The queue is empty.`:g&&!o.trim()?`Type to search ${Ik[g]}.`:d?`No music matches.`:`Loading…`}),i===`library`&&g&&_&&(0,p.jsx)(`li`,{className:`hud-empty`,children:_}),v.map(({track:e,index:a},o)=>{let s=i===`queue`&&a===n.index;return(0,p.jsxs)(`li`,{className:`hud-tab hud-cut${s?` current`:``}${t===`full`?` hud-boot`:``}`,style:{"--i":Math.min(o,12)},children:[(0,p.jsxs)(`button`,{type:`button`,className:`hud-tab-main`,"aria-current":s?`true`:void 0,onPointerDown:t===`off`?void 0:dk,onClick:()=>r(i===`queue`?{type:`jump`,index:a}:{type:`play`,tracks:(d?.tracks??[]).map(Vk),mode:`replace`,start:a}),children:[(0,p.jsx)(`span`,{className:`hud-tab-title`,children:e.title}),(0,p.jsxs)(`small`,{children:[e.artist||e.album,Nk(e.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`SPOTIFY`}),Pk(e.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`SOUNDCLOUD`}),Fk(e.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`AUDIUS`})]})]}),i===`library`&&(0,p.jsx)(`button`,{type:`button`,className:`hud-mini`,"aria-label":`Add ${e.title} to the queue`,title:`Add to the queue`,onClick:()=>r({type:`play`,tracks:[e],mode:`add`}),children:`+`}),i===`queue`&&(0,p.jsx)(`button`,{type:`button`,className:`hud-mini`,"aria-label":`Remove ${e.title} from the queue`,title:`Remove`,onClick:()=>r({type:`remove`,index:a}),children:`×`})]},`${e.id}-${a}`)})]})]})}function qk({player:e,music:t,animations:n}){let{state:r,dispatch:i,current:a,blocked:o,notice:s,analyser:c,unlock:u}=e,d=(0,l.useMemo)(Dk,[]),f=Lk(a?.id),m=r.view===`full`,h=uk(a?.title??``,n===`full`);if(!t?.folderSet||r.view===`hidden`)return null;let g=r.duration>0?r.position/r.duration:0,_=n!==`off`;return(0,p.jsxs)(B,{id:`music`,label:`Music player`,wholeBox:!0,testId:`music`,className:`hud hud-music hud-cut ${m?`full`:`mini`}${r.playing?` playing`:``}${n===`full`?` hud-boot`:``}`,children:[(0,p.jsxs)(`header`,{className:`hud-music-head`,children:[(0,p.jsx)(`span`,{className:`hud-kicker`,children:`Media player`}),(0,p.jsxs)(`span`,{className:`hud-head-actions`,children:[(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":m?`Smaller player`:`Bigger player`,title:m?`Smaller`:`Bigger`,onClick:()=>i({type:`view`,view:m?`mini`:`full`}),children:m?(0,p.jsx)(Ck,{}):(0,p.jsx)(Sk,{})}),(0,p.jsx)(`button`,{type:`button`,className:`hud-btn`,"aria-label":`Hide the player`,title:`Hide (the music keeps playing)`,onClick:()=>i({type:`view`,view:`hidden`}),children:(0,p.jsx)(wk,{})})]})]}),(0,p.jsxs)(`div`,{className:`hud-music-body`,children:[(0,p.jsxs)(`div`,{className:`hud-music-left`,children:[m&&(0,p.jsx)(Hk,{levels:d,animate:_,side:`left`}),(0,p.jsx)(kk,{progress:g,playing:r.playing,cover:f,analyser:c,levels:d,visualizer:t.visualizer,animate:_,size:m?250:112}),m&&(0,p.jsx)(Hk,{levels:d,animate:_,side:`right`})]}),(0,p.jsxs)(`div`,{className:`hud-music-main`,children:[(0,p.jsxs)(`div`,{className:`hud-now`,"aria-live":`polite`,children:[(0,p.jsx)(`b`,{className:`hud-title`,children:a?h:`Nothing playing`}),(0,p.jsxs)(`small`,{className:`hud-sub`,children:[a?[a.artist,a.album].filter(Boolean).join(` — `):`Press play, or ask for some music.`,a&&Nk(a.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`SPOTIFY`}),a&&Pk(a.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`SOUNDCLOUD`}),a&&Fk(a.id)&&(0,p.jsx)(`em`,{className:`hud-source`,children:`AUDIUS`}),e.remote&&(0,p.jsx)(`em`,{className:`hud-source`,children:`THIS PC`})]})]}),(0,p.jsx)(Wk,{player:e}),(0,p.jsx)(Uk,{player:e,anim:n}),m&&(0,p.jsx)(Gk,{player:e}),s&&(0,p.jsx)(`p`,{className:`hud-notice`,role:`status`,children:s}),o&&(0,p.jsx)(`button`,{type:`button`,className:`hud-unlock`,onClick:u,children:`Tap to enable sound`})]}),m&&(0,p.jsx)(Kk,{player:e,anim:n})]})]})}var Jk=/^spotify:/,Yk=class{local;makeSpotify;active;spotify=null;listeners=new Map;wrapped=new Map;vol=1;mute=!1;pre=``;constructor(e,t){this.local=e,this.makeSpotify=t,this.active=e}get element(){return this.local}get error(){return this.active.error??null}wrap(e){let t=this.wrapped.get(e);return t||(t={local:()=>{this.active===this.local&&e()},spot:()=>{this.spotify&&this.active===this.spotify&&e()}},this.wrapped.set(e,t)),t}spot(){if(!this.spotify){let e=this.makeSpotify();e.volume=this.vol,e.muted=this.mute,e.preload=this.pre;for(let[t,n]of this.listeners)for(let r of n)e.addEventListener(t,this.wrap(r).spot);this.spotify=e}return this.spotify}dispose(){this.spotify?.dispose?.(),this.spotify=null,this.active=this.local}get src(){return this.active.src}set src(e){let t=Jk.test(e)?this.spot():this.local;t===this.active?e===``&&this.active.pause():(this.active.pause(),this.active=t),this.active.src=e}get currentTime(){return this.active.currentTime}set currentTime(e){this.active.currentTime=e}get duration(){return this.active.duration}get paused(){return this.active.paused}get volume(){return this.vol}set volume(e){this.vol=e,this.local.volume=e,this.spotify&&(this.spotify.volume=e)}get muted(){return this.mute}set muted(e){this.mute=e,this.local.muted=e,this.spotify&&(this.spotify.muted=e)}get preload(){return this.pre}set preload(e){this.pre=e,this.local.preload=e,this.spotify&&(this.spotify.preload=e)}play(){return this.active.play()}pause(){this.active.pause()}addEventListener(e,t){let n=this.listeners.get(e);n||this.listeners.set(e,n=new Set),n.add(t);let r=this.wrap(t);this.local.addEventListener(e,r.local),this.spotify?.addEventListener(e,r.spot)}removeEventListener(e,t){this.listeners.get(e)?.delete(t);let n=this.wrap(t);this.local.removeEventListener(e,n.local),this.spotify?.removeEventListener(e,n.spot)}},Xk=/^spotify:([A-Za-z0-9_-]{1,64})$/,Zk=`Spotify Premium is needed to play on this screen.`;async function Qk(){let e=await fetch(`/api/music/spotify/token`,{cache:`no-store`});if(!e.ok)throw Error(`Spotify is not connected.`);return(await e.json()).accessToken}function $k(){let e=window;return e.Spotify?Promise.resolve(e.Spotify):new Promise((t,n)=>{e.onSpotifyWebPlaybackSDKReady=()=>e.Spotify?t(e.Spotify):n(Error(`no sdk`));let r=document.createElement(`script`);r.src=`https://sdk.scdn.co/spotify-player.js`,r.async=!0,r.onerror=()=>n(Error(`blocked`)),document.head.appendChild(r)})}function eA(e){let t=e.fetch??((...e)=>fetch(...e)),n=e.now??Date.now,r=new Map,i=null,a=null,o=null,s=null,c=!1,l=null,u=null,d=0,f=0,p=0,m=!0,h=1,g=!1,_,v=e=>{for(let t of r.get(e)??[])t()},y=()=>g?0:h,b=()=>{_&&clearInterval(_),_=void 0},x=()=>{_||=setInterval(()=>v(`timeupdate`),250)},S={error:null,preload:``,get src(){return s??``},set src(e){let t=Xk.exec(e);c=e!==``&&!t,s=t?e:null,l=null,u=null,d=0,p=0,S.error=null,t||b()},get currentTime(){return m?d:d+(n()-f)/1e3},set currentTime(e){d=e,f=n(),i?.seek(Math.round(e*1e3)).catch(()=>{})},get duration(){return p},get paused(){return m},get volume(){return h},set volume(e){h=e,i?.setVolume(y()).catch(()=>{})},get muted(){return g},set muted(e){g=e,i?.setVolume(y()).catch(()=>{})},async play(){if(c||!s)throw Error(`That is not a Spotify track.`);let r=Xk.exec(s),a=s,o=await T();if(s!==a)return;if(l===s){await i?.resume().catch(()=>{}),m=!1,f=n(),x();return}let u=await e.getToken().catch(()=>null);if(!u)throw C(`Spotify is not connected. Connect it in Plugins, Spotify.`);let d;try{d=await t(`https://api.spotify.com/v1/me/player/play?device_id=${encodeURIComponent(o)}`,{method:`PUT`,headers:{authorization:`Bearer ${u}`,"content-type":`application/json`},body:JSON.stringify({uris:[`spotify:track:${r[1]}`]})})}catch{throw C(`Friend could not reach Spotify right now.`)}if(d.status===403)throw C(Zk);if(d.status===401)throw C(`Spotify sign-in has ended. Reconnect Spotify in Plugins, Spotify.`);if(d.status===404)throw C(`Spotify could not find this screen or that track.`);if(d.status===429)throw C(`Spotify is asking Friend to slow down. Try again in a minute.`);if(!d.ok)throw C(`Spotify could not play that.`);s===a&&(l=a,m=!1,f=n(),x())},pause(){m=!0,d+=(n()-f)/1e3,f=n(),b(),i?.pause().catch(()=>{})},dispose(){b();try{i?.disconnect()}catch{}i=null,a=null,s=null,l=null},addEventListener(e,t){let n=r.get(e);n||r.set(e,n=new Set),n.add(t)},removeEventListener(e,t){r.get(e)?.delete(t)}};function C(e){S.error=e,m=!0,b(),v(`error`);let t=Error(e),n=o;return o=null,n?.reject(t),t}function w(e){if(!e)return;d=e.position/1e3,f=n(),p=e.duration/1e3,m=e.paused,v(`timeupdate`),v(`loadedmetadata`),v(`durationchange`);let t=s?Xk.exec(s)?.[1]:void 0;t&&e.paused&&e.position===0&&u!==s&&(e.track_window.previous_tracks??[]).some(e=>e.id===t)&&(u=s,b(),v(`ended`))}function T(){if(a)return Promise.resolve(a);if(o)return o.promise;let t,n,r=new Promise((e,r)=>{t=e,n=r}),s={promise:r,resolve:t,reject:n};o=s;let c=setTimeout(()=>{o===s&&C(`Spotify's player did not start. Check that this browser allows Spotify's player, then try again.`)},e.readyTimeoutMs??15e3),l=()=>clearTimeout(c);return r.then(l,l),(async()=>{try{if(!i){let t;try{t=await(e.loadSdk??$k)()}catch{o===s&&C(`Spotify's player could not be loaded. Check that nothing blocks sdk.scdn.co.`);return}let n=new t.Player({name:e.deviceName??`Friend`,volume:y(),getOAuthToken:t=>{e.getToken().then(t,()=>{})}});i=n,n.addListener(`ready`,(e=>{a=e.device_id;let t=o;o=null,t?.resolve(e.device_id)})),n.addListener(`not_ready`,(()=>{a=null})),n.addListener(`player_state_changed`,(e=>w(e))),n.addListener(`account_error`,(()=>void C(Zk))),n.addListener(`authentication_error`,(()=>void C(`Spotify sign-in has ended. Reconnect Spotify in Plugins, Spotify.`))),n.addListener(`initialization_error`,(()=>void C(`Spotify's player does not work in this browser.`))),n.addListener(`playback_error`,(()=>void C(`Spotify could not play that.`)))}!await i.connect()&&o===s&&C(`Spotify's player could not connect.`)}catch{o===s&&C(`Spotify's player could not connect.`)}})(),r}return S}var tA=e=>{let t=Wl(e);return t?t.source===`local`?`/api/music/track/${t.id}`:t.source===`soundcloud`||t.source===`audius`?`/api/music/stream/${e}`:e:`/api/music/track/${e}`},nA=(e,t)=>vu(e,t),rA=`friend.music`,iA=1e3,aA=1.5,oA=()=>{try{return JSON.parse(localStorage.getItem(rA)??`{}`)}catch{return{}}},sA=e=>{try{localStorage.setItem(rA,JSON.stringify({volume:e.volume,muted:e.muted,shuffle:e.shuffle,repeat:e.repeat,view:e.view}))}catch{}};function cA({music:e,cmd:t,send:n,connection:r,createAudio:i,createSpotify:a,remote:o=!1}){let[s,c]=(0,l.useReducer)(nA,void 0,()=>{let e=oA();return mu({volume:e.volume??70,shuffle:e.shuffle??!1,repeat:e.repeat??`all`,view:e.view??`mini`})}),[u,d]=(0,l.useState)(!1),[f,p]=(0,l.useState)(null),[m,h]=(0,l.useState)(null),g=(0,l.useRef)(null),_=(0,l.useRef)(!1),v=(0,l.useRef)(s);v.current=s;let y=(0,l.useRef)(!1),b=(0,l.useRef)(null),x=(0,l.useRef)(0),S=(0,l.useRef)(!1);(0,l.useEffect)(()=>{if(!e||S.current)return;S.current=!0;let t=oA();c({type:`volume`,level:t.volume??e.volume}),c({type:`repeat`,mode:t.repeat??e.repeat}),(t.shuffle??e.shuffle)&&c({type:`shuffle`,on:!0}),c({type:`view`,view:t.view??e.startView}),t.muted&&c({type:`mute`,on:!0})},[e]);let C=()=>{if(!g.current){let e=new Yk(i?i():new Audio,a??(()=>eA({getToken:Qk})));e.preload=`auto`,g.current=e}return g.current},w=(0,l.useRef)(!1),T=(0,l.useCallback)(()=>{let e=g.current;if(e&&e.src){w.current=!0;try{let t=e.play();t&&typeof t.then==`function`?t.then(()=>{w.current=!1,d(!1)},()=>{w.current=!1;let e=g.current?.error??null;e?p(e):d(!0)}):(w.current=!1,d(!1))}catch{w.current=!1,d(!0)}E.current||O()}},[]),E=(0,l.useRef)(!1),D=(0,l.useRef)(null),O=()=>{let e=g.current,t=e instanceof Yk?e.element:e,n=typeof window<`u`?window.AudioContext??window.webkitAudioContext:void 0;if(t&&n&&typeof t.play==`function`)try{let e=new n;D.current=e;let r=e.createMediaElementSource(t),i=e.createAnalyser();i.fftSize=256,i.smoothingTimeConstant=.82,r.connect(i),i.connect(e.destination),E.current=!0,h(i)}catch{E.current=!0}};(0,l.useEffect)(()=>{if(o)return;let e=C(),t=0,n=()=>{let n=Date.now();n-t<250||(t=n,c({type:`time`,position:e.currentTime||0,duration:Number.isFinite(e.duration)?e.duration:0}))},r=()=>c({type:`time`,position:e.currentTime||0,duration:Number.isFinite(e.duration)?e.duration:0}),i=()=>c({type:`ended`}),a=()=>{let t=e.error??null;p(t),c(t?{type:`pause`}:{type:`failed`})};return e.addEventListener(`timeupdate`,n),e.addEventListener(`loadedmetadata`,r),e.addEventListener(`durationchange`,r),e.addEventListener(`ended`,i),e.addEventListener(`error`,a),()=>{e.removeEventListener(`timeupdate`,n),e.removeEventListener(`loadedmetadata`,r),e.removeEventListener(`durationchange`,r),e.removeEventListener(`ended`,i),e.removeEventListener(`error`,a),e.pause(),D.current?.close().catch(()=>{}),D.current=null,e.dispose(),b.current=null,g.current=null,E.current=!1,h(null)}},[o]),(0,l.useEffect)(()=>{o&&c({type:`stop`})},[o]);let k=s.index>=0?s.queue[s.index]??null:null;(0,l.useEffect)(()=>{let e=g.current;if(o||!e)return;let t=k?.id??null;if(t!==b.current){if(b.current=t,!t){e.pause(),e.src=``;return}p(null),e.src=tA(t),s.playing&&T()}},[k?.id,s.playing,T,o]),(0,l.useEffect)(()=>{let e=g.current;!o&&e&&e.src&&(s.playing&&e.paused&&!_.current&&!w.current?T():!s.playing&&!e.paused&&e.pause())},[s.playing,s.position,T,o]),(0,l.useEffect)(()=>{let e=g.current;e&&(e.volume=s.volume/100,e.muted=s.muted)},[s.volume,s.muted]),(0,l.useEffect)(()=>{let e=g.current;e&&e.src&&Math.abs((e.currentTime||0)-s.position)>aA&&(e.currentTime=s.position)},[s.position]),(0,l.useEffect)(()=>sA(s),[s.volume,s.muted,s.shuffle,s.repeat,s.view]),(0,l.useEffect)(()=>{if(!t||t.n===x.current)return;x.current=t.n;let e=yu(t.command);e&&c(e)},[t]),(0,l.useEffect)(()=>{let e=()=>{y.current=!0,_.current&&T()};return window.addEventListener(`pointerdown`,e,{passive:!0}),window.addEventListener(`keydown`,e),()=>{window.removeEventListener(`pointerdown`,e),window.removeEventListener(`keydown`,e)}},[T]),_.current=u;let A=(0,l.useRef)(0);return(0,l.useEffect)(()=>{if(r!==`open`||o)return;let e=()=>{let e=v.current,t=e.index>=0?e.queue[e.index]:void 0;A.current=Date.now(),n({type:`music.state`,state:{playing:e.playing,trackId:t?.id??null,title:t?.title??``,artist:t?.artist??``,album:t?.album??``,position:e.position,duration:e.duration,volume:e.volume,muted:e.muted,shuffle:e.shuffle,repeat:e.repeat,view:e.view,queue:e.queue.slice(0,50).map(e=>({id:e.id,title:e.title.slice(0,200)})),index:e.index,active:(typeof document>`u`||document.visibilityState===`visible`)&&y.current}})};e();let t=setInterval(()=>s.playing&&Date.now()-A.current>=iA&&e(),iA);return()=>clearInterval(t)},[r,o,k?.id,s.playing,s.volume,s.muted,s.shuffle,s.repeat,s.view,s.queue.length,s.index]),(0,l.useEffect)(()=>{let e=typeof navigator<`u`?navigator.mediaSession:void 0;if(e&&!o)try{k&&typeof MediaMetadata<`u`&&(e.metadata=new MediaMetadata({title:k.title,artist:k.artist,album:k.album,artwork:[{src:`/api/music/cover/${k.id}`}]})),e.playbackState=s.playing?`playing`:k?`paused`:`none`,e.setActionHandler(`play`,()=>c({type:`resume`})),e.setActionHandler(`pause`,()=>c({type:`pause`})),e.setActionHandler(`previoustrack`,()=>c({type:`previous`})),e.setActionHandler(`nexttrack`,()=>c({type:`next`})),e.setActionHandler(`seekto`,e=>typeof e.seekTime==`number`&&c({type:`seek`,seconds:e.seekTime}))}catch{}},[k?.id,s.playing,o]),{remote:!1,state:s,dispatch:c,current:k,blocked:u,notice:f,analyser:m,unlock:T,audio:g}}function lA(e,t){if(!e)return{state:{queue:[],index:-1,playing:!1,position:0,duration:0,volume:70,muted:!1,shuffle:!1,repeat:`all`,view:t},current:null};let n=e.queue.map((t,n)=>n===e.index?{id:t.id,title:e.title||t.title,artist:e.artist,album:e.album,durationSec:e.duration>0?e.duration:null}:{id:t.id,title:t.title,artist:``,album:``,durationSec:null});return{state:{queue:n,index:e.index,playing:e.playing,position:e.position,duration:e.duration,volume:e.volume,muted:e.muted,shuffle:e.shuffle,repeat:e.repeat,view:t},current:e.index>=0?n[e.index]??null:null}}function uA({local:e,host:t,send:n}){let r=e.state.view,{state:i,current:a}=(0,l.useMemo)(()=>lA(t,r),[t,r]),o=e.dispatch,s=(0,l.useCallback)(e=>{if(e.type===`view`)return o(e);let t=bu(e);t&&n({type:`music.remote`,command:t})},[o,n]);return(0,l.useMemo)(()=>({...e,remote:!0,state:i,dispatch:s,current:a,blocked:!1,notice:null,analyser:null,unlock:()=>{}}),[e,i,s,a])}function dA(e){let t=new URLSearchParams(e).get(`music`);return t===`connected`?{level:`info`,text:`Spotify is connected. Ask Friend to play something.`}:t===`failed`?{level:`warn`,text:`Spotify did not connect. Open Plugins, Spotify and press Connect again.`}:null}function fA({onSignedOut:e}){let{state:t,send:n,dispatch:r,voice:i,useHere:a}=IO(e);JO(i),YO(i),tk(n,t.connection);let[o,s]=(0,l.useState)(!1),[c,u]=(0,l.useState)(!1),[d,f]=(0,l.useState)(!1),[m,h]=(0,l.useState)(!1),[g,_]=(0,l.useState)(void 0),[v,y]=(0,l.useState)(null),[b,x]=(0,l.useState)(!1),[S,C]=(0,l.useState)(0),[w,T]=(0,l.useState)(null),E=de(t.view),D=t.music?.output===`host`,O=cA({music:t.music,cmd:t.musicCmd,send:n,connection:t.connection,remote:D}),k=uA({local:O,host:t.hostMusic,send:n}),j=D?k:O,ee=t.hud?.animations??`full`,M=e=>{let{type:i,value:a}=e.action;if(i===`url`)window.open(a,`_blank`,`noopener,noreferrer`);else if(i===`prompt`)n({type:`chat.send`,text:a});else if(i===`music`||i===`panel`&&a===`music`){if(!t.music?.folderSet){r({type:`alert.add`,level:`info`,text:`No music folder is chosen yet. Pick one in Settings, Widgets, and the player opens.`}),y(`widgets`);return}if(i===`panel`){E.toggle(`music`,!0),j.state.view===`hidden`&&j.dispatch({type:`view`,view:`mini`});return}let e=yu({action:a});e&&j.dispatch(e)}else a===`plugins`?h(!0):a===`settings`?y(`model`):(a===`chat`||a===`tasks`)&&E.toggle(a,!0)},N=(0,l.useMemo)(()=>o?{...t,objects:[],captions:``}:t,[o,t]),P=(0,l.useRef)(!1);(0,l.useEffect)(()=>{P.current||!t.voice.available||t.voice.enrolled||(P.current=!0,r({type:`alert.add`,level:`info`,text:`Voice recognition is not set up. Press Esc, then Enroll my voice.`}))},[t.voice.available,t.voice.enrolled,r]);let te=ne(),L=(0,l.useRef)(!1);(0,l.useEffect)(()=>{if(!te||L.current||t.connection!==`open`)return;L.current=!0;let e=!1;try{e=localStorage.getItem(`friend.touchHint`)===`1`,localStorage.setItem(`friend.touchHint`,`1`)}catch{}e||r({type:`alert.add`,level:`info`,text:`Hold the round mic button to talk, or tap it once to start and again to send. The keyboard button types; the menu button opens settings.`})},[te,t.connection,r]);let re=t.uiOpen?.n??0,ie=t.uiOpen?.integration;(0,l.useEffect)(()=>{re!==0&&(_(ie),h(!0))},[re,ie]);let ae=(0,l.useRef)(!1);(0,l.useEffect)(()=>{if(ae.current)return;ae.current=!0;let e=dA(window.location.search);e&&(r({type:`alert.add`,level:e.level,text:e.text}),window.history.replaceState(null,``,window.location.pathname))},[r]);let oe=(0,l.useRef)(!1);(0,l.useEffect)(()=>{oe.current||t.connection!==`open`||(oe.current=!0,fetch(`/api/history`).then(e=>e.ok?e.json():[]).then(e=>r({type:`chat.seed`,lines:e})).catch(()=>{}))},[t.connection,r]),(0,l.useEffect)(()=>{t.connection===`open`&&n({type:`ui.panels`,open:[...E.show.chat?[`chat`]:[],...E.show.tasks?[`tasks`]:[]]})},[t.connection,E.show.chat,E.show.tasks,n]);let se=(0,l.useRef)(!1);(0,l.useEffect)(()=>{t.viewKnown&&t.view===`minimal`&&!se.current&&(se.current=!0,r({type:`alert.add`,level:`info`,text:`The view is Minimal, so the status line and clock are hidden. Press Esc, then View, to bring them back.`}))},[t.viewKnown,t.view,r]);let ce=e=>{ze.save({view:e}).catch(e=>r({type:`alert.add`,level:`warn`,text:e.message}))},le=(0,l.useMemo)(()=>F({notify:e=>r({type:`alert.add`,level:`info`,text:e}),openSettings:()=>y(`model`),openLook:()=>y(`look`),openConnectors:()=>x(!0),openPlugins:()=>h(!0),openVoice:t.voice.available?()=>u(!0):null,muted:o,setMuted:s,cameraOn:t.camera.enabled,setCamera:e=>r({type:`camera.enable`,value:e}),clearScreen:()=>{for(let e of t.objects)n({type:`stage.event`,objectId:e.id,event:`dismiss`})},statusLine:()=>Ee({connection:t.connection,deviceOnline:t.deviceOnline,approval:t.approval,voiceMode:t.voice.mode,busy:t.busy,activity:t.activity}).text,endSession:t=>{fetch(t===`lock`?`/api/lock`:`/api/logout`,{method:`POST`,headers:{"content-type":`application/json`},body:`{}`}).catch(()=>{}).finally(e)},panelOn:e=>E.show[e],setPanel:(e,t)=>E.toggle(e,t),view:t.view,setView:ce,openHelp:T,resetLayout:()=>{ue(),window.location.reload()}}),[r,n,o,e,E.show,E.toggle,t.view,t.voice.available,t.voice.mode,t.camera.enabled,t.objects,t.connection,t.deviceOnline,t.approval,t.busy,t.activity]);return(0,p.jsxs)(p.Fragment,{children:[(0,p.jsx)(bE,{state:N,send:n,dispatch:r,voice:i,slash:le,onMenu:()=>C(e=>e+1)}),(0,p.jsxs)(ke,{approval:t.approval,challenge:t.challenge,cameraStream:t.camera.stream,alerts:t.alerts,connection:t.connection,deviceOnline:t.deviceOnline,voiceMode:t.voice.mode,busy:t.busy,activity:t.activity,showStatus:t.viewKnown&&E.show.status,showClock:t.viewKnown&&E.show.clock,profile:t.viewKnown&&E.show.profile?{ownerName:t.ownerName,speaker:t.speaker}:null,assistantName:t.assistantName,hud:t.hud,send:n,dispatch:r,children:[t.viewKnown&&E.show.chat&&(0,p.jsx)(fe,{lines:t.chat,live:t.chatLive,onSend:e=>n({type:`chat.send`,text:e}),onClose:()=>E.toggle(`chat`,!1)}),t.viewKnown&&E.show.tasks&&(0,p.jsx)(he,{busy:t.busy,onClose:()=>E.toggle(`tasks`,!1)}),t.viewKnown&&E.show.launcher&&t.hud&&(0,p.jsx)(fk,{items:t.hud.launcher,animations:ee,onAction:M}),t.viewKnown&&E.show.music&&(0,p.jsx)(qk,{player:j,music:t.music,animations:ee}),c&&(0,p.jsx)(UO,{onClose:()=>u(!1)}),d&&(0,p.jsx)(ok,{onClose:()=>f(!1)}),m&&(0,p.jsx)(bd,{...g?{initialConfigure:g}:{},onClose:()=>{h(!1),_(void 0)}}),v&&(0,p.jsx)(gx,{initialTab:v,onClose:()=>y(null)}),b&&(0,p.jsx)(A,{onClose:()=>x(!1)}),w&&(0,p.jsx)(I,{commands:w,onClose:()=>T(null)})]}),(0,p.jsx)(V,{muted:o,onToggleMute:()=>s(e=>!e),onSignedOut:e,voiceAvailable:t.voice.available,voiceEnrolled:t.voice.enrolled,onEnroll:()=>u(!0),onHousehold:()=>f(!0),onPlugins:()=>h(!0),onSettings:()=>y(`model`),onConnectors:()=>x(!0),cameraOn:t.camera.enabled,onToggleCamera:()=>r({type:`camera.enable`,value:!t.camera.enabled}),chatOn:E.show.chat,onToggleChat:()=>E.toggle(`chat`),tasksOn:E.show.tasks,onToggleTasks:()=>E.toggle(`tasks`),musicOn:E.show.music,onToggleMusic:()=>E.toggle(`music`),launcherOn:E.show.launcher,onToggleLauncher:()=>E.toggle(`launcher`),view:t.view,onView:ce,openRequest:S}),t.connection===`elsewhere`&&(0,p.jsx)(XO,{onUseHere:a})]})}function pA(){let[e,t]=(0,l.useState)(`loading`);return(0,l.useEffect)(()=>{let e=!0,n=n=>e&&t(n);return(async()=>{try{if(!(await(await fetch(`/api/state`)).json()).hasOwner)return n(`setup`);let e=await(await fetch(`/api/session`,{cache:`no-store`})).json();n(e.signedIn===!0?`stage`:`login`)}catch{n(`login`)}})(),()=>{e=!1}},[]),e===`loading`?(0,p.jsx)(`div`,{className:`boot`,"aria-busy":`true`}):e===`setup`?(0,p.jsx)(g,{onDone:()=>t(`login`)}):e===`login`?(0,p.jsx)(h,{onLoggedIn:()=>t(`stage`)}):(0,p.jsx)(fA,{onSignedOut:()=>t(`login`)})}(0,u.createRoot)(document.getElementById(`root`)).render((0,p.jsx)(l.StrictMode,{children:(0,p.jsx)(pA,{})}));
@@ -8,8 +8,8 @@
8
8
  <meta name="apple-mobile-web-app-capable" content="yes" />
9
9
  <meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
10
10
  <title>Friend</title>
11
- <script type="module" crossorigin src="/assets/index-Cg-1ZV_2.js"></script>
12
- <link rel="stylesheet" crossorigin href="/assets/index-qwk36PfU.css">
11
+ <script type="module" crossorigin src="/assets/index-mPlDREuW.js"></script>
12
+ <link rel="stylesheet" crossorigin href="/assets/index-CRWuir4x.css">
13
13
  </head>
14
14
  <body>
15
15
  <div id="root"></div>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "friend-assistant",
3
- "version": "0.1.39",
3
+ "version": "0.1.40",
4
4
  "description": "A self-hosted personal AI assistant for your own PC: a full-screen stage, voice, tools with your approval, and your Claude subscription or a local model.",
5
5
  "keywords": ["ai", "assistant", "jarvis", "voice", "claude", "ollama", "mcp", "self-hosted"],
6
6
  "license": "UNLICENSED",