aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/app.js20
-rw-r--r--src/features/nostrlogin.js53
-rw-r--r--src/i18n.js3
3 files changed, 53 insertions, 23 deletions
diff --git a/src/app.js b/src/app.js
index 2e52e56..e6c9018 100644
--- a/src/app.js
+++ b/src/app.js
@@ -2800,15 +2800,17 @@ function onboardScreen() {
o.step = 'seed';
render();
} }, t('onbStart')),
- // Same shape as the sign-in button on the unlock screen: .btn-block
- // forces display:block, so the flex centering goes on an inner wrapper.
- h('button', { class: 'btn-block', style: 'padding:14px', onClick: () => {
- o.step = 'signin';
- ui.nostrLoginOpen = true;
- render();
- } }, h('span', { style: 'display:flex;align-items:center;justify-content:center;gap:8px' },
- h('span', { style: 'display:flex;flex-shrink:0', html: NOSTR_MARK }),
- t('nlSignIn'))),
+ // All the sign-in doors right on the welcome screen (Google, passkey,
+ // Nostr) — the feature supplies them; the single-button fallback keeps
+ // builds without it working.
+ featureHook('frontDoorSignin')
+ || h('button', { class: 'btn-block', style: 'padding:14px', onClick: () => {
+ o.step = 'signin';
+ ui.nostrLoginOpen = true;
+ render();
+ } }, h('span', { style: 'display:flex;align-items:center;justify-content:center;gap:8px' },
+ h('span', { style: 'display:flex;flex-shrink:0', html: NOSTR_MARK }),
+ t('nlSignIn'))),
ui.onbError ? h('div', { class: 'notice err' }, ui.onbError) : null,
]);
}
diff --git a/src/features/nostrlogin.js b/src/features/nostrlogin.js
index fdab973..fa6627b 100644
--- a/src/features/nostrlogin.js
+++ b/src/features/nostrlogin.js
@@ -263,11 +263,11 @@ export function nostrLoginFeature(ctx) {
}
}
- // The ways in, as buttons. `run` receives a signer factory.
- function signerButtons(run) {
- const hasExt = typeof window !== 'undefined' && !!window.nostr;
+ // Google + passkey, with their transient status rows — shared between the
+ // collapsed front-door card and the expanded signer list.
+ function externalButtons(run) {
const hasPasskey = typeof window !== 'undefined' && !!window.PublicKeyCredential && !!navigator.credentials;
- return h('div', { class: 'col', style: 'gap:8px' },
+ return [
h('button', { class: 'btn-block', disabled: ui.nostrLoginBusy,
onClick: () => googleLogin(run) }, t('nlGoogle')),
ui.nostrLoginStatus ? h('div', { class: 'row gap6', style: 'align-items:center;justify-content:center' },
@@ -282,6 +282,14 @@ export function nostrLoginFeature(ctx) {
h('button', { class: 'btn-sm', disabled: ui.nostrLoginBusy, onClick: () => passkeyCreateLogin(run) }, t('nlPasskeyCreate')),
h('button', { class: 'btn-sm btn-ghost', onClick: () => { ui.passkeyOffer = null; render(); } }, t('cancel')))
: null,
+ ];
+ }
+
+ // The ways in, as buttons. `run` receives a signer factory.
+ function signerButtons(run) {
+ const hasExt = typeof window !== 'undefined' && !!window.nostr;
+ return h('div', { class: 'col', style: 'gap:8px' },
+ ...externalButtons(run),
hasExt
? h('button', { class: 'btn-block', disabled: ui.nostrLoginBusy,
onClick: () => run(() => extensionSigner()) }, t('nlExtension'))
@@ -331,16 +339,20 @@ export function nostrLoginFeature(ctx) {
h('button', { class: 'btn-primary grow', disabled: ui.nostrLoginBusy, onClick: createForSigner },
ui.nostrLoginBusy ? h('span', { class: 'spinner' }) : t('nlCreateBtn'))));
}
- // Collapsed by default: one button, expanded only when asked for.
+ // Collapsed by default: Google, passkey, and Nostr right on the front
+ // door; the Nostr button expands into the full signer list.
if (!ui.nostrLoginOpen) {
- // NB .btn-block forces display:block, so the flex centering lives on an
- // inner wrapper rather than the button itself.
- return h('button', {
- class: 'btn-block',
- onClick: () => { ui.nostrLoginOpen = true; ui.nostrLoginError = ''; render(); },
- }, h('span', { style: 'display:flex;align-items:center;justify-content:center;gap:8px' },
- h('span', { style: 'display:flex;flex-shrink:0', html: OSTRICH }),
- t('nlSignIn')));
+ return h('div', { class: 'col', style: 'gap:8px' },
+ ...externalButtons(loginWith),
+ // NB .btn-block forces display:block, so the flex centering lives on
+ // an inner wrapper rather than the button itself.
+ h('button', {
+ class: 'btn-block',
+ onClick: () => { ui.nostrLoginOpen = true; ui.nostrLoginError = ''; render(); },
+ }, h('span', { style: 'display:flex;align-items:center;justify-content:center;gap:8px' },
+ h('span', { style: 'display:flex;flex-shrink:0', html: OSTRICH }),
+ t('nlSignInNostr'))),
+ ui.nostrLoginError ? h('div', { class: 'notice err' }, ui.nostrLoginError) : null);
}
return h('div', { class: 'card col', style: 'gap:10px' },
h('div', { class: 'row between' },
@@ -563,6 +575,21 @@ export function nostrLoginFeature(ctx) {
} finally { resuming = null; }
},
unlockExtra() { return unlockExtra(); },
+ // The welcome screen's sign-in block: Google and passkey act right there;
+ // the Nostr button steps into the wizard's signer list.
+ frontDoorSignin() {
+ return h('div', { class: 'col', style: 'gap:8px' },
+ ...externalButtons(loginWith),
+ h('button', { class: 'btn-block', style: 'padding:14px', onClick: () => {
+ if (ui.onb) ui.onb.step = 'signin';
+ ui.nostrLoginOpen = true;
+ ui.nostrLoginError = '';
+ render();
+ } }, h('span', { style: 'display:flex;align-items:center;justify-content:center;gap:8px' },
+ h('span', { style: 'display:flex;flex-shrink:0', html: OSTRICH }),
+ t('nlSignInNostr'))),
+ ui.nostrLoginError ? h('div', { class: 'notice err' }, ui.nostrLoginError) : null);
+ },
nostrSettingsCards() { return [settingsCard()]; },
};
}
diff --git a/src/i18n.js b/src/i18n.js
index 773a219..ab3315d 100644
--- a/src/i18n.js
+++ b/src/i18n.js
@@ -624,7 +624,8 @@ const STR = {
nlOpenSigner: 'Open signer app',
nlWaitingSigner: 'Waiting for your signer to connect…',
nlTitle: 'Log in with Nostr',
- nlDesc: 'Use your Nostr account to open your wallet — on any device, with the same account.',
+ nlSignInNostr: 'Sign in with Nostr',
+ nlDesc: 'Open the same wallet on any device — with Google, a passkey, or your Nostr account.',
nlExtension: 'Use browser extension',
nlGoogle: 'Sign in with Google',
nlGoogleStatus_checking: 'Checking your account…',