Back to Nostr Pet
SOURCE / PINNED RELEASE

Made of little things.

Nostr Pet

Release
6bb26cd5d23d…
Author-recorded commit
Not provided
License
Check the original source

The hash-verified playable HTML, which may contain bundled or minified code. This view does not execute it.

index.html
<!doctype html>
<html lang="en">
  <head><meta name="description" content="A portable Nostr activity pet tied to signed Nostr posts.">
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="color-scheme" content="light dark" />
    <title>Nostr Pet</title>
    <script type="module" crossorigin>var gr=Object.defineProperty;var br=(t,e,n)=>e in t?gr(t,e,{enumerable:!0,configurable:!0,writable:!0,value:n}):t[e]=n;var u=(t,e,n)=>br(t,typeof e!="symbol"?e+"":e,n);function wr(){const t=new Map;function e(r,i){if(t.has(r))throw new Error(`NAP domain "${r}" is already registered`);t.set(r,i)}function n(r){const i=r.type.indexOf(".");if(i<=0)return!1;const s=r.type.slice(0,i),a=t.get(s);return a?(a(r),!0):!1}function o(){return Array.from(t.keys())}return{registerNap:e,dispatch:n,getRegisteredDomains:o}}var vr=wr(),Er=vr.registerNap,kr="theme";function po(){var e;const t=window;if(!((e=t.napplet)!=null&&e.theme))throw new Error("window.napplet.theme is unavailable -- runtime did not inject this domain");return t.napplet.theme}function xr(){return po().get()}function $r(t){return po().onChanged(t)}Er(kr,t=>{});function Ir(){const t=window;if(!t.napplet)throw new Error("window.napplet is unavailable -- runtime did not inject the napplet namespace");return t.napplet}function g(t){const n=Ir()[t];if(!n)throw new Error(`window.napplet.${String(t)} is unavailable -- runtime did not inject this domain`);return n}var yo={subscribe(t,e,n,o){return g("relay").subscribe(t,e,n,o)},publish(t,e){return g("relay").publish(t,e)},publishEncrypted(t,e,n="nip44"){return g("relay").publishEncrypted(t,e,n)},query(t){return g("relay").query(t)}},Fe={getItem(t){return g("storage").getItem(t)},setItem(t,e){return g("storage").setItem(t,e)},removeItem(t){return g("storage").removeItem(t)},keys(){return g("storage").keys()},instance:{getItem(t){return g("storage").instance.getItem(t)},setItem(t,e){return g("storage").instance.setItem(t,e)},removeItem(t){return g("storage").instance.removeItem(t)},keys(){return g("storage").instance.keys()}}},Ar={registerAction(t){return g("keys").registerAction(t)},unregisterAction(t){g("keys").unregisterAction(t)},onAction(t,e){return g("keys").onAction(t,e)},async register(t,e){const n=g("keys"),o=await n.registerAction(t),r=n.onAction(t.id,e);return{...o,close(){r.close(),n.unregisterAction(t.id)}}}},Je={getPublicKey(){return g("identity").getPublicKey()},onChanged(t){return g("identity").onChanged(t)},getRelays(){return g("identity").getRelays()},getProfile(){return g("identity").getProfile()},getFollows(){return g("identity").getFollows()},getList(t){return g("identity").getList(t)},getZaps(){return g("identity").getZaps()},getMutes(){return g("identity").getMutes()},getBlocked(){return g("identity").getBlocked()},getBadges(){return g("identity").getBadges()}},Rr={get(){return g("config").get()},subscribe(t){return g("config").subscribe(t)},openSettings(t){g("config").openSettings(t)},registerSchema(t,e){return g("config").registerSchema(t,e)},onSchemaError(t){return g("config").onSchemaError(t)},get schema(){return g("config").schema}},Sr={info(){return g("resource").info()},bytes(t,e){return g("resource").bytes(t,e)},bytesMany(t,e){return g("resource").bytesMany(t,e)},bytesAsObjectURL(t){return g("resource").bytesAsObjectURL(t)}},It={getEvent(t,e){return g("outbox").getEvent(t,e)},query(t,e){return g("outbox").query(t,e)},subscribe(t,e){return g("outbox").subscribe(t,e)},publish(t,e){return g("outbox").publish(t,e)},resolveRelays(t){return g("outbox").resolveRelays(t)}},Mr={open(t,e){return g("link").open(t,e)}},Or={encodeNip19(t){return g("common").encodeNip19(t)},decodeNip19(t){return g("common").decodeNip19(t)},getProfile(t){return g("common").getProfile(t)},follows(){return g("common").follows()},follow(...t){return g("common").follow(...t)},unfollow(...t){return g("common").unfollow(...t)},react(t,e,n){return g("common").react(t,e,n)},report(t,e,n){return g("common").report(t,e,n)}};/*! noble-hashes - MIT License (c) 2022 Paul Miller (paulmillr.com) */function Pr(t){return t instanceof Uint8Array||ArrayBuffer.isView(t)&&t.constructor.name==="Uint8Array"}function bn(t,e=""){if(!Number.isSafeInteger(t)||t<0){const n=e&&`"${e}" `;throw new Error(`${n}expected integer >= 0, got ${t}`)}}function Q(t,e,n=""){const o=Pr(t),r=t==null?void 0:t.length,i=e!==void 0;if(!o||i&&r!==e){const s=n&&`"${n}" `,a=i?` of length ${e}`:"",l=o?`length=${r}`:`type=${typeof t}`;throw new Error(s+"expected Uint8Array"+a+", got "+l)}return t}function _n(t,e=!0){if(t.destroyed)throw new Error("Hash instance has been destroyed");if(e&&t.finished)throw new Error("Hash#digest() has already been called")}function Cr(t,e){Q(t,void 0,"digestInto() output");const n=e.outputLen;if(t.length<n)throw new Error('"digestInto() output" expected to be of length >='+n)}function nn(...t){for(let e=0;e<t.length;e++)t[e].fill(0)}function Kt(t){return new DataView(t.buffer,t.byteOffset,t.byteLength)}function he(t,e){return t<<32-e|t>>>e}const mo=typeof Uint8Array.from([]).toHex=="function"&&typeof Uint8Array.fromHex=="function",Tr=Array.from({length:256},(t,e)=>e.toString(16).padStart(2,"0"));function X(t){if(Q(t),mo)return t.toHex();let e="";for(let n=0;n<t.length;n++)e+=Tr[t[n]];return e}const ye={_0:48,_9:57,A:65,F:70,a:97,f:102};function qn(t){if(t>=ye._0&&t<=ye._9)return t-ye._0;if(t>=ye.A&&t<=ye.F)return t-(ye.A-10);if(t>=ye.a&&t<=ye.f)return t-(ye.a-10)}function _e(t){if(typeof t!="string")throw new Error("hex string expected, got "+typeof t);if(mo)return Uint8Array.fromHex(t);const e=t.length,n=e/2;if(e%2)throw new Error("hex string expected, got unpadded hex of length "+e);const o=new Uint8Array(n);for(let r=0,i=0;r<n;r++,i+=2){const s=qn(t.charCodeAt(i)),a=qn(t.charCodeAt(i+1));if(s===void 0||a===void 0){const l=t[i]+t[i+1];throw new Error('hex string expected, got non-hex character "'+l+'" at index '+i)}o[r]=s*16+a}return o}function Lt(...t){let e=0;for(let o=0;o<t.length;o++){const r=t[o];Q(r),e+=r.length}const n=new Uint8Array(e);for(let o=0,r=0;o<t.length;o++){const i=t[o];n.set(i,r),r+=i.length}return n}function Br(t,e={}){const n=(r,i)=>t(i).update(r).digest(),o=t(void 0);return n.outputLen=o.outputLen,n.blockLen=o.blockLen,n.create=r=>t(r),Object.assign(n,e),Object.freeze(n)}function go(t=32){const e=typeof globalThis=="object"?globalThis.crypto:null;if(typeof(e==null?void 0:e.getRandomValues)!="function")throw new Error("crypto.getRandomValues must be defined");return e.getRandomValues(new Uint8Array(t))}const Nr=t=>({oid:Uint8Array.from([6,9,96,134,72,1,101,3,4,2,t])});/*! scure-base - MIT License (c) 2022 Paul Miller (paulmillr.com) */function bo(t){return t instanceof Uint8Array||ArrayBuffer.isView(t)&&t.constructor.name==="Uint8Array"}function wo(t,e){return Array.isArray(e)?e.length===0?!0:t?e.every(n=>typeof n=="string"):e.every(n=>Number.isSafeInteger(n)):!1}function Lr(t){if(typeof t!="function")throw new Error("function expected");return!0}function Et(t,e){if(typeof e!="string")throw new Error(`${t}: string expected`);return!0}function vo(t){if(!Number.isSafeInteger(t))throw new Error(`invalid integer: ${t}`)}function on(t){if(!Array.isArray(t))throw new Error("array expected")}function Eo(t,e){if(!wo(!0,e))throw new Error(`${t}: array of strings expected`)}function ko(t,e){if(!wo(!1,e))throw new Error(`${t}: array of numbers expected`)}function _r(...t){const e=i=>i,n=(i,s)=>a=>i(s(a)),o=t.map(i=>i.encode).reduceRight(n,e),r=t.map(i=>i.decode).reduce(n,e);return{encode:o,decode:r}}function qr(t){const e=typeof t=="string"?t.split(""):t,n=e.length;Eo("alphabet",e);const o=new Map(e.map((r,i)=>[r,i]));return{encode:r=>(on(r),r.map(i=>{if(!Number.isSafeInteger(i)||i<0||i>=n)throw new Error(`alphabet.encode: digit index outside alphabet "${i}". Allowed: ${t}`);return e[i]})),decode:r=>(on(r),r.map(i=>{Et("alphabet.decode",i);const s=o.get(i);if(s===void 0)throw new Error(`Unknown letter: "${i}". Allowed: ${t}`);return s}))}}function Hr(t=""){return Et("join",t),{encode:e=>(Eo("join.decode",e),e.join(t)),decode:e=>(Et("join.decode",e),e.split(t))}}const xo=(t,e)=>e===0?t:xo(e,t%e),_t=(t,e)=>t+(e-xo(t,e)),Mt=(()=>{let t=[];for(let e=0;e<40;e++)t.push(2**e);return t})();function rn(t,e,n,o){if(on(t),e<=0||e>32)throw new Error(`convertRadix2: wrong from=${e}`);if(n<=0||n>32)throw new Error(`convertRadix2: wrong to=${n}`);if(_t(e,n)>32)throw new Error(`convertRadix2: carry overflow from=${e} to=${n} carryBits=${_t(e,n)}`);let r=0,i=0;const s=Mt[e],a=Mt[n]-1,l=[];for(const d of t){if(vo(d),d>=s)throw new Error(`convertRadix2: invalid data word=${d} from=${e}`);if(r=r<<e|d,i+e>32)throw new Error(`convertRadix2: carry overflow pos=${i} from=${e}`);for(i+=e;i>=n;i-=n)l.push((r>>i-n&a)>>>0);const f=Mt[i];if(f===void 0)throw new Error("invalid carry");r&=f-1}if(r=r<<n-i&a,!o&&i>=e)throw new Error("Excess padding");if(!o&&r>0)throw new Error(`Non-zero padding: ${r}`);return o&&i>0&&l.push(r>>>0),l}function Dr(t,e=!1){if(vo(t),t<=0||t>32)throw new Error("radix2: bits should be in (0..32]");if(_t(8,t)>32||_t(t,8)>32)throw new Error("radix2: carry overflow");return{encode:n=>{if(!bo(n))throw new Error("radix2.encode input should be Uint8Array");return rn(Array.from(n),8,t,!e)},decode:n=>(ko("radix2.decode",n),Uint8Array.from(rn(n,t,8,e)))}}function Hn(t){return Lr(t),function(...e){try{return t.apply(null,e)}catch{}}}const sn=_r(qr("qpzry9x8gf2tvdw0s3jn54khce6mua7l"),Hr("")),Dn=[996825010,642813549,513874426,1027748829,705979059];function ct(t){const e=t>>25;let n=(t&33554431)<<5;for(let o=0;o<Dn.length;o++)(e>>o&1)===1&&(n^=Dn[o]);return n}function Fn(t,e,n=1){const o=t.length;let r=1;for(let i=0;i<o;i++){const s=t.charCodeAt(i);if(s<33||s>126)throw new Error(`Invalid prefix (${t})`);r=ct(r)^s>>5}r=ct(r);for(let i=0;i<o;i++)r=ct(r)^t.charCodeAt(i)&31;for(let i of e)r=ct(r)^i;for(let i=0;i<6;i++)r=ct(r);return r^=n,sn.encode(rn([r%Mt[30]],30,5,!1))}function Fr(t){const e=t==="bech32"?1:734539939,n=Dr(5),o=n.decode,r=n.encode,i=Hn(o);function s(c,y,b=90){Et("bech32.encode prefix",c),bo(y)&&(y=Array.from(y)),ko("bech32.encode",y);const R=c.length;if(R===0)throw new TypeError(`Invalid prefix length ${R}`);const O=R+7+y.length;if(b!==!1&&O>b)throw new TypeError(`Length ${O} exceeds limit ${b}`);const D=c.toLowerCase(),K=Fn(D,y,e);return`${D}1${sn.encode(y)}${K}`}function a(c,y=90){Et("bech32.decode input",c);const b=c.length;if(b<8||y!==!1&&b>y)throw new TypeError(`invalid string length: ${b} (${c}). Expected (8..${y})`);const R=c.toLowerCase();if(c!==R&&c!==c.toUpperCase())throw new Error("String must be lowercase or uppercase");const O=R.lastIndexOf("1");if(O===0||O===-1)throw new Error('Letter "1" must be present between prefix and data only');const D=R.slice(0,O),K=R.slice(O+1);if(K.length<6)throw new Error("Data must be at least 6 characters long");const $e=sn.decode(K).slice(0,-6),de=Fn(D,$e,e);if(!K.endsWith(de))throw new Error(`Invalid checksum in ${c}: expected "${de}"`);return{prefix:D,words:$e}}const l=Hn(a);function d(c){const{prefix:y,words:b}=a(c,!1);return{prefix:y,words:b,bytes:o(b)}}function f(c,y){return s(c,r(y))}return{encode:s,decode:a,encodeFromBytes:f,decodeToBytes:d,decodeUnsafe:l,fromWords:o,fromWordsUnsafe:i,toWords:r}}const qt=Fr("bech32");var Rt=new TextDecoder("utf-8");new TextEncoder;var $o=5e3;function Ur(t){var r,i,s,a,l,d,f;let{prefix:e,words:n}=qt.decode(t,$o),o=new Uint8Array(qt.fromWords(n));switch(e){case"nprofile":{let c=Xt(o);if(!((r=c[0])!=null&&r[0]))throw new Error("missing TLV 0 for nprofile");if(c[0][0].length!==32)throw new Error("TLV 0 should be 32 bytes");return{type:"nprofile",data:{pubkey:X(c[0][0]),relays:c[1]?c[1].map(y=>Rt.decode(y)):[]}}}case"nevent":{let c=Xt(o);if(!((i=c[0])!=null&&i[0]))throw new Error("missing TLV 0 for nevent");if(c[0][0].length!==32)throw new Error("TLV 0 should be 32 bytes");if(c[2]&&c[2][0].length!==32)throw new Error("TLV 2 should be 32 bytes");if(c[3]&&c[3][0].length!==4)throw new Error("TLV 3 should be 4 bytes");return{type:"nevent",data:{id:X(c[0][0]),relays:c[1]?c[1].map(y=>Rt.decode(y)):[],author:(s=c[2])!=null&&s[0]?X(c[2][0]):void 0,kind:(a=c[3])!=null&&a[0]?parseInt(X(c[3][0]),16):void 0}}}case"naddr":{let c=Xt(o);if(!((l=c[0])!=null&&l[0]))throw new Error("missing TLV 0 for naddr");if(!((d=c[2])!=null&&d[0]))throw new Error("missing TLV 2 for naddr");if(c[2][0].length!==32)throw new Error("TLV 2 should be 32 bytes");if(!((f=c[3])!=null&&f[0]))throw new Error("missing TLV 3 for naddr");if(c[3][0].length!==4)throw new Error("TLV 3 should be 4 bytes");return{type:"naddr",data:{identifier:Rt.decode(c[0][0]),pubkey:X(c[2][0]),kind:parseInt(X(c[3][0]),16),relays:c[1]?c[1].map(y=>Rt.decode(y)):[]}}}case"nsec":return{type:e,data:o};case"npub":case"note":return{type:e,data:X(o)};default:throw new Error(`unknown prefix ${e}`)}}function Xt(t){let e={},n=t;for(;n.length>0;){let o=n[0],r=n[1],i=n.slice(2,2+r);if(n=n.slice(2+r),i.length<r)throw new Error(`not enough data to read on TLV ${o}`);e[o]=e[o]||[],e[o].push(i)}return e}function zr(t){return Vr("npub",_e(t))}function Yr(t,e){let n=qt.toWords(e);return qt.encode(t,n,$o)}function Vr(t,e){return Yr(t,e)}function jr(t){return t.tags.some(e=>e[0]==="e")}function Un(t,e=86400){return t<3*e?"happy":t<7*e?"content":t<14*e?"lonely":t<30*e?"sick":t<45*e?"critical":"dead"}function Zr(t){const e=t.daySeconds;let n=t.birthCreatedAt;const o=t.notes.filter(s=>s.pubkey===t.ownerPubkey&&s.created_at>=t.birthCreatedAt&&s.created_at<=t.at).sort((s,a)=>s.created_at-a.created_at||s.id.localeCompare(a.id));for(const s of o){const a=Un(Math.max(0,s.created_at-n),e);if(a==="dead")break;(t.verifiedMedicineIds.has(s.id)||!jr(s)&&a!=="sick"&&a!=="critical")&&(n=s.created_at)}const r=Math.max(0,t.at-n),i=Un(r,e);return{state:i,lastCareAt:n,daysQuiet:Math.floor(r/e),canFeed:i==="happy"||i==="content"||i==="lonely"}}function Io(t,e){var o;if(!t.ok)throw new Error(((o=t.error)==null?void 0:o.trim())||"No relay accepted the event.");const n=t.event;if(!n)throw new Error("The signer did not return a signed event.");if(n.pubkey!==e.ownerPubkey)throw new Error("The signer returned an event for a different account.");if(n.kind!==e.kind)throw new Error("The signer returned a different event kind.");if(!/^[0-9a-f]{64}$/i.test(n.id)||!/^[0-9a-f]{128}$/i.test(n.sig)||t.eventId&&t.eventId!==n.id)throw new Error("The signer returned an invalid signed event.");return n}function wn(t,e){const n=new Map(t.map(o=>[o.id,o]));for(const o of e)n.set(o.id,o);return[...n.values()].sort((o,r)=>r.created_at-o.created_at||o.id.localeCompare(r.id))}function Gr(t){return Object.values(t.relays??{}).filter(Boolean).length}function Kr(t,e){return e??t}function Xr(t){var e;return!!(!t.ok&&((e=t.error)!=null&&e.trim().toLowerCase().includes("relay list unavailable")))}async function Wr(t,e,n={},o=[]){const r=await t(e,n);if(!Xr(r)||o.length===0)return r;const{toInboxes:i,...s}=n;return t(e,{...s,relays:o,toOutbox:!1})}const Jr="ws://127.0.0.1:7777";function Qr(t){if(typeof t!="string")return"";try{const e=new URL(t);return(e.hostname==="127.0.0.1"||e.hostname==="localhost"||e.hostname==="[::1]")&&(e.protocol==="ws:"||e.protocol==="wss:")?e.origin:""}catch{return""}}function Ht(t){return[...new Set(t.filter(Boolean))]}function ei(t,e,n){var r;return t.localRelayOnly?[t.localRelayUrl]:t.localRelayMirror?(e==null?void 0:e.source)==="nip65"&&(((r=e.missingAuthors)==null?void 0:r.length)??0)===0?[t.localRelayUrl]:Ht([t.localRelayUrl,...(e==null?void 0:e.relays)??[],...n]):[]}function ti(t,e){return t.localRelayMirror?{...e,relays:Ht([...e.relays??[],t.localRelayUrl])}:e}function Ot(t){const e=t.nostrPetLocalRelayOnly===!0,n=t.nostrPetLocalRelayMirror===!0;if(!e&&!n)return{localRelayOnly:!1,localRelayMirror:!1,localRelayUrl:""};const o=Qr(t.nostrPetLocalRelayUrl??Jr);return o?e?{localRelayOnly:!0,localRelayMirror:!1,localRelayUrl:o}:{localRelayOnly:!1,localRelayMirror:!0,localRelayUrl:o}:{localRelayOnly:!1,localRelayMirror:!1,localRelayUrl:""}}async function ni(t,e,n,o,r){return t.localRelayOnly?{events:await e(o)}:n(o,ti(t,r??{}))}async function oi(t,e,n,o={},r=[],i){if(t.localRelayOnly)return e(n,{relays:[t.localRelayUrl],toOutbox:!1});const s=t.localRelayMirror?{...o,relays:Ht([t.localRelayUrl,...o.relays??[]])}:o,a=t.localRelayMirror?Ht([t.localRelayUrl,...r]):r;if(t.localRelayMirror&&i===!1){const{toInboxes:l,...d}=o;return e(n,{...d,relays:a,toOutbox:!1})}return Wr(e,n,s,a)}function ri(t,e){var s;const n=t.tags.filter(a=>a[0]==="e"&&a[1]),r=n.find(a=>a[3]==="reply")??n.at(-1),i=(s=t.tags.find(a=>a[0]==="p"&&a[1]&&a[1]!==e))==null?void 0:s[1];return!(r!=null&&r[1])||!i?null:{id:r[1],pubkey:i,relay:r[2]??""}}function ii(t,e,n=40){const o=t.filter(l=>l.pubkey===e&&l.tags.some(d=>d[0]==="e")).sort((l,d)=>d.created_at-l.created_at).slice(0,Math.max(0,n)),r=new Map;for(const l of o){const d=ri(l,e);if(!d)continue;const f=`${d.id}:${d.pubkey}`,c=r.get(f);if(c){c.replyIds.push(l.id),!c.relay&&d.relay&&(c.relay=d.relay);continue}r.set(f,{...d,replyIds:[l.id]})}const i=[...r.values()],s=[...new Set(i.map(l=>l.pubkey))],a=[...new Set(i.map(l=>l.relay).filter(Boolean))];return{targets:i,authors:s,relays:a,filters:i.length?[{ids:[...new Set(i.map(l=>l.id))],authors:s,kinds:[1],limit:i.length}]:[]}}function si(t,e,n){const o=new Set(e.filter(i=>i.kind===1&&i.pubkey!==n&&t.targets.some(s=>s.id===i.id&&s.pubkey===i.pubkey)).map(i=>`${i.id}:${i.pubkey}`)),r=new Set;for(const i of t.targets)if(o.has(`${i.id}:${i.pubkey}`))for(const s of i.replyIds)r.add(s);return r}const we=14;function Wt(t,e){return typeof t=="number"&&Number.isFinite(t)&&t<=e?t:0}function ai(t){const e=t.daySeconds,n=we*e,o=Math.max(Wt(t.birthCreatedAt,t.at),Wt(t.lastHabitatChangeAt,t.at),Wt(t.lastMedicineAt,t.at)),r=Math.max(0,t.at-o),i=t.incomplete?Math.floor(r/e):0;return{sick:t.incomplete&&r>=n,riskSince:o,daysIncomplete:i,daysUntilSick:t.incomplete?Math.max(0,we-i):we}}function li(t,e){return e&&(t==="happy"||t==="content"||t==="lonely")?"sick":t}function ci(t){const e=t.trim().toLowerCase();if(!e.startsWith("npub1"))throw new Error("Enter a public npub beginning with npub1.");try{const n=Ur(e);if(n.type==="npub"&&typeof n.data=="string"&&/^[0-9a-f]{64}$/.test(n.data))return n.data}catch{}throw new Error("That npub is not valid. Check it and try again.")}function di(t,e){return!!(t&&t!==e)}const dt=["happy","content","lonely","sick","critical"],ui={bodyY:0,bodyRotation:0,bodyScaleX:1,bodyScaleY:1,headTilt:0,eyeOpen:1,eyeSmile:0,browTilt:0,mouthOpen:0,mouthCurve:.2,earDroop:0,cheekIntensity:1,saturation:1,opacity:1},fi={happy:{bodyY:-2,eyeSmile:.8,mouthCurve:1,cheekIntensity:1},content:{eyeOpen:.9,eyeSmile:.25,mouthCurve:.35,cheekIntensity:.8},lonely:{bodyY:2,headTilt:-3,eyeOpen:.72,browTilt:-.25,mouthCurve:-.25,earDroop:.3},sick:{bodyY:4,headTilt:-4,eyeOpen:.48,browTilt:-.45,mouthCurve:-.5,earDroop:.6,cheekIntensity:.35,saturation:.72},critical:{bodyY:7,bodyRotation:-1.5,eyeOpen:.24,browTilt:-.7,mouthCurve:-.7,earDroop:.85,cheekIntensity:.15,saturation:.45},dead:{bodyY:13,bodyRotation:-3,eyeOpen:0,eyeSmile:0,mouthOpen:0,mouthCurve:0,earDroop:1,cheekIntensity:0,saturation:.2,opacity:.78}},hi={neutral:{},calm:{eyeOpen:.82,eyeSmile:.2,mouthCurve:.25,earDroop:.08},joyful:{bodyY:-3,eyeOpen:.85,eyeSmile:1,mouthOpen:.15,mouthCurve:1,cheekIntensity:1},curious:{headTilt:7,eyeOpen:1.08,browTilt:.25,mouthCurve:.15},worried:{headTilt:-3,eyeOpen:.78,browTilt:-.5,mouthCurve:-.35,earDroop:.35},tired:{bodyY:2,eyeOpen:.5,mouthCurve:-.1,earDroop:.4},proud:{bodyY:-1,headTilt:3,eyeOpen:.88,eyeSmile:.55,mouthCurve:.7}},Ze={notice:{id:"notice",durationMs:480,priority:10,allowedConditions:dt,keyframes:[{offset:0,pose:{}},{offset:.35,pose:{headTilt:6,eyeOpen:1.15,earDroop:0}},{offset:1,pose:{}}],reducedMotionPose:{eyeOpen:1.08}},"tap-hop":{id:"tap-hop",durationMs:620,priority:20,allowedConditions:["happy","content","lonely"],keyframes:[{offset:0,pose:{}},{offset:.35,pose:{bodyY:-13,bodyScaleX:.94,bodyScaleY:1.07,eyeSmile:.8}},{offset:.7,pose:{bodyY:1,bodyScaleX:1.04,bodyScaleY:.96}},{offset:1,pose:{}}],reducedMotionPose:{eyeSmile:.8}},celebrate:{id:"celebrate",durationMs:1050,priority:30,allowedConditions:["happy","content","lonely"],keyframes:[{offset:0,pose:{}},{offset:.1,pose:{bodyY:5,bodyScaleX:1.1,bodyScaleY:.9,eyeOpen:1.08,mouthOpen:.2}},{offset:.24,pose:{bodyY:-9,bodyScaleX:.94,bodyScaleY:1.08,eyeSmile:1,mouthOpen:.55,mouthCurve:1}},{offset:.7,pose:{bodyY:-6,eyeSmile:1,mouthOpen:.45,mouthCurve:1,cheekIntensity:1}},{offset:.9,pose:{bodyY:2,bodyScaleX:1.08,bodyScaleY:.92,eyeSmile:.8}},{offset:1,pose:{}}],reducedMotionPose:{eyeOpen:1.08,eyeSmile:1,mouthOpen:.45,mouthCurve:1,cheekIntensity:1}},"reply-roll":{id:"reply-roll",durationMs:1800,priority:50,allowedConditions:dt,keyframes:[{offset:0,pose:{}},{offset:.1,pose:{bodyY:4,bodyScaleX:1.08,bodyScaleY:.92,eyeOpen:1.08}},{offset:.28,pose:{bodyY:-9,bodyScaleX:.95,bodyScaleY:1.05,eyeSmile:.9,mouthCurve:1}},{offset:.68,pose:{bodyY:-7,eyeSmile:1,mouthCurve:1,cheekIntensity:1}},{offset:.9,pose:{bodyY:3,bodyScaleX:1.1,bodyScaleY:.9}},{offset:1,pose:{}}],reducedMotionPose:{eyeSmile:.9,mouthCurve:1,cheekIntensity:1}},startled:{id:"startled",durationMs:420,priority:40,allowedConditions:dt,keyframes:[{offset:0,pose:{}},{offset:.3,pose:{bodyY:-5,bodyScaleX:.96,bodyScaleY:1.04,eyeOpen:1.2,mouthOpen:.5}},{offset:1,pose:{}}],reducedMotionPose:{eyeOpen:1.15,mouthOpen:.3}},"receive-care":{id:"receive-care",durationMs:1e3,priority:60,allowedConditions:dt,keyframes:[{offset:0,pose:{}},{offset:.45,pose:{eyeOpen:.75,eyeSmile:.75,mouthCurve:.65,cheekIntensity:1}},{offset:1,pose:{}}],reducedMotionPose:{eyeSmile:.65,mouthCurve:.55}},recover:{id:"recover",durationMs:1400,priority:80,allowedConditions:["happy","content","lonely"],keyframes:[{offset:0,pose:{bodyY:4,eyeOpen:.5,earDroop:.6,saturation:.7}},{offset:.65,pose:{bodyY:-8,eyeOpen:.9,eyeSmile:.8,mouthCurve:.8,earDroop:0,saturation:1}},{offset:1,pose:{}}],reducedMotionPose:{eyeSmile:.7,mouthCurve:.7,saturation:1}},"zap-celebrate":{id:"zap-celebrate",durationMs:2400,priority:70,allowedConditions:dt,keyframes:[{offset:0,pose:{}},{offset:.08,pose:{bodyY:-4,eyeOpen:1.12,mouthOpen:.3,mouthCurve:1}},{offset:.36,pose:{bodyY:-3,eyeSmile:1,mouthOpen:.25,mouthCurve:1}},{offset:.78,pose:{bodyY:-2,eyeSmile:1,mouthCurve:1,cheekIntensity:1}},{offset:1,pose:{}}],reducedMotionPose:{eyeSmile:1,mouthOpen:.2,mouthCurve:1,cheekIntensity:1}}};function zn(t,e,n){return Math.min(n,Math.max(e,t))}function Yn(t,e){return{...t,...e}}function pi(t,e,n){const o={...t};for(const r of Object.keys(e)){const i=e[r];i!==void 0&&(o[r]+=(i-o[r])*n)}return o}function yi(t){return t==="dead"?0:t==="critical"?.2:t==="sick"?.35:t==="lonely"?.65:1}function mi(t,e,n){const o=zn(e,0,1);let r=t.keyframes[0],i=t.keyframes[t.keyframes.length-1];for(let f=1;f<t.keyframes.length;f+=1)if(o<=t.keyframes[f].offset){i=t.keyframes[f],r=t.keyframes[f-1];break}const s=Math.max(1e-4,i.offset-r.offset),a=zn((o-r.offset)/s,0,1),l=new Set([...Object.keys(r.pose),...Object.keys(i.pose)]),d={};for(const f of l){const c=r.pose[f]??n[f],y=i.pose[f]??n[f];d[f]=c+(y-c)*a}return d}function vn(t){const e=t.mood??"neutral";let n=Yn({...ui},fi[t.condition]);if(n=pi(n,hi[e],yi(t.condition)),t.reaction){const o=Ze[t.reaction];if(o.allowedConditions.includes(t.condition)){const r=t.reducedMotion?o.reducedMotionPose??{}:mi(o,t.reactionProgress??0,n);n=Yn(n,r)}}return n}class gi{constructor(e){u(this,"condition");u(this,"mood","neutral");u(this,"activeReaction",null);u(this,"now");u(this,"reducedMotion");u(this,"listeners",new Set);u(this,"log");this.condition=(e==null?void 0:e.condition)??"happy",this.now=(e==null?void 0:e.now)??(()=>performance.now()),this.reducedMotion=(e==null?void 0:e.reducedMotion)??(()=>!1),this.log=(e==null?void 0:e.logger)??((n,o)=>console.log(n,o??{})),this.log("[nappagochi:emotion] controller created",{condition:this.condition})}setCondition(e){const n=this.condition;this.condition=e,e==="dead"&&this.activeReaction&&(this.log("[nappagochi:emotion] reaction cancelled by terminal condition",{reaction:this.activeReaction.id}),this.activeReaction=null),n!==e&&this.log("[nappagochi:emotion] condition changed",{previous:n,condition:e}),this.notify()}setMood(e){const n=this.mood;this.mood=e,n!==e&&this.log("[nappagochi:emotion] mood changed",{previous:n,mood:e}),this.notify()}react(e){var r;const n=Ze[e];if(!n.allowedConditions.includes(this.condition))return this.log("[nappagochi:emotion] reaction rejected by condition",{reaction:e,condition:this.condition}),!1;if(this.activeReaction&&Ze[this.activeReaction.id].priority>n.priority&&!this.reactionFinished(this.activeReaction))return this.log("[nappagochi:emotion] reaction rejected by priority",{reaction:e,activeReaction:this.activeReaction.id,requestedPriority:n.priority,activePriority:Ze[this.activeReaction.id].priority}),!1;const o=((r=this.activeReaction)==null?void 0:r.id)??null;return this.activeReaction={id:e,startedAt:this.now()},this.log("[nappagochi:emotion] reaction started",{reaction:e,condition:this.condition,durationMs:n.durationMs,priority:n.priority,interruptedReaction:o,reducedMotion:this.reducedMotion()}),this.notify(),!0}cancelReaction(e){var n,o;if(!e||((n=this.activeReaction)==null?void 0:n.id)===e){const r=((o=this.activeReaction)==null?void 0:o.id)??null;this.activeReaction=null,r&&this.log("[nappagochi:emotion] reaction cancelled",{reaction:r}),this.notify()}}snapshot(e=this.now()){var i;this.activeReaction&&this.reactionFinished(this.activeReaction,e)&&(this.log("[nappagochi:emotion] reaction completed",{reaction:this.activeReaction.id,condition:this.condition}),this.activeReaction=null);const n=((i=this.activeReaction)==null?void 0:i.id)??null,o=n?Ze[n]:null,r=o&&this.activeReaction?(e-this.activeReaction.startedAt)/o.durationMs:0;return{condition:this.condition,mood:this.mood,reaction:n,pose:vn({condition:this.condition,mood:this.mood,reaction:n??void 0,reactionProgress:r,reducedMotion:this.reducedMotion()})}}subscribe(e){return this.listeners.add(e),e(this.snapshot()),()=>this.listeners.delete(e)}destroy(){var e;this.log("[nappagochi:emotion] controller destroyed",{activeReaction:((e=this.activeReaction)==null?void 0:e.id)??null,listenerCount:this.listeners.size}),this.activeReaction=null,this.listeners.clear()}reactionFinished(e,n=this.now()){return n-e.startedAt>=Ze[e.id].durationMs}notify(){const e=this.snapshot();for(const n of this.listeners)n(e)}}function Ao(t){return[`--pet-pose-body-y:${t.bodyY.toFixed(2)}px`,`--pet-pose-body-rotation:${t.bodyRotation.toFixed(2)}deg`,`--pet-pose-scale-x:${t.bodyScaleX.toFixed(3)}`,`--pet-pose-scale-y:${t.bodyScaleY.toFixed(3)}`,`--pet-pose-head-tilt:${t.headTilt.toFixed(2)}deg`,`--pet-pose-eye-open:${t.eyeOpen.toFixed(3)}`,`--pet-pose-mouth-open:${t.mouthOpen.toFixed(3)}`,`--pet-pose-ear-droop-angle:${(t.earDroop*12).toFixed(2)}deg`,`--pet-pose-cheek:${t.cheekIntensity.toFixed(3)}`].join(";")}function bi(t){return!Number.isInteger(t)||t<0||t>=3?null:1e3*2**t}class wi{constructor(e){u(this,"id");u(this,"mountedAt");u(this,"openChannel");u(this,"now");u(this,"maxRememberedEventIds");u(this,"log");u(this,"channels",new Map);u(this,"rememberedEventIds",new Set);u(this,"eventIdOrder",[]);u(this,"deliveryListeners",new Set);u(this,"statusListeners",new Set);u(this,"destroyed",!1);this.mountedAt=e.mountedAt,this.openChannel=e.openChannel,this.now=e.now??(()=>Math.floor(Date.now()/1e3)),this.maxRememberedEventIds=Math.max(1,e.maxRememberedEventIds??2e3),this.id=e.sessionId??`live-${e.mountedAt}`,this.log=e.logger??((n,o)=>console.log(n,o??{})),this.log("[nappagochi:live] session created",{sessionId:this.id,mountedAt:this.mountedAt,maxRememberedEventIds:this.maxRememberedEventIds})}replaceChannel(e){var i,s;if(this.destroyed){this.log("[nappagochi:live] channel open ignored after destroy",{channelId:e.id});return}this.closeChannel(e.id);const n=Symbol(e.id),o=e.filters.map(a=>({...a,since:Math.max(this.mountedAt,a.since??this.mountedAt)})),r={...e,filters:o};this.log("[nappagochi:live] channel opening",{sessionId:this.id,channelId:e.id,filters:o,authorCount:((i=e.authors)==null?void 0:i.length)??0,relayHintCount:((s=e.relays)==null?void 0:s.length)??0}),this.channels.set(e.id,{token:n,handle:{close:()=>{}}});try{const a=this.openChannel(r,d=>this.receive(e.id,n,d),d=>this.markClosed(e.id,n,d)),l=this.channels.get(e.id);(l==null?void 0:l.token)===n?(l.handle=a,this.log("[nappagochi:live] channel open",{sessionId:this.id,channelId:e.id}),this.emitStatus({id:e.id,state:"open"})):a.close()}catch(a){this.channels.delete(e.id),this.emitStatus({id:e.id,state:"closed",reason:a instanceof Error?a.message:"open-failed"}),this.log("[nappagochi:live] channel open failed",{sessionId:this.id,channelId:e.id,reason:a instanceof Error?a.message:"open-failed"})}}closeChannel(e){const n=this.channels.get(e);n&&(this.channels.delete(e),n.handle.close(),this.log("[nappagochi:live] channel closed locally",{sessionId:this.id,channelId:e}),this.emitStatus({id:e,state:"closed",reason:"replaced-or-closed"}))}onDelivery(e){return this.deliveryListeners.add(e),()=>this.deliveryListeners.delete(e)}onStatus(e){return this.statusListeners.add(e),()=>this.statusListeners.delete(e)}destroy(){if(!this.destroyed){this.destroyed=!0,this.log("[nappagochi:live] session destroying",{sessionId:this.id,activeChannelCount:this.channels.size,rememberedEventCount:this.rememberedEventIds.size});for(const e of this.channels.values())e.handle.close();this.channels.clear(),this.rememberedEventIds.clear(),this.eventIdOrder=[],this.deliveryListeners.clear(),this.statusListeners.clear()}}receive(e,n,o){var s;if(this.destroyed||((s=this.channels.get(e))==null?void 0:s.token)!==n){this.log("[nappagochi:live] delivery ignored from stale channel",{sessionId:this.id,channelId:e,eventId:o.event.id});return}const r=o.event;if(r.created_at<this.mountedAt){this.log("[nappagochi:live] historical delivery ignored",{sessionId:this.id,channelId:e,eventId:r.id,eventCreatedAt:r.created_at,mountedAt:this.mountedAt});return}if(this.rememberedEventIds.has(r.id)){this.log("[nappagochi:live] duplicate delivery ignored",{sessionId:this.id,channelId:e,eventId:r.id});return}this.rememberEventId(r.id);const i={sessionId:this.id,channelId:e,event:r,receivedAt:this.now()};this.log("[nappagochi:live] delivery accepted",{sessionId:this.id,channelId:e,eventId:r.id,kind:r.kind,actorPubkey:r.pubkey,eventCreatedAt:r.created_at,receivedAt:i.receivedAt});for(const a of this.deliveryListeners)a(i)}rememberEventId(e){for(this.rememberedEventIds.add(e),this.eventIdOrder.push(e);this.eventIdOrder.length>this.maxRememberedEventIds;){const n=this.eventIdOrder.shift();n&&this.rememberedEventIds.delete(n)}}markClosed(e,n,o){var r;((r=this.channels.get(e))==null?void 0:r.token)===n&&(this.channels.delete(e),this.log("[nappagochi:live] channel closed upstream",{sessionId:this.id,channelId:e,reason:o??"unspecified"}),this.emitStatus({id:e,state:"closed",reason:o}))}emitStatus(e){for(const n of this.statusListeners)n(e)}}function vi(t,e,n){return t&e^~t&n}function Ei(t,e,n){return t&e^t&n^e&n}class ki{constructor(e,n,o,r){u(this,"blockLen");u(this,"outputLen");u(this,"padOffset");u(this,"isLE");u(this,"buffer");u(this,"view");u(this,"finished",!1);u(this,"length",0);u(this,"pos",0);u(this,"destroyed",!1);this.blockLen=e,this.outputLen=n,this.padOffset=o,this.isLE=r,this.buffer=new Uint8Array(e),this.view=Kt(this.buffer)}update(e){_n(this),Q(e);const{view:n,buffer:o,blockLen:r}=this,i=e.length;for(let s=0;s<i;){const a=Math.min(r-this.pos,i-s);if(a===r){const l=Kt(e);for(;r<=i-s;s+=r)this.process(l,s);continue}o.set(e.subarray(s,s+a),this.pos),this.pos+=a,s+=a,this.pos===r&&(this.process(n,0),this.pos=0)}return this.length+=e.length,this.roundClean(),this}digestInto(e){_n(this),Cr(e,this),this.finished=!0;const{buffer:n,view:o,blockLen:r,isLE:i}=this;let{pos:s}=this;n[s++]=128,nn(this.buffer.subarray(s)),this.padOffset>r-s&&(this.process(o,0),s=0);for(let c=s;c<r;c++)n[c]=0;o.setBigUint64(r-8,BigInt(this.length*8),i),this.process(o,0);const a=Kt(e),l=this.outputLen;if(l%4)throw new Error("_sha2: outputLen must be aligned to 32bit");const d=l/4,f=this.get();if(d>f.length)throw new Error("_sha2: outputLen bigger than state");for(let c=0;c<d;c++)a.setUint32(4*c,f[c],i)}digest(){const{buffer:e,outputLen:n}=this;this.digestInto(e);const o=e.slice(0,n);return this.destroy(),o}_cloneInto(e){e||(e=new this.constructor),e.set(...this.get());const{blockLen:n,buffer:o,length:r,finished:i,destroyed:s,pos:a}=this;return e.destroyed=s,e.finished=i,e.length=r,e.pos=a,r%n&&e.buffer.set(o),e}clone(){return this._cloneInto()}}const Ie=Uint32Array.from([1779033703,3144134277,1013904242,2773480762,1359893119,2600822924,528734635,1541459225]),xi=Uint32Array.from([1116352408,1899447441,3049323471,3921009573,961987163,1508970993,2453635748,2870763221,3624381080,310598401,607225278,1426881987,1925078388,2162078206,2614888103,3248222580,3835390401,4022224774,264347078,604807628,770255983,1249150122,1555081692,1996064986,2554220882,2821834349,2952996808,3210313671,3336571891,3584528711,113926993,338241895,666307205,773529912,1294757372,1396182291,1695183700,1986661051,2177026350,2456956037,2730485921,2820302411,3259730800,3345764771,3516065817,3600352804,4094571909,275423344,430227734,506948616,659060556,883997877,958139571,1322822218,1537002063,1747873779,1955562222,2024104815,2227730452,2361852424,2428436474,2756734187,3204031479,3329325298]),Ae=new Uint32Array(64);class $i extends ki{constructor(e){super(64,e,8,!1)}get(){const{A:e,B:n,C:o,D:r,E:i,F:s,G:a,H:l}=this;return[e,n,o,r,i,s,a,l]}set(e,n,o,r,i,s,a,l){this.A=e|0,this.B=n|0,this.C=o|0,this.D=r|0,this.E=i|0,this.F=s|0,this.G=a|0,this.H=l|0}process(e,n){for(let c=0;c<16;c++,n+=4)Ae[c]=e.getUint32(n,!1);for(let c=16;c<64;c++){const y=Ae[c-15],b=Ae[c-2],R=he(y,7)^he(y,18)^y>>>3,O=he(b,17)^he(b,19)^b>>>10;Ae[c]=O+Ae[c-7]+R+Ae[c-16]|0}let{A:o,B:r,C:i,D:s,E:a,F:l,G:d,H:f}=this;for(let c=0;c<64;c++){const y=he(a,6)^he(a,11)^he(a,25),b=f+y+vi(a,l,d)+xi[c]+Ae[c]|0,O=(he(o,2)^he(o,13)^he(o,22))+Ei(o,r,i)|0;f=d,d=l,l=a,a=s+b|0,s=i,i=r,r=o,o=b+O|0}o=o+this.A|0,r=r+this.B|0,i=i+this.C|0,s=s+this.D|0,a=a+this.E|0,l=l+this.F|0,d=d+this.G|0,f=f+this.H|0,this.set(o,r,i,s,a,l,d,f)}roundClean(){nn(Ae)}destroy(){this.set(0,0,0,0,0,0,0,0),nn(this.buffer)}}class Ii extends $i{constructor(){super(32);u(this,"A",Ie[0]|0);u(this,"B",Ie[1]|0);u(this,"C",Ie[2]|0);u(this,"D",Ie[3]|0);u(this,"E",Ie[4]|0);u(this,"F",Ie[5]|0);u(this,"G",Ie[6]|0);u(this,"H",Ie[7]|0)}}const an=Br(()=>new Ii,Nr(1));/*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */const En=BigInt(0),ln=BigInt(1);function Vn(t,e=""){if(typeof t!="boolean"){const n=e&&`"${e}" `;throw new Error(n+"expected boolean, got type="+typeof t)}return t}function Ai(t){if(typeof t=="bigint"){if(!Mi(t))throw new Error("positive bigint expected, got "+t)}else bn(t);return t}function Ro(t){if(typeof t!="string")throw new Error("hex string expected, got "+typeof t);return t===""?En:BigInt("0x"+t)}function kn(t){return Ro(X(t))}function So(t){return Ro(X(Ri(Q(t)).reverse()))}function xn(t,e){bn(e),t=Ai(t);const n=_e(t.toString(16).padStart(e*2,"0"));if(n.length!==e)throw new Error("number too large");return n}function Mo(t,e){return xn(t,e).reverse()}function Ri(t){return Uint8Array.from(t)}function Si(t){return Uint8Array.from(t,(e,n)=>{const o=e.charCodeAt(0);if(e.length!==1||o>127)throw new Error(`string contains non-ASCII character "${t[n]}" with code ${o} at position ${n}`);return o})}const Mi=t=>typeof t=="bigint"&&En<=t;function Oi(t){let e;for(e=0;t>En;t>>=ln,e+=1);return e}const Oo=t=>(ln<<BigInt(t))-ln;function Po(t,e={},n={}){if(!t||typeof t!="object")throw new Error("expected valid options object");function o(i,s,a){const l=t[i];if(a&&l===void 0)return;const d=typeof l;if(d!==s||l===null)throw new Error(`param "${i}" is invalid: expected ${s}, got ${d}`)}const r=(i,s)=>Object.entries(i).forEach(([a,l])=>o(a,l,s));r(e,!1),r(n,!0)}function jn(t){const e=new WeakMap;return(n,...o)=>{const r=e.get(n);if(r!==void 0)return r;const i=t(n,...o);return e.set(n,i),i}}/*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */const W=BigInt(0),G=BigInt(1),qe=BigInt(2),Co=BigInt(3),To=BigInt(4),Bo=BigInt(5),Pi=BigInt(7),No=BigInt(8),Ci=BigInt(9),Lo=BigInt(16);function le(t,e){const n=t%e;return n>=W?n:e+n}function oe(t,e,n){let o=t;for(;e-- >W;)o*=o,o%=n;return o}function Zn(t,e){if(t===W)throw new Error("invert: expected non-zero number");if(e<=W)throw new Error("invert: expected positive modulus, got "+e);let n=le(t,e),o=e,r=W,i=G;for(;n!==W;){const a=o/n,l=o%n,d=r-i*a;o=n,n=l,r=i,i=d}if(o!==G)throw new Error("invert: does not exist");return le(r,e)}function $n(t,e,n){if(!t.eql(t.sqr(e),n))throw new Error("Cannot find square root")}function _o(t,e){const n=(t.ORDER+G)/To,o=t.pow(e,n);return $n(t,o,e),o}function Ti(t,e){const n=(t.ORDER-Bo)/No,o=t.mul(e,qe),r=t.pow(o,n),i=t.mul(e,r),s=t.mul(t.mul(i,qe),r),a=t.mul(i,t.sub(s,t.ONE));return $n(t,a,e),a}function Bi(t){const e=Yt(t),n=qo(t),o=n(e,e.neg(e.ONE)),r=n(e,o),i=n(e,e.neg(o)),s=(t+Pi)/Lo;return(a,l)=>{let d=a.pow(l,s),f=a.mul(d,o);const c=a.mul(d,r),y=a.mul(d,i),b=a.eql(a.sqr(f),l),R=a.eql(a.sqr(c),l);d=a.cmov(d,f,b),f=a.cmov(y,c,R);const O=a.eql(a.sqr(f),l),D=a.cmov(d,f,O);return $n(a,D,l),D}}function qo(t){if(t<Co)throw new Error("sqrt is not defined for small field");let e=t-G,n=0;for(;e%qe===W;)e/=qe,n++;let o=qe;const r=Yt(t);for(;Gn(r,o)===1;)if(o++>1e3)throw new Error("Cannot find square root: probably non-prime P");if(n===1)return _o;let i=r.pow(o,e);const s=(e+G)/qe;return function(l,d){if(l.is0(d))return d;if(Gn(l,d)!==1)throw new Error("Cannot find square root");let f=n,c=l.mul(l.ONE,i),y=l.pow(d,e),b=l.pow(d,s);for(;!l.eql(y,l.ONE);){if(l.is0(y))return l.ZERO;let R=1,O=l.sqr(y);for(;!l.eql(O,l.ONE);)if(R++,O=l.sqr(O),R===f)throw new Error("Cannot find square root");const D=G<<BigInt(f-R-1),K=l.pow(c,D);f=R,c=l.sqr(K),y=l.mul(y,c),b=l.mul(b,K)}return b}}function Ni(t){return t%To===Co?_o:t%No===Bo?Ti:t%Lo===Ci?Bi(t):qo(t)}const Li=["create","isValid","is0","neg","inv","sqrt","sqr","eql","add","sub","mul","pow","div","addN","subN","mulN","sqrN"];function _i(t){const e={ORDER:"bigint",BYTES:"number",BITS:"number"},n=Li.reduce((o,r)=>(o[r]="function",o),e);return Po(t,n),t}function qi(t,e,n){if(n<W)throw new Error("invalid exponent, negatives unsupported");if(n===W)return t.ONE;if(n===G)return e;let o=t.ONE,r=e;for(;n>W;)n&G&&(o=t.mul(o,r)),r=t.sqr(r),n>>=G;return o}function Ho(t,e,n=!1){const o=new Array(e.length).fill(n?t.ZERO:void 0),r=e.reduce((s,a,l)=>t.is0(a)?s:(o[l]=s,t.mul(s,a)),t.ONE),i=t.inv(r);return e.reduceRight((s,a,l)=>t.is0(a)?s:(o[l]=t.mul(s,o[l]),t.mul(s,a)),i),o}function Gn(t,e){const n=(t.ORDER-G)/qe,o=t.pow(e,n),r=t.eql(o,t.ONE),i=t.eql(o,t.ZERO),s=t.eql(o,t.neg(t.ONE));if(!r&&!i&&!s)throw new Error("invalid Legendre symbol result");return r?1:i?0:-1}function Hi(t,e){e!==void 0&&bn(e);const n=e!==void 0?e:t.toString(2).length,o=Math.ceil(n/8);return{nBitLength:n,nByteLength:o}}class Di{constructor(e,n={}){u(this,"ORDER");u(this,"BITS");u(this,"BYTES");u(this,"isLE");u(this,"ZERO",W);u(this,"ONE",G);u(this,"_lengths");u(this,"_sqrt");u(this,"_mod");var s;if(e<=W)throw new Error("invalid field: expected ORDER > 0, got "+e);let o;this.isLE=!1,n!=null&&typeof n=="object"&&(typeof n.BITS=="number"&&(o=n.BITS),typeof n.sqrt=="function"&&(this.sqrt=n.sqrt),typeof n.isLE=="boolean"&&(this.isLE=n.isLE),n.allowedLengths&&(this._lengths=(s=n.allowedLengths)==null?void 0:s.slice()),typeof n.modFromBytes=="boolean"&&(this._mod=n.modFromBytes));const{nBitLength:r,nByteLength:i}=Hi(e,o);if(i>2048)throw new Error("invalid field: expected ORDER of <= 2048 bytes");this.ORDER=e,this.BITS=r,this.BYTES=i,this._sqrt=void 0,Object.preventExtensions(this)}create(e){return le(e,this.ORDER)}isValid(e){if(typeof e!="bigint")throw new Error("invalid field element: expected bigint, got "+typeof e);return W<=e&&e<this.ORDER}is0(e){return e===W}isValidNot0(e){return!this.is0(e)&&this.isValid(e)}isOdd(e){return(e&G)===G}neg(e){return le(-e,this.ORDER)}eql(e,n){return e===n}sqr(e){return le(e*e,this.ORDER)}add(e,n){return le(e+n,this.ORDER)}sub(e,n){return le(e-n,this.ORDER)}mul(e,n){return le(e*n,this.ORDER)}pow(e,n){return qi(this,e,n)}div(e,n){return le(e*Zn(n,this.ORDER),this.ORDER)}sqrN(e){return e*e}addN(e,n){return e+n}subN(e,n){return e-n}mulN(e,n){return e*n}inv(e){return Zn(e,this.ORDER)}sqrt(e){return this._sqrt||(this._sqrt=Ni(this.ORDER)),this._sqrt(this,e)}toBytes(e){return this.isLE?Mo(e,this.BYTES):xn(e,this.BYTES)}fromBytes(e,n=!1){Q(e);const{_lengths:o,BYTES:r,isLE:i,ORDER:s,_mod:a}=this;if(o){if(!o.includes(e.length)||e.length>r)throw new Error("Field.fromBytes: expected "+o+" bytes, got "+e.length);const d=new Uint8Array(r);d.set(e,i?0:d.length-e.length),e=d}if(e.length!==r)throw new Error("Field.fromBytes: expected "+r+" bytes, got "+e.length);let l=i?So(e):kn(e);if(a&&(l=le(l,s)),!n&&!this.isValid(l))throw new Error("invalid field element: outside of range 0..ORDER");return l}invertBatch(e){return Ho(this,e)}cmov(e,n,o){return o?n:e}}function Yt(t,e={}){return new Di(t,e)}function Do(t){if(typeof t!="bigint")throw new Error("field order must be bigint");const e=t.toString(2).length;return Math.ceil(e/8)}function Fi(t){const e=Do(t);return e+Math.ceil(e/2)}function Ui(t,e,n=!1){Q(t);const o=t.length,r=Do(e),i=Fi(e);if(o<16||o<i||o>1024)throw new Error("expected "+i+"-1024 bytes of input, got "+o);const s=n?So(t):kn(t),a=le(s,e-G)+G;return n?Mo(a,r):xn(a,r)}/*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */const Qe=BigInt(0),He=BigInt(1);function Dt(t,e){const n=e.negate();return t?n:e}function Kn(t,e){const n=Ho(t.Fp,e.map(o=>o.Z));return e.map((o,r)=>t.fromAffine(o.toAffine(n[r])))}function Fo(t,e){if(!Number.isSafeInteger(t)||t<=0||t>e)throw new Error("invalid window size, expected [1.."+e+"], got W="+t)}function Jt(t,e){Fo(t,e);const n=Math.ceil(e/t)+1,o=2**(t-1),r=2**t,i=Oo(t),s=BigInt(t);return{windows:n,windowSize:o,mask:i,maxNumber:r,shiftBy:s}}function Xn(t,e,n){const{windowSize:o,mask:r,maxNumber:i,shiftBy:s}=n;let a=Number(t&r),l=t>>s;a>o&&(a-=i,l+=He);const d=e*o,f=d+Math.abs(a)-1,c=a===0,y=a<0,b=e%2!==0;return{nextN:l,offset:f,isZero:c,isNeg:y,isNegF:b,offsetF:d}}const Qt=new WeakMap,Uo=new WeakMap;function en(t){return Uo.get(t)||1}function Wn(t){if(t!==Qe)throw new Error("invalid wNAF")}class zi{constructor(e,n){u(this,"BASE");u(this,"ZERO");u(this,"Fn");u(this,"bits");this.BASE=e.BASE,this.ZERO=e.ZERO,this.Fn=e.Fn,this.bits=n}_unsafeLadder(e,n,o=this.ZERO){let r=e;for(;n>Qe;)n&He&&(o=o.add(r)),r=r.double(),n>>=He;return o}precomputeWindow(e,n){const{windows:o,windowSize:r}=Jt(n,this.bits),i=[];let s=e,a=s;for(let l=0;l<o;l++){a=s,i.push(a);for(let d=1;d<r;d++)a=a.add(s),i.push(a);s=a.double()}return i}wNAF(e,n,o){if(!this.Fn.isValid(o))throw new Error("invalid scalar");let r=this.ZERO,i=this.BASE;const s=Jt(e,this.bits);for(let a=0;a<s.windows;a++){const{nextN:l,offset:d,isZero:f,isNeg:c,isNegF:y,offsetF:b}=Xn(o,a,s);o=l,f?i=i.add(Dt(y,n[b])):r=r.add(Dt(c,n[d]))}return Wn(o),{p:r,f:i}}wNAFUnsafe(e,n,o,r=this.ZERO){const i=Jt(e,this.bits);for(let s=0;s<i.windows&&o!==Qe;s++){const{nextN:a,offset:l,isZero:d,isNeg:f}=Xn(o,s,i);if(o=a,!d){const c=n[l];r=r.add(f?c.negate():c)}}return Wn(o),r}getPrecomputes(e,n,o){let r=Qt.get(n);return r||(r=this.precomputeWindow(n,e),e!==1&&(typeof o=="function"&&(r=o(r)),Qt.set(n,r))),r}cached(e,n,o){const r=en(e);return this.wNAF(r,this.getPrecomputes(r,e,o),n)}unsafe(e,n,o,r){const i=en(e);return i===1?this._unsafeLadder(e,n,r):this.wNAFUnsafe(i,this.getPrecomputes(i,e,o),n,r)}createCache(e,n){Fo(n,this.bits),Uo.set(e,n),Qt.delete(e)}hasCache(e){return en(e)!==1}}function Yi(t,e,n,o){let r=e,i=t.ZERO,s=t.ZERO;for(;n>Qe||o>Qe;)n&He&&(i=i.add(r)),o&He&&(s=s.add(r)),r=r.double(),n>>=He,o>>=He;return{p1:i,p2:s}}function Jn(t,e,n){if(e){if(e.ORDER!==t)throw new Error("Field.ORDER must match order: Fp == p, Fn == n");return _i(e),e}else return Yt(t,{isLE:n})}function Vi(t,e,n={},o){if(o===void 0&&(o=t==="edwards"),!e||typeof e!="object")throw new Error(`expected valid ${t} CURVE object`);for(const l of["p","n","h"]){const d=e[l];if(!(typeof d=="bigint"&&d>Qe))throw new Error(`CURVE.${l} must be positive bigint`)}const r=Jn(e.p,n.Fp,o),i=Jn(e.n,n.Fn,o),a=["Gx","Gy","a","b"];for(const l of a)if(!r.isValid(e[l]))throw new Error(`CURVE.${l} must be valid field element of CURVE.Fp`);return e=Object.freeze(Object.assign({},e)),{CURVE:e,Fp:r,Fn:i}}function ji(t,e){return function(o){const r=t(o);return{secretKey:r,publicKey:e(r)}}}/*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */const Qn=(t,e)=>(t+(t>=0?e:-e)/Gi)/e;function Zi(t,e,n){const[[o,r],[i,s]]=e,a=Qn(s*t,n),l=Qn(-r*t,n);let d=t-a*o-l*i,f=-a*r-l*s;const c=d<ft,y=f<ft;c&&(d=-d),y&&(f=-f);const b=Oo(Math.ceil(Oi(n)/2))+Pt;if(d<ft||d>=b||f<ft||f>=b)throw new Error("splitScalar (endomorphism): failed, k="+t);return{k1neg:c,k1:d,k2neg:y,k2:f}}const ft=BigInt(0),Pt=BigInt(1),Gi=BigInt(2),St=BigInt(3),Ki=BigInt(4);function Xi(t,e={}){const n=Vi("weierstrass",t,e),{Fp:o,Fn:r}=n;let i=n.CURVE;const{h:s,n:a}=i;Po(e,{},{allowInfinityPoint:"boolean",clearCofactor:"function",isTorsionFree:"function",fromBytes:"function",toBytes:"function",endo:"object"});const{endo:l}=e;if(l&&(!o.is0(i.a)||typeof l.beta!="bigint"||!Array.isArray(l.basises)))throw new Error('invalid endo: expected "beta": bigint and "basises": array');const d=Ji(o,r);function f(){if(!o.isOdd)throw new Error("compression is not supported: Field does not have .isOdd()")}function c(C,h,m){const{x:k,y:$}=h.toAffine(),T=o.toBytes(k);if(Vn(m,"isCompressed"),m){f();const S=!o.isOdd($);return Lt(Wi(S),T)}else return Lt(Uint8Array.of(4),T,o.toBytes($))}function y(C){Q(C,void 0,"Point");const{publicKey:h,publicKeyUncompressed:m}=d,k=C.length,$=C[0],T=C.subarray(1);if(k===h&&($===2||$===3)){const S=o.fromBytes(T);if(!o.isValid(S))throw new Error("bad point: is not on curve, wrong x");const I=O(S);let v;try{v=o.sqrt(I)}catch(ne){const F=ne instanceof Error?": "+ne.message:"";throw new Error("bad point: is not on curve, sqrt error"+F)}f();const A=o.isOdd(v);return($&1)===1!==A&&(v=o.neg(v)),{x:S,y:v}}else if(k===m&&$===4){const S=o.BYTES,I=o.fromBytes(T.subarray(0,S)),v=o.fromBytes(T.subarray(S,S*2));if(!D(I,v))throw new Error("bad point: is not on curve");return{x:I,y:v}}else throw new Error(`bad point: got length ${k}, expected compressed=${h} or uncompressed=${m}`)}const b=e.toBytes||c,R=e.fromBytes||y;function O(C){const h=o.sqr(C),m=o.mul(h,C);return o.add(o.add(m,o.mul(C,i.a)),i.b)}function D(C,h){const m=o.sqr(h),k=O(C);return o.eql(m,k)}if(!D(i.Gx,i.Gy))throw new Error("bad curve params: generator point");const K=o.mul(o.pow(i.a,St),Ki),$e=o.mul(o.sqr(i.b),BigInt(27));if(o.is0(o.add(K,$e)))throw new Error("bad curve params: a or b");function de(C,h,m=!1){if(!o.isValid(h)||m&&o.is0(h))throw new Error(`bad point coordinate ${C}`);return h}function Ue(C){if(!(C instanceof ie))throw new Error("Weierstrass Point expected")}function Be(C){if(!l||!l.basises)throw new Error("no endo");return Zi(C,l.basises,r.ORDER)}const ze=jn((C,h)=>{const{X:m,Y:k,Z:$}=C;if(o.eql($,o.ONE))return{x:m,y:k};const T=C.is0();h==null&&(h=T?o.ONE:o.inv($));const S=o.mul(m,h),I=o.mul(k,h),v=o.mul($,h);if(T)return{x:o.ZERO,y:o.ZERO};if(!o.eql(v,o.ONE))throw new Error("invZ was invalid");return{x:S,y:I}}),Gt=jn(C=>{if(C.is0()){if(e.allowInfinityPoint&&!o.is0(C.Y))return;throw new Error("bad point: ZERO")}const{x:h,y:m}=C.toAffine();if(!o.isValid(h)||!o.isValid(m))throw new Error("bad point: x or y not field elements");if(!D(h,m))throw new Error("bad point: equation left != right");if(!C.isTorsionFree())throw new Error("bad point: not in prime-order subgroup");return!0});function ue(C,h,m,k,$){return m=new ie(o.mul(m.X,C),m.Y,m.Z),h=Dt(k,h),m=Dt($,m),h.add(m)}const N=class N{constructor(h,m,k){u(this,"X");u(this,"Y");u(this,"Z");this.X=de("x",h),this.Y=de("y",m,!0),this.Z=de("z",k),Object.freeze(this)}static CURVE(){return i}static fromAffine(h){const{x:m,y:k}=h||{};if(!h||!o.isValid(m)||!o.isValid(k))throw new Error("invalid affine point");if(h instanceof N)throw new Error("projective point not allowed");return o.is0(m)&&o.is0(k)?N.ZERO:new N(m,k,o.ONE)}static fromBytes(h){const m=N.fromAffine(R(Q(h,void 0,"point")));return m.assertValidity(),m}static fromHex(h){return N.fromBytes(_e(h))}get x(){return this.toAffine().x}get y(){return this.toAffine().y}precompute(h=8,m=!0){return lt.createCache(this,h),m||this.multiply(St),this}assertValidity(){Gt(this)}hasEvenY(){const{y:h}=this.toAffine();if(!o.isOdd)throw new Error("Field doesn't support isOdd");return!o.isOdd(h)}equals(h){Ue(h);const{X:m,Y:k,Z:$}=this,{X:T,Y:S,Z:I}=h,v=o.eql(o.mul(m,I),o.mul(T,$)),A=o.eql(o.mul(k,I),o.mul(S,$));return v&&A}negate(){return new N(this.X,o.neg(this.Y),this.Z)}double(){const{a:h,b:m}=i,k=o.mul(m,St),{X:$,Y:T,Z:S}=this;let I=o.ZERO,v=o.ZERO,A=o.ZERO,P=o.mul($,$),ne=o.mul(T,T),F=o.mul(S,S),B=o.mul($,T);return B=o.add(B,B),A=o.mul($,S),A=o.add(A,A),I=o.mul(h,A),v=o.mul(k,F),v=o.add(I,v),I=o.sub(ne,v),v=o.add(ne,v),v=o.mul(I,v),I=o.mul(B,I),A=o.mul(k,A),F=o.mul(h,F),B=o.sub(P,F),B=o.mul(h,B),B=o.add(B,A),A=o.add(P,P),P=o.add(A,P),P=o.add(P,F),P=o.mul(P,B),v=o.add(v,P),F=o.mul(T,S),F=o.add(F,F),P=o.mul(F,B),I=o.sub(I,P),A=o.mul(F,ne),A=o.add(A,A),A=o.add(A,A),new N(I,v,A)}add(h){Ue(h);const{X:m,Y:k,Z:$}=this,{X:T,Y:S,Z:I}=h;let v=o.ZERO,A=o.ZERO,P=o.ZERO;const ne=i.a,F=o.mul(i.b,St);let B=o.mul(m,T),se=o.mul(k,S),ae=o.mul($,I),Ye=o.add(m,k),j=o.add(T,S);Ye=o.mul(Ye,j),j=o.add(B,se),Ye=o.sub(Ye,j),j=o.add(m,$);let fe=o.add(T,I);return j=o.mul(j,fe),fe=o.add(B,ae),j=o.sub(j,fe),fe=o.add(k,$),v=o.add(S,I),fe=o.mul(fe,v),v=o.add(se,ae),fe=o.sub(fe,v),P=o.mul(ne,j),v=o.mul(F,ae),P=o.add(v,P),v=o.sub(se,P),P=o.add(se,P),A=o.mul(v,P),se=o.add(B,B),se=o.add(se,B),ae=o.mul(ne,ae),j=o.mul(F,j),se=o.add(se,ae),ae=o.sub(B,ae),ae=o.mul(ne,ae),j=o.add(j,ae),B=o.mul(se,j),A=o.add(A,B),B=o.mul(fe,j),v=o.mul(Ye,v),v=o.sub(v,B),B=o.mul(Ye,se),P=o.mul(fe,P),P=o.add(P,B),new N(v,A,P)}subtract(h){return this.add(h.negate())}is0(){return this.equals(N.ZERO)}multiply(h){const{endo:m}=e;if(!r.isValidNot0(h))throw new Error("invalid scalar: out of range");let k,$;const T=S=>lt.cached(this,S,I=>Kn(N,I));if(m){const{k1neg:S,k1:I,k2neg:v,k2:A}=Be(h),{p:P,f:ne}=T(I),{p:F,f:B}=T(A);$=ne.add(B),k=ue(m.beta,P,F,S,v)}else{const{p:S,f:I}=T(h);k=S,$=I}return Kn(N,[k,$])[0]}multiplyUnsafe(h){const{endo:m}=e,k=this;if(!r.isValid(h))throw new Error("invalid scalar: out of range");if(h===ft||k.is0())return N.ZERO;if(h===Pt)return k;if(lt.hasCache(this))return this.multiply(h);if(m){const{k1neg:$,k1:T,k2neg:S,k2:I}=Be(h),{p1:v,p2:A}=Yi(N,k,T,I);return ue(m.beta,v,A,$,S)}else return lt.unsafe(k,h)}toAffine(h){return ze(this,h)}isTorsionFree(){const{isTorsionFree:h}=e;return s===Pt?!0:h?h(N,this):lt.unsafe(this,a).is0()}clearCofactor(){const{clearCofactor:h}=e;return s===Pt?this:h?h(N,this):this.multiplyUnsafe(s)}isSmallOrder(){return this.multiplyUnsafe(s).is0()}toBytes(h=!0){return Vn(h,"isCompressed"),this.assertValidity(),b(N,this,h)}toHex(h=!0){return X(this.toBytes(h))}toString(){return`<Point ${this.is0()?"ZERO":this.toHex()}>`}};u(N,"BASE",new N(i.Gx,i.Gy,o.ONE)),u(N,"ZERO",new N(o.ZERO,o.ONE,o.ZERO)),u(N,"Fp",o),u(N,"Fn",r);let ie=N;const Ln=r.BITS,lt=new zi(ie,e.endo?Math.ceil(Ln/2):Ln);return ie.BASE.precompute(8),ie}function Wi(t){return Uint8Array.of(t?2:3)}function Ji(t,e){return{secretKey:e.BYTES,publicKey:1+t.BYTES,publicKeyUncompressed:1+2*t.BYTES,publicKeyHasPrefix:!0,signature:2*e.BYTES}}/*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */const Vt={p:BigInt("0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f"),n:BigInt("0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141"),h:BigInt(1),a:BigInt(0),b:BigInt(7),Gx:BigInt("0x79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798"),Gy:BigInt("0x483ada7726a3c4655da4fbfc0e1108a8fd17b448a68554199c47d08ffb10d4b8")},Qi={beta:BigInt("0x7ae96a2b657c07106e64479eac3434e99cf0497512f58995c1396c28719501ee"),basises:[[BigInt("0x3086d221a7d46bcde86c90e49284eb15"),-BigInt("0xe4437ed6010e88286f547fa90abfe4c3")],[BigInt("0x114ca50f7a8e2f3f657c1108d9d44cfd8"),BigInt("0x3086d221a7d46bcde86c90e49284eb15")]]},es=BigInt(0),cn=BigInt(2);function ts(t){const e=Vt.p,n=BigInt(3),o=BigInt(6),r=BigInt(11),i=BigInt(22),s=BigInt(23),a=BigInt(44),l=BigInt(88),d=t*t*t%e,f=d*d*t%e,c=oe(f,n,e)*f%e,y=oe(c,n,e)*f%e,b=oe(y,cn,e)*d%e,R=oe(b,r,e)*b%e,O=oe(R,i,e)*R%e,D=oe(O,a,e)*O%e,K=oe(D,l,e)*D%e,$e=oe(K,a,e)*O%e,de=oe($e,n,e)*f%e,Ue=oe(de,s,e)*R%e,Be=oe(Ue,o,e)*d%e,ze=oe(Be,cn,e);if(!Ft.eql(Ft.sqr(ze),t))throw new Error("Cannot find square root");return ze}const Ft=Yt(Vt.p,{sqrt:ts}),it=Xi(Vt,{Fp:Ft,endo:Qi}),eo={};function Ut(t,...e){let n=eo[t];if(n===void 0){const o=an(Si(t));n=Lt(o,o),eo[t]=n}return an(Lt(n,...e))}const In=t=>t.toBytes(!0).slice(1),An=t=>t%cn===es;function dn(t){const{Fn:e,BASE:n}=it,o=e.fromBytes(t),r=n.multiply(o);return{scalar:An(r.y)?o:e.neg(o),bytes:In(r)}}function zo(t){const e=Ft;if(!e.isValidNot0(t))throw new Error("invalid x: Fail if x ≥ p");const n=e.create(t*t),o=e.create(n*t+BigInt(7));let r=e.sqrt(o);An(r)||(r=e.neg(r));const i=it.fromAffine({x:t,y:r});return i.assertValidity(),i}const wt=kn;function Yo(...t){return it.Fn.create(wt(Ut("BIP0340/challenge",...t)))}function to(t){return dn(t).bytes}function ns(t,e,n=go(32)){const{Fn:o}=it,r=Q(t,void 0,"message"),{bytes:i,scalar:s}=dn(e),a=Q(n,32,"auxRand"),l=o.toBytes(s^wt(Ut("BIP0340/aux",a))),d=Ut("BIP0340/nonce",l,i,r),{bytes:f,scalar:c}=dn(d),y=Yo(f,i,r),b=new Uint8Array(64);if(b.set(f,0),b.set(o.toBytes(o.create(c+y*s)),32),!Vo(b,r,i))throw new Error("sign: Invalid signature produced");return b}function Vo(t,e,n){const{Fp:o,Fn:r,BASE:i}=it,s=Q(t,64,"signature"),a=Q(e,void 0,"message"),l=Q(n,32,"publicKey");try{const d=zo(wt(l)),f=wt(s.subarray(0,32));if(!o.isValidNot0(f))return!1;const c=wt(s.subarray(32,64));if(!r.isValidNot0(c))return!1;const y=Yo(r.toBytes(f),In(d),a),b=i.multiplyUnsafe(c).add(d.multiplyUnsafe(r.neg(y))),{x:R,y:O}=b.toAffine();return!(b.is0()||!An(O)||R!==f)}catch{return!1}}const ut=(()=>{const n=(o=go(48))=>Ui(o,Vt.n);return{keygen:ji(n,to),getPublicKey:to,sign:ns,verify:Vo,Point:it,utils:{randomSecretKey:n,taggedHash:Ut,lift_x:zo,pointToBytes:In},lengths:{secretKey:32,publicKey:32,publicKeyHasPrefix:!1,signature:64,seed:48}}})();var Ve=Symbol("verified"),os=t=>t instanceof Object;function jo(t){if(!os(t)||typeof t.kind!="number"||typeof t.content!="string"||typeof t.created_at!="number"||typeof t.pubkey!="string"||!t.pubkey.match(/^[a-f0-9]{64}$/)||!Array.isArray(t.tags))return!1;for(let e=0;e<t.tags.length;e++){let n=t.tags[e];if(!Array.isArray(n))return!1;for(let o=0;o<n.length;o++)if(typeof n[o]!="string")return!1}return!0}new TextDecoder("utf-8");var rs=new TextEncoder,is=class{generateSecretKey(){return ut.utils.randomSecretKey()}getPublicKey(t){return X(ut.getPublicKey(t))}finalizeEvent(t,e){const n=t;return n.pubkey=X(ut.getPublicKey(e)),n.id=tn(n),n.sig=X(ut.sign(_e(tn(n)),e)),n[Ve]=!0,n}verifyEvent(t){if(typeof t[Ve]=="boolean")return t[Ve];try{const e=tn(t);if(e!==t.id)return t[Ve]=!1,!1;const n=ut.verify(_e(t.sig),_e(e),_e(t.pubkey));return t[Ve]=n,n}catch{return t[Ve]=!1,!1}}};function ss(t){if(!jo(t))throw new Error("can't serialize event with wrong or missing properties");return JSON.stringify([0,t.pubkey,t.created_at,t.kind,t.tags,t.content])}function tn(t){let e=an(rs.encode(ss(t)));return X(e)}var jt=new is;jt.generateSecretKey;jt.getPublicKey;jt.finalizeEvent;var as=jt.verifyEvent;function ls(t){return t.event.kind!==1?null:{id:`owner-activity:${t.event.id}`,channelId:"owner-activity",eventId:t.event.id,actorPubkey:t.event.pubkey,receivedAt:t.receivedAt,eventCreatedAt:t.event.created_at,type:t.event.tags.some(e=>e[0]==="e")?"owner-replied":"owner-published"}}function cs(t){const e=ds(t.event,t.ownerPubkey);return e?{id:`inbound-engagement:${t.event.id}`,channelId:"inbound-engagement",eventId:t.event.id,actorPubkey:t.event.pubkey,receivedAt:t.receivedAt,eventCreatedAt:t.event.created_at,type:"zap-received",zap:e}:null}function ds(t,e){var r,i;if(t.kind!==9735||!t.tags.some(s=>s[0]==="p"&&s[1]===e))return null;const n=(r=t.tags.find(s=>s[0]==="description"))==null?void 0:r[1],o=(i=t.tags.find(s=>s[0]==="bolt11"))==null?void 0:i[1];if(!n||!o)return null;try{const s=JSON.parse(n);if(!jo(s)||!as(s)||s.kind!==9734||!s.tags.some(l=>l[0]==="relays"&&!!l[1])||!s.tags.some(l=>l[0]==="p"&&l[1]===e))return null;const a=us(o);return!Number.isFinite(a)||a<=0?null:{amountSats:a,senderPubkey:s.pubkey,zapRequestId:s.id}}catch{return null}}function us(t){if(t.length<50)return 0;const e=t.substring(0,50),n=e.lastIndexOf("1");if(n===-1)return 0;const o=e.substring(0,n);if(!o.startsWith("lnbc"))return 0;const r=o.substring(4);if(!r)return 0;const i=r.at(-1)??"",s=!/^[0-9]$/.test(i),a=Number.parseInt(s?r.slice(0,-1):r,10);return Number.isFinite(a)?s?i==="m"?a*1e5:i==="u"?a*100:i==="n"?a/10:i==="p"?a/1e4:0:a*1e8:0}class fs{constructor(e){u(this,"windowMs");u(this,"onAggregate");u(this,"signals",[]);u(this,"timer",null);u(this,"log");this.onAggregate=e.onAggregate,this.windowMs=Math.max(0,e.windowMs??700),this.log=e.logger??((n,o)=>console.log(n,o??{})),this.log("[nappagochi:live] aggregator created",{windowMs:this.windowMs})}push(e){this.signals.push(e),this.log("[nappagochi:live] signal queued",{signalId:e.id,channelId:e.channelId,type:e.type,eventId:e.eventId,queuedSignals:this.signals.length}),this.timer===null&&(this.log("[nappagochi:live] aggregate window started",{windowMs:this.windowMs}),this.timer=window.setTimeout(()=>this.flush(),this.windowMs))}flush(){if(this.timer!==null&&window.clearTimeout(this.timer),this.timer=null,!this.signals.length)return;const e=this.signals;this.signals=[];const n={};for(const r of e)n[r.type]=(n[r.type]??0)+1;const o={windowStartedAt:Math.min(...e.map(r=>r.receivedAt)),windowEndedAt:Math.max(...e.map(r=>r.receivedAt)),total:e.length,actorCount:new Set(e.map(r=>r.actorPubkey)).size,byType:n,representativeSignal:[...e].reverse().find(r=>r.type==="zap-received")??e[e.length-1]};this.log("[nappagochi:live] aggregate emitted",{total:o.total,actorCount:o.actorCount,byType:o.byType,windowStartedAt:o.windowStartedAt,windowEndedAt:o.windowEndedAt}),this.onAggregate(o)}destroy(){this.timer!==null&&window.clearTimeout(this.timer),this.timer=null,this.signals=[],this.log("[nappagochi:live] aggregator destroyed")}}function hs(t){return(t.byType["zap-received"]??0)>0?"zap-celebrate":(t.byType["owner-replied"]??0)>0?"reply-roll":(t.byType["owner-published"]??0)>0?"celebrate":"notice"}const ps={gentle:[(t,e)=>`Oh! ${e} sent ${t} sats! Thank you so much!`,(t,e)=>`${t} sats of kindness from ${e} just arrived!`,(t,e)=>`A ${t} sat zap from ${e}! My heart feels warm.`,(t,e)=>`${e} sent ${t} sats? That is so sweet!`,(t,e)=>`${t} sats from ${e}! I will treasure this little spark.`,(t,e)=>`${e} zapped ${t} sats! What a lovely surprise!`,(t,e)=>`A warm ${t} sat zap from ${e} found its way here!`,(t,e)=>`${t} sats from ${e}! Thank you for thinking of us.`,(t,e)=>`${e}'s ${t} sat zap made my ears perk up!`,(t,e)=>`${e} sent ${t} sats and brightened my whole habitat!`,(t,e)=>`I felt ${e}'s ${t} sat zap all the way in my paws!`,(t,e)=>`A ${t} sat gift from ${e}! May your day be gentle too.`,(t,e)=>`${t} sats from ${e}? I am doing my happiest little dance!`,(t,e)=>`Thank you, ${e}, for the ${t} sat lightning hug!`,(t,e)=>`${t} sats from ${e} arrived with a tiny sparkle!`,(t,e)=>`A ${t} sat zap from ${e}! You are very kind.`,(t,e)=>`${e} sent ${t} sats! I feel extra cared for today.`,(t,e)=>`What a cozy ${t} sat surprise from ${e}!`,(t,e)=>`${t} sats of pure encouragement from ${e}! Thank you!`,(t,e)=>`A ${t} sat zap from ${e} for us? I am beaming!`]},ys=["happy","content","lonely","sick","critical"];function no(t,e,n){const o=t.representativeSignal.zap;if((t.byType["zap-received"]??0)>0&&o){const r=ps[e],i=r[ms(o.zapRequestId,r.length)];return{id:`zap:${o.zapRequestId}`,intent:"gratitude",text:i(gs(o.amountSats),n||"someone"),durationMs:4400,priority:80}}return(t.byType["owner-published"]??0)>0?{id:`published:${t.representativeSignal.eventId}`,intent:"activity",text:t.total>1?"So much activity! I feel energized!":"You posted! I feel energized!",durationMs:3100,priority:40}:{id:`conversation:${t.representativeSignal.eventId}`,intent:"conversation",text:"Making conversation? I love that!",durationMs:3800,priority:30}}function ms(t,e){let n=2166136261;for(let o=0;o<t.length;o+=1)n^=t.charCodeAt(o),n=Math.imul(n,16777619);return(n>>>0)%e}function gs(t){return new Intl.NumberFormat("en-US",{maximumFractionDigits:0}).format(t)}class bs{constructor(e){u(this,"condition");u(this,"active",null);u(this,"queue",[]);u(this,"timer",null);u(this,"listeners",new Set);u(this,"schedule");u(this,"cancel");u(this,"log");this.condition=(e==null?void 0:e.condition)??"happy",this.schedule=(e==null?void 0:e.schedule)??((n,o)=>setTimeout(n,o)),this.cancel=(e==null?void 0:e.cancel)??(n=>clearTimeout(n)),this.log=(e==null?void 0:e.logger)??((n,o)=>console.log(n,o??{})),this.log("[nappagochi:speech] controller created",{condition:this.condition})}setCondition(e){this.condition=e,e==="dead"&&this.clear("terminal-condition")}say(e){var n;if(!ys.includes(this.condition)||!e.text.trim())return this.log("[nappagochi:speech] utterance rejected",{utteranceId:e.id,condition:this.condition}),!1;if(!this.active||e.priority>=this.active.priority){const o=((n=this.active)==null?void 0:n.id)??null;this.start(e),this.log("[nappagochi:speech] utterance started",{utteranceId:e.id,intent:e.intent,durationMs:e.durationMs,interruptedId:o})}else this.queue.push(e),this.log("[nappagochi:speech] utterance queued",{utteranceId:e.id,activeId:this.active.id,queuedCount:this.queue.length}),this.notify();return!0}snapshot(){return{utterance:this.active,queuedCount:this.queue.length}}refineActive(e){return!this.active||this.active.id!==e.id?!1:(this.active=e,this.log("[nappagochi:speech] active utterance refined",{utteranceId:e.id,intent:e.intent}),this.notify(),!0)}subscribe(e){return this.listeners.add(e),e(this.snapshot()),()=>this.listeners.delete(e)}destroy(){this.clear("destroyed"),this.listeners.clear()}start(e){this.timer!==null&&this.cancel(this.timer),this.active=e,this.timer=this.schedule(()=>this.advance(),Math.max(500,e.durationMs)),this.notify()}advance(){var o;const e=((o=this.active)==null?void 0:o.id)??null;this.timer=null,this.active=null;const n=this.queue.shift();this.log("[nappagochi:speech] utterance completed",{utteranceId:e,nextId:(n==null?void 0:n.id)??null,queuedCount:this.queue.length}),n?this.start(n):this.notify()}clear(e){this.timer!==null&&this.cancel(this.timer);const n=!!(this.active||this.queue.length);this.timer=null,this.active=null,this.queue=[],n&&(this.log("[nappagochi:speech] speech cleared",{reason:e}),this.notify())}notify(){const e=this.snapshot();for(const n of this.listeners)n(e)}}const ws={celebrate:[{delayMs:70,durationMs:220,startHz:210,endHz:610,gain:.045,wave:"triangle"},{delayMs:760,durationMs:150,startHz:125,endHz:62,gain:.075,wave:"sine"},{delayMs:825,durationMs:90,startHz:520,endHz:760,gain:.025,wave:"sine"}],"reply-roll":[{delayMs:50,durationMs:480,startHz:240,endHz:760,gain:.045,wave:"sine"},{delayMs:560,durationMs:410,startHz:760,endHz:330,gain:.04,wave:"sine"},{delayMs:1440,durationMs:160,startHz:130,endHz:58,gain:.075,wave:"triangle"}],"zap-celebrate":[{delayMs:20,durationMs:310,startHz:150,endHz:300,gain:.04,wave:"triangle"},{delayMs:340,durationMs:310,startHz:210,endHz:420,gain:.045,wave:"triangle"},{delayMs:710,durationMs:1120,startHz:290,endHz:690,gain:.04,wave:"sine"},{delayMs:1900,durationMs:260,startHz:690,endHz:920,gain:.035,wave:"sine"}]};function vs(t){return ws[t]??[]}function Es(t){return t!=="disabled"}class ks{constructor(e){u(this,"enabled",!1);u(this,"context",null);u(this,"createContext");u(this,"log");this.createContext=(e==null?void 0:e.createContext)??(()=>{const n=globalThis.AudioContext;return typeof n=="function"?new n:null}),this.log=(e==null?void 0:e.logger)??((n,o)=>console.log(n,o??{}))}isEnabled(){return this.enabled}setEnabled(e,n){if(this.enabled=e,this.log("[nappagochi:sound] preference changed",{enabled:e}),e){(n==null?void 0:n.unlock)!==!1&&this.unlock();return}const o=this.context;this.context=null,o&&o.state!=="closed"&&o.close()}async unlock(){if(!this.enabled)return!1;if(this.context??(this.context=this.createContext()),!this.context)return this.log("[nappagochi:sound] Web Audio unavailable"),!1;if(this.context.state==="suspended")try{await this.context.resume()}catch{return this.log("[nappagochi:sound] audio unlock deferred until another gesture"),!1}return this.context.state==="running"}async play(e){const n=vs(e);if(!this.enabled||!n.length)return!1;if(this.context??(this.context=this.createContext()),!this.context)return this.log("[nappagochi:sound] Web Audio unavailable"),!1;if(this.context.state!=="running")return this.log("[nappagochi:sound] reaction sound skipped; audio not ready",{reaction:e,contextState:this.context.state}),this.unlock(),!1;for(const o of n)this.scheduleTone(this.context,o);return this.log("[nappagochi:sound] reaction sound scheduled",{reaction:e,cueCount:n.length}),!0}destroy(){this.enabled=!1;const e=this.context;this.context=null,e&&e.state!=="closed"&&e.close()}scheduleTone(e,n){const o=e.currentTime+n.delayMs/1e3,r=o+n.durationMs/1e3,i=e.createOscillator(),s=e.createGain();i.type=n.wave,i.frequency.setValueAtTime(n.startHz,o),i.frequency.exponentialRampToValueAtTime(n.endHz,r),s.gain.setValueAtTime(1e-4,o),s.gain.exponentialRampToValueAtTime(n.gain,o+.018),s.gain.exponentialRampToValueAtTime(1e-4,r),i.connect(s),s.connect(e.destination),i.start(o),i.stop(r+.03)}}class xs{constructor(e){u(this,"cache",new Map);u(this,"inFlight",new Map);u(this,"lookupProfile");u(this,"now");u(this,"timeoutMs");u(this,"cacheTtlMs");u(this,"schedule");u(this,"cancel");u(this,"log");this.lookupProfile=e.lookupProfile,this.timeoutMs=Math.max(100,e.timeoutMs??900),this.cacheTtlMs=Math.max(1e3,e.cacheTtlMs??10*6e4),this.now=e.now??Date.now,this.schedule=e.schedule??((n,o)=>setTimeout(n,o)),this.cancel=e.cancel??(n=>clearTimeout(n)),this.log=e.logger??((n,o)=>console.log(n,o??{}))}async enrichApprovedReaction(e){if(!e.reactionAccepted||!e.actorPubkey)return this.log("[nappagochi:enrichment] metadata lookup skipped",{reactionId:e.reactionId,reactionAccepted:e.reactionAccepted,hasActor:!!e.actorPubkey}),null;const n=this.cache.get(e.actorPubkey);if(n&&n.expiresAt>this.now())return this.log("[nappagochi:enrichment] metadata cache hit",{reactionId:e.reactionId,actorPubkey:e.actorPubkey,hasName:!!n.actor.name}),n.actor;this.log("[nappagochi:enrichment] approved reaction metadata lookup started",{reactionId:e.reactionId,actorPubkey:e.actorPubkey,timeoutMs:this.timeoutMs});const o=this.inFlight.get(e.actorPubkey)??this.startLookup(e.actorPubkey);try{const r=await this.withTimeout(o);return this.log("[nappagochi:enrichment] metadata lookup completed",{reactionId:e.reactionId,actorPubkey:e.actorPubkey,hasName:!!r.name,hasPicture:!!r.picture}),r}catch(r){return this.log("[nappagochi:enrichment] metadata lookup ended without enrichment",{reactionId:e.reactionId,actorPubkey:e.actorPubkey,reason:r instanceof Error?r.message:"lookup-failed"}),{pubkey:e.actorPubkey}}}startLookup(e){const n=this.lookupProfile(e).then(o=>{const r={pubkey:e,name:oo(o==null?void 0:o.displayName)||oo(o==null?void 0:o.name)||void 0,picture:$s(o==null?void 0:o.picture)};return this.cache.set(e,{actor:r,expiresAt:this.now()+this.cacheTtlMs}),r}).finally(()=>this.inFlight.delete(e));return this.inFlight.set(e,n),n}withTimeout(e){return new Promise((n,o)=>{const r=this.schedule(()=>o(new Error("metadata-timeout")),this.timeoutMs);e.then(i=>{this.cancel(r),n(i)},i=>{this.cancel(r),o(i)})})}}function oo(t){return typeof t=="string"?t.trim().replace(/\s+/g," ").slice(0,40):""}function $s(t){if(typeof t=="string")try{const e=new URL(t);return e.protocol==="https:"?e.href:void 0}catch{return}}function Is(t){const e=t.filter(s=>s.assessed!==!1),n=e.filter(s=>s.point).length,o=e.length,r=o>0?n/o:0,i=r===1?"excellent":r>=.75?"healthy":r>=.5?"attention":"incomplete";return{score:n,max:o,tier:i}}const As=1e3;function Rs(t,e=As){return new Promise(n=>{let o=!1,r=null,i=null;const s=a=>{o||(o=!0,i!==null&&clearTimeout(i),r==null||r(),n(a))};i=setTimeout(()=>s({}),Math.max(0,e));try{r=t.onSchemaError(()=>s({}))}catch{}if(!o)try{t.get().then(a=>s(a??{}),()=>s({}))}catch{s({})}})}const Rn="nostr.pet.birth.v1",Ss="nostr.pet.profile.v1:",et=86400,un=7*et,Sn=600,Ms=8,Os=2500,Zo="https://github.com/dergigi/napplet-workshop/tree/master/profile-health",Ps=new Set([0,3,10002,10019,10050,17375,37375]),ro=["name","displayName","about","picture","banner"],Cs=new Set(["blossom.primal.net","cdn.satellite.earth","files.v0l.io","blossom.oxtr.dev","blossom.band","media.nostr.build"]),Go=["wss://relay.damus.io","wss://nos.lol","wss://relay.primal.net","wss://relay.snort.social"],Ts=Math.floor(Date.now()/1e3),xe={base:"momo-01",palette:"peach",eyes:"round",accessory:"none"},fn={colors:{background:"#fff7e9",text:"#30241f",primary:"#ef6b55"}},Z={happy:{label:"Thriving",face:"^",note:"Bright-eyed and delighted to see you.",next:"Content after 3 quiet days"},content:{label:"Content",face:"•",note:"Cozy, calm, and still feeling connected.",next:"Lonely after 7 quiet days"},lonely:{label:"Lonely",face:"﹏",note:"Missing your voice on Nostr.",next:"Sick after 14 quiet days"},sick:{label:"Sick",face:"×",note:"A normal post is no longer enough. Save your pet with medicine.",next:"Critical after 30 quiet days"},critical:{label:"Critical",face:"—",note:"Time matters. A thoughtful message can still save your pet.",next:"Dies after 45 quiet days"},dead:{label:"Remembered",face:"·",note:"This life is complete. Its history cannot be rewritten.",next:"You may adopt a new pet"}},hn={score:0,max:Ms,tier:"incomplete",checks:[]},kt=document.querySelector("#app");if(!kt)throw new Error("Missing app root");let re="",Re="",M="",Mn=[],ke=[],J=[],Ne=[],tt=new Set,E=null,nt={...xe},pn=null,yn=0,p=null,H={...hn},ce="pending",De=[],pe=[],Ke="pending",Pe=!1,ht=!0,V=!1,L="",q=null,ee=!1,Oe=!1,te=null,ve=[],Se=null,zt=!1,x=Ot({}),Ct=null,Tt=null,pt=null,Ko=!1,mn=null,vt=null,Ee=0,U=null,Me=null,yt=null,me=null,mt=0,Le=!1;const gt=new Set;let ge=null,be=null,Ge=null,Bt=0;const xt=new gi({reducedMotion:()=>window.matchMedia("(prefers-reduced-motion: reduce)").matches}),ot=new bs,At=new ks,Bs=new xs({lookupProfile:da});function z(){return Math.floor(Date.now()/1e3)}function _(t){return String(t??"").replaceAll("&","&amp;").replaceAll("<","&lt;").replaceAll(">","&gt;").replaceAll('"',"&quot;").replaceAll("'","&#039;")}function Xo(t){return t?`${t.slice(0,7)}…${t.slice(-5)}`:"signed out"}function On(t){if(!/^[0-9a-f]{64}$/i.test(t))return t;try{return zr(t.toLowerCase())}catch{return t}}function Ns(t){const e=On(t);return e.startsWith("npub1")?`${e.slice(0,12)}…${e.slice(-8)}`:Xo(t)}function st(){return di(Re,re)}function Nt(){return!!(re&&M===re&&!st())}function io(t,e){var n;return(n=t.tags.find(o=>o[0]===e))==null?void 0:n[1]}function Ls(t){return t.tags.some(e=>e[0]==="e")}function Pn(t){return t==="peach"||t==="mint"||t==="night"}function Wo(t){return t==="round"||t==="sleepy"||t==="sparkle"}function Jo(t){return t==="none"||t==="bow"||t==="hat"}function Qo(t){if(!t||typeof t!="object")return{...xe};const e=t;return{base:"momo-01",palette:Pn(e.palette)?e.palette:"peach",eyes:Wo(e.eyes)?e.eyes:"round",accessory:Jo(e.accessory)?e.accessory:"none"}}function Y(t){return typeof t=="string"?t.trim():""}function Xe(t,...e){return t.filter(n=>e.includes(n.kind)).sort((n,o)=>o.created_at-n.created_at)[0]??null}function er(t){if(!t)return null;try{const e=JSON.parse(t.content);return{name:Y(e.name),displayName:Y(e.display_name)||Y(e.displayName),about:Y(e.about),picture:Y(e.picture),banner:Y(e.banner),nip05:Y(e.nip05),lud16:Y(e.lud16),website:Y(e.website)}}catch{return null}}function _s(t){if(!t)return null;const e={};for(const n of t.tags){if(n[0]!=="r"||!n[1])continue;const o=n[2];e[n[1]]={read:o!=="write",write:o!=="read"}}return e}function qs(t){return t?[...new Set(t.tags.filter(e=>e[0]==="p"&&e[1]).map(e=>e[1]))]:null}function Cn(t){const e=t.trim().toLowerCase(),n=e.includes("@")?e.split("@"):["_",e];return n.length!==2||!n[0]||!/^[a-z0-9.-]+$/i.test(n[1])||!n[1].includes(".")?null:{name:n[0],domain:n[1]}}async function so(){try{(await Mr.open(Zo,{label:"Open Gigi's Profile Health project"})).status==="opened"?(L="Link sent to Paja. If no tab opened, use the project address shown here.",w()):(L="The shell did not open the Habitat source.",w())}catch{L="The Habitat source is unavailable in this shell.",w()}}async function tr(t){const e=new AbortController,n=window.setTimeout(()=>e.abort(),Os);try{return await Sr.bytes(t,{signal:e.signal})}finally{window.clearTimeout(n)}}async function nr(t){const e=await tr(t),n=JSON.parse(await e.text());if(!n||typeof n!="object"||Array.isArray(n))throw new Error("Invalid JSON response");return n}async function Hs(t,e){if(!t)return{label:"NIP-05",status:"fail",detail:"Not set",point:!1};const n=Cn(t);if(!n)return{label:"NIP-05",status:"warn",detail:`${t} is not a valid identifier`,point:!1};try{const r=(await nr(`https://${n.domain}/.well-known/nostr.json?name=${encodeURIComponent(n.name)}`)).names;return(r&&typeof r=="object"?r[n.name]:void 0)===e?{label:"NIP-05",status:"pass",detail:t,point:!0}:{label:"NIP-05",status:"warn",detail:`${t} does not resolve to this profile`,point:!1}}catch{return{label:"NIP-05",status:"unavailable",detail:`${t} could not be assessed in this runtime`,point:!1,assessed:!1}}}async function Ds(t){if(!t)return{label:"Lightning address",status:"fail",detail:"Not set",point:!1};const e=Cn(t);if(!e||e.name==="_")return{label:"Lightning address",status:"warn",detail:`${t} is not valid`,point:!1};try{const n=await nr(`https://${e.domain}/.well-known/lnurlp/${encodeURIComponent(e.name)}`);return Y(n.callback)?{label:"Lightning address",status:"pass",detail:t,point:!0}:{label:"Lightning address",status:"warn",detail:`${t} returned no callback`,point:!1}}catch{return{label:"Lightning address",status:"unavailable",detail:`${t} could not be assessed in this runtime`,point:!1,assessed:!1}}}function Fs(t){const e=Cn(t);return(e==null?void 0:e.name)==="_"?e.domain:""}function Us(t){return t<1024?`${t} B`:t<1024*1024?`${(t/1024).toFixed(0)} KB`:`${(t/(1024*1024)).toFixed(1)} MB`}async function ao(t,e,n){if(!e)return{label:t,status:"fail",detail:"Not set",point:!1};let o;try{if(o=new URL(e),o.protocol!=="https:")throw new Error("Unsupported URL")}catch{return{label:t,status:"fail",detail:"Invalid URL",point:!1}}try{const r=await tr(e),i=o.hostname.toLowerCase(),s=Cs.has(i)?"Blossom":n&&i===n?"own domain":"third-party host",a=r.size>1024*1024,l=s!=="third-party host";return{label:t,status:l&&!a?"pass":"warn",detail:`${s} · ${Us(r.size)}${a?" · large file":""}`,point:l}}catch{return{label:t,status:"unavailable",detail:"Could not assess the image in this runtime",point:!1,assessed:!1}}}function zs(t){if(!t)return{label:"Profile",status:"fail",detail:"No kind 0 profile found",point:!1};const e=ro.filter(o=>Y(t[o])).length,n=ro.length-e;return{label:"Profile",status:e>=3?"pass":e>0?"warn":"fail",detail:`${e}/5 fields${n?` · ${n} missing`:" · complete"}`,point:e>0}}function Ys(t,e){const n=Object.values(t),o=n.filter(s=>s.read).length,r=n.filter(s=>s.write).length,i=(e==null?void 0:e.tags.filter(s=>s[0]==="relay"&&s[1]).length)??0;return{label:"Relay setup",status:n.length>=2?i?"pass":"warn":n.length?"warn":"fail",detail:`${n.length} public · ${o} read · ${r} write · ${i?`${i} DM`:"no DM list"}`,point:n.length>=2}}function Vs(t){return t.length?{label:"Follow list",status:"pass",detail:`${t.length} ${t.length===1?"follow":"follows"}`,point:!0}:{label:"Follow list",status:"fail",detail:"No follows found",point:!1}}function js(t,e){return t?{label:"NIP-60 wallet",status:e?"pass":"warn",detail:`${t.kind===37375?"legacy wallet":"wallet found"} · ${e?"nutzaps ready":"no nutzap info"}`,point:!0}:{label:"NIP-60 wallet",status:"fail",detail:"No wallet event found",point:!1}}async function Zs(t,e,n,o,r){const i=Fs(Y(e==null?void 0:e.nip05)),[s,a,l,d]=await Promise.all([Hs(Y(e==null?void 0:e.nip05),t),ao("Profile picture",Y(e==null?void 0:e.picture),i),ao("Banner",Y(e==null?void 0:e.banner),i),Ds(Y(e==null?void 0:e.lud16))]),f=[zs(e),s,a,l,d,Ys(o,Xe(r,10050)),Vs(n),js(Xe(r,17375,37375),Xe(r,10019))];return{...Is(f),checks:f}}function Gs(t){if(t.kind!==78||io(t,"d")!==Rn||t.created_at>z()+Sn)return null;try{const e=JSON.parse(t.content);if(e.v!==1||e.species!=="momo")return null;const n=String(e.name??"").trim().slice(0,28);return n?{event:t,previousId:io(t,"e"),data:{v:1,name:n,species:"momo",appearance:Qo(e.appearance),ruleset:"gentle-v1"}}:null}catch{return null}}function Ks(t,e){return Ne.filter(n=>Ps.has(n.kind)&&n.created_at>=t.event.created_at&&n.created_at<=e).reduce((n,o)=>Math.max(n,o.created_at),t.event.created_at)}function Xs(t,e){return J.filter(n=>tt.has(n.id)&&n.created_at>=t.event.created_at&&n.created_at<=e).reduce((n,o)=>Math.max(n,o.created_at),t.event.created_at)}function at(t,e){const n=Zr({birthCreatedAt:t.event.created_at,ownerPubkey:M,notes:J,verifiedMedicineIds:tt,at:e,daySeconds:et}),o=ai({incomplete:ce==="ready"&&H.tier==="incomplete",birthCreatedAt:t.event.created_at,lastHabitatChangeAt:Ks(t,e),lastMedicineAt:Xs(t,e),at:e,daySeconds:et});return{...n,state:li(n.state,o.sick),activityState:n.state,canFeed:n.canFeed&&!o.sick,habitatSick:o.sick,habitatDaysIncomplete:o.daysIncomplete}}function Tn(){const t=[...ke].sort((o,r)=>o.event.created_at-r.event.created_at||o.event.id.localeCompare(r.event.id));if(!t.length)return null;let e=t.find(o=>!o.previousId)??t[0];const n=new Set([e.event.id]);for(;;){const o=t.find(r=>!n.has(r.event.id)&&r.previousId===e.event.id&&r.event.created_at>=e.event.created_at&&at(e,r.event.created_at).state==="dead");if(!o)return e;e=o,n.add(e.event.id)}}async function Bn(t){const e=ii(t,M);if(!e.filters.length)return new Set;try{const n=await Ce(e.filters,{authors:e.authors,...!x.localRelayOnly&&e.relays.length?{relays:e.relays}:{},limit:e.targets.length,timeoutMs:4e3});return si(e,n.events.map(o=>o.event),M)}catch{return new Set}}function or(t){return`${Ss}${t}`}async function Ws(t){try{const e=await Ce([{authors:[M],kinds:[30078],"#d":[or(t.event.id)],limit:20}],{authors:[M],limit:20,timeoutMs:5e3});Pe||(Pe=!!e.incomplete);const n=e.events.map(r=>r.event).filter(r=>r.created_at<=z()+Sn).sort((r,i)=>i.created_at-r.created_at||i.id.localeCompare(r.id))[0];if(!n)return t.data.appearance;const o=JSON.parse(n.content);return Qo(o.appearance)}catch{return t.data.appearance}}async function Js(){try{const t=await Fe.getItem("pet-preview-state");return t&&t in Z?t:null}catch{return null}}async function lo(t){try{t?await Fe.setItem("pet-preview-state",t):await Fe.removeItem("pet-preview-state")}catch{}}async function Qs(){try{const t=await Fe.getItem("pet-care-panel-visibility");(t==="hidden"||t==="shown")&&(ee=t==="hidden",console.log("[nappagochi:layout] care panel preference restored",{hidden:ee}))}catch{}}async function ea(){try{await Fe.setItem("pet-care-panel-visibility",ee?"hidden":"shown"),console.log("[nappagochi:layout] care panel preference saved",{hidden:ee})}catch{}}function rr(){ee=!ee,console.log("[nappagochi:layout] care panel visibility changed",{hidden:ee}),ea(),w()}async function ta(){var t;if((t=window.napplet)!=null&&t.keys)try{const e=await Ar.register({id:"pet.toggle-care-panel",label:"Toggle pet care panel",defaultKey:"Alt+P"},rr);Ko?e.close():pt=e}catch(e){console.log("[nappagochi:degradation] keyboard action unavailable; use the panel button",{reason:e instanceof Error?e.message:"keys-unavailable"})}}async function na(){Oe=!0;try{Oe=Es(await Fe.getItem("pet-sound-effects"))}catch{}At.setEnabled(Oe,{unlock:!1})}async function oa(){try{await Fe.setItem("pet-sound-effects",Oe?"enabled":"disabled")}catch{}}function ir(){Oe&&At.unlock()}const ra=(t,e,n)=>{var r,i;if(x.localRelayOnly)return yo.subscribe(t.filters,e,()=>{},{relay:x.localRelayUrl});const o=It.subscribe(t.filters,{...(r=t.authors)!=null&&r.length?{authors:t.authors}:{},...(i=t.relays)!=null&&i.length?{relays:t.relays}:{},limit:t.limit,timeoutMs:t.timeoutMs});return o.on("event",e),o.on("closed",n),o};function sr(){U==null||U.closeChannel("owner-activity"),U==null||U.closeChannel("inbound-engagement")}function ar(){me!==null&&window.clearTimeout(me),me=null,mt=0,Le=!1,gt.clear()}function ia(t){if(t.state==="closed"&&t.reason==="replaced-or-closed")return;t.state==="open"?gt.delete(t.id):gt.add(t.id);const e=Le;if(Le=gt.size>0,!Le)mt=0,me!==null&&window.clearTimeout(me),me=null;else if(me===null){const n=bi(mt);if(n===null){console.log("[nappagochi:degradation] live channel retries exhausted",{failedChannels:[...gt]}),e!==Le&&w();return}mt+=1,console.log("[nappagochi:degradation] live channel retry scheduled",{channelId:t.id,reason:t.reason??"closed",attempt:mt,delayMs:n}),me=window.setTimeout(()=>{me=null,M&&ke.length&&lr()},n)}e!==Le&&w()}function lr(){if(sr(),!U||!M||!ke.length){console.log("[nappagochi:live] owner activity channel not started",{hasSession:!!U,hasOwner:!!M,hasBirth:ke.length>0});return}const t={id:"owner-activity",filters:[{authors:[M],kinds:[1]}],authors:[M],...pe.length?{relays:pe}:{},limit:200,timeoutMs:5e3};U.replaceChannel(t),U.replaceChannel({id:"inbound-engagement",filters:[{"#p":[M]}],...pe.length?{relays:pe}:{},limit:500,timeoutMs:5e3})}function sa(){if(vt!==null){console.log("[nappagochi:projection] activity refresh already scheduled",{ownerPubkey:M,generation:Ee});return}const t=Ee,e=M,n=E==null?void 0:E.event.id;console.log("[nappagochi:projection] activity invalidated by live signal",{ownerPubkey:e,birthId:n,generation:t,debounceMs:250}),vt=window.setTimeout(()=>{vt=null,aa(t,e,n)},250)}async function aa(t,e,n){if(!(!e||!n)){console.log("[nappagochi:projection] activity history refresh started",{ownerPubkey:e,birthId:n,generation:t});try{const o=await Ce([{authors:[e],kinds:[1],limit:500}],{authors:[e],limit:500,timeoutMs:8e3});if(t!==Ee||e!==M||n!==(E==null?void 0:E.event.id)){console.log("[nappagochi:projection] stale activity refresh discarded",{ownerPubkey:e,birthId:n,requestedGeneration:t,activeGeneration:Ee});return}if(J=wn(J,o.events.map(r=>r.event)),tt=await Bn(J),t!==Ee||e!==M)return;E&&(p=at(E,z())),Pe=Pe||!!o.incomplete,console.log("[nappagochi:projection] activity history refresh applied",{ownerPubkey:e,birthId:n,generation:t,noteCount:J.length,verifiedMedicineCount:tt.size,healthState:(p==null?void 0:p.state)??null,incomplete:!!o.incomplete}),w()}catch(o){console.log("[nappagochi:projection] activity history refresh failed; last projection retained",{ownerPubkey:e,birthId:n,generation:t,reason:o instanceof Error?o.message:"unknown-error"})}}}function la(t){var i,s;const{channelId:e,event:n,receivedAt:o}=t,r=e==="owner-activity"?n.pubkey===M?ls({event:n,receivedAt:o}):null:e==="inbound-engagement"?cs({event:n,ownerPubkey:M,receivedAt:o}):null;if(!r){console.log("[nappagochi:live] accepted delivery produced no reaction signal",{channelId:e,eventId:n.id,kind:n.kind});return}console.log("[nappagochi:live] reaction signal classified",{signalId:r.id,eventId:r.eventId,type:r.type,actorPubkey:r.actorPubkey,zapAmountSats:(i=r.zap)==null?void 0:i.amountSats,zapSenderPubkey:(s=r.zap)==null?void 0:s.senderPubkey}),Me==null||Me.push(r),e==="owner-activity"&&sa()}async function cr(t=!0){t&&(tt=await Bn(J)),E=Tn(),E&&(p=at(E,z())),w()}async function ca(t){if(x.localRelayOnly)return{[x.localRelayUrl]:{read:!0,write:!0}};if(!t)return{};try{return await Je.getRelays()}catch{return{}}}async function Ce(t,e){const n=pe.length&&!x.localRelayOnly?{...e,relays:Nn([...(e==null?void 0:e.relays)??[],...pe])}:e;return ni(x,o=>yo.query(o),(o,r)=>It.query(o,r),t,n)}async function da(t){try{const r=await Or.getProfile(t);if(console.log("[nappagochi:enrichment] NAP-COMMON profile lookup returned",{actorPubkey:t,ok:r.ok,hasProfile:!!r.profile}),r.ok)return r.profile??null}catch(r){console.log("[nappagochi:enrichment] NAP-COMMON profile lookup failed",{actorPubkey:t,reason:r instanceof Error?r.message:"lookup-failed"})}console.log("[nappagochi:enrichment] using outbox kind 0 fallback",{actorPubkey:t});const n=(await It.query([{authors:[t],kinds:[0],limit:1}],{authors:[t],limit:1,timeoutMs:700})).events.map(r=>r.event).filter(r=>r.kind===0&&r.pubkey===t).sort((r,i)=>i.created_at-r.created_at)[0]??null,o=er(n);return o?{...o}:null}async function ua(t){var n;if(x.localRelayOnly){pe=[x.localRelayUrl],Ke="local-only";return}if(!x.localRelayMirror){pe=[],Ke="normal";return}let e=null;try{e=await It.resolveRelays({authors:[t],direction:"read"})}catch{e=null}pe=ei(x,e,Go),Ke=(e==null?void 0:e.source)==="nip65"&&(((n=e.missingAuthors)==null?void 0:n.length)??0)===0?"nip65":"fallback"}async function fa(){x=Ot({});try{const t=await Rs(Rr);x=Ot(t)}catch{x=Ot({})}}function We(t,e){return t===Ee&&e===M}async function ha(t,e,n,o){try{const r=yn,i=x.localRelayOnly||!n?Promise.resolve(null):Je.getProfile().catch(ue=>(console.log("[nappagochi:degradation] identity profile unavailable; using outbox metadata",{reason:ue instanceof Error?ue.message:"profile-unavailable"}),null)),s=x.localRelayOnly||!n?Promise.resolve([]):Je.getFollows().catch(()=>[]),a=ca(n),l=Ce([{authors:[e],kinds:[0,3,10002,10019,10050,17375,37375],limit:20}],{authors:[e],limit:20,timeoutMs:8e3}),d=E?Ws(E):Promise.resolve({...xe}),f=st()?Promise.resolve(null):Js(),[c,y,b,R,O,D]=await Promise.all([i,s,a,l,d,f]);if(!We(t,e))return;Ne=R.events.map(ue=>ue.event);const K=Xe(Ne,10002),$e=er(Xe(Ne,0)),de=qs(Xe(Ne,3)),Ue=$e??c,Be=de??y,ze=_s(K)??b,Gt=await Zs(e,Ue,Be,ze,Ne);if(!We(t,e))return;if(Mn=Be,!n)De=[];else if(x.localRelayOnly)De=[x.localRelayUrl];else{const ue=Object.entries(b).filter(([,ie])=>ie.write).map(([ie])=>ie);De=Nn([...x.localRelayMirror?[x.localRelayUrl]:[],...ue.length?ue:Go])}Pe||(Pe=!!R.incomplete),H=Gt,ce="ready",r===yn&&(nt=O),te=D,E=Tn(),p=E?at(E,z()):null,console.log("[nappagochi:startup] optional details hydrated",{ownerPubkey:e,elapsedMs:Math.round(performance.now()-o),profileTier:H.tier}),w()}catch(r){if(!We(t,e))return;ce="unavailable",console.log("[nappagochi:degradation] optional startup details unavailable",{ownerPubkey:e,reason:r instanceof Error?r.message:"detail-sync-failed"}),w()}}async function $t(){const t=++Ee,e=performance.now();Bt+=1,ht=!0,L="",Pe=!1,ce="pending",H={...hn},M=Re||re,ar(),sr(),w();try{if(re=await Je.getPublicKey(),t!==Ee)return;if(Re&&Re===re&&(Re=""),M=Re||re,!M){Mn=[],ke=[],J=[],Ne=[],E=null,p=null,H={...hn},ce="pending",De=[],pe=[],Ke="pending",ht=!1,w();return}const n=M,o=n===re;if(await ua(n),!We(t,n))return;const r=Ce([{authors:[n],kinds:[78],"#d":[Rn],limit:100}],{authors:[n],limit:100,timeoutMs:6e3}),i=Ce([{authors:[n],kinds:[1],limit:500}],{authors:[n],limit:500,timeoutMs:8e3}),[s,a]=await Promise.all([r,i]);if(!We(t,n)||(Pe=!!(s.incomplete||a.incomplete),ke=s.events.map(l=>Gs(l.event)).filter(l=>!!l),J=a.events.map(l=>l.event),tt=await Bn(J),!We(t,n)))return;E=Tn(),p=E?at(E,z()):null,nt=E?E.data.appearance:{...xe},te=null,lr(),ht=!1,console.log("[nappagochi:startup] core pet visible",{ownerPubkey:n,elapsedMs:Math.round(performance.now()-e),hasPet:!!E}),w(),ha(t,n,o,e)}catch(n){if(t!==Ee)return;L=n instanceof Error?n.message:"The Nostr history could not be loaded.",ce="unavailable",ht=!1,w()}}function Nn(t){return[...new Set(t.map(e=>e.trim()).filter(e=>/^wss?:\/\/[^/\s]+/i.test(e)))]}function dr(t){return t==="excellent"?"Excellent":t==="healthy"?"Healthy":t==="attention"?"Needs attention":"Incomplete"}function pa(t){return ce!=="ready"?Z[t]:t==="sick"&&(p!=null&&p.habitatSick)&&(p.activityState==="happy"||p.activityState==="content"||p.activityState==="lonely")?{label:"Sick",note:`Its habitat has remained incomplete for ${we} days. Medicine can help it recover.`}:t==="happy"?H.tier==="excellent"?{label:"Radiant",note:"Bright-eyed, active, and flourishing in an excellent Nostr habitat."}:H.tier==="healthy"?Z.happy:H.tier==="attention"?{label:"Unsettled",note:"Active and safe, but its Nostr habitat could use a little care."}:{label:"Fragile",note:"Active and alive, though its Nostr habitat is still very sparse."}:t==="content"?H.tier==="excellent"||H.tier==="healthy"?Z.content:H.tier==="attention"?{label:"Unsettled",note:"Cozy for now, with a few gaps in its Nostr habitat."}:{label:"Fragile",note:"Calm for now, but its Nostr habitat needs more support."}:Z[t]}function ya(t){return new Intl.DateTimeFormat(void 0,{dateStyle:"medium"}).format(t*1e3)}function ur(t){const e=Math.max(0,z()-t);return e<60?"just now":e<3600?`${Math.floor(e/60)}m ago`:e<et?`${Math.floor(e/3600)}h ago`:`${Math.floor(e/et)}d ago`}function ma(){return te??(p==null?void 0:p.state)??"happy"}function rt(t,e,n=Z[t].label){const o=e.accessory==="bow"?'<span class="pet-accessory bow" aria-hidden="true">◆</span>':e.accessory==="hat"?'<span class="pet-accessory hat" aria-hidden="true"></span>':"",r=e.eyes==="sleepy"?"⌒":e.eyes==="sparkle"?"✦":"●",i=Ao(vn({condition:t})),s=ot.snapshot().utterance;return`
    <span class="pet-speech${s?" pet-speech--visible":""}" role="status"
      aria-live="polite">${s?_(s.text):""}</span>
    <div class="pet pet--${t} palette--${e.palette}" style="${i}" role="img"
      aria-label="${_(n)} Nostr pet">
      <span class="pet-shadow"></span>
      <span class="pet-turner">
        <span class="pet-face pet-face--front">
          <span class="pet-ear pet-ear--left"></span>
          <span class="pet-ear pet-ear--right"></span>
          <span class="pet-body">
            ${o}
            <span class="pet-cheek pet-cheek--left"></span>
            <span class="pet-cheek pet-cheek--right"></span>
            <span class="pet-eye pet-eye--left">${r}</span>
            <span class="pet-eye pet-eye--right">${r}</span>
            <span class="pet-mouth">${Z[t].face}</span>
            <span class="pet-patch"></span>
          </span>
          <span class="pet-signal" aria-hidden="true">⌁</span>
        </span>
        <span class="pet-face pet-face--back" aria-hidden="true">
          <span class="pet-ear pet-ear--left"></span>
          <span class="pet-ear pet-ear--right"></span>
          <span class="pet-back-body">
            ${o}
            <span class="pet-back-patch"></span>
            <span class="pet-tail"></span>
          </span>
        </span>
      </span>
    </div>
  `}function fr(){return st()?`
    <section class="viewer-banner" aria-label="Read-only pet view">
      <span>
        <strong>Read-only view</strong>
        This pet belongs to <code>${_(On(M))}</code>.
        Your connected signer has not changed.
      </span>
      <button class="secondary-button" type="button" data-action="view-own-pet">
        ${re?"Back to my pet":"Stop viewing"}
      </button>
    </section>
  `:""}function ga(){const t=x.localRelayOnly?"Finding your pet on the local relay…":x.localRelayMirror?"Finding your pet through NIP-65 and the local mirror…":"Finding your pet across Nostr…",e=x.localRelayOnly?"Public relay discovery is disabled for this debug session.":x.localRelayMirror?"If NIP-65 is unavailable, the shell also checks the local and public fallback relays.":"Birth, activity, and appearance events are being reconciled.";return`
    <section class="loading-card">
      <div class="loading-orbit" aria-hidden="true"><span></span></div>
      <p>${t}</p>
      <small>${e}</small>
    </section>
  `}function ba(){return`
    <section class="welcome-card">
      <div class="mini-pet">${rt("content",xe)}</div>
      <p class="eyebrow">Tied to your Nostr posts</p>
      <h1>Connect your Nostr signer</h1>
      <div class="sign-in-status" role="status">
        <span class="status-pulse" aria-hidden="true"></span>
        <span><strong>Waiting for a signer</strong><small>NIP-07 on desktop · Amber via Bunker on Android.</small></span>
      </div>
      <div class="viewer-entry">
        <strong>Or view a public pet without signing in</strong>
        <span>Paste an npub to inspect its Nostr-derived condition in read-only mode.</span>
        ${yr("signed-out-view-form")}
      </div>
    </section>
  `}function hr(t){const e=!!t;return`
    <section class="adoption-layout">
      <div class="adoption-art">
        ${rt("happy",xe)}
        <span class="spark spark--one">✦</span>
        <span class="spark spark--two">·</span>
      </div>
      <form id="adopt-form" class="adoption-card" novalidate>
        <p class="eyebrow">${e?"A new chapter":x.localRelayOnly?"No pet found on the local relay":x.localRelayMirror?"No pet found through NIP-65, local, or public relays":"No pet found for this npub"}</p>
        <h1>${e?"Adopt another pet":"Meet your Nostr companion"}</h1>
        <p>${e?`${_(t==null?void 0:t.data.name)} stays in your history. This creates a separate life.`:"Its birthday will be the timestamp of a signed Nostr birth event."}</p>
        <label>
          Pet name
          <input
            name="name"
            value="Momo"
            maxlength="28"
            autocomplete="off"
            aria-describedby="pet-name-help"
            required
          />
          <small id="pet-name-help">Momo is ready, or type another name.</small>
        </label>
        <fieldset>
          <legend>First color</legend>
          <div class="swatches">
            ${pr("peach")}
          </div>
        </fieldset>
        <button class="primary-button" type="button" data-submit="adopt" ${V?"disabled":""}>
          ${V?"Creating signed event…":"Adopt this pet"}
        </button>
        <button class="secondary-button" type="button" data-action="view-pet">
          View another pet
        </button>
        <small>
          You will approve a kind 78 event in your Nostr host. Paja chooses relays
          first; fallbacks are tried only when its relay list is unavailable.
        </small>
      </form>
    </section>
  `}function wa(){return`
    ${fr()}
    <section class="adoption-layout viewed-empty-layout">
      <div class="adoption-art">
        ${rt("lonely",xe)}
      </div>
      <div class="adoption-card">
        <p class="eyebrow">No signed pet birth found</p>
        <h1>This npub has no visible pet</h1>
        <p>
          The local and selected Nostr relays did not return a valid
          <strong>nostr.pet.birth.v1</strong> event for this account.
        </p>
        <button class="primary-button" type="button" data-action="view-pet">
          View another npub
        </button>
        <button class="secondary-button" type="button" data-action="view-own-pet">
          ${re?"Back to my pet":"Stop viewing"}
        </button>
      </div>
    </section>
  `}function pr(t){return[{id:"peach",label:"Peach"},{id:"mint",label:"Mint"},{id:"night",label:"Night"}].map(({id:n,label:o})=>`
        <label class="swatch swatch--${n}">
          <input type="radio" name="palette" value="${n}" ${t===n?"checked":""} />
          <span aria-hidden="true"></span>
          ${o}
        </label>`).join("")}function va(){if(!E||!p)return hr();p.state==="dead"&&q===null&&ke.length>0;const t=ma(),e=Z[t],n=te?e:pa(t),o=Math.max(0,Math.floor((z()-E.event.created_at)/et)),r=!!te,i=st(),a=!r&&p.habitatSick&&(p.activityState==="happy"||p.activityState==="content"||p.activityState==="lonely")?`Medicine restarts the ${we}-day habitat timer`:e.next,l=p.state==="sick"?p.habitatSick&&p.activityState==="sick"?"Inactivity + habitat":p.habitatSick?"Habitat incomplete":"Kind 1 inactivity":"",d=`<button class="habitat-source-link" type="button" data-action="habitat-source"
    title="View Gigi’s Profile Health source">Habitat</button>`,f=ce==="ready"?`${H.score}/${H.max} · ${_(dr(H.tier))}`:ce==="pending"?"Checking…":"Unavailable",c=i?`<div class="pet-stage pet-stage--readonly">${rt(t,nt,n.label)}</div>`:`<button class="pet-stage" data-action="pet-menu" aria-label="Open pet actions">${rt(t,nt,n.label)}</button>`,y=i?`<div class="view-only-card">
        <strong>Viewing only</strong>
        <span>Care actions and appearance changes are available only to this pet’s signer.</span>
        <button class="secondary-button" type="button" data-action="view-pet">View another npub</button>
      </div>`:`<div class="action-grid">
        <button class="care-button" data-action="note" ${p.state==="dead"?"disabled":""}>
          <span>✎</span><strong>Write a note</strong><small>${p.canFeed?"Feeds your pet":"Keeps your voice active"}</small>
        </button>
        <button class="care-button care-button--doctor" data-action="doctor"
          ${p.state==="dead"?"disabled":""}>
          <span>+</span><strong>SAVE YOUR PET</strong><small>Get medicine</small>
        </button>
      </div>
      <button class="secondary-button view-another-button" type="button" data-action="view-pet">
        View another pet
      </button>`;return`
    ${fr()}
    <section class="pet-layout${ee?" pet-layout--compact":""}">
      <div class="habitat">
        ${Le?'<span class="live-paused-pill habitat-live-status" role="status" title="Live reactions are temporarily unavailable; historical pet state is still active">live paused</span>':""}
        <button class="panel-toggle" type="button" data-action="toggle-panel"
          aria-controls="care-panel" aria-expanded="${ee?"false":"true"}"
          title="${ee?"Show pet details":"Hide pet details"}">
          <span aria-hidden="true">${ee?"‹":"›"}</span>
          <span>${ee?"Show details":"Hide details"}</span>
        </button>
        <div class="ambient-shape ambient-shape--one"></div>
        <div class="ambient-shape ambient-shape--two"></div>
        ${c}
        <div class="state-caption">
          ${r?'<span class="preview-flag">visual preview</span>':""}
          <span class="state-kicker">${_(n.label)}</span>
          <h1>${_(E.data.name)}</h1>
          <p>${_(n.note)}</p>
        </div>
      </div>

      <aside class="care-panel" id="care-panel" ${ee?"hidden":""}>
        <div class="care-heading">
          <div>
            <p class="eyebrow">Today’s pulse</p>
            <h2>${p.state==="dead"?"Memorial":`${p.daysQuiet} quiet ${p.daysQuiet===1?"day":"days"}`}</h2>
          </div>
          ${i?"":'<button class="icon-button" data-action="settings" aria-label="Appearance settings">⚙</button>'}
        </div>

        <div class="vital-track" aria-label="Pet lifecycle">
          ${["happy","content","lonely","sick","critical","dead"].map(b=>`<span class="${b===(p==null?void 0:p.state)?"active":""}" title="${Z[b].label}"></span>`).join("")}
        </div>
        <div class="next-state">
          <span>${_(a)}</span>
          ${i?"":'<button class="text-button" data-action="preview">Preview states</button>'}
        </div>

        ${y}

        <dl class="pet-facts">
          <div><dt>Activity state</dt><dd>${_(Z[p.activityState].label)}</dd></div>
          ${l?`<div><dt>Sickness cause</dt><dd>${_(l)}</dd></div>`:""}
          <div><dt>Born</dt><dd>${ya(E.event.created_at)}</dd></div>
          <div><dt>Age</dt><dd>${o} ${o===1?"day":"days"}</dd></div>
          <div><dt>Last care</dt><dd>${ur(p.lastCareAt)}</dd></div>
          <div>
            <dt>${d}</dt>
            <dd>
              <button class="text-button habitat-link" data-action="profile">
                ${f}
              </button>
            </dd>
          </div>
          <div><dt>Proof</dt><dd>${Xo(E.event.id)}</dd></div>
        </dl>

        ${p.state==="dead"&&!i?'<button class="secondary-button full-width" data-action="adopt-next">Adopt a new pet</button>':""}
      </aside>
    </section>
  `}function Ea(){return Te("Write a Nostr note",`
      <p class="modal-copy">${p!=null&&p.canFeed?"A top-level kind 1 note will feed your pet.":"Your pet is sick, so this note will not heal it. A reply is the medicine."}</p>
      <p class="modal-copy">Paja’s confirmation authorizes the request; your connected signer may prompt separately. Success appears only after the signer returns an event and a relay accepts it.</p>
      <form id="note-form">
        <label>Your note
          <textarea name="content" maxlength="1000" rows="5" placeholder="What’s on your mind?" required></textarea>
        </label>
        <button class="primary-button" type="button" data-submit="note" ${V?"disabled":""}>
          ${V?"Publishing…":"Review and publish"}
        </button>
      </form>
    `)}function ka(){const t=Se==="follows"?"These are recent notes from people you follow.":"No usable follow notes were found, so these are recent public Discover notes—not a universal trending ranking.",e=ve.map((n,o)=>`
        <label class="note-choice">
          <input type="radio" name="candidate" value="${o}" ${o===0?"checked":""} />
          <span>
            <strong title="${_(On(n.event.pubkey))}">${_(Ns(n.event.pubkey))}</strong>
            <small>${ur(n.event.created_at)}</small>
            <em>${_(n.event.content.slice(0,180)||"(media or tag-only note)")}</em>
          </span>
        </label>`).join("");return Te(`Help ${(E==null?void 0:E.data.name)??"your pet"} recover`,zt?'<div class="doctor-loading">Finding recent notes…</div>':ve.length?`
          <p class="modal-copy">Choose a note and add something thoughtful!</p>
          <p class="modal-copy">${t}</p>
          <form id="doctor-form">
            <fieldset class="note-choices">
              <legend>${Se==="follows"?"From your follows":"Discover notes"}</legend>
              ${e}
            </fieldset>
            <label>Your message
              <textarea name="content" maxlength="1000" rows="4" placeholder="Add something thoughtful…" required></textarea>
            </label>
            <button class="primary-button" type="button" data-submit="doctor" ${V?"disabled":""}>
              ${V?"Publishing…":"Publish and give medicine"}
            </button>
          </form>`:`
          <div class="empty-state">
            <strong>No recent public notes found</strong>
            <p>Try again when your shell’s outbox routes have recent public kind 1 notes.</p>
            <button class="secondary-button" data-action="reload-doctor">Try again</button>
          </div>`)}function xa(){return Te("About Habitat",`
      <p class="modal-copy">
        The Habitat score is adapted from Gigi’s Profile Health project.
      </p>
      <button class="primary-button full-width" type="button" data-action="habitat-source-open">
        Open Gigi’s project ↗
      </button>
      <label class="source-address">Project address
        <input type="text" readonly value="${_(Zo)}" />
      </label>
      <p class="modal-copy">
        If Paja does not open a new tab, select and copy the project address above.
      </p>
    `)}function $a(){const t=Kr(nt,pn);return Te("Pet settings",`
      <form id="settings-form">
        <fieldset>
          <legend>Color</legend>
          <div class="swatches">${pr(t.palette)}</div>
        </fieldset>
        <div class="form-columns">
          <label>Eyes
            <select name="eyes">
              ${co(["round","sleepy","sparkle"],t.eyes)}
            </select>
          </label>
          <label>Accessory
            <select name="accessory">
              ${co(["none","bow","hat"],t.accessory)}
            </select>
          </label>
        </div>
        <p class="modal-copy">Saving publishes a replaceable kind 30078 appearance event. It does not alter the birth event.</p>
        <button
          class="primary-button"
          type="button"
          data-submit="settings"
          ${V||(p==null?void 0:p.state)==="dead"?"disabled":""}
        >
          ${(p==null?void 0:p.state)==="dead"?"Memorial appearance is fixed":V?"Saving…":"Save appearance"}
        </button>
      </form>
      <section class="local-setting" aria-labelledby="sound-setting-title">
        <span>
          <strong id="sound-setting-title">Sound effects</strong>
          <small>On by default for posts, replies, and zaps. After opening, tap Nappagochi once to allow audio.</small>
        </span>
        <label class="sound-switch" aria-label="Enable sound effects">
          <input type="checkbox" data-action="toggle-sound" ${Oe?"checked":""}>
          <span aria-hidden="true"></span>
        </label>
      </section>
    `)}function co(t,e){return t.map(n=>`<option value="${n}" ${n===e?"selected":""}>${n[0].toUpperCase()}${n.slice(1)}</option>`).join("")}function Ia(){const t=Object.keys(Z).map(e=>`
        <button class="state-option ${te===e?"active":""}" data-preview="${e}">
          <span class="state-dot state-dot--${e}"></span>
          <span><strong>${Z[e].label}</strong><small>${Z[e].note}</small></span>
        </button>`).join("");return Te("Visual state lab",`
      <p class="modal-copy">Preview only changes the drawing. Your canonical Nostr-derived state remains <strong>${p?Z[p.state].label:"unknown"}</strong>.</p>
      <div class="state-options">${t}</div>
      <button class="secondary-button full-width" data-action="clear-preview">Return to live state</button>
    `)}function Aa(){if(ce!=="ready"){const n=ce==="pending";return Te("Nostr habitat",`
        <div class="empty-state">
          <strong>${n?"Checking your Nostr habitat…":"Habitat check unavailable"}</strong>
          <p>${n?"Your pet is already visible while optional profile and resource checks finish in the background.":"Activity still controls the pet. Try again after the shell reconnects to Nostr."}</p>
        </div>
      `)}const t=H.checks.map(n=>`
        <li class="profile-check profile-check--${n.status}">
          <span class="profile-check-mark" aria-hidden="true">${n.status==="pass"?"✓":n.status==="warn"?"!":n.status==="unavailable"?"?":"×"}</span>
          <span>
            <strong>${_(n.label)}</strong>
            <small>${_(n.detail)}</small>
          </span>
          <b aria-label="${n.assessed===!1?"Excluded because it could not be assessed":n.point?"Contributes one point":"No point"}">${n.assessed===!1?"?":n.point?"+1":"—"}</b>
        </li>`).join(""),e=p&&H.tier==="incomplete"?p.habitatSick?`The incomplete habitat has reached ${we} days and is now a sickness cause.`:`${Math.min(p.habitatDaysIncomplete,we)}/${we} days toward habitat sickness.`:"The habitat is above the incomplete tier, so this sickness timer is not active.";return Te("Nostr habitat",`
      <div class="profile-score-card profile-score-card--${H.tier}">
        <span><strong>${H.score}</strong> / ${H.max}</span>
        <div>
          <b>${_(dr(H.tier))}</b>
          <small>Profile-health habitat score</small>
        </div>
      </div>
      <p class="modal-copy">
        This score enriches a living pet’s condition. Activity alone controls critical
        decline and irreversible death. An incomplete habitat becomes a separate sickness
        cause after ${we} days; medicine restarts that timer.
      </p>
      <p class="modal-copy"><strong>${_(e)}</strong></p>
      ${t?`<ul class="profile-checks">${t}</ul>`:'<div class="empty-state"><strong>No profile checks loaded</strong><p>Try reopening this view after your Nostr data has synced.</p></div>'}
      <p class="profile-method-note">
        Eight possible checks: profile, NIP-05, picture, banner, Lightning address, relay setup,
        follows, and NIP-60 wallet. Checks unavailable in this runtime are excluded from the score.
      </p>
    `)}function yr(t){return`
    <form id="${_(t)}" class="viewer-form" novalidate>
      <label>
        Public account
        <input
          name="npub"
          type="text"
          inputmode="text"
          placeholder="npub1…"
          autocomplete="off"
          autocapitalize="none"
          spellcheck="false"
          aria-label="Nostr npub to view"
          required
        />
      </label>
      <button class="primary-button" type="button" data-submit="view">
        View this pet
      </button>
    </form>
  `}function Ra(){return Te("View another Nappagochi",`
      <p class="modal-copy">
        Paste a public <strong>npub</strong>. This changes only the account being
        viewed; it never changes or uses your connected signer.
      </p>
      ${yr("modal-view-form")}
      <p class="security-note">
        <span><strong>Read-only:</strong> viewing cannot post, feed, heal, adopt, or edit another pet.</span>
        <span><strong>Do not paste an nsec.</strong> Private-key input is rejected.</span>
      </p>
      ${st()?`<button class="secondary-button full-width" type="button" data-action="view-own-pet">
              ${re?"Back to my pet":"Stop viewing"}
            </button>`:""}
    `)}function Te(t,e){return`
    <div class="modal-backdrop" data-action="close-modal">
      <section class="modal-card" role="dialog" aria-modal="true" aria-labelledby="modal-title">
        <header>
          <h2 id="modal-title">${_(t)}</h2>
          <button class="icon-button" data-action="close-modal" aria-label="Close">×</button>
        </header>
        ${e}
      </section>
    </div>
  `}function Sa(){return q==="note"?Ea():q==="doctor"?ka():q==="settings"?$a():q==="preview"?Ia():q==="profile"?Aa():q==="habitat-source"?xa():q==="viewer"?Ra():""}function mr(){var e,n;const t=window.napplet;return!!(t&&typeof((e=t.identity)==null?void 0:e.getPublicKey)=="function"&&typeof t.identity.getProfile=="function"&&typeof t.identity.getFollows=="function"&&typeof t.identity.onChanged=="function"&&typeof((n=t.outbox)==null?void 0:n.getEvent)=="function"&&typeof t.outbox.query=="function"&&typeof t.outbox.subscribe=="function"&&typeof t.outbox.publish=="function")}function w(){if(!mr()){kt.innerHTML=`
      <section class="runtime-guard">
        ${rt("lonely",xe)}
        <h1>Nappagochi needs a compatible napplet host</h1>
        <p>Open the built artifact through Paja or another NIP-5D-compatible shell with identity and outbox support.</p>
      </section>`;return}let t="";ht?t=ga():M?E?t=va():t=st()?wa():hr():t=ba(),kt.innerHTML=`
    <div class="app-shell">
      ${t}
      ${L?`<div class="toast" role="status">${_(L)}</div>`:""}
      ${Sa()}
    </div>`,Ca(),Oa()}function gn(t){const e=document.querySelector(".pet-stage .pet");e&&(e.setAttribute("style",Ao(t.pose)),t.reaction?e.dataset.reaction=t.reaction:delete e.dataset.reaction)}function Ma(t){var n;const e=document.querySelector(".pet-stage .pet-speech");e&&(e.textContent=((n=t.utterance)==null?void 0:n.text)??"",e.classList.toggle("pet-speech--visible",!!t.utterance),t.utterance?e.dataset.intent=t.utterance.intent:delete e.dataset.intent)}function Oa(){if(ge==null||ge(),ge=null,be==null||be(),be=null,!(!E||!p)){if(xt.setCondition(p.state),ot.setCondition(p.state),be=ot.subscribe(Ma),te){gn({reaction:null,pose:vn({condition:te})});return}ge=xt.subscribe(gn)}}function Pa(){Ge!==null&&window.cancelAnimationFrame(Ge);const t=()=>{const e=xt.snapshot();gn(e),e.reaction?Ge=window.requestAnimationFrame(t):(Ge=null,console.log("[nappagochi:emotion] renderer animation loop settled",{condition:e.condition,mood:e.mood}))};t()}function Ca(){je("signed-out-view-form","view",uo,!0),je("modal-view-form","view",uo,!0),je("adopt-form","adopt",Ta,!0),je("note-form","note",Ba),je("doctor-form","doctor",Na),je("settings-form","settings",La),document.querySelectorAll("[data-action]").forEach(t=>{t.addEventListener("click",e=>{const n=t.dataset.action;n==="close-modal"&&e.target!==t&&t.classList.contains("modal-backdrop")||(n==="close-modal"?(q=null,w()):n==="view-pet"?(q="viewer",L="",w()):n==="view-own-pet"?(Re="",q=null,te=null,$t()):(n==="note"||n==="pet-menu")&&Nt()?(q="note",w()):n==="doctor"&&Nt()?(q="doctor",ve=[],Se=null,zt=!0,w(),ho()):n==="settings"&&Nt()?(q="settings",w()):n==="toggle-sound"&&t instanceof HTMLInputElement?(Oe=t.checked,At.setEnabled(Oe),oa(),w()):n==="toggle-panel"?rr():n==="preview"?(q="preview",w()):n==="profile"?(q="profile",w()):n==="habitat-source"?(q="habitat-source",L="",w(),so()):n==="habitat-source-open"?so():n==="clear-preview"?(te=null,lo(null),w()):n==="reload-doctor"?(ve=[],Se=null,zt=!0,w(),ho()):n==="adopt-next"&&(E=null,p=null,w()))})}),document.querySelectorAll("[data-preview]").forEach(t=>{t.addEventListener("click",()=>{const e=t.dataset.preview;e in Z&&(te=e,lo(e),w())})})}function je(t,e,n,o=!1){const r=document.querySelector(`#${t}`),i=r==null?void 0:r.querySelector(`[data-submit="${e}"]`);!r||!i||(i.addEventListener("click",()=>{n(r)}),o&&r.addEventListener("keydown",s=>{s.key!=="Enter"||s.target instanceof HTMLTextAreaElement||(s.preventDefault(),i.disabled||n(r))}))}async function Zt(t,e={},n=[]){if(!Nt())throw new Error("Viewing mode is read-only. Return to your own pet to publish.");const o=Nn([...De,...e.relays??[],...n]);return oi(x,(r,i)=>It.publish(r,i),t,e,o,Ke==="nip65"?!0:Ke==="fallback"?!1:void 0)}async function uo(t){const e=new FormData(t);try{const n=ci(String(e.get("npub")??""));Re=n===re?"":n,q=null,te=null,await $t()}catch(n){L=n instanceof Error?n.message:"That npub could not be opened.",w()}}async function Ta(t){const e=new FormData(t),n=String(e.get("name")??"").trim().slice(0,28),o=e.get("palette"),r=Pn(o)?o:"peach";if(!n){L="Please give your pet a name.",w();return}V=!0,L="",w();const i=ke.length?[...ke].sort((l,d)=>d.event.created_at-l.event.created_at)[0]:void 0,s={v:1,name:n,species:"momo",appearance:{...xe,palette:r},ruleset:"gentle-v1"},a=[["d",Rn],["t","nostr-pet"],["alt",`Birth event for Nostr Pet ${n}`]];i&&a.push(["e",i.event.id]);try{const l=await Zt({kind:78,content:JSON.stringify(s),tags:a,created_at:z()});if(!l.ok)throw new Error(l.error||"The birth event was not accepted.");await $t(),L=`${n} has been born.`}catch(l){L=l instanceof Error?l.message:"The birth event could not be published."}finally{V=!1,w()}}async function Ba(t){var n;const e=String(new FormData(t).get("content")??"").trim();if(!e){L="Write a note before publishing.",w();return}V=!0,w();try{const o=await Zt({kind:1,content:e,tags:[],created_at:z()}),r=Io(o,{ownerPubkey:M,kind:1}),i=!!(p!=null&&p.canFeed);J=wn(J,[r]),q=null,await cr(!1);const s=Gr(o),a=!!(x.localRelayUrl&&((n=o.relays)!=null&&n[x.localRelayUrl])),l=x.localRelayOnly&&a?"the local relay":x.localRelayMirror&&a?`${s} relay${s===1?"":"s"}, including the local mirror`:x.localRelayMirror&&s?`${s} relay${s===1?"":"s"}; the local mirror did not accept it`:s?`${s} relay${s===1?"":"s"}`:"the shell’s relay plan";L=i?`Note signed and accepted by ${l}. Pulse refreshed to ${(p==null?void 0:p.daysQuiet)??0} quiet days.`:`Note signed and accepted by ${l}.`}catch(o){L=o instanceof Error?o.message:"The note could not be published."}finally{V=!1,w()}}function fo(t,e){const n=z()-un,o=z()+Sn,r=new Set;return t.filter(({event:i})=>i.kind===1&&i.pubkey!==M&&i.created_at>=n&&i.created_at<=o&&!Ls(i)&&i.content.trim().length>0&&(!e||e.has(i.pubkey))).sort((i,s)=>s.event.created_at-i.event.created_at).filter(({event:i})=>r.has(i.pubkey)?!1:(r.add(i.pubkey),!0)).slice(0,6).map(i=>{var s,a;return{event:i.event,relayHint:((a=(s=i.sidecar)==null?void 0:s.relayHints)==null?void 0:a[0])??""}})}async function ho(){Se=null;try{const t=(x.localRelayOnly?Mn:await Je.getFollows().catch(()=>[])).filter(n=>n!==M).slice(0,30);if(t.length)try{const n=await Ce([{authors:t,kinds:[1],since:z()-un,limit:60}],{authors:t,limit:60,timeoutMs:7e3});Pe||(Pe=!!n.incomplete);const o=fo(n.events,new Set(t));if(o.length){ve=o,Se="follows";return}}catch{}const e=await Ce([{kinds:[1],since:z()-un,limit:80}],{limit:80,timeoutMs:7e3,...De.length?{relays:De}:{}});Pe||(Pe=!!e.incomplete),ve=fo(e.events),Se=ve.length?"discovery":null}catch(t){L=t instanceof Error?t.message:"Reply candidates could not be loaded.",ve=[],Se=null}finally{zt=!1,w()}}async function Na(t){const e=new FormData(t),n=ve[Number(e.get("candidate"))],o=String(e.get("content")??"").trim();if(!n||!o){L=n?"Add something thoughtful before publishing.":"Choose a note first.",w();return}V=!0,w();const r=n.relayHint;try{const i=await Zt({kind:1,content:o,tags:[["e",n.event.id,r,"reply",n.event.pubkey],["p",n.event.pubkey,r]],created_at:z()},{toOutbox:!0,toInboxes:[n.event.pubkey]},r?[r]:[]),s=Io(i,{ownerPubkey:M,kind:1});J=wn(J,[s]),q=null,await cr(),L="Published. The verified medicine is working."}catch(i){L=i instanceof Error?i.message:"Your message could not be published."}finally{V=!1,w()}}async function La(t){if(!E||(p==null?void 0:p.state)==="dead")return;const e=new FormData(t),n=e.get("palette"),o=e.get("eyes"),r=e.get("accessory"),i={base:"momo-01",palette:Pn(n)?n:"peach",eyes:Wo(o)?o:"round",accessory:Jo(r)?r:"none"};pn=i,V=!0,w();try{const s=await Zt({kind:30078,content:JSON.stringify({v:1,name:E.data.name,appearance:i}),tags:[["d",or(E.event.id)],["e",E.event.id],["t","nostr-pet"],["alt",`Appearance for Nostr Pet ${E.data.name}`]],created_at:z()});if(!s.ok)throw new Error(s.error||"The appearance event was not accepted.");yn+=1,nt=i,q=null,L="Appearance saved to Nostr."}catch(s){L=s instanceof Error?s.message:"Appearance could not be saved."}finally{V=!1,pn=null,w()}}function bt(t){const e=document.documentElement;e.style.setProperty("--shell-bg",t.colors.background),e.style.setProperty("--shell-text",t.colors.text),e.style.setProperty("--shell-primary",t.colors.primary),e.style.background=t.colors.background,e.style.color=t.colors.text,document.body.style.background=t.colors.background,document.body.style.color=t.colors.text,kt.style.background=t.colors.background,kt.style.color=t.colors.text}async function _a(){bt(fn);try{bt(await xr())}catch{bt(fn);return}try{Tt=$r(bt)}catch{console.log("[nappagochi:degradation] live theme updates unavailable; current theme retained")}}function qa(){Ko=!0,U==null||U.destroy(),U=null,Me==null||Me.destroy(),Me=null,yt==null||yt(),yt=null,ar(),ge==null||ge(),ge=null,xt.destroy(),be==null||be(),be=null,ot.destroy(),At.destroy(),document.removeEventListener("pointerdown",ir),Ge!==null&&window.cancelAnimationFrame(Ge),vt!==null&&window.clearTimeout(vt),Ct==null||Ct.close(),Tt==null||Tt.close(),pt==null||pt.close(),pt=null,mn!==null&&window.clearInterval(mn)}async function Ha(){bt(fn),w(),mr()&&(_a(),Qs().then(()=>w()),ta(),na(),document.addEventListener("pointerdown",ir,{passive:!0}),await fa(),U=new wi({mountedAt:Ts,openChannel:ra}),U.onDelivery(la),yt=U.onStatus(ia),Me=new fs({onAggregate:t=>{var o;const e=hs(t),n=xt.react(e);if(console.log("[nappagochi:emotion] live aggregate evaluated",{reaction:e,accepted:n,totalSignals:t.total,actorCount:t.actorCount,byType:t.byType,authoritativeCondition:(p==null?void 0:p.state)??null,previewActive:!!te}),n){Pa(),At.play(e);const r=no(t,"gentle");ot.say(r);const i=++Bt,s=(o=t.representativeSignal.zap)==null?void 0:o.senderPubkey;Bs.enrichApprovedReaction({reactionAccepted:n,reactionId:e,actorPubkey:s}).then(a=>{if(i!==Bt){console.log("[nappagochi:enrichment] stale reaction metadata discarded",{reaction:e,enrichmentGeneration:i,activeGeneration:Bt});return}a!=null&&a.name&&ot.refineActive(no(t,"gentle",a.name))})}}}),Ct=Je.onChanged(()=>{$t()}),await $t(),mn=window.setInterval(()=>{E&&(p=at(E,z()),w())},6e4))}window.addEventListener("beforeunload",qa);Ha();</script>
    <style rel="stylesheet" crossorigin>:root{--shell-bg: #fff7e9;--shell-text: #30241f;--shell-primary: #ef6b55;--paper: color-mix(in srgb, var(--shell-bg) 88%, white);--paper-strong: color-mix(in srgb, var(--shell-bg) 70%, white);--ink-muted: color-mix(in srgb, var(--shell-text) 62%, transparent);--line: color-mix(in srgb, var(--shell-text) 13%, transparent);--accent-soft: color-mix(in srgb, var(--shell-primary) 16%, var(--paper));--shadow: 0 24px 70px color-mix(in srgb, var(--shell-text) 13%, transparent);color:var(--shell-text);background:var(--shell-bg);font-family:Inter,ui-rounded,SF Pro Rounded,Segoe UI,system-ui,-apple-system,sans-serif;font-synthesis:none;text-rendering:optimizeLegibility}*{box-sizing:border-box}html,body,#app{min-width:100%;min-height:100%;margin:0;color:var(--shell-text);background:var(--shell-bg)}body{min-height:100vh}button,input,textarea,select{font:inherit}button{color:inherit}button:focus-visible,input:focus-visible,textarea:focus-visible,select:focus-visible{outline:3px solid color-mix(in srgb,var(--shell-primary) 42%,transparent);outline-offset:2px}.app-shell{container-type:inline-size;min-height:100vh;overflow:hidden;background:radial-gradient(circle at 8% 0%,color-mix(in srgb,var(--shell-primary) 10%,transparent),transparent 30%),var(--shell-bg)}.live-paused-pill,.preview-flag{padding:4px 8px;border-radius:999px;font-size:10px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.live-paused-pill{color:#8a3d16;background:#ffe4cc}.viewer-banner{display:flex;position:relative;z-index:3;align-items:center;justify-content:space-between;gap:18px;padding:12px clamp(16px,4vw,48px);border-bottom:1px solid color-mix(in srgb,#648ec6 28%,var(--line));background:color-mix(in srgb,#dfeaff 52%,var(--paper));color:var(--ink-muted);font-size:12px;line-height:1.5}.viewer-banner>span{min-width:0}.viewer-banner strong{margin-right:6px;color:var(--shell-text)}.viewer-banner code{word-break:break-all}.viewer-banner .secondary-button{flex:0 0 auto;min-height:36px;padding-block:7px}.pet-layout{display:grid;min-height:100vh;grid-template-columns:minmax(0,1.4fr) minmax(320px,.8fr)}.pet-layout--compact{grid-template-columns:minmax(0,1fr)}.pet-layout--compact .habitat{min-height:100vh}.habitat{position:relative;display:grid;min-height:570px;place-content:center;place-items:center;overflow:hidden;padding:48px 40px 62px;isolation:isolate}.panel-toggle{position:absolute;z-index:3;top:18px;right:18px;display:inline-flex;align-items:center;gap:7px;min-height:38px;padding:7px 11px 7px 9px;border:1px solid var(--line);border-radius:12px;color:var(--ink-muted);background:color-mix(in srgb,var(--paper-strong) 90%,transparent);box-shadow:0 9px 24px color-mix(in srgb,var(--shell-text) 8%,transparent);cursor:pointer;font-size:12px;font-weight:750;-webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px)}.panel-toggle span[aria-hidden=true]{font-size:20px;line-height:.8}.panel-toggle:hover{border-color:color-mix(in srgb,var(--shell-primary) 45%,var(--line));color:var(--shell-text)}.habitat-live-status{position:absolute;z-index:3;top:20px;left:20px}.habitat:before{position:absolute;z-index:-2;width:min(47vw,560px);aspect-ratio:1;border:1px solid color-mix(in srgb,var(--shell-primary) 16%,transparent);border-radius:50%;background:radial-gradient(circle at 50% 44%,var(--paper-strong),color-mix(in srgb,var(--shell-primary) 6%,var(--paper)));box-shadow:inset 0 0 0 18px color-mix(in srgb,var(--paper) 48%,transparent),0 36px 120px color-mix(in srgb,var(--shell-primary) 12%,transparent);content:""}.ambient-shape{position:absolute;z-index:-1;border-radius:50%;filter:blur(1px)}.ambient-shape--one{top:12%;left:14%;width:16px;height:16px;background:var(--shell-primary);box-shadow:46px 80px 0 -4px color-mix(in srgb,var(--shell-primary) 40%,transparent),400px 24px 0 -5px color-mix(in srgb,var(--shell-primary) 55%,transparent);opacity:.5}.ambient-shape--two{right:14%;bottom:21%;width:110px;height:34px;border:1px solid var(--line);transform:rotate(-12deg);opacity:.56}.pet-stage{position:relative;border:0;padding:0;background:none;cursor:pointer;transition:transform .18s ease}.pet-stage:hover{transform:translateY(-3px) scale(1.01)}.pet-stage:active{transform:translateY(1px) scale(.985)}.pet-stage--readonly{cursor:default}.pet-stage--readonly:hover,.pet-stage--readonly:active{transform:none}.pet{--pet-main: #efa276;--pet-dark: #b45d51;--pet-light: #ffd1ae;--pet-cheek: #e97878;position:relative;width:clamp(184px,25vw,280px);height:clamp(190px,26vw,288px);perspective:900px;animation:pet-breathe 3.2s ease-in-out infinite}.pet-turner,.pet-face{position:absolute;top:0;right:0;bottom:0;left:0}.pet-turner{transform-style:preserve-3d;transform-origin:50% 88%}.pet-face{-webkit-backface-visibility:hidden;backface-visibility:hidden;transform-style:flat}.pet-face--front{z-index:2;transform:rotateY(0)}.pet-face--back{z-index:1;transform:rotateY(180deg)}.pet-speech{position:absolute;z-index:5;right:3%;bottom:96%;width:max-content;max-width:min(240px,72vw);padding:12px 16px;border:2px solid #292929;border-radius:18px;color:#202020;background:#fff;box-shadow:4px 5px #292929;font-size:14px;font-weight:650;line-height:1.35;opacity:0;pointer-events:none;transform:translateY(10px) scale(.78);transform-origin:100% 100%;transition:opacity .12s ease,transform .16s ease}.pet-speech:before,.pet-speech:after{position:absolute;top:100%;right:18px;border:9px solid transparent;border-top-color:#292929;content:""}.pet-speech:after{right:20px;border-width:7px;border-top-color:#fff}.pet-speech--visible{opacity:1;transform:translateY(0) scale(1);animation:speech-pop .26s cubic-bezier(.2,1.5,.5,1)}.pet-speech[data-intent=gratitude]{border-color:#292929;background:#fff}.palette--mint{--pet-main: #83c8af;--pet-dark: #327c71;--pet-light: #c8f0d9;--pet-cheek: #f39996}.palette--night{--pet-main: #68678d;--pet-dark: #343550;--pet-light: #a7a5c6;--pet-cheek: #d78397}.pet-shadow{position:absolute;right:10%;bottom:1%;left:10%;height:17%;border-radius:50%;background:color-mix(in srgb,var(--shell-text) 18%,transparent);filter:blur(9px);animation:shadow-breathe 3.2s ease-in-out infinite}.pet-body,.pet-back-body{position:absolute;top:18%;right:6%;bottom:6%;left:6%;border:2px solid color-mix(in srgb,var(--pet-dark) 54%,transparent);border-radius:48% 48% 44% 44%/46% 46% 55% 55%;background:radial-gradient(circle at 37% 64%,var(--pet-cheek) 0 3%,transparent 3.5%),radial-gradient(circle at 63% 64%,var(--pet-cheek) 0 3%,transparent 3.5%),linear-gradient(145deg,var(--pet-light),var(--pet-main) 55%,var(--pet-dark));box-shadow:inset 22px 20px 26px color-mix(in srgb,white 20%,transparent),inset -17px -12px 28px color-mix(in srgb,var(--pet-dark) 20%,transparent),0 18px 28px color-mix(in srgb,var(--pet-dark) 24%,transparent);transform:translateY(var(--pet-pose-body-y, 0)) rotate(calc(var(--pet-pose-body-rotation, 0deg) + var(--pet-pose-head-tilt, 0deg))) scale(var(--pet-pose-scale-x, 1),var(--pet-pose-scale-y, 1));transform-origin:50% 72%;transition:transform .3s cubic-bezier(.2,.8,.2,1)}.pet-back-body{background:radial-gradient(circle at 50% 44%,color-mix(in srgb,var(--pet-dark) 20%,transparent) 0 14%,transparent 14.5%),linear-gradient(215deg,var(--pet-light),var(--pet-main) 55%,var(--pet-dark))}.pet-ear{position:absolute;z-index:-1;top:8%;width:32%;height:38%;border:2px solid color-mix(in srgb,var(--pet-dark) 54%,transparent);background:linear-gradient(145deg,var(--pet-light),var(--pet-main))}.pet-ear--left{left:9%;border-radius:85% 18% 52% 45%;transform:rotate(calc(-24deg - var(--pet-pose-ear-droop-angle, 0deg)))}.pet-ear--right{right:9%;border-radius:18% 85% 45% 52%;transform:rotate(calc(24deg + var(--pet-pose-ear-droop-angle, 0deg)))}.pet-eye,.pet-mouth,.pet-cheek,.pet-patch,.pet-accessory{position:absolute}.pet-eye{top:39%;color:var(--pet-dark);font-size:clamp(12px,2vw,20px);line-height:1;text-shadow:0 1px color-mix(in srgb,white 20%,transparent);transform:scaleY(var(--pet-pose-eye-open, 1));transition:transform .22s ease}.pet-eye--left{left:31%}.pet-eye--right{right:31%}.pet-mouth{top:53%;left:50%;color:var(--pet-dark);font-family:ui-monospace,monospace;font-size:clamp(19px,2.8vw,30px);transform:translate(-50%) scaleY(calc(1 + var(--pet-pose-mouth-open, 0) * .45));transition:transform .22s ease}.pet-patch{right:13%;bottom:13%;width:25%;height:14%;border-radius:55% 43% 50% 60%;background:color-mix(in srgb,var(--pet-dark) 16%,transparent);transform:rotate(-10deg)}.pet-back-patch{position:absolute;top:28%;left:34%;width:32%;height:37%;border-radius:52% 48% 55% 45%;background:color-mix(in srgb,var(--pet-dark) 18%,transparent);transform:rotate(8deg)}.pet-tail{position:absolute;right:-5%;bottom:17%;width:25%;height:25%;border:2px solid color-mix(in srgb,var(--pet-dark) 54%,transparent);border-radius:50%;background:linear-gradient(145deg,var(--pet-light),var(--pet-main));box-shadow:inset -7px -5px 10px color-mix(in srgb,var(--pet-dark) 20%,transparent)}.pet-accessory.bow{z-index:2;top:-4%;left:50%;color:var(--shell-primary);font-size:clamp(34px,5vw,50px);filter:drop-shadow(0 4px 3px color-mix(in srgb,var(--pet-dark) 20%,transparent));transform:translate(-50%) rotate(45deg) scaleX(1.5)}.pet-accessory.hat{z-index:2;top:-14%;left:50%;width:38%;height:22%;border-radius:50% 50% 17% 17%;background:var(--shell-primary);box-shadow:inset 0 -9px color-mix(in srgb,var(--shell-primary) 70%,black);transform:translate(-50%) rotate(-4deg)}.pet-signal{position:absolute;top:3%;right:-3%;display:grid;width:42px;height:42px;place-items:center;border:1px solid var(--line);border-radius:50%;color:var(--shell-primary);background:var(--paper);box-shadow:0 9px 24px color-mix(in srgb,var(--shell-text) 10%,transparent);font-size:25px;font-weight:900;animation:signal-pulse 2.6s ease-out infinite}.pet--lonely{animation-duration:4.8s}.pet--sick{animation:pet-sick 2.7s ease-in-out infinite;filter:saturate(.72)}.pet--critical{animation:pet-critical 1.4s ease-in-out infinite;filter:saturate(.45)}.pet--dead{animation:none;filter:grayscale(.88) saturate(.2);opacity:.78;transform:translateY(13px) rotate(-3deg)}.pet--dead .pet-signal,.pet--sick .pet-signal,.pet--critical .pet-signal{color:#bb4b4b}.pet--dead .pet-signal{animation:none;opacity:.42}.pet[data-reaction=celebrate] .pet-turner{animation:kind1-jumpy 1.05s cubic-bezier(.36,.07,.19,.97) both;will-change:transform}.pet[data-reaction=celebrate] .pet-shadow{animation:kind1-jump-shadow 1.05s ease-in-out both}.pet[data-reaction=celebrate] .pet-signal{color:#e28422;background:color-mix(in srgb,#ffb84d 22%,var(--paper));animation:kind1-signal .3s ease-in-out infinite alternate}.pet[data-reaction=reply-roll] .pet-turner{animation:reply-roll-up-down 1.8s cubic-bezier(.45,.04,.35,1) both;will-change:transform}.pet[data-reaction=reply-roll] .pet-shadow{animation:reply-roll-shadow 1.8s ease-in-out both}.pet[data-reaction=reply-roll] .pet-signal{color:#398b79;background:color-mix(in srgb,#73d6bd 22%,var(--paper));animation:kind1-signal .36s ease-in-out infinite alternate}.pet[data-reaction=zap-celebrate] .pet-turner{animation:zap-standing-turn 2.4s linear both;will-change:transform}.pet[data-reaction=zap-celebrate] .pet-shadow{animation:zap-turn-shadow 2.4s linear both}.pet[data-reaction=zap-celebrate] .pet-signal{color:#f4a900;background:color-mix(in srgb,#ffd85a 24%,var(--paper));animation:zap-signal .42s ease-in-out infinite alternate}.state-caption{max-width:520px;margin-top:16px;text-align:center}.state-caption h1,.adoption-card h1,.welcome-card h1,.runtime-guard h1{margin:4px 0 8px;font-family:Iowan Old Style,Baskerville,Georgia,serif;font-size:clamp(34px,5vw,56px);font-weight:620;letter-spacing:-.045em;line-height:1}.state-caption p{max-width:45ch;margin:0 auto;color:var(--ink-muted);line-height:1.55}.state-kicker{display:inline-block;color:var(--shell-primary);font-size:12px;font-weight:850;letter-spacing:.12em;text-transform:uppercase}.preview-flag{display:inline-block;margin-right:7px;color:#65520e;background:#fff1ad}.care-panel{align-self:stretch;padding:clamp(32px,5vw,64px) clamp(24px,4vw,54px);border-left:1px solid var(--line);background:color-mix(in srgb,var(--paper) 90%,transparent)}.care-panel[hidden]{display:none}.care-heading{display:flex;align-items:flex-start;justify-content:space-between;gap:18px}.eyebrow{margin:0 0 8px;color:var(--shell-primary);font-size:11px;font-weight:850;letter-spacing:.12em;text-transform:uppercase}.care-heading h2,.modal-card h2{margin:0;font-size:clamp(24px,3vw,34px);letter-spacing:-.035em}.icon-button{display:grid;flex:0 0 auto;width:40px;height:40px;place-items:center;border:1px solid var(--line);border-radius:13px;background:var(--paper-strong);cursor:pointer}.icon-button:hover{border-color:color-mix(in srgb,var(--shell-primary) 45%,var(--line))}.vital-track{display:grid;grid-template-columns:repeat(6,1fr);gap:5px;margin-top:34px}.vital-track span{height:8px;border-radius:10px;background:var(--line)}.vital-track span:nth-child(1).active{background:#68b77b}.vital-track span:nth-child(2).active{background:#9aba6f}.vital-track span:nth-child(3).active{background:#e1aa4d}.vital-track span:nth-child(4).active{background:#e37758}.vital-track span:nth-child(5).active{background:#c8484f}.vital-track span:nth-child(6).active{background:#777079}.next-state{display:flex;align-items:center;justify-content:space-between;gap:10px;margin-top:10px;color:var(--ink-muted);font-size:12px}.text-button{border:0;padding:0;color:var(--shell-primary);background:none;font-size:12px;font-weight:760;cursor:pointer}.action-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:12px;margin:34px 0}.view-another-button{width:100%;margin:-22px 0 34px}.view-only-card{display:grid;gap:7px;margin:34px 0;border:1px solid color-mix(in srgb,#648ec6 30%,var(--line));border-radius:18px;padding:16px;background:color-mix(in srgb,#dfeaff 28%,var(--paper-strong))}.view-only-card span{color:var(--ink-muted);font-size:12px;line-height:1.5}.view-only-card .secondary-button{margin-top:5px}.care-button{display:grid;min-height:124px;justify-items:start;padding:17px;border:1px solid var(--line);border-radius:19px;background:var(--paper-strong);cursor:pointer;text-align:left;transition:transform .16s ease,border-color .16s ease,box-shadow .16s ease}.care-button:hover:not(:disabled){border-color:color-mix(in srgb,var(--shell-primary) 48%,var(--line));box-shadow:0 12px 30px color-mix(in srgb,var(--shell-text) 8%,transparent);transform:translateY(-2px)}.care-button:disabled{cursor:not-allowed;opacity:.44}.care-button>span{display:grid;width:32px;height:32px;place-items:center;border-radius:11px;color:#fff;background:var(--shell-primary)}.care-button--doctor>span{background:#5b927a}.care-button strong{align-self:end;margin-top:13px;font-size:14px}.care-button small{margin-top:3px;color:var(--ink-muted)}.pet-facts{margin:0 0 24px;border-top:1px solid var(--line)}.pet-facts div{display:flex;justify-content:space-between;gap:16px;padding:13px 0;border-bottom:1px solid var(--line)}.pet-facts dt{color:var(--ink-muted);font-size:13px}.habitat-source-link{border:0;padding:0;color:inherit;background:none;font:inherit;cursor:pointer;text-decoration:underline;text-decoration-style:dotted;text-underline-offset:3px}.habitat-source-link:hover{color:var(--shell-primary)}.source-address{margin-top:16px}.source-address input{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;font-size:11px}.pet-facts dd{margin:0;font-size:13px;font-weight:720;text-align:right}.habitat-link{font-size:13px}.habitat-link:hover{text-decoration:underline;text-underline-offset:3px}.primary-button,.secondary-button{min-height:46px;border-radius:14px;padding:11px 17px;font-weight:780;cursor:pointer}.primary-button{border:1px solid var(--shell-primary);color:#fff;background:var(--shell-primary);box-shadow:0 11px 24px color-mix(in srgb,var(--shell-primary) 24%,transparent)}.secondary-button{border:1px solid var(--line);background:var(--paper-strong)}.primary-button:disabled,.secondary-button:disabled{cursor:not-allowed;filter:grayscale(.5);opacity:.54}.full-width{width:100%}.adoption-layout{display:grid;min-height:100vh;grid-template-columns:minmax(0,1.05fr) minmax(330px,.95fr);align-items:center;gap:clamp(30px,7vw,100px);padding:clamp(30px,7vw,90px)}.adoption-art{position:relative;display:grid;min-height:440px;place-items:center;border:1px solid var(--line);border-radius:48% 48% 42% 42%/40% 40% 50% 50%;background:linear-gradient(145deg,color-mix(in srgb,var(--shell-primary) 8%,var(--paper)),var(--paper-strong));box-shadow:var(--shadow)}.spark{position:absolute;color:var(--shell-primary);font-size:30px;animation:spark-float 3s ease-in-out infinite}.spark--one{top:19%;right:20%}.spark--two{bottom:23%;left:20%;font-size:70px;animation-delay:-1.5s}.adoption-card,.welcome-card,.loading-card,.runtime-guard{max-width:540px}.adoption-card h1,.welcome-card h1,.runtime-guard h1{font-size:clamp(38px,5.5vw,62px);line-height:.98}.adoption-card>p:not(.eyebrow),.welcome-card>p,.runtime-guard>p{color:var(--ink-muted);line-height:1.62}form{display:grid;gap:20px}label,legend{color:var(--ink-muted);font-size:12px;font-weight:740;letter-spacing:.02em}input[type=text],input:not([type]),textarea,select{width:100%;margin-top:8px;border:1px solid var(--line);border-radius:13px;padding:12px 13px;color:var(--shell-text);background:var(--paper-strong)}textarea{min-height:110px;resize:vertical;line-height:1.5}fieldset{min-width:0;margin:0;border:0;padding:0}.swatches{display:grid;grid-template-columns:repeat(3,1fr);gap:10px;margin-top:9px}.swatch{display:flex;align-items:center;gap:8px;border:1px solid var(--line);border-radius:13px;padding:9px;color:var(--shell-text);background:var(--paper-strong);cursor:pointer}.swatch input{position:absolute;opacity:0;pointer-events:none}.swatch>span{width:24px;height:24px;border:2px solid color-mix(in srgb,var(--shell-text) 12%,transparent);border-radius:50%;background:#efa276;box-shadow:inset 0 0 0 3px color-mix(in srgb,white 50%,transparent)}.swatch--mint>span{background:#83c8af}.swatch--night>span{background:#68678d}.swatch:has(input:checked){border-color:var(--shell-primary);box-shadow:0 0 0 2px color-mix(in srgb,var(--shell-primary) 15%,transparent)}form>small{color:var(--ink-muted);text-align:center}.welcome-card,.loading-card,.runtime-guard{display:grid;min-height:100vh;align-content:center;justify-items:center;margin:auto;padding:40px 24px;text-align:center}.mini-pet{transform:scale(.56);height:180px}.sign-in-status{display:grid;grid-template-columns:auto minmax(0,1fr);align-items:center;gap:12px;border:1px solid var(--line);border-radius:16px;padding:13px 15px;background:var(--paper)}.sign-in-status>span:last-child{display:grid;gap:3px}.sign-in-status small{color:var(--ink-muted);font-size:12px;line-height:1.4}.sign-in-status{width:min(100%,500px);margin-top:18px;border-color:color-mix(in srgb,var(--shell-primary) 45%,var(--line));text-align:left}.status-pulse{width:12px;height:12px;margin:9px;border-radius:50%;background:var(--shell-primary);box-shadow:0 0 color-mix(in srgb,var(--shell-primary) 45%,transparent);animation:status-pulse 1.8s ease-out infinite}.security-note{display:grid;gap:5px;max-width:500px;margin:14px 0 0;font-size:12px}.viewer-entry{display:grid;gap:7px;width:min(100%,560px);margin-top:18px;border-top:1px solid var(--line);padding-top:18px;color:var(--ink-muted);font-size:12px;text-align:left}.viewer-entry>strong{color:var(--shell-text);font-size:14px}.viewer-form{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:end;gap:10px;margin-top:5px}.viewer-form .primary-button{min-width:130px}.viewed-empty-layout .adoption-card{display:grid;gap:14px}.viewed-empty-layout .adoption-card .primary-button,.viewed-empty-layout .adoption-card .secondary-button{width:100%}.notice,.empty-state{border:1px solid var(--line);border-radius:16px;padding:16px;color:var(--ink-muted);background:var(--paper);font-size:13px;line-height:1.5}.loading-orbit{position:relative;width:70px;height:70px;border:1px solid var(--line);border-radius:50%}.loading-orbit span{position:absolute;top:-5px;left:calc(50% - 5px);width:10px;height:10px;border-radius:50%;background:var(--shell-primary);animation:orbit 1.4s linear infinite;transform-origin:5px 40px}.loading-card p{margin:22px 0 5px;font-weight:780}.loading-card small{color:var(--ink-muted)}.runtime-guard{min-height:100vh}.runtime-guard .pet{transform:scale(.68);margin:-30px}.modal-backdrop{position:fixed;z-index:20;top:0;right:0;bottom:0;left:0;display:grid;place-items:center;overflow-y:auto;padding:18px;background:color-mix(in srgb,var(--shell-text) 30%,transparent);-webkit-backdrop-filter:blur(9px);backdrop-filter:blur(9px)}.modal-card{width:min(560px,100%);max-height:calc(100vh - 36px);overflow:auto;border:1px solid var(--line);border-radius:24px;padding:clamp(20px,4vw,32px);background:var(--paper);box-shadow:var(--shadow)}.modal-card>header{display:flex;align-items:center;justify-content:space-between;gap:18px;margin-bottom:20px}.modal-copy{margin:-4px 0 20px;color:var(--ink-muted);font-size:13px;line-height:1.55}.profile-score-card{display:flex;align-items:center;gap:16px;margin-bottom:20px;border:1px solid color-mix(in srgb,var(--shell-primary) 24%,var(--line));border-radius:18px;padding:16px;background:var(--accent-soft)}.profile-score-card>span{min-width:86px;color:var(--shell-primary);font-weight:760}.profile-score-card>span strong{font-size:34px;letter-spacing:-.06em}.profile-score-card>div{display:grid;gap:3px}.profile-score-card>div b{font-size:15px}.profile-score-card>div small{color:var(--ink-muted)}.profile-score-card--excellent{border-color:color-mix(in srgb,#4b9f70 46%,var(--line));background:color-mix(in srgb,#74c98f 18%,var(--paper))}.profile-score-card--attention,.profile-score-card--incomplete{border-color:color-mix(in srgb,#d59745 42%,var(--line));background:color-mix(in srgb,#efbc67 16%,var(--paper))}.profile-checks{display:grid;gap:8px;margin:0;padding:0;list-style:none}.profile-check{display:grid;grid-template-columns:auto 1fr auto;align-items:center;gap:11px;border:1px solid var(--line);border-radius:14px;padding:11px 12px;background:var(--paper-strong)}.profile-check-mark{display:grid;width:26px;height:26px;place-items:center;border-radius:50%;color:#fff;background:#6dad7b;font-weight:850}.profile-check--warn .profile-check-mark{background:#ce9345}.profile-check--unavailable .profile-check-mark{color:var(--ink-muted);background:var(--paper-strong)}.profile-check--fail .profile-check-mark{background:#a69ca0}.profile-check>span:nth-child(2){display:grid;gap:2px;min-width:0}.profile-check strong{font-size:13px}.profile-check small{overflow:hidden;color:var(--ink-muted);font-size:11px;line-height:1.4;text-overflow:ellipsis}.profile-check>b{color:var(--shell-primary);font-size:12px}.profile-method-note{margin:16px 2px 0;color:var(--ink-muted);font-size:11px;line-height:1.5}.form-columns{display:grid;grid-template-columns:1fr 1fr;gap:12px}.local-setting{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:center;gap:18px;margin-top:22px;border-top:1px solid var(--line);padding-top:18px}.local-setting>span{display:grid;gap:4px}.local-setting strong{color:var(--shell-text);font-size:14px}.local-setting small{color:var(--ink-muted);font-size:12px;line-height:1.45}.sound-switch{position:relative;display:block;width:48px;height:28px;cursor:pointer}.sound-switch input{position:absolute;opacity:0}.sound-switch>span{position:absolute;top:0;right:0;bottom:0;left:0;border:1px solid var(--line);border-radius:999px;background:var(--paper-strong);transition:background .16s ease,border-color .16s ease}.sound-switch>span:after{position:absolute;top:3px;left:3px;width:20px;height:20px;border-radius:50%;background:var(--ink-muted);content:"";transition:transform .16s ease,background .16s ease}.sound-switch input:checked+span{border-color:var(--shell-primary);background:color-mix(in srgb,var(--shell-primary) 24%,var(--paper-strong))}.sound-switch input:checked+span:after{background:var(--shell-primary);transform:translate(20px)}.sound-switch input:focus-visible+span{outline:3px solid color-mix(in srgb,var(--shell-primary) 32%,transparent);outline-offset:2px}.note-choices{display:grid;gap:8px}.note-choices legend{margin-bottom:5px}.note-choice{position:relative;display:block;color:var(--shell-text);cursor:pointer}.note-choice input{position:absolute;opacity:0}.note-choice>span{display:grid;grid-template-columns:1fr auto;gap:4px 12px;border:1px solid var(--line);border-radius:14px;padding:12px;background:var(--paper-strong)}.note-choice input:checked+span{border-color:var(--shell-primary);box-shadow:0 0 0 2px color-mix(in srgb,var(--shell-primary) 14%,transparent)}.note-choice strong{font-size:12px}.note-choice small{color:var(--ink-muted);font-size:11px}.note-choice em{display:-webkit-box;grid-column:1 / -1;overflow:hidden;color:var(--ink-muted);font-size:13px;font-style:normal;line-height:1.4;-webkit-box-orient:vertical;-webkit-line-clamp:2}.doctor-loading{padding:36px 10px;color:var(--ink-muted);text-align:center}.state-options{display:grid;gap:7px;margin-bottom:16px}.state-option{display:grid;grid-template-columns:auto 1fr;align-items:center;gap:12px;border:1px solid var(--line);border-radius:14px;padding:11px 13px;background:var(--paper-strong);cursor:pointer;text-align:left}.state-option.active{border-color:var(--shell-primary)}.state-option span:last-child{display:grid;gap:2px}.state-option small{color:var(--ink-muted)}.state-dot{width:12px;height:12px;border-radius:50%;background:#68b77b}.state-dot--content{background:#9aba6f}.state-dot--lonely{background:#e1aa4d}.state-dot--sick{background:#e37758}.state-dot--critical{background:#c8484f}.state-dot--dead{background:#777079}.toast{position:fixed;z-index:40;right:18px;bottom:18px;max-width:min(430px,calc(100vw - 36px));border:1px solid var(--line);border-radius:15px;padding:12px 16px;color:var(--shell-text);background:var(--paper);box-shadow:var(--shadow);font-size:13px;animation:toast-in .22s ease-out}@keyframes pet-breathe{0%,to{transform:translateY(0) rotate(-.4deg)}50%{transform:translateY(-9px) rotate(.5deg)}}@keyframes shadow-breathe{0%,to{opacity:.72;transform:scaleX(1)}50%{opacity:.45;transform:scaleX(.88)}}@keyframes signal-pulse{0%{box-shadow:0 0 color-mix(in srgb,var(--shell-primary) 30%,transparent)}70%,to{box-shadow:0 0 0 14px transparent}}@keyframes zap-signal{0%{box-shadow:0 0 color-mix(in srgb,#ffd85a 55%,transparent),0 9px 24px color-mix(in srgb,var(--shell-text) 10%,transparent);transform:rotate(-8deg) scale(1)}to{box-shadow:0 0 0 13px transparent,0 0 24px color-mix(in srgb,#f4a900 55%,transparent);transform:rotate(8deg) scale(1.16)}}@keyframes kind1-jumpy{0%{transform:translateY(0) rotate(0) scale(1)}10%{transform:translateY(8px) rotate(-3deg) scale(1.1,.88)}24%{transform:translateY(-18px) rotate(3deg) scale(.92,1.1)}50%{transform:translateY(-84px) rotate(-4deg) scale(.98,1.02)}62%{transform:translateY(-84px) rotate(4deg) scale(1)}88%{transform:translateY(-10px) rotate(-2deg) scale(.96,1.06)}94%{transform:translateY(5px) rotate(0) scale(1.12,.86)}to{transform:translateY(0) rotate(0) scale(1)}}@keyframes kind1-jump-shadow{0%,10%,94%,to{opacity:1;transform:scaleX(1)}50%,62%{opacity:.35;transform:scaleX(.48)}}@keyframes reply-roll-up-down{0%{transform:translateY(0) rotate(0) scale(1)}10%{transform:translateY(8px) rotate(-10deg) scale(1.1,.88)}48%{transform:translateY(-88px) rotate(540deg) scale(.94)}62%{transform:translateY(-88px) rotate(600deg) scale(.98)}91%{transform:translateY(5px) rotate(720deg) scale(1.12,.86)}to{transform:translateY(0) rotate(720deg) scale(1)}}@keyframes reply-roll-shadow{0%,10%,91%,to{opacity:1;transform:scaleX(1)}48%,62%{opacity:.3;transform:scaleX(.42)}}@keyframes zap-standing-turn{0%,4%{transform:translateY(0) rotateY(0) scale(1)}20%{transform:translateY(-5px) rotateY(360deg) scale(1.02)}36%{transform:translateY(-4px) rotateY(720deg) scale(1.01)}48%{transform:translateY(-3px) rotateY(810deg) scale(1.01)}63%{transform:translateY(-2px) rotateY(900deg) scale(1)}80%{transform:translateY(-1px) rotateY(990deg) scale(1)}96%,to{transform:translateY(0) rotateY(1080deg) scale(1)}}@keyframes zap-turn-shadow{0%,4%,12%,20%,28%,36%,55%,71%,88%,96%,to{opacity:1;transform:scaleX(1)}8%,16%,24%,32%,48%,63%,80%{opacity:.42;transform:scaleX(.52)}}@keyframes kind1-signal{0%{box-shadow:0 0 color-mix(in srgb,#ffb84d 48%,transparent),0 9px 24px color-mix(in srgb,var(--shell-text) 10%,transparent);transform:scale(1)}to{box-shadow:0 0 0 10px transparent,0 0 20px color-mix(in srgb,#e28422 45%,transparent);transform:scale(1.12)}}@keyframes pet-sick{0%,to{transform:translateY(3px) rotate(-1deg)}50%{transform:translateY(0) rotate(1deg)}}@keyframes pet-critical{0%,to{transform:translate(-1px) translateY(6px)}50%{transform:translate(1px) translateY(4px)}}@keyframes spark-float{0%,to{opacity:.35;transform:translateY(0) rotate(0)}50%{opacity:.9;transform:translateY(-12px) rotate(15deg)}}@keyframes orbit{to{transform:rotate(360deg)}}@keyframes toast-in{0%{opacity:0;transform:translateY(10px)}}@keyframes speech-pop{0%{opacity:0;transform:translateY(12px) scale(.65) rotate(2deg)}72%{opacity:1;transform:translateY(-2px) scale(1.06) rotate(-.5deg)}to{opacity:1;transform:translateY(0) scale(1) rotate(0)}}@keyframes status-pulse{70%{box-shadow:0 0 0 8px transparent}to{box-shadow:0 0 0 0 transparent}}@media(prefers-reduced-motion:reduce){*,*:before,*:after{scroll-behavior:auto!important;animation-duration:.01ms!important;animation-iteration-count:1!important;transition-duration:.01ms!important}.pet[data-reaction=celebrate] .pet-turner,.pet[data-reaction=reply-roll] .pet-turner,.pet[data-reaction=zap-celebrate] .pet-turner{animation:none!important;filter:drop-shadow(0 0 14px color-mix(in srgb,#ffb84d 45%,transparent));transform:translateY(-4px) scale(1.04)}}@container (max-width: 760px){.pet-layout,.adoption-layout{grid-template-columns:1fr}.pet-layout,.pet-layout--compact .habitat{min-height:100vh}.habitat{min-height:390px;padding:26px 18px 30px}.panel-toggle{top:12px;right:12px}.habitat-live-status{top:14px;left:14px}.habitat:before{width:min(78vw,410px)}.care-panel{border-top:1px solid var(--line);border-left:0;padding:26px 18px 34px}.state-caption h1{font-size:38px}.adoption-layout{gap:24px;padding:24px 18px 40px}.adoption-art{min-height:340px}.viewer-banner{align-items:flex-start;padding:10px 14px}}@container (max-width: 420px){.panel-toggle{width:36px;min-height:36px;justify-content:center;padding:0}.panel-toggle span:not([aria-hidden=true]){display:none}.habitat{min-height:330px;place-content:center}.habitat:before{width:295px}.pet{width:174px;height:180px}.state-caption{margin-top:4px}.state-caption p,.next-state>span,.pet-facts div:nth-child(2){display:none}.state-caption h1{margin-top:1px;font-size:31px}.care-panel{padding-top:20px}.care-heading h2{font-size:23px}.vital-track{margin-top:20px}.action-grid{margin:22px 0}.care-button{min-height:105px;padding:13px}.care-button small{display:none}.pet-facts{margin-bottom:18px}.adoption-art{display:none}.adoption-layout{min-height:100vh}.adoption-card h1{font-size:42px}.welcome-card{align-content:start;min-height:100vh;padding:22px 15px 30px}.welcome-card h1{font-size:40px}.mini-pet{height:145px}.sign-in-status{margin-top:12px;padding:11px 12px}.modal-card{border-radius:20px;padding:18px}.form-columns{grid-template-columns:1fr}.viewer-banner{display:grid}.viewer-banner .secondary-button{width:100%}.viewer-form{grid-template-columns:1fr}.viewer-form .primary-button{width:100%}}</style>
  </head>
  <body>
    <main id="app" aria-live="polite"></main>
  </body>
</html>