/* profile.jsx — the "You" hamburger hub. A clean menu: identity, open-a-new
   account (accordion), and entries into Settings / Documents / Help. Settings
   is its own screen with collapsible sections. */

const Toggle = ({ on, onChange }) =>
<button className="press" role="switch" aria-checked={on} onClick={() => onChange(!on)} style={{ width: 40, height: 23, padding: 0, position: "relative", background: on ? "var(--accent)" : "var(--rule-2)", border: "none", borderRadius: 999, cursor: "pointer", flex: "none", transition: "background 180ms ease" }}>
    <span style={{ position: "absolute", top: 2.5, left: on ? 20 : 2.5, width: 18, height: 18, borderRadius: "50%", background: "#fff", transition: "left 180ms var(--ease)", boxShadow: "0 1px 3px rgba(0,0,0,0.3)" }} />
  </button>;


const SettingRow = ({ label, sub, right, last }) =>
<div style={{ display: "flex", alignItems: "center", gap: 12, padding: "13px 16px", borderBottom: last ? "none" : "1px solid var(--rule)" }}>
    <div style={{ flex: 1, minWidth: 0 }}>
      <div style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 500 }}>{label}</div>
      {sub && <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", marginTop: 3 }}>{sub}</div>}
    </div>
    {right}
  </div>;


/* hold-to-confirm — press and hold 3s to commit a sensitive change */
const HoldButton = ({ label, onConfirm }) => {
  const [progress, setProgress] = useState(0);
  const raf = useRef(null);
  const startT = useRef(0);
  const DURATION = 3000;
  const stop = (done) => {
    if (raf.current) cancelAnimationFrame(raf.current);
    raf.current = null;startT.current = 0;
    setProgress(0);
    if (done) onConfirm();
  };
  const frame = (t) => {
    if (!startT.current) startT.current = t;
    const p = Math.min(1, (t - startT.current) / DURATION);
    setProgress(p);
    if (p >= 1) {stop(true);return;}
    raf.current = requestAnimationFrame(frame);
  };
  const begin = (e) => {e.preventDefault();startT.current = 0;raf.current = requestAnimationFrame(frame);};
  const holding = progress > 0 && progress < 1;
  return (
    <button className="press"
    onPointerDown={begin} onPointerUp={() => stop(false)} onPointerLeave={() => stop(false)} onPointerCancel={() => stop(false)}
    style={{ position: "relative", overflow: "hidden", width: "100%", padding: "12px 16px", border: "1px solid var(--hold-accent)", background: "transparent", color: "var(--hold-accent)", fontFamily: "var(--f-display)", fontSize: 13, fontWeight: 600, cursor: "pointer", borderRadius: 10, touchAction: "none", WebkitUserSelect: "none", userSelect: "none" }}>
      <span style={{ position: "absolute", top: 0, left: 0, bottom: 0, width: `${progress * 100}%`, background: "var(--hold-accent)", opacity: 0.32, transition: holding ? "none" : "width 180ms ease" }} />
      <span style={{ position: "relative" }}>{holding ? "Keep holding…" : label}</span>
    </button>);

};

const TILE = { width: 34, height: 34, flex: "none", border: "1px solid var(--rule-2)", borderRadius: 999, display: "grid", placeItems: "center" };

/* square check control used by the close-accounts list */
const CheckBox = ({ on, disabled }) =>
<span style={{ flex: "none", width: 20, height: 20, borderRadius: 5, display: "grid", placeItems: "center", border: "1.5px solid " + (on ? "var(--accent)" : "var(--rule-2)"), background: on ? "var(--accent)" : "transparent", opacity: disabled ? 0.4 : 1, transition: "background 140ms ease, border-color 140ms ease" }}>
    {on && <Icon name="check" size={13} color="var(--accent-ink)" stroke={2.4} />}
  </span>;


/* close-accounts — multi-select with eligibility gating. An account can be
   closed only when (1) it has no pending trades, transfers, or unsettled funds
   and (2) its balance is $0. Ineligible accounts are dimmed and locked with the
   blocking reason; eligible ones are tappable and selectable (incl. select-all). */
const CLOSEABLE = [
{ id: "ca-bro", name: "Brokerage", sub: "Yoshi · Individual Taxable", bal: 48210.33, pending: 0, holds: true },
{ id: "ca-roth", name: "Roth IRA", sub: "Yoshi · Retirement", bal: 22640.10, pending: 0, holds: true },
{ id: "ca-crypto", name: "Crypto", sub: "Yoshi · Spot ••8841", bal: 5121.74, pending: 1, holds: true },
{ id: "ca-cash", name: "Cash", sub: "Yoshi ••8841", bal: 1284.50, pending: 0, holds: false },
{ id: "ca-legacy", name: "Brokerage (2023)", sub: "Yoshi · Individual Taxable", bal: 0, pending: 0, holds: true },
{ id: "ca-paper", name: "Test drive 1", sub: "Yoshi · Simulated", bal: 0, pending: 0, holds: true }];

const closeBlocker = (a) =>
a.pending ? `${a.pending} pending item${a.pending > 1 ? "s" : ""} — must settle before closing` :
a.bal > 0 ? a.holds ? "Sell or transfer holdings to reach $0" : "Withdraw balance to $0 first" :
null;

/* ---- hidden-accounts (shared store with the Accounts tab) ----------------
   The Accounts tab hides an account via ••• → eye; it persists to this same
   localStorage key and broadcasts "yoshi-hidden". Surfaced here read+unhide. */
const P_HIDDEN_KEY = "yoshi_hidden_accts";
const HIDEABLE_META = {
  Chase: "Checking ••4417 · external",
  Schwab: "Brokerage ••5520 · external",
  Coinbase: "Crypto ••3097 · external"
};
const useHiddenP = () => {
  const read = () => {try {return JSON.parse(localStorage.getItem(P_HIDDEN_KEY) || "[]");} catch (e) {return [];}};
  const [hidden, setHidden] = useState(read);
  useEffect(() => {const f = () => setHidden(read());window.addEventListener("yoshi-hidden", f);return () => window.removeEventListener("yoshi-hidden", f);}, []);
  const unhide = (name) => {try {const cur = read();localStorage.setItem(P_HIDDEN_KEY, JSON.stringify(cur.filter((n) => n !== name)));} catch (e) {}window.dispatchEvent(new CustomEvent("yoshi-hidden"));};
  return [hidden, unhide];
};

const HiddenAccounts = () => {
  const [hidden, unhide] = useHiddenP();
  const list = hidden.filter((n) => HIDEABLE_META[n]);
  return (
    <div style={{ padding: "2px 16px 16px" }}>
      <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", lineHeight: 1.55, marginBottom: list.length ? 13 : 0 }}>
        Accounts you've hidden from your totals and summaries. <span style={{ color: "var(--ink-2)", fontWeight: 600 }}></span>.
      </div>
      {list.length === 0 ?
      <div style={{ fontFamily: "var(--f-display)", fontSize: 12.5, color: "var(--ink-3)", padding: "6px 0" }}>No hidden accounts.</div> :
      <div style={{ border: "1px solid var(--rule-2)", borderRadius: 12, overflow: "hidden" }}>
        {list.map((name, i) =>
        <div key={name} style={{ display: "flex", alignItems: "center", gap: 12, padding: "12px 13px", borderBottom: i === list.length - 1 ? "none" : "1px solid var(--rule)" }}>
          <Icon name="eye" size={17} color="var(--ink-3)" stroke={1.6} />
          <div style={{ flex: 1, minWidth: 0 }}>
            <div style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 600 }}>{name}</div>
            <div style={{ fontFamily: "var(--f-display)", fontSize: 11, color: "var(--ink-3)", marginTop: 3 }}>{HIDEABLE_META[name]}</div>
          </div>
          <Btn kind="ghost" onClick={() => unhide(name)} style={{ padding: "7px 12px", fontSize: 12, whiteSpace: "nowrap" }}>Unhide</Btn>
        </div>
        )}
      </div>}
    </div>);

};

const CloseAccounts = () => {
  const [sel, setSel] = useState([]);
  const [closed, setClosed] = useState([]);
  const [deleted, setDeleted] = useState(false);
  const list = CLOSEABLE.filter((a) => !closed.includes(a.id));
  const eligible = list.filter((a) => !closeBlocker(a));
  const toggle = (id) => setSel((s) => s.includes(id) ? s.filter((x) => x !== id) : [...s, id]);
  const allSel = eligible.length > 0 && eligible.every((a) => sel.includes(a.id));
  const toggleAll = () => setSel(allSel ? [] : eligible.map((a) => a.id));
  const commit = () => {const n = sel.length;setClosed((c) => [...c, ...sel]);setSel([]);return n;};

  return (
    <div style={{ padding: "2px 16px 16px" }}>
      <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", lineHeight: 1.55, marginBottom: 13 }}>
        Closing is permanent. An account can be closed only once it has <span style={{ color: "var(--ink-2)", fontWeight: 600 }}>no pending trades, transfers, or unsettled funds</span> and a <span style={{ color: "var(--ink-2)", fontWeight: 600 }}>$0 balance</span>.
      </div>

      {closed.length > 0 &&
      <div style={{ display: "flex", alignItems: "center", gap: 8, padding: "10px 12px", marginBottom: 12, border: "1px solid color-mix(in srgb, var(--accent) 35%, var(--rule-2))", background: "color-mix(in srgb, var(--accent) 8%, transparent)", borderRadius: 10 }}>
          <Icon name="check" size={15} color="var(--accent)" stroke={2.2} />
          <span style={{ fontFamily: "var(--f-display)", fontSize: 12.5, fontWeight: 600, color: "var(--ink)" }}>{closed.length} account{closed.length > 1 ? "s" : ""} closed</span>
        </div>}

      {list.length === 0 ?
      <div style={{ fontFamily: "var(--f-display)", fontSize: 12.5, color: "var(--ink-3)", padding: "8px 0" }}>No accounts available to close.</div> :
      <>
          {eligible.length > 1 &&
        <button className="press" onClick={toggleAll} style={{ display: "flex", alignItems: "center", gap: 10, background: "none", border: "none", padding: "0 0 11px", cursor: "pointer" }}>
              <CheckBox on={allSel} />
              <span style={{ fontFamily: "var(--f-display)", fontSize: 12.5, fontWeight: 600, color: "var(--ink-2)" }}>Select all eligible ({eligible.length})</span>
            </button>}

          <div style={{ border: "1px solid var(--rule-2)", borderRadius: 12, overflow: "hidden" }}>
            {list.map((a, i) => {
            const block = closeBlocker(a);
            const on = sel.includes(a.id);
            const last = i === list.length - 1;
            return (
              <button key={a.id} className="press" disabled={!!block} onClick={() => !block && toggle(a.id)}
              style={{ width: "100%", textAlign: "left", display: "flex", alignItems: "center", gap: 12, padding: "12px 13px", background: on ? "color-mix(in srgb, var(--accent) 9%, transparent)" : "transparent", border: "none", borderBottom: last ? "none" : "1px solid var(--rule)", cursor: block ? "default" : "pointer", opacity: block ? 0.6 : 1 }}>
                  <CheckBox on={on} disabled={!!block} />
                  <div style={{ flex: 1, minWidth: 0 }}>
                    <div style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 600, color: "var(--ink)" }}>{a.name}</div>
                    <div style={{ display: "flex", alignItems: "center", gap: 5, marginTop: 3 }}>
                      {a.pending > 0 && <Icon name="clock" size={11} color="var(--signal-neg)" stroke={1.8} />}
                      <span style={{ fontFamily: "var(--f-display)", fontSize: 11, lineHeight: 1.4, color: block ? "var(--signal-neg)" : "var(--accent)", fontWeight: block ? 500 : 600 }}>{block || "Ready to close"}</span>
                    </div>
                  </div>
                  <Money value={a.bal} size={12.5} color={a.bal > 0 ? "var(--ink-2)" : "var(--ink-3)"} />
                </button>);

          })}
          </div>

          <div style={{ marginTop: 14 }}>
            {sel.length > 0 ?
          <HoldButton label={`Hold to close ${sel.length} account${sel.length > 1 ? "s" : ""}`} onConfirm={commit} /> :
          <div style={{ width: "100%", padding: "12px 16px", border: "1px solid var(--rule-2)", borderRadius: 10, textAlign: "center", fontFamily: "var(--f-display)", fontSize: 13, fontWeight: 600, color: "var(--ink-3)" }}>
                Select accounts to close
              </div>}
          </div>
        </>}

      {/* danger zone — delete the entire Yoshi account */}
      <div style={{ marginTop: 22, paddingTop: 18, borderTop: "1px solid var(--rule)" }}>
        <div style={{ fontFamily: "var(--f-display)", fontSize: 13, fontWeight: 700, color: "var(--signal-danger)", letterSpacing: "-0.01em" }}>Delete your Yoshi account</div>
        <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", lineHeight: 1.55, marginTop: 5 }}>
          Permanently closes every Yoshi account and removes your profile. All balances must be withdrawn first. Statements and tax documents stay downloadable for seven years.
        </div>
        {deleted ?
        <div style={{ display: "flex", alignItems: "center", gap: 8, padding: "11px 12px", marginTop: 12, border: "1px solid color-mix(in srgb, var(--signal-danger) 40%, var(--rule-2))", background: "color-mix(in srgb, var(--signal-danger) 8%, transparent)", borderRadius: 10 }}>
          <Icon name="check" size={15} color="var(--signal-danger)" stroke={2.2} />
          <span style={{ fontFamily: "var(--f-display)", fontSize: 12.5, fontWeight: 600, color: "var(--ink)" }}>Deletion requested — we'll email you to confirm.</span>
        </div> :
        <div style={{ marginTop: 12, "--hold-accent": "var(--signal-danger)" }}>
          <HoldButton label="Hold to delete your Yoshi account" onConfirm={() => setDeleted(true)} />
        </div>}
      </div>
    </div>);

};


/* a tappable hub row with a leading icon tile */
const MenuRow = ({ icon, label, sub, onClick, last }) =>
<button className="press" onClick={onClick} style={{ width: "100%", background: "none", border: "none", borderBottom: last ? "none" : "1px solid var(--rule)", textAlign: "left", cursor: "pointer", display: "flex", alignItems: "center", gap: 12, padding: "14px 16px" }}>
    <Icon name={icon} size={22} stroke={1.5} color="var(--ink)" />
    <div style={{ flex: 1, minWidth: 0 }}>
      <div style={{ fontFamily: "var(--f-display)", fontSize: 14.5, fontWeight: 600 }}>{label}</div>
      {sub && <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", marginTop: 3 }}>{sub}</div>}
    </div>
    <Icon name="back" size={15} color="var(--ink-3)" style={{ transform: "scaleX(-1)" }} />
  </button>;


/* a collapsible group — tap the header to expand */
const Accordion = ({ icon, label, sub, children, defaultOpen, last, tag }) => {
  const [open, setOpen] = useState(!!defaultOpen);
  return (
    <div style={{ borderBottom: last ? "none" : "1px solid var(--rule)" }}>
      <button className="press" onClick={() => setOpen((o) => !o)} style={{ width: "100%", background: "none", border: "none", textAlign: "left", cursor: "pointer", display: "flex", alignItems: "center", gap: 12, padding: "14px 16px" }}>
        {icon && <Icon name={icon} size={22} stroke={1.5} color="var(--ink)" />}
        <div style={{ flex: 1, minWidth: 0 }}>
          <div style={{ display: "flex", alignItems: "center", gap: 7 }}>
            <span style={{ fontFamily: "var(--f-display)", fontSize: 14.5, fontWeight: 600 }}>{label}</span>
            {tag && <span style={{ fontFamily: "var(--f-display)", fontSize: 8.5, fontWeight: 700, letterSpacing: "0.06em", textTransform: "uppercase", color: "var(--ink-3)", border: "1px solid var(--rule-2)", padding: "2px 6px" }}>{tag}</span>}
          </div>
          {sub && <div style={{ fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)", marginTop: 3 }}>{sub}</div>}
        </div>
        <Icon name="down" size={16} color="var(--ink-3)" style={{ transform: open ? "rotate(180deg)" : "none", transition: "transform 180ms ease" }} />
      </button>
      {open && <div>{children}</div>}
    </div>);

};

const COMING_SOON_ACCOUNTS = [
["Crypto", "A dedicated spot wallet"],
["Retirement", "Roth & Traditional IRA"],
["Joint", "Shared with another person"]];


/* ---- profile form fields · Yoshi-styled (sharp, hairline) ----------------- */
const PInput = ({ label, value, onChange, placeholder, mono }) =>
<div style={{ marginBottom: 12 }}>
    {label && <div style={{ fontFamily: "var(--f-display)", fontSize: 11, fontWeight: 600, color: "var(--ink-2)", marginBottom: 6 }}>{label}</div>}
    <input value={value || ""} onChange={(e) => onChange && onChange(e.target.value)} placeholder={placeholder}
  style={{ width: "100%", padding: "11px 12px", background: "var(--bg-2)", border: "1px solid var(--rule-2)", outline: "none", color: "var(--ink)", fontFamily: mono ? "var(--f-mono)" : "var(--f-display)", fontSize: 14 }} />
  </div>;

const PSelect = ({ label, value, onChange, options }) =>
<div style={{ marginBottom: 12 }}>
    {label && <div style={{ fontFamily: "var(--f-display)", fontSize: 11, fontWeight: 600, color: "var(--ink-2)", marginBottom: 6 }}>{label}</div>}
    <div style={{ position: "relative" }}>
      <select value={value} onChange={(e) => onChange && onChange(e.target.value)}
    style={{ width: "100%", padding: "11px 30px 11px 12px", background: "var(--bg-2)", border: "1px solid var(--rule-2)", outline: "none", color: value && value !== "Select" ? "var(--ink)" : "var(--ink-3)", fontFamily: "var(--f-display)", fontSize: 14, appearance: "none", WebkitAppearance: "none", borderRadius: 0, cursor: "pointer" }}>
        {options.map((o) => <option key={o} value={o}>{o}</option>)}
      </select>
      <Icon name="down" size={15} color="var(--ink-3)" style={{ position: "absolute", right: 10, top: "50%", marginTop: -7, pointerEvents: "none" }} />
    </div>
  </div>;

const PTwo = ({ children }) => <div style={{ display: "grid", gridTemplateColumns: "1fr 1fr", gap: 10 }}>{children}</div>;
const PDivider = () => <div style={{ height: 1, background: "var(--rule)", margin: "6px 0 14px" }} />;

const PersonalInfoForm = () => {
  const [f, setF] = useState({ preferred: "Rivka", first: "Rivka", last: "Lipson", tcFirst: "", tcLast: "", tcEmail: "" });
  const set = (k) => (v) => setF((s) => ({ ...s, [k]: v }));
  return (
    <div style={{ padding: "4px 16px 16px" }}>
      <PInput label="Preferred name" value={f.preferred} onChange={set("preferred")} />
      <PTwo>
        <PInput label="First name" value={f.first} onChange={set("first")} />
        <PInput label="Last name" value={f.last} onChange={set("last")} />
      </PTwo>
      <PDivider />
      <div style={{ fontFamily: "var(--f-display)", fontSize: 13, fontWeight: 600, marginBottom: 10 }}>Trusted contact</div>
      <PTwo>
        <PInput label="First name" value={f.tcFirst} onChange={set("tcFirst")} placeholder="First name" />
        <PInput label="Last name" value={f.tcLast} onChange={set("tcLast")} placeholder="Last name" />
      </PTwo>
      <PInput label="Email" value={f.tcEmail} onChange={set("tcEmail")} placeholder="name@email.com" />
      <PDivider />
      <div style={{ display: "flex", alignItems: "center", gap: 10 }}>
        <div style={{ flex: 1 }}>
          <div style={{ fontFamily: "var(--f-display)", fontSize: 13.5, fontWeight: 600 }}>Address</div>
          <div style={{ fontFamily: "var(--f-display)", fontSize: 11, color: "var(--ink-3)", marginTop: 3 }}>148 Mercer St, New York, NY</div>
        </div>
        <Btn kind="ghost" onClick={() => {}} style={{ padding: "8px 13px", fontSize: 12 }}>Edit address</Btn>
      </div>
    </div>);

};

const InvestorProfileForm = () => {
  const [f, setF] = useState({ accepted: false, risk: "Select", horizon: "Select", income: "$100k–$150k", liquid: "$50k–$100k", total: "", tax: "Single", exp: "Intermediate", jur: "US", obj: "Retirement, emergency fund, home purchase", liq: "" });
  const set = (k) => (v) => setF((s) => ({ ...s, [k]: v }));
  return (
    <div style={{ padding: "4px 16px 16px" }}>
      <div style={{ display: "flex", alignItems: "baseline", gap: 10, marginBottom: 14 }}>
        <div style={{ flex: 1, minWidth: 0 }}>
          <div style={{ fontFamily: "var(--f-display)", fontSize: 13.5, fontWeight: 600 }}>Advice profile</div>
          <div style={{ fontFamily: "var(--f-display)", fontSize: 11, color: "var(--ink-3)", marginTop: 3 }}>Suitability and advisory-client state.</div>
        </div>
        <span style={{ fontFamily: "var(--f-display)", fontSize: 9, fontWeight: 700, letterSpacing: "0.06em", textTransform: "uppercase", color: "var(--ink-3)", border: "1px solid var(--rule-2)", padding: "3px 8px", whiteSpace: "nowrap" }}>{f.accepted ? "Active" : "Not set"}</span>
      </div>
      <div style={{ display: "flex", alignItems: "center", marginBottom: 14 }}>
        <span style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 500, flex: 1 }}>Advisory agreement accepted</span>
        <Toggle on={f.accepted} onChange={set("accepted")} />
      </div>
      <PTwo>
        <PSelect label="Risk tolerance" value={f.risk} onChange={set("risk")} options={["Select", "Conservative", "Moderate", "Aggressive"]} />
        <PSelect label="Time horizon" value={f.horizon} onChange={set("horizon")} options={["Select", "Under 3 years", "3–10 years", "10+ years"]} />
      </PTwo>
      <PTwo>
        <PInput label="Annual income band" value={f.income} onChange={set("income")} />
        <PInput label="Liquid net worth" value={f.liquid} onChange={set("liquid")} />
      </PTwo>
      <PTwo>
        <PInput label="Total net worth" value={f.total} onChange={set("total")} placeholder="—" />
        <PInput label="Tax status" value={f.tax} onChange={set("tax")} />
      </PTwo>
      <PTwo>
        <PInput label="Investment experience" value={f.exp} onChange={set("exp")} />
        <PInput label="Jurisdiction" value={f.jur} onChange={set("jur")} />
      </PTwo>
      <PInput label="Objectives" value={f.obj} onChange={set("obj")} placeholder="Retirement, emergency fund…" />
      <PInput label="Liquidity needs" value={f.liq} onChange={set("liq")} placeholder="e.g. 6 months of cash available" />
    </div>);

};

/* ============ SETTINGS — its own screen, collapsible sections. On web it
   renders as a page beside the menu drawer (like the Agents pane); on mobile
   it pushes over the You hub. ============ */
const SettingsScreen = ({ palette, setPalette, onClose }) => {
  const [channels, setChannels] = useState(PROFILE.channels.map((c) => c[2]));
  const [dailyCap, setDailyCap] = useState(5000);
  const [pendingCap, setPendingCap] = useState(5000);
  const [autoOn, setAutoOn] = useState(true);
  const [emailNotif, setEmailNotif] = useState(true);
  return (
    <div className="push-enter" style={{ position: "absolute", inset: 0, zIndex: 40, background: "var(--bg)", display: "flex", flexDirection: "column" }} data-screen-label="Settings">
      <NavBar title="Settings" onBack={onClose} />
      <div className="scroll" style={{ paddingBottom: 24 }}>
        <div style={{ borderTop: "1px solid var(--rule)" }}>
          <Accordion icon="profile" label="Personal information" sub="Contact details and trusted contact">
            <PersonalInfoForm />
          </Accordion>

          <Accordion icon="doc" label="Investor profile" sub="Suitability and advisory state">
            <InvestorProfileForm />
          </Accordion>

          <Accordion icon="bell" label="Notifications" sub="How Yoshi reaches you">
            {PROFILE.channels.map(([name, detail], i) => {
            const web = window.__YOSHI_WEB && i === 0;
            return <SettingRow key={name} label={web ? "Browser notifications" : name} sub={web ? "This browser" : detail}
            right={<Toggle on={channels[i]} onChange={(v) => setChannels((c) => c.map((x, j) => j === i ? v : x))} />} />;
            })}
            <SettingRow label="Email notifications" sub="Briefs and confirmations to your inbox" last right={<Toggle on={emailNotif} onChange={setEmailNotif} />} />
          </Accordion>

          <Accordion icon="shield" label="Security">
            <SettingRow label="Passkeys" right={<span style={{ fontFamily: "var(--f-display)", fontSize: 12.5, color: "var(--ink-3)" }}>2 devices →</span>} />
            <SettingRow label="Google sign-in" sub="Manage the Google account and email used to sign in to Yoshi" last
            right={<Btn kind="ghost" onClick={() => {}} style={{ padding: "8px 13px", fontSize: 12, whiteSpace: "nowrap" }}>Change</Btn>} />
          </Accordion>

          {!window.__YOSHI_WEB && <Accordion icon="display" label="Appearance">
            <div style={{ padding: "4px 16px 16px" }}>
              <div style={{ display: "flex", alignItems: "center", marginBottom: 11 }}>
                <span style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 500 }}>Theme</span>
                <span style={{ marginLeft: "auto", fontFamily: "var(--f-display)", fontSize: 11.5, color: "var(--ink-3)" }}>{palette === "graphite" ? "Graphite · dark" : "Bone · light"}</span>
              </div>
              <Segmented options={[{ value: "graphite", label: "Dark" }, { value: "bone", label: "Light" }]} value={palette} onChange={setPalette} />
            </div>
          </Accordion>}

          <Accordion icon="gear" label="Automations" sub="Daily autonomous cap" tag="Soon">
            <SettingRow label="Automations active" sub={autoOn ? "Standing rules run inside your limits" : "All standing rules are paused"} right={<Toggle on={autoOn} onChange={setAutoOn} />} />
            <div style={{ padding: "2px 16px 16px", opacity: autoOn ? 1 : 0.45, pointerEvents: autoOn ? "auto" : "none", transition: "opacity .15s" }}>
              <div style={{ display: "flex", alignItems: "baseline", gap: 8 }}>
                <span style={{ fontFamily: "var(--f-display)", fontSize: 14, fontWeight: 500 }}>Daily autonomous cap</span>
                <span style={{ marginLeft: "auto", fontFamily: "var(--f-mono)", fontSize: 15, fontWeight: 500, color: "var(--accent)", fontVariantNumeric: "tabular-nums" }}>{usd(pendingCap, 0)}</span>
              </div>
              <input className="yo-range" type="range" min={0} max={25000} step={500} value={pendingCap}
              onChange={(e) => setPendingCap(parseInt(e.target.value, 10))} style={{ marginTop: 11 }} />
              <div style={{ fontFamily: "var(--f-display)", fontSize: 11, color: "var(--ink-3)", marginTop: 7, lineHeight: 1.45 }}>
                The most your agents can move in a day without asking. Per-automation limits are set on each proposal.
              </div>
              {pendingCap !== dailyCap &&
              <div style={{ marginTop: 13 }}><HoldButton label="Tap & hold to confirm" onConfirm={() => setDailyCap(pendingCap)} /></div>
              }
            </div>
          </Accordion>

          <Accordion icon="eye" label="Hidden accounts" sub="Accounts kept out of your totals">
            <HiddenAccounts />
          </Accordion>

          <Accordion icon="shield" label="Close accounts" last>
            <CloseAccounts />
          </Accordion>
        </div>
      </div>
    </div>);
};
window.SettingsScreen = SettingsScreen;

const Profile = ({ palette, setPalette, nav, onClose }) => {
  const [view, setView] = useState("menu");
  const openBrokerage = () => nav.ask("Open a new Brokerage account", "Happy to. A second brokerage account keeps a strategy separate, so you can hold long-term positions apart from active trades. It opens instantly under your existing KYC, so want me to set it up?");
  const openPaper = () => nav.ask("Open a Paper trading account", "Done. I can open a paper trading account with $100,000 in virtual funds so you can test strategies with no real money at risk. Orders fill at live prices, and you can mirror any paper trade into your real brokerage in one tap. Want me to set it up?");
  if (view === "settings") return <SettingsScreen palette={palette} setPalette={setPalette} onClose={() => setView("menu")} />;
  return (
    <div style={{ flex: 1, display: "flex", flexDirection: "column", minHeight: 0 }}>
      {window.__YOSHI_WEB ? (
        /* drawer header: an X aligned to the top-left hamburger it pulled out from */
        <div style={{ flex: "none", height: 58, display: "flex", alignItems: "center", padding: "0 22px 0 14px", borderBottom: "1px solid var(--rule)" }}>
          <button className="press" aria-label="Close menu" title="Close" onClick={() => (onClose ? onClose() : nav.tab("home"))} style={{ width: 38, height: 38, flex: "none", borderRadius: 10, display: "grid", placeItems: "center", background: "none", border: "none", color: "var(--ink)", cursor: "pointer" }}>
            <Icon name="close" size={22} />
          </button>
        </div>
      ) : (
        <NavBar title="You" border={false} onBack={() => nav.tab("home")} />
      )}
      <div className="scroll" style={{ paddingBottom: 24 }}>
        {/* identity */}
        <div style={{ padding: "0 16px 16px", display: "flex", alignItems: "center", gap: 14 }}>
          <div style={{ width: 56, height: 56, borderRadius: 999, background: "var(--accent)", color: "var(--accent-ink)", display: "grid", placeItems: "center", fontFamily: "var(--f-display)", fontSize: 22, fontWeight: 600 }}>RL</div>
          <div style={{ flex: 1 }}>
            <div style={{ fontFamily: "var(--f-display)", fontSize: 20, fontWeight: 600, letterSpacing: "-0.02em" }}>{PROFILE.name}</div>
          </div>
        </div>

        <div style={{ borderTop: "1px solid var(--rule)" }}>
          <MenuRow icon="accounts" label="Connect an external account" sub="Link a bank or brokerage, read-only" onClick={() => nav.sheet({ type: "link" })} />
          <MenuRow icon="easel" label="Connect an external agent" sub="Bring Yoshi to Claude, ChatGPT, or your own agent" onClick={() => nav.sheet({ type: "connect" })} />

          {/* open a new account — surfaced directly in the menu */}
          <MenuRow icon="plus" label="Open a Brokerage account" sub="Taxable investing across stocks and ETFs" onClick={openBrokerage} />
          <MenuRow icon="trade" label="Open a Paper trading account" sub="Practice with $100k in virtual funds" onClick={openPaper} />
          <MenuRow icon="gear" label="Settings" sub="Automations, channels, security, appearance" onClick={() => (window.__YOSHI_WEB ? nav.menuPage("settings") : setView("settings"))} />
          <MenuRow icon="doc" label="Documents" sub="Statements, tax forms, agreements" onClick={() => (window.__YOSHI_WEB ? nav.menuPage("documents") : nav.sheet({ type: "documents" }))} />
          <MenuRow icon="lifebuoy" label="Support" sub="Chat with Fin, our support assistant" onClick={() => nav.sheet({ type: "support" })} last />
        </div>

        <div style={{ padding: "8px 16px 0" }}>
          <Btn kind="ghost" full onClick={() => nav.signOut()}>Sign out</Btn>
        </div>
      </div>
    </div>);

};

window.Profile = Profile;