{"release_id":"01a1c502-4ad1-0000-ec62-adc54d3c69aa","chunk_id":"01a1c502-4bcc-7c33-9597-4028729f197f","file":"B9w52eY2.mjs","mappings":"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","names":["size","svg","root","path","root_1","path_1","root_2","path_2","root_3","path_3","root_4","path_4","root_5","path_5","root_6","$$props","$$render","consequent_1","consequent_2","consequent_4","alternate","$.set_attribute","PROFILE_LINKS_MAX","PROFILE_LINK_HANDLE_MAX","PROFILE_LINK_URL_MAX","PROFILE_LINK_KINDS","v","hostOf","linkKindDef","kind","k","url","u","groups","$.derived","CATEGORY_ORDER","cat","i","g","when","iso","LOCALE_INFO","locale","CATEGORY_LABEL","msg","TIER_LABEL","label","t","div","$.get","$$anchor","earned","div_1","$.first_child","fragment","span","span_1","div_2","a","article","$0","AchievementMedal","node","div_3","$.sibling","div_4","span_2","span_3","p","div_5","span_4","span_5","div_6","div_7","i_1","span_6","div_8","span_7","$.template_effect","$.set_text","text_8","consequent","classes","text_1","stage","$.state","message","fileInput","code","codeError","fetchCode","$.set","res","body","$.user_effect","onPick","e","input","raw","f","isHeic","heicToJpeg","clean","stripExifClient","fd","finish","button","button_1","h3","button_2","$.delegated","h3_1","p_1","fragment_1","h3_2","p_2","button_3","text_9","root_7","consequent_3","text_10","ul","li","b","text_13","li_1","li_2","p_3","root_8","input_1","node_3","$$value","button_4","p_4","alternate_1","$1","$$args","copied","busy","copyTimer","writeToClipboard","text","ta","ok","copyLink","trackProfileShareClick","$.child","text_2","$.reset","$.append"],"sources":["../../../../../../src/lib/components/ProfileLinkIcon.svelte","../../../../../../src/lib/profile-links.ts","../../../../../../src/lib/components/achievements/AchievementGrid.svelte","../../../../../../src/lib/components/VerifyModal.svelte","../../../../../../src/lib/components/profile/ShareButton.svelte"],"sourcesContent":["<script lang=\"ts\">\n\t/** Mono-tone glyph for a profile link kind. Inherits `currentColor`. */\n\tlet { kind, size = 15 }: { kind: string; size?: number } = $props();\n</script>\n\n<svg width={size} height={size} viewBox=\"0 0 24 24\" fill=\"currentColor\" aria-hidden=\"true\">\n\t{#if kind === 'x'}\n\t\t<path d=\"M18.9 2H22l-7 8 8.2 12h-6.4l-5-6.6L6 22H2.9l7.5-8.6L2.5 2h6.6l4.5 6 5.3-6zm-1.1 18h1.8L7.3 3.9H5.4L17.8 20z\" />\n\t{:else if kind === 'reddit'}\n\t\t<path d=\"M22 12.1a2.2 2.2 0 0 0-3.7-1.6c-1.5-1-3.5-1.7-5.7-1.8l1-4.5 3.1.7a1.6 1.6 0 1 0 .2-.9l-3.5-.8a.5.5 0 0 0-.5.3L11.7 8.7c-2.2.1-4.3.8-5.8 1.8A2.2 2.2 0 1 0 3.5 14a4 4 0 0 0 0 .6c0 3.2 3.8 5.9 8.5 5.9s8.5-2.6 8.5-5.9a4 4 0 0 0 0-.6 2.2 2.2 0 0 0 1.5-1.9zM7 13.6a1.6 1.6 0 1 1 3.2 0 1.6 1.6 0 0 1-3.2 0zm8.9 4.2c-1.1 1.1-3.2 1.2-3.9 1.2s-2.8-.1-3.9-1.2a.4.4 0 0 1 .6-.6c.7.7 2.2.9 3.3.9s2.6-.2 3.3-.9a.4.4 0 0 1 .6.6zm-.3-2.6a1.6 1.6 0 1 1 0-3.2 1.6 1.6 0 0 1 0 3.2z\" />\n\t{:else if kind === 'instagram'}\n\t\t<path d=\"M12 7.4a4.6 4.6 0 1 0 0 9.2 4.6 4.6 0 0 0 0-9.2zm0 7.6a3 3 0 1 1 0-6 3 3 0 0 1 0 6zm5.9-7.8a1.1 1.1 0 1 1-2.2 0 1.1 1.1 0 0 1 2.2 0zM21 8.3c-.1-1.4-.4-2.7-1.4-3.7S17.3 3.3 15.9 3.2c-1.5-.1-6-.1-7.5 0-1.4.1-2.7.4-3.7 1.4S3.3 6.9 3.2 8.3c-.1 1.5-.1 6 0 7.5.1 1.4.4 2.7 1.4 3.7s2.3 1.3 3.7 1.4c1.5.1 6 .1 7.5 0 1.4-.1 2.7-.4 3.7-1.4s1.3-2.3 1.4-3.7c.1-1.5.1-6 0-7.5zm-2 9.1a3 3 0 0 1-1.7 1.7c-1.2.5-4 .4-5.3.4s-4.1.1-5.3-.4a3 3 0 0 1-1.7-1.7c-.5-1.2-.4-4-.4-5.3s-.1-4.1.4-5.3A3 3 0 0 1 6.7 5c1.2-.5 4-.4 5.3-.4s4.1-.1 5.3.4A3 3 0 0 1 19 6.7c.5 1.2.4 4 .4 5.3s.1 4.1-.4 5.4z\" />\n\t{:else if kind === 'telegram'}\n\t\t<path d=\"M21.9 4.6 18.7 19.7c-.2 1.1-.9 1.3-1.8.8l-5-3.7-2.4 2.3c-.3.3-.5.5-1 .5l.4-5.1 9.2-8.3c.4-.4-.1-.6-.6-.2L6.1 13.2 1.2 11.7c-1.1-.3-1.1-1.1.2-1.6L20.5 2.7c.9-.3 1.7.2 1.4 1.9z\" />\n\t{:else if kind === 'onlyfans'}\n\t\t<path d=\"M12 2a10 10 0 1 0 0 20 10 10 0 0 0 0-20zm0 14.5a4.5 4.5 0 1 1 0-9 4.5 4.5 0 0 1 0 9z\" />\n\t{:else}\n\t\t<path d=\"M10.6 13.4a1 1 0 0 1 0 1.4 4 4 0 0 1-5.7 0l-1.7-1.7a4 4 0 0 1 0-5.7l2.8-2.8a4 4 0 0 1 5.7 0 1 1 0 0 1-1.4 1.4 2 2 0 0 0-2.9 0L4.6 8.8a2 2 0 0 0 0 2.9l1.7 1.7a2 2 0 0 0 2.9 0 1 1 0 0 1 1.4 0zm2.8-2.8a1 1 0 0 1 0-1.4 4 4 0 0 1 5.7 0l1.7 1.7a4 4 0 0 1 0 5.7l-2.8 2.8a4 4 0 0 1-5.7 0 1 1 0 0 1 1.4-1.4 2 2 0 0 0 2.9 0l2.8-2.8a2 2 0 0 0 0-2.9l-1.7-1.7a2 2 0 0 0-2.9 0 1 1 0 0 1-1.4 0z\" />\n\t{/if}\n</svg>\n","/** Social links on the public profile: reddit / x / instagram / telegram /\n *  onlyfans handles + one free https url. Client-safe (form + render share\n *  it); the server validates with the same functions before saving. */\n\nexport type ProfileLinkKind = 'reddit' | 'x' | 'instagram' | 'telegram' | 'onlyfans' | 'url';\nexport interface ProfileLink {\n\tkind: ProfileLinkKind;\n\t/** the handle for a network, the full https url for 'url' */\n\tvalue: string;\n}\n\nexport const PROFILE_LINKS_MAX = 5;\nexport const PROFILE_LINK_HANDLE_MAX = 40;\nexport const PROFILE_LINK_URL_MAX = 200;\n\nexport const PROFILE_LINK_KINDS: {\n\tkind: ProfileLinkKind;\n\tname: string;\n\t/** what the settings field shows before the input */\n\tprefix: string;\n\t/** rendered label on the profile pill */\n\tlabel: (v: string) => string;\n\thref: (v: string) => string;\n}[] = [\n\t{ kind: 'reddit', name: 'reddit', prefix: 'reddit.com/u/', label: (v) => `u/${v}`, href: (v) => `https://www.reddit.com/user/${encodeURIComponent(v)}` },\n\t{ kind: 'x', name: 'x', prefix: 'x.com/', label: (v) => `@${v}`, href: (v) => `https://x.com/${encodeURIComponent(v)}` },\n\t{ kind: 'instagram', name: 'instagram', prefix: 'instagram.com/', label: (v) => `@${v}`, href: (v) => `https://www.instagram.com/${encodeURIComponent(v)}` },\n\t{ kind: 'telegram', name: 'telegram', prefix: 't.me/', label: (v) => v, href: (v) => `https://t.me/${encodeURIComponent(v)}` },\n\t{ kind: 'onlyfans', name: 'onlyfans', prefix: 'onlyfans.com/', label: (v) => v, href: (v) => `https://onlyfans.com/${encodeURIComponent(v)}` },\n\t{ kind: 'url', name: 'link', prefix: 'https://', label: (v) => hostOf(v), href: (v) => v }\n];\n\nexport function linkKindDef(kind: string) {\n\treturn PROFILE_LINK_KINDS.find((k) => k.kind === kind) ?? null;\n}\n\nfunction hostOf(url: string): string {\n\ttry {\n\t\tconst u = new URL(url);\n\t\treturn u.host.replace(/^www\\./, '') + (u.pathname !== '/' ? u.pathname.replace(/\\/$/, '') : '');\n\t} catch {\n\t\treturn url;\n\t}\n}\n\nconst HANDLE_RE = /^[a-z0-9_.-]{1,40}$/i;\n/** link shorteners + the usual scam hosts: a free url may not point here */\nconst BLOCKED_HOSTS = ['bit.ly', 'tinyurl.com', 't.co', 'goo.gl', 'is.gd', 'cutt.ly', 'rb.gy', 'shorturl.at', 'tiny.cc', 'linktr.ee.'];\n\n/** Trim, strip a pasted prefix (@, u/, full url) and lowercase where the\n *  network is case-insensitive. Returns null when it isn't a usable handle. */\nexport function normalizeHandle(kind: ProfileLinkKind, raw: string): string | null {\n\tlet v = raw.trim();\n\t// a pasted full url → take the last path segment\n\tconst m = v.match(/^(?:https?:\\/\\/)?(?:www\\.)?(?:reddit\\.com\\/(?:u|user)\\/|x\\.com\\/|twitter\\.com\\/|instagram\\.com\\/|t\\.me\\/|onlyfans\\.com\\/)([^/?#]+)/i);\n\tif (m) v = m[1];\n\tv = v.replace(/^@/, '').replace(/^u\\//i, '').replace(/\\/+$/, '');\n\tif (kind === 'reddit' || kind === 'x') v = v.toLowerCase();\n\tif (!HANDLE_RE.test(v)) return null;\n\treturn v;\n}\n\nexport function normalizeUrl(raw: string): string | null {\n\tlet v = raw.trim();\n\tif (!v) return null;\n\tif (!/^https?:\\/\\//i.test(v)) v = 'https://' + v;\n\tlet u: URL;\n\ttry {\n\t\tu = new URL(v);\n\t} catch {\n\t\treturn null;\n\t}\n\tif (u.protocol !== 'https:') return null;\n\tif (!u.hostname.includes('.') || /\\s/.test(v)) return null;\n\tif (BLOCKED_HOSTS.some((h) => u.hostname === h || u.hostname.endsWith('.' + h))) return null;\n\tu.hash = '';\n\tconst out = u.toString();\n\treturn out.length > PROFILE_LINK_URL_MAX ? null : out;\n}\n\n/** Validate + normalise a whole list. Returns the clean list or an error\n *  message for the form. One entry per kind. */\nexport function cleanProfileLinks(input: unknown): { ok: true; links: ProfileLink[] } | { ok: false; error: string } {\n\tif (!Array.isArray(input)) return { ok: true, links: [] };\n\tconst out: ProfileLink[] = [];\n\tconst seen = new Set<string>();\n\tfor (const raw of input) {\n\t\tif (!raw || typeof raw !== 'object') continue;\n\t\tconst kind = (raw as { kind?: unknown }).kind;\n\t\tconst value = (raw as { value?: unknown }).value;\n\t\tif (typeof kind !== 'string' || typeof value !== 'string' || !linkKindDef(kind)) continue;\n\t\tconst k = kind as ProfileLinkKind;\n\t\tif (!value.trim()) continue; // an empty field is \"remove\"\n\t\tif (seen.has(k)) return { ok: false, error: `only one ${linkKindDef(k)!.name} link` };\n\t\tconst v = k === 'url' ? normalizeUrl(value) : normalizeHandle(k, value);\n\t\tif (!v) {\n\t\t\treturn {\n\t\t\t\tok: false,\n\t\t\t\terror: k === 'url' ? \"that's not a url. https only, no spaces, no shorteners.\" : `that's not a ${linkKindDef(k)!.name} handle. letters, numbers, _ . - only.`\n\t\t\t};\n\t\t}\n\t\tseen.add(k);\n\t\tout.push({ kind: k, value: v });\n\t\tif (out.length > PROFILE_LINKS_MAX) return { ok: false, error: `max ${PROFILE_LINKS_MAX} links` };\n\t}\n\treturn { ok: true, links: out };\n}\n","<script lang=\"ts\">\n\timport { t, locale, LOCALE_INFO } from '$lib/i18n';\n\timport AchievementMedal from './AchievementMedal.svelte';\n\timport { msg } from '$lib/i18n/mark';\n\timport { CATEGORY_ORDER, type AchievementCategory, type AchievementTier } from '$lib/achievements/catalog';\n\timport type { AchievementView } from '$lib/server/achievements';\n\n\tlet { items }: { items: AchievementView[] } = $props();\n\n\tconst groups = $derived(\n\t\tCATEGORY_ORDER.map((cat) => ({\n\t\t\tcat,\n\t\t\titems: items.filter((i) => i.category === cat)\n\t\t})).filter((g) => g.items.length)\n\t);\n\n\tfunction when(iso: string | null): string {\n\t\tif (!iso) return '';\n\t\treturn new Date(iso).toLocaleDateString(LOCALE_INFO[locale()].hreflang, { month: 'short', day: 'numeric' });\n\t}\n\t// The category and tier names are enum values in the catalog; their text lives here.\n\tconst CATEGORY_LABEL: Record<AchievementCategory, string> = {\n\t\ttenure: msg('tenure'),\n\t\tactivity: msg('activity'),\n\t\tcombat: msg('combat'),\n\t\tshame: msg('shame'),\n\t\tsocial: msg('social'),\n\t\tdedication: msg('dedication'),\n\t\tevent: msg('event'),\n\t\tsecret: msg('secret')\n\t};\n\tconst TIER_LABEL: Record<AchievementTier, string> = {\n\t\tbronze: msg('bronze'),\n\t\tsilver: msg('silver'),\n\t\tgold: msg('gold'),\n\t\tmythic: msg('mythic')\n\t};\n\tfunction label(cat: AchievementCategory): string {\n\t\treturn t(CATEGORY_LABEL[cat]);\n\t}\n</script>\n\n<div class=\"ach\">\n\t{#each groups as g (g.cat)}\n\t\t{@const earned = g.items.filter((i) => i.earned).length}\n\t\t<div class=\"cat-head\">\n\t\t\t<span class=\"cat-name\">{label(g.cat)}</span>\n\t\t\t<span class=\"cat-count\">{earned}/{g.items.length}</span>\n\t\t</div>\n\t\t<div class=\"row\">\n\t\t\t{#each g.items as a (a.id)}\n\t\t\t\t<article class=\"card tier-{a.tier}\" class:earned={a.earned} class:locked={!a.earned}>\n\t\t\t\t\t<AchievementMedal glyph={a.glyph} tier={a.tier} size={54} locked={!a.earned} />\n\t\t\t\t\t<div class=\"meta\">\n\t\t\t\t\t\t<div class=\"row1\">\n\t\t\t\t\t\t\t<span class=\"title\">{t(a.title)}</span>\n\t\t\t\t\t\t\t<span class=\"chip\">{t(TIER_LABEL[a.tier])}</span>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t\t<p class=\"desc\">{t(a.desc)}</p>\n\t\t\t\t\t\t{#if a.earned}\n\t\t\t\t\t\t\t<div class=\"foot\"><span class=\"rarity\">◆ {t('unlocked')}</span><span class=\"muted\">{when(a.earnedAt)}</span></div>\n\t\t\t\t\t\t{:else if a.progress}\n\t\t\t\t\t\t\t<div class=\"foot foot--prog\">\n\t\t\t\t\t\t\t\t<div class=\"bar\"><i style=\"width:{Math.round((a.progress[0] / a.progress[1]) * 100)}%\"></i></div>\n\t\t\t\t\t\t\t\t<span class=\"muted\">{a.progress[0].toLocaleString()} / {a.progress[1].toLocaleString()}</span>\n\t\t\t\t\t\t\t</div>\n\t\t\t\t\t\t{:else}\n\t\t\t\t\t\t\t<div class=\"foot\"><span class=\"muted\">{t('locked')}</span></div>\n\t\t\t\t\t\t{/if}\n\t\t\t\t\t</div>\n\t\t\t\t</article>\n\t\t\t{/each}\n\t\t</div>\n\t{/each}\n</div>\n\n<style>\n\t.ach { display: flex; flex-direction: column; }\n\t.cat-head { display: flex; align-items: baseline; gap: 10px; margin: 22px 0 12px; }\n\t.cat-head:first-child { margin-top: 4px; }\n\t.cat-name { font-family: var(--font-display, inherit); font-size: 12px; font-weight: 800; letter-spacing: 0.16em; text-transform: uppercase; color: var(--color-text); }\n\t.cat-count { font-size: 11px; font-weight: 700; color: var(--color-muted); font-variant-numeric: tabular-nums; }\n\t.cat-head::after { content: ''; flex: 1; height: 1px; background: var(--color-border); }\n\n\t.row { display: grid; grid-template-columns: repeat(auto-fill, minmax(248px, 1fr)); gap: 12px; }\n\n\t.card {\n\t\tposition: relative; display: flex; gap: 13px; align-items: center;\n\t\tborder: 1px solid var(--color-border); background: var(--color-surface);\n\t\tborder-radius: 16px; padding: 13px 14px;\n\t\ttransition: transform .16s ease, border-color .16s ease, background .16s ease;\n\t}\n\t.card:hover { transform: translateY(-2px); }\n\t.card.earned { border-color: color-mix(in srgb, var(--r2) 32%, var(--color-border)); }\n\t.card.earned:hover { border-color: color-mix(in srgb, var(--r2) 60%, var(--color-border)); background: color-mix(in srgb, var(--r2) 5%, var(--color-surface)); }\n\t.card.locked { opacity: 0.62; }\n\t.card.locked:hover { opacity: 0.82; border-color: var(--color-muted); }\n\n\t.meta { min-width: 0; flex: 1; }\n\t.row1 { display: flex; align-items: center; gap: 8px; }\n\t.title { font-family: var(--font-display, inherit); font-weight: 800; font-size: 14px; letter-spacing: -0.01em; color: var(--color-text); }\n\t.chip {\n\t\tfont-family: var(--font-display, inherit);\n\t\tfont-size: 8.5px; font-weight: 800; letter-spacing: 0.1em; text-transform: uppercase;\n\t\tpadding: 2px 7px; border-radius: 999px; color: #0d0d0f;\n\t\tbackground: linear-gradient(180deg, var(--r1), var(--r2));\n\t}\n\t.desc { color: var(--color-muted); font-size: 11.5px; line-height: 1.4; margin: 4px 0 0; }\n\t.foot { display: flex; align-items: center; gap: 8px; margin-top: 9px; font-size: 10px; font-weight: 700; }\n\t.rarity { color: var(--r2); }\n\t.muted { color: var(--color-muted); font-variant-numeric: tabular-nums; white-space: nowrap; }\n\t.foot--prog { gap: 9px; }\n\t.bar { flex: 1; height: 5px; border-radius: 999px; background: rgba(255,255,255,.07); overflow: hidden; }\n\t.bar i { display: block; height: 100%; border-radius: 999px; background: linear-gradient(90deg, var(--r2), var(--r1)); }\n\n\t.tier-bronze { --r1: #f0b27a; --r2: #c8803c; }\n\t.tier-silver { --r1: #f4f7fa; --r2: #c2cad3; }\n\t.tier-gold   { --r1: #ffe9a8; --r2: #f5b50a; }\n\t.tier-mythic { --r1: #f3e8ff; --r2: #a855f7; }\n\t/* mythic chip reads better with light text on the violet fill. */\n\t.tier-mythic .chip { color: #fff; }\n\t/* the secret one should read as rare — stronger violet edge + tint than the\n\t   generic earned card (no neon glow, just a clear border + faint fill). */\n\t.card.tier-mythic.earned {\n\t\tborder-color: rgba(168, 85, 247, 0.5);\n\t\tbackground: color-mix(in srgb, #a855f7 8%, var(--color-surface));\n\t}\n\t.card.tier-mythic.earned:hover {\n\t\tborder-color: rgba(168, 85, 247, 0.78);\n\t\tbackground: color-mix(in srgb, #a855f7 12%, var(--color-surface));\n\t}\n</style>\n","<script lang=\"ts\">\n\timport { t } from '$lib/i18n';\n\timport { stripExifClient } from '$lib/utils/strip-exif-client';\n\timport { heicToJpeg, isHeic } from '$lib/utils/heic-to-jpeg';\n\n\tinterface Props {\n\t\topen: boolean;\n\t\tonclose: () => void;\n\t\tonverified: () => void;\n\t}\n\tlet { open, onclose, onverified }: Props = $props();\n\n\ttype Stage = 'intro' | 'submitting' | 'done' | 'error';\n\tlet stage = $state<Stage>('intro');\n\tlet message = $state('');\n\tlet fileInput = $state<HTMLInputElement | null>(null);\n\n\t// Challenge code — issued when the modal opens, valid 10 minutes. The user\n\t// writes THIS in the photo (not their username), so prefab/edited proof\n\t// photos can't pass.\n\tlet code = $state<string | null>(null);\n\tlet codeError = $state(false);\n\n\tasync function fetchCode() {\n\t\tcode = null;\n\t\tcodeError = false;\n\t\ttry {\n\t\t\tconst res = await fetch('/api/verify/challenge');\n\t\t\tconst body = await res.json().catch(() => ({}));\n\t\t\tif (res.ok && body.code) {\n\t\t\t\tcode = body.code as string;\n\t\t\t} else {\n\t\t\t\tcodeError = true;\n\t\t\t}\n\t\t} catch {\n\t\t\tcodeError = true;\n\t\t}\n\t}\n\n\t$effect(() => {\n\t\tif (open) void fetchCode();\n\t});\n\n\tasync function onPick(e: Event) {\n\t\tconst input = e.currentTarget as HTMLInputElement;\n\t\tconst raw = input.files?.[0] ?? null;\n\t\tinput.value = '';\n\t\tif (!raw) return;\n\t\tstage = 'submitting';\n\t\tmessage = '';\n\t\ttry {\n\t\t\tlet f = raw;\n\t\t\tif (await isHeic(f)) f = await heicToJpeg(f);\n\t\t\tconst clean = await stripExifClient(f);\n\t\t\tconst fd = new FormData();\n\t\t\tfd.append('file', clean);\n\t\t\tconst res = await fetch('/api/verify', { method: 'POST', body: fd });\n\t\t\tconst body = await res.json().catch(() => ({}));\n\t\t\tif (res.ok && body.verified) {\n\t\t\t\tstage = 'done';\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// soft \"no match\" verdict (200 with verified:false) or a hard error\n\t\t\tstage = 'error';\n\t\t\tmessage = body.reason || body.error || t('verification failed — try again.');\n\t\t\t// A failed attempt may have burned the clock — refresh the code so the\n\t\t\t// retry instructions always show a live one.\n\t\t\tvoid fetchCode();\n\t\t} catch {\n\t\t\tstage = 'error';\n\t\t\tmessage = t('network error — check your connection and try again.');\n\t\t}\n\t}\n\n\tfunction finish() {\n\t\tonverified();\n\t\tonclose();\n\t}\n</script>\n\n{#if open}\n\t<div class=\"ov\" role=\"dialog\" aria-modal=\"true\">\n\t\t<button class=\"bg\" aria-label={t('close')} onclick={onclose}></button>\n\t\t<div class=\"card\">\n\t\t\t<button class=\"x\" aria-label={t('close')} onclick={onclose}>\n\t\t\t\t<svg width=\"16\" height=\"16\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.5\" stroke-linecap=\"round\"><line x1=\"18\" y1=\"6\" x2=\"6\" y2=\"18\" /><line x1=\"6\" y1=\"6\" x2=\"18\" y2=\"18\" /></svg>\n\t\t\t</button>\n\n\t\t\t{#if stage === 'done'}\n\t\t\t\t<div class=\"center\">\n\t\t\t\t\t<div class=\"check\">\n\t\t\t\t\t\t<svg width=\"30\" height=\"30\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"3\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M20 6L9 17l-5-5\" /></svg>\n\t\t\t\t\t</div>\n\t\t\t\t\t<h3 class=\"h\">{t(\"you're verified.\")}</h3>\n\t\t\t\t\t<p class=\"sub\">{t('the badge is on your profile now. no catfish here.')}</p>\n\t\t\t\t\t<button class=\"cta\" onclick={finish}>{t('nice')}</button>\n\t\t\t\t</div>\n\t\t\t{:else if stage === 'submitting'}\n\t\t\t\t<div class=\"center\">\n\t\t\t\t\t<div class=\"spinner\"></div>\n\t\t\t\t\t<h3 class=\"h\">{t('checking your photo…')}</h3>\n\t\t\t\t\t<p class=\"sub\">{t('running moderation + reading your username. a few seconds.')}</p>\n\t\t\t\t</div>\n\t\t\t{:else}\n\t\t\t\t<div class=\"eyebrow\">{t('get verified')}</div>\n\t\t\t\t<h3 class=\"h\">{t(\"prove it's really you.\")}</h3>\n\t\t\t\t<p class=\"sub\">\n\t\t\t\t\t{t('write your one-time code')}\n\t\t\t\t\t{#if code}<span class=\"tag\">{code}</span>{:else if codeError}<button type=\"button\" class=\"tag tag-retry\" onclick={fetchCode}>{t('tap to get a code')}</button>{:else}<span class=\"tag\">…</span>{/if}\n\t\t\t\t\t{t('on a piece of paper (or on your skin) and take a clear photo of it with your dick in frame. we read the code, then')} <span class=\"em\">{t('delete the photo')}</span> {t('— it never goes public. you just get the badge.')}\n\t\t\t\t</p>\n\n\t\t\t\t<ul class=\"steps\">\n\t\t\t\t\t<li><span class=\"n\">1</span> {t('write')} <b>{code ?? t('your code')}</b> {t('big and legible')}</li>\n\t\t\t\t\t<li><span class=\"n\">2</span> {t('shoot it in the same frame, well-lit')}</li>\n\t\t\t\t\t<li><span class=\"n\">3</span> {t('upload within 10 minutes — we verify and bin the photo')}</li>\n\t\t\t\t</ul>\n\n\t\t\t\t{#if stage === 'error'}\n\t\t\t\t\t<p class=\"err\">{message}</p>\n\t\t\t\t{/if}\n\n\t\t\t\t<input\n\t\t\t\t\ttype=\"file\"\n\t\t\t\t\taccept=\"image/*\"\n\t\t\t\t\tclass=\"hidden\"\n\t\t\t\t\tbind:this={fileInput}\n\t\t\t\t\tonchange={onPick}\n\t\t\t\t/>\n\t\t\t\t<button class=\"cta\" disabled={!code} onclick={() => fileInput?.click()}>\n\t\t\t\t\t{stage === 'error' ? t('try another photo') : t('upload verification photo')}\n\t\t\t\t</button>\n\t\t\t\t<p class=\"fine\">{t('private · deleted right after · jpg / png / webp · 5MB')}</p>\n\t\t\t{/if}\n\t\t</div>\n\t</div>\n{/if}\n\n<style>\n\t.ov {\n\t\tposition: fixed;\n\t\tinset: 0;\n\t\tz-index: 100;\n\t\tdisplay: flex;\n\t\talign-items: flex-end;\n\t\tjustify-content: center;\n\t}\n\t@media (min-width: 640px) {\n\t\t.ov {\n\t\t\talign-items: center;\n\t\t}\n\t}\n\t.bg {\n\t\tposition: absolute;\n\t\tinset: 0;\n\t\tbackground: rgba(0, 0, 0, 0.7);\n\t\tbackdrop-filter: blur(4px);\n\t\tborder: none;\n\t}\n\t.card {\n\t\tposition: relative;\n\t\twidth: 100%;\n\t\tmax-width: 420px;\n\t\tbackground: var(--color-bg);\n\t\tborder: 1px solid var(--color-border);\n\t\tborder-radius: 24px 24px 0 0;\n\t\tpadding: 28px 22px 26px;\n\t}\n\t@media (min-width: 640px) {\n\t\t.card {\n\t\t\tborder-radius: 24px;\n\t\t\tmargin: 0 16px;\n\t\t}\n\t}\n\t.x {\n\t\tposition: absolute;\n\t\ttop: 14px;\n\t\tright: 14px;\n\t\tdisplay: flex;\n\t\theight: 32px;\n\t\twidth: 32px;\n\t\talign-items: center;\n\t\tjustify-content: center;\n\t\tborder-radius: 999px;\n\t\tbackground: var(--color-surface);\n\t\tborder: none;\n\t\tcolor: color-mix(in srgb, var(--color-muted) 60%, transparent);\n\t\tcursor: pointer;\n\t}\n\t.x:hover {\n\t\tcolor: var(--color-muted);\n\t}\n\t.eyebrow {\n\t\tfont-size: 11px;\n\t\tfont-weight: 800;\n\t\tletter-spacing: 0.2em;\n\t\ttext-transform: uppercase;\n\t\tcolor: #3f86e6;\n\t}\n\t.h {\n\t\tfont-family: var(--font-display);\n\t\tfont-size: 26px;\n\t\tfont-weight: 800;\n\t\tletter-spacing: -0.02em;\n\t\tmargin-top: 6px;\n\t\tcolor: var(--color-text);\n\t}\n\t.sub {\n\t\tfont-size: 14px;\n\t\tline-height: 1.55;\n\t\tcolor: var(--color-muted);\n\t\tmargin-top: 10px;\n\t}\n\t.tag {\n\t\tdisplay: inline-block;\n\t\tpadding: 1px 7px;\n\t\tborder-radius: 6px;\n\t\tbackground: color-mix(in srgb, #3f86e6 16%, transparent);\n\t\tcolor: #7fb0f0;\n\t\tfont-weight: 700;\n\t\tletter-spacing: 0.08em;\n\t}\n\t.tag-retry {\n\t\tborder: none;\n\t\tcursor: pointer;\n\t\tletter-spacing: normal;\n\t}\n\t.cta:disabled {\n\t\topacity: 0.5;\n\t\tcursor: not-allowed;\n\t}\n\t.em {\n\t\tcolor: var(--color-text);\n\t\tfont-weight: 600;\n\t}\n\t.steps {\n\t\tlist-style: none;\n\t\tmargin: 18px 0 0;\n\t\tpadding: 0;\n\t\tdisplay: flex;\n\t\tflex-direction: column;\n\t\tgap: 10px;\n\t}\n\t.steps li {\n\t\tdisplay: flex;\n\t\talign-items: center;\n\t\tgap: 10px;\n\t\tfont-size: 13.5px;\n\t\tcolor: color-mix(in srgb, var(--color-text) 82%, transparent);\n\t}\n\t.steps .n {\n\t\tdisplay: inline-grid;\n\t\tplace-items: center;\n\t\twidth: 22px;\n\t\theight: 22px;\n\t\tflex-shrink: 0;\n\t\tborder-radius: 999px;\n\t\tbackground: color-mix(in srgb, #3f86e6 18%, transparent);\n\t\tcolor: #7fb0f0;\n\t\tfont-size: 11px;\n\t\tfont-weight: 800;\n\t}\n\t.cta {\n\t\tdisplay: block;\n\t\twidth: 100%;\n\t\tmargin-top: 20px;\n\t\tpadding: 14px;\n\t\tborder-radius: 12px;\n\t\tborder: none;\n\t\tbackground: #2f7fe0;\n\t\tcolor: #fff;\n\t\tfont-family: var(--font-display);\n\t\tfont-size: 15px;\n\t\tfont-weight: 700;\n\t\tcursor: pointer;\n\t\ttransition: background 0.15s;\n\t}\n\t.cta:hover {\n\t\tbackground: #2569c4;\n\t}\n\t.fine {\n\t\ttext-align: center;\n\t\tfont-size: 11px;\n\t\tcolor: color-mix(in srgb, var(--color-muted) 60%, transparent);\n\t\tmargin-top: 10px;\n\t}\n\t.err {\n\t\tmargin-top: 16px;\n\t\tpadding: 10px 12px;\n\t\tborder-radius: 10px;\n\t\tborder: 1px solid color-mix(in srgb, var(--color-coral) 30%, transparent);\n\t\tbackground: color-mix(in srgb, var(--color-coral) 8%, transparent);\n\t\tfont-size: 12.5px;\n\t\tcolor: var(--color-coral);\n\t}\n\t.center {\n\t\ttext-align: center;\n\t\tpadding: 10px 0 4px;\n\t}\n\t.check {\n\t\tdisplay: inline-grid;\n\t\tplace-items: center;\n\t\twidth: 60px;\n\t\theight: 60px;\n\t\tborder-radius: 999px;\n\t\tmargin-bottom: 8px;\n\t\tbackground: linear-gradient(155deg, #5eb3ff, #2f7fe0 60%, #1f5fb0);\n\t\tcolor: #fff;\n\t}\n\t.center .h {\n\t\tmargin-top: 4px;\n\t}\n\t.center .sub {\n\t\tmargin-top: 6px;\n\t}\n\t.spinner {\n\t\twidth: 40px;\n\t\theight: 40px;\n\t\tmargin: 6px auto 4px;\n\t\tborder-radius: 999px;\n\t\tborder: 3px solid var(--color-border);\n\t\tborder-top-color: #2f7fe0;\n\t\tanimation: spin 0.8s linear infinite;\n\t}\n\t@keyframes spin {\n\t\tto {\n\t\t\ttransform: rotate(360deg);\n\t\t}\n\t}\n\t.hidden {\n\t\tdisplay: none;\n\t}\n</style>\n","<script lang=\"ts\">\n\timport { t } from '$lib/i18n';\n\timport { trackProfileShareClick } from '$lib/analytics';\n\n\tinterface Props {\n\t\tnickname: string;\n\t\tisOwnProfile: boolean;\n\t}\n\n\tlet { nickname, isOwnProfile }: Props = $props();\n\n\tlet copied = $state(false);\n\tlet busy = $state(false);\n\tlet copyTimer: ReturnType<typeof setTimeout> | null = null;\n\n\tconst url = $derived.by(() => {\n\t\tif (typeof window === 'undefined') return `/u/${encodeURIComponent(nickname)}`;\n\t\tconst u = new URL(`/u/${encodeURIComponent(nickname)}`, window.location.origin);\n\t\tu.searchParams.set('utm_source', 'profile_share');\n\t\treturn u.toString();\n\t});\n\n\t// RAT-301: clipboard-only. The previous shareOrCopy() path opened the\n\t// native share sheet via navigator.share({url, title, text}); when the\n\t// user picked \"Copy\" from the sheet on iOS several targets pasted the\n\t// `text` field (\"rate them on ratemyd ↗\") instead of the URL — the\n\t// labeled intent (\"copy link\") was broken. Going straight to\n\t// clipboard.writeText guarantees the URL lands on paste. Other share\n\t// entry points (duel, arena, niche, post) keep shareOrCopy because\n\t// their UX explicitly wants the share sheet's app picker.\n\tasync function writeToClipboard(text: string): Promise<boolean> {\n\t\t// Modern path. Requires HTTPS or localhost — both prod + dev qualify.\n\t\tif (navigator.clipboard?.writeText) {\n\t\t\ttry {\n\t\t\t\tawait navigator.clipboard.writeText(text);\n\t\t\t\treturn true;\n\t\t\t} catch {\n\t\t\t\t// Permission denied / transient — fall through to legacy.\n\t\t\t}\n\t\t}\n\t\t// Legacy fallback for very old Safari / lockdown contexts. A hidden\n\t\t// textarea + execCommand('copy') still works where Clipboard API\n\t\t// doesn't. Cheap to keep, helps the tail.\n\t\ttry {\n\t\t\tconst ta = document.createElement('textarea');\n\t\t\tta.value = text;\n\t\t\tta.style.position = 'fixed';\n\t\t\tta.style.opacity = '0';\n\t\t\tdocument.body.appendChild(ta);\n\t\t\tta.focus();\n\t\t\tta.select();\n\t\t\tconst ok = document.execCommand('copy');\n\t\t\tdocument.body.removeChild(ta);\n\t\t\treturn ok;\n\t\t} catch {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\tasync function copyLink() {\n\t\tif (busy) return;\n\t\tbusy = true;\n\t\ttry {\n\t\t\tconst ok = await writeToClipboard(url);\n\t\t\tif (ok) {\n\t\t\t\tcopied = true;\n\t\t\t\ttrackProfileShareClick({ isOwnProfile, method: 'clipboard' });\n\t\t\t\tif (copyTimer) clearTimeout(copyTimer);\n\t\t\t\tcopyTimer = setTimeout(() => (copied = false), 2000);\n\t\t\t}\n\t\t} finally {\n\t\t\tbusy = false;\n\t\t}\n\t}\n</script>\n\n<button\n\ttype=\"button\"\n\tonclick={copyLink}\n\tdisabled={busy}\n\taria-label={t('copy profile link')}\n\tclass=\"inline-flex shrink-0 cursor-pointer items-center gap-1.5 rounded-lg border border-border bg-surface px-3 py-2 text-sm font-semibold text-text transition-colors hover:border-muted disabled:cursor-wait disabled:opacity-70\"\n>\n\t{#if copied}\n\t\t<svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.4\" stroke-linecap=\"round\" stroke-linejoin=\"round\" class=\"text-green\">\n\t\t\t<path d=\"M20 6L9 17l-5-5\"/>\n\t\t</svg>\n\t\t<span class=\"text-green\">{t('copied')}</span>\n\t{:else}\n\t\t<svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n\t\t\t<rect x=\"9\" y=\"9\" width=\"13\" height=\"13\" rx=\"2\" ry=\"2\"/>\n\t\t\t<path d=\"M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2 2v1\"/>\n\t\t</svg>\n\t\t{t('copy link')}\n\t{/if}\n</button>\n"],"version":3}