Skip to content

Commit a7bb9a2

Browse files
committed
Update layout success and error layout
1 parent 39313fb commit a7bb9a2

File tree

4 files changed

+129
-8
lines changed

4 files changed

+129
-8
lines changed

src/components/NewsletterForm.jsx

Lines changed: 88 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,27 @@
11
import React from 'react'
2-
import styled from 'styled-components'
3-
2+
import styled, { keyframes } from 'styled-components'
43
import useNewsletter from 'hooks/useNewsletter'
4+
import ArrowPathIcon from './icons/heroicons/ArrowPathicon'
5+
import CheckIcon from './icons/heroicons/CheckIcon'
6+
7+
const spin = keyframes`
8+
from {
9+
transform: rotate(0deg);
10+
}
11+
to {
12+
transform: rotate(360deg);
13+
}
14+
`
15+
16+
const SpinningIcon = styled.div`
17+
display: inline-flex;
18+
animation: ${spin} 1s linear infinite;
19+
20+
svg {
21+
width: 1.25rem;
22+
height: 1.25rem;
23+
}
24+
`
525

626
const Input = styled.input`
727
width: 100%;
@@ -34,23 +54,74 @@ const Button = styled.button`
3454
font-weight: 600;
3555
cursor: pointer;
3656
transition: background-color 0.2s;
57+
display: flex;
58+
align-items: center;
59+
justify-content: center;
60+
gap: 0.5rem;
3761
3862
&:hover {
3963
background: ${(p) => p.theme.colors.main.dark};
4064
}
65+
66+
&:disabled {
67+
opacity: 0.7;
68+
cursor: not-allowed;
69+
}
70+
`
71+
72+
const ErrorMessage = styled.p`
73+
color: #dc2626;
74+
font-size: 0.875rem;
75+
margin-top: 0.5rem;
76+
`
77+
78+
const SuccessMessage = styled.div`
79+
display: flex;
80+
text-align: center;
81+
align-items: center;
82+
justify-content: center;
83+
gap: 0.5rem;
84+
background-color: #f0fdf4;
85+
border: 1px solid #86efac;
86+
border-radius: 8px;
87+
padding: 0rem;
88+
color: #166534;
89+
90+
svg {
91+
width: 1.25rem;
92+
height: 1.25rem;
93+
}
94+
95+
p {
96+
font-size: 0.875rem;
97+
color: #15803d;
98+
}
4199
`
42100

43101
const NewsletterForm = () => {
44102
const [email, setEmail] = React.useState('')
45103
const { subscribe } = useNewsletter()
46104
const [status, setStatus] = React.useState('idle')
105+
const [error, setError] = React.useState(null)
47106

48107
const handleSubmit = (e) => {
49108
e.preventDefault()
50109
setStatus('loading')
51110
subscribe(email)
52111
.then(() => setStatus('success'))
53-
.catch(() => setStatus('error'))
112+
.catch((err) => {
113+
setStatus('error')
114+
setError(err.message)
115+
})
116+
}
117+
118+
if (status === 'success') {
119+
return (
120+
<SuccessMessage>
121+
<CheckIcon />
122+
<p>Thanks for subscribing!</p>
123+
</SuccessMessage>
124+
)
54125
}
55126

56127
return (
@@ -62,11 +133,21 @@ const NewsletterForm = () => {
62133
onChange={(e) => setEmail(e.target.value)}
63134
disabled={status === 'loading'}
64135
required
136+
style={{ marginTop: '0rem' }}
65137
/>
66-
<Button type="submit">Subscribe</Button>
67-
{status === 'loading' && <p>Loading...</p>}
68-
{status === 'success' && <p>Success!</p>}
69-
{status === 'error' && <p>Error</p>}
138+
<Button type="submit" disabled={status === 'loading'}>
139+
{status === 'loading' ? (
140+
<>
141+
<SpinningIcon>
142+
<ArrowPathIcon />
143+
</SpinningIcon>
144+
Subscribing...
145+
</>
146+
) : (
147+
'Subscribe'
148+
)}
149+
</Button>
150+
{status === 'error' && <ErrorMessage>{error}</ErrorMessage>}
70151
</form>
71152
)
72153
}

src/components/RightPanel.jsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,7 +180,7 @@ const RightPanel = ({ isOpen, onClose }) => (
180180
<Typography
181181
variant="typo11"
182182
color="gray.6"
183-
style={{ marginBottom: '0rem' }}
183+
style={{ marginBottom: '1.25rem' }}
184184
>
185185
Get monthly updates about new features and tips to get the the most out
186186
of Meilisearch.
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import React from 'react'
2+
3+
export default function ArrowPathIcon() {
4+
return (
5+
<svg
6+
xmlns="http://www.w3.org/2000/svg"
7+
fill="none"
8+
viewBox="0 0 24 24"
9+
strokeWidth={1.5}
10+
stroke="currentColor"
11+
className="size-6"
12+
>
13+
<path
14+
strokeLinecap="round"
15+
strokeLinejoin="round"
16+
d="M16.023 9.348h4.992v-.001M2.985 19.644v-4.992m0 0h4.992m-4.993 0 3.181 3.183a8.25 8.25 0 0 0 13.803-3.7M4.031 9.865a8.25 8.25 0 0 1 13.803-3.7l3.181 3.182m0-4.991v4.99"
17+
/>
18+
</svg>
19+
)
20+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import React from 'react'
2+
3+
export default function CheckIcon() {
4+
return (
5+
<svg
6+
xmlns="http://www.w3.org/2000/svg"
7+
fill="none"
8+
viewBox="0 0 24 24"
9+
strokeWidth={1.5}
10+
stroke="currentColor"
11+
className="size-6"
12+
>
13+
<path
14+
strokeLinecap="round"
15+
strokeLinejoin="round"
16+
d="m4.5 12.75 6 6 9-13.5"
17+
/>
18+
</svg>
19+
)
20+
}

0 commit comments

Comments
 (0)