aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2026-08-15 14:18:48 -0700
committerAdam Soltys <[email protected]>2026-08-15 14:18:48 -0700
commit16ee8bff43e8733848ef1b944b9d9312ce4ec223 (patch)
tree849e15a4bd35a3565d42171455db7d6d6cd48223 /src
parent97e11aa254354801e20fc6da0aa7693d7558209d (diff)
downloadcoinosv3-16ee8bff43e8733848ef1b944b9d9312ce4ec223.tar.gz
coinosv3-16ee8bff43e8733848ef1b944b9d9312ce4ec223.zip
The header speaks in icons: gear for settings, padlock to lock, and the avatar goes straight to your profile — the popup menu retires
Co-Authored-By: Claude Fable 5 <[email protected]> Claude-Session: https://claude.ai/code/session_014tE4U5nEjGTQy8PwYqamfv
Diffstat (limited to 'src')
-rw-r--r--src/app.js53
1 files changed, 33 insertions, 20 deletions
diff --git a/src/app.js b/src/app.js
index 6c30c34..583a488 100644
--- a/src/app.js
+++ b/src/app.js
@@ -1627,33 +1627,44 @@ function lock({ offerPassword = false } = {}) {
}
// ================================================================ WALLET
-// The avatar anchors the identity menu: Edit profile, Settings, Messages,
-// Logout. The avatar node itself comes from the messages feature (profile
-// cache + punk fallback); without that feature there's no menu.
+// The avatar IS your profile now — one tap opens it (edit lives there).
+// Settings and Lock stand beside it as their own icons; no popup menu.
function avatarMenu() {
const me = (featureHook('nostrLoginIdentity') || {}).pubkey || (wallet.nostrPubkey && wallet.nostrPubkey());
- // No identity (watch-only wallet): the menu still exists — Settings and
- // Logout don't need keys — behind a neutral face.
+ // No identity (watch-only wallet): a neutral face with nowhere to go.
const node = (me && featureHook('headerAvatar', me))
|| h('span', {
class: 'chat-avatar header-ava fallback',
html: '<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M20 21v-2a4 4 0 0 0-4-4H8a4 4 0 0 0-4 4v2"/><circle cx="12" cy="7" r="4"/></svg>',
});
- const item = (label, fn) => h('button', {
- class: 'icon-select-item',
- onClick: () => { ui.avatarMenu = false; fn(); render(); },
- }, label);
- return h('span', { class: 'avatar-menu-wrap' },
- h('button', { class: 'header-avatar', onClick: () => { ui.avatarMenu = !ui.avatarMenu; render(); } }, node),
- (() => { const dt = animWindow('avmenu', !!ui.avatarMenu, 220); return ui.avatarMenu
- ? h('span', {},
- h('div', { class: 'menu-backdrop', onClick: () => { ui.avatarMenu = false; render(); } }),
- (() => { const m = h('div', { class: 'icon-select-menu avatar-menu' },
- me ? item(t('profEdit'), () => featureHook('showProfile', me)) : null,
- item(t('tabSettings'), () => { ui.chatOpen = false; ui.profilePk = null; ui.screen = 'wallet'; ui.tab = 'settings'; ui.settingsPage = null; }),
- me ? item(t('msgDmsTitle'), () => { ui.profilePk = null; ui.chatOpen = true; }) : null,
- item(t('lockWallet'), () => lock({ offerPassword: true }))); applyAnim(m, 'anim-menu', dt); return m; })())
- : null; })());
+ return h('button', {
+ class: 'header-avatar',
+ title: me ? t('profEdit') : undefined,
+ onClick: me ? () => { featureHook('showProfile', me); render(); } : undefined,
+ }, node);
+}
+
+function settingsBtn() {
+ return h('button', {
+ class: 'header-msgs', title: t('tabSettings'), 'aria-label': t('tabSettings'),
+ onClick: () => {
+ ui.chatOpen = false; ui.profilePk = null; ui.userSearch = null; ui.noteThread = null;
+ ui.screen = 'wallet'; ui.tab = 'settings'; ui.settingsPage = null; render();
+ },
+ }, h('span', {
+ class: 'hm-ico',
+ html: '<svg width="21" height="21" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="3"/><path d="M19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1-2.83 2.83l-.06-.06a1.65 1.65 0 0 0-1.82-.33 1.65 1.65 0 0 0-1 1.51V21a2 2 0 0 1-4 0v-.09a1.65 1.65 0 0 0-1-1.51 1.65 1.65 0 0 0-1.82.33l-.06.06a2 2 0 0 1-2.83-2.83l.06-.06a1.65 1.65 0 0 0 .33-1.82 1.65 1.65 0 0 0-1.51-1H3a2 2 0 0 1 0-4h.09a1.65 1.65 0 0 0 1.51-1 1.65 1.65 0 0 0-.33-1.82l-.06-.06a2 2 0 0 1 2.83-2.83l.06.06a1.65 1.65 0 0 0 1.82.33h.09a1.65 1.65 0 0 0 1-1.51V3a2 2 0 0 1 4 0v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 2.83l-.06.06a1.65 1.65 0 0 0-.33 1.82v.09a1.65 1.65 0 0 0 1.51 1H21a2 2 0 0 1 0 4h-.09a1.65 1.65 0 0 0-1.51 1z"/></svg>',
+ }));
+}
+
+function lockBtn() {
+ return h('button', {
+ class: 'header-msgs', title: t('lockWallet'), 'aria-label': t('lockWallet'),
+ onClick: () => lock({ offerPassword: true }),
+ }, h('span', {
+ class: 'hm-ico',
+ html: '<svg width="21" height="21" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round"><rect x="3" y="11" width="18" height="11" rx="2"/><path d="M7 11V7a5 5 0 0 1 10 0v4"/></svg>',
+ }));
}
// Messages sit one tap away, left of the wallet selector. The dot is presence,
@@ -1705,6 +1716,8 @@ function brandHeader(withLock) {
? h('div', { class: 'row gap6', style: 'align-items:center' },
searchBtn(),
messagesBtn(),
+ settingsBtn(),
+ lockBtn(),
h('button', { class: 'btn-sm', onClick: () => { ui.screen = 'accounts'; render(); } },
acc ? acc.label : t('accounts')),
avatarMenu())