11import { EmailSigninForm } from '@/components/auth/EmailSigninForm' ;
2- import { Box , Frame , Heading , Link , Logo } from '@alef/sys' ;
2+ import { EmailSignupForm } from '@/components/auth/EmailSignupForm' ;
3+ import { OAuthSigninButton } from '@/components/auth/OAuthSigninButton' ;
4+ import { Box , Frame , Heading , Icon , Link , Logo , Tabs } from '@alef/sys' ;
35import { useSearchParams } from '@verdant-web/react-router' ;
46
57const LoginPage = ( ) => {
6- const [ searchParams ] = useSearchParams ( ) ;
8+ const [ searchParams , updateSearch ] = useSearchParams ( ) ;
79 const returnTo = searchParams . get ( 'returnTo' ) ?? undefined ;
10+ const tab = searchParams . get ( 'tab' ) ?? 'login' ;
811 const error = searchParams . get ( 'error' ) ?? undefined ;
912
1013 return (
@@ -16,14 +19,60 @@ const LoginPage = () => {
1619 alef
1720 </ Heading >
1821 </ Box >
19-
20- < Heading level = { 1 } > Login</ Heading >
21- { error && (
22+ { error && (
2223 < Box p style = { { backgroundColor : 'var(--error-paper)' , color : 'var(--error-ink)' } } >
2324 { error }
2425 </ Box >
2526 ) }
26- < EmailSigninForm returnTo = { returnTo } />
27+
28+ < Tabs
29+ value = { tab }
30+ onValueChange = { ( value ) =>
31+ updateSearch ( ( s ) => {
32+ s . set ( 'tab' , value ) ;
33+ return s ;
34+ } )
35+ }
36+ >
37+ < Box align = "stretch" stacked gapped >
38+ < Box justify = "center" >
39+ < Tabs . List >
40+ < Tabs . Trigger value = "login" >
41+ < Box gapped >
42+ < Icon name = "hand" />
43+ Log in
44+ </ Box >
45+ </ Tabs . Trigger >
46+ < Tabs . Trigger value = "signup" >
47+ < Box gapped >
48+ < Icon name = "square-check-big" />
49+ Sign up
50+ </ Box >
51+ </ Tabs . Trigger >
52+ </ Tabs . List >
53+ </ Box >
54+ < Tabs . Content value = "login" >
55+ < Box stacked gapped >
56+ < Heading level = { 1 } > Log in</ Heading >
57+ < OAuthSigninButton provider = "google" returnTo = { returnTo } style = { { margin : '0 auto' } } >
58+ Log in with Google
59+ </ OAuthSigninButton >
60+ < Or />
61+ < EmailSigninForm returnTo = { returnTo } />
62+ </ Box >
63+ </ Tabs . Content >
64+ < Tabs . Content value = "signup" >
65+ < Box stacked gapped >
66+ < Heading level = { 1 } > Sign up</ Heading >
67+ < OAuthSigninButton provider = "google" returnTo = { returnTo } style = { { margin : '0 auto' } } >
68+ Sign up with Google
69+ </ OAuthSigninButton >
70+ < Or />
71+ < EmailSignupForm returnTo = { returnTo } />
72+ </ Box >
73+ </ Tabs . Content >
74+ </ Box >
75+ </ Tabs >
2776 </ Frame >
2877 < Box gapped p = "small" style = { { fontSize : '0.8rem' , color : 'var(--faded)' } } >
2978 < Link to = "https://alef.io/tos" > Terms of Service</ Link >
@@ -33,4 +82,12 @@ const LoginPage = () => {
3382 ) ;
3483} ;
3584
85+ const Or = ( ) => (
86+ < Box justify = "between" align = "center" gapped >
87+ < Box full style = { { borderBottom : 'var(--border)' } } />
88+ < Box > or</ Box >
89+ < Box full style = { { borderBottom : 'var(--border)' } } />
90+ </ Box >
91+ ) ;
92+
3693export default LoginPage ;
0 commit comments