Skip to content

Commit c182b13

Browse files
committed
feat(web): add provider icons
1 parent 1b64027 commit c182b13

15 files changed

+107
-20
lines changed
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
import { useRef, useState } from 'react';
2+
3+
import { styled } from 'leather-styles/jsx';
4+
5+
import { useOnMount } from '@leather.io/ui';
6+
7+
type ImgLoaderState = 'loading' | 'loaded' | 'error';
8+
9+
interface ImgFillLoaderProps {
10+
src: string;
11+
alt?: string;
12+
fill: string;
13+
width: string;
14+
height?: string;
15+
}
16+
export function ImgFillLoader({ fill, width, height, src, alt, ...props }: ImgFillLoaderProps) {
17+
const [state, setState] = useState<ImgLoaderState>('loading');
18+
19+
useOnMount(() => {
20+
if (ref.current?.complete) {
21+
setState('loaded');
22+
return;
23+
}
24+
ref.current?.addEventListener('load', () => setState('loaded'));
25+
ref.current?.addEventListener('error', () => setState('error'));
26+
});
27+
28+
const ref = useRef<HTMLImageElement>(null);
29+
30+
return (
31+
<>
32+
<styled.div
33+
width={width}
34+
height={height ?? width}
35+
style={{ background: state !== 'loaded' ? fill : 'none' }}
36+
overflow="hidden"
37+
borderRadius="xs"
38+
{...props}
39+
>
40+
<styled.img
41+
src={src}
42+
ref={ref}
43+
width="100%"
44+
height="100%"
45+
onLoad={() => setState('loaded')}
46+
onError={() => setState('error')}
47+
style={{ display: state === 'error' ? 'none' : 'block' }}
48+
alt={alt}
49+
data-state={state}
50+
/>
51+
</styled.div>
52+
</>
53+
);
54+
}

apps/web/app/components/table.tsx

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -40,15 +40,6 @@ export const TableHead = forwardRef<HTMLTableSectionElement, HTMLStyledProps<'th
4040
(props, ref) => <styled.thead height="40px" className={theadBorderBottom} ref={ref} {...props} />
4141
);
4242

43-
// <styled.th
44-
// key={header.id}
45-
// colSpan={header.colSpan}
46-
// textStyle="label.03"
47-
// color="ink.text-subdued"
48-
// style={{ width: `${header.getSize()}%` }}
49-
// align={(header.column.columnDef.meta as any)?.align}
50-
// >
51-
5243
export const TableHeader = forwardRef<HTMLTableCellElement, HTMLStyledProps<'th'>>((props, ref) => (
5344
<styled.th textStyle="label.03" color="ink.text-subdued" ref={ref} {...props} />
5445
));

apps/web/app/pages/earn/components/earn-provider-table.tsx

Lines changed: 53 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { useMemo, useState } from 'react';
1+
import { ReactElement, useMemo, useState } from 'react';
22

33
import {
44
type ColumnDef,
@@ -13,6 +13,7 @@ import { Flex, type HTMLStyledProps, styled } from 'leather-styles/jsx';
1313
import { DummyIcon } from '~/components/dummy';
1414
import { BitcoinIcon } from '~/components/icons/bitcoin-icon';
1515
import { StacksIcon } from '~/components/icons/stacks-icon';
16+
import { ImgFillLoader } from '~/components/img-loader';
1617
import { SortableHeader, Table, theadBorderBottom } from '~/components/table';
1718

1819
import { Button, Flag } from '@leather.io/ui';
@@ -30,14 +31,44 @@ interface EarnProvider {
3031
minAmount: string | null;
3132
estApr: string;
3233
payout: string;
34+
icon: ReactElement;
3335
}
3436
const earnProviders: EarnProvider[] = [
35-
{ provider: 'Fast Pool', minAmount: null, estApr: '5%', payout: 'STX' },
36-
{ provider: 'PlanBetter', minAmount: '200 STX', estApr: '10%', payout: 'STX' },
37-
{ provider: 'Restake', minAmount: '100 STX', estApr: '11%', payout: 'STX' },
38-
{ provider: 'Xverse Pool', minAmount: '100 STX', estApr: '10%', payout: 'BTC' },
39-
{ provider: 'Stacking DAO', minAmount: '100 STX', estApr: '16%', payout: 'STX' },
40-
{ provider: 'Xverse', minAmount: null, estApr: '10%', payout: 'STX' },
37+
{
38+
provider: 'Fast Pool',
39+
icon: <ImgFillLoader src="icons/fastpool.webp" width="24" fill="black" />,
40+
minAmount: null,
41+
estApr: '5%',
42+
payout: 'STX',
43+
},
44+
{
45+
provider: 'PlanBetter',
46+
icon: <ImgFillLoader src="icons/planbetter.webp" width="24" fill="black" />,
47+
minAmount: '200 STX',
48+
estApr: '10%',
49+
payout: 'STX',
50+
},
51+
{
52+
provider: 'Restake',
53+
icon: <ImgFillLoader src="icons/restake.webp" width="24" fill="#124044" />,
54+
minAmount: '100 STX',
55+
estApr: '11%',
56+
payout: 'STX',
57+
},
58+
{
59+
provider: 'Xverse Pool',
60+
icon: <ImgFillLoader src="icons/xverse.webp" width="24" fill="black" />,
61+
minAmount: '100 STX',
62+
estApr: '10%',
63+
payout: 'BTC',
64+
},
65+
{
66+
provider: 'Stacking DAO',
67+
icon: <ImgFillLoader src="icons/stacking-dao.webp" width="24" fill="#1C3830" />,
68+
minAmount: '100 STX',
69+
estApr: '16%',
70+
payout: 'STX',
71+
},
4172
];
4273

4374
export function EarnProviderTable(props: HTMLStyledProps<'div'>) {
@@ -47,7 +78,7 @@ export function EarnProviderTable(props: HTMLStyledProps<'div'>) {
4778
{
4879
accessorKey: 'provider',
4980
cell: info => (
50-
<Flag img={<DummyIcon />}>
81+
<Flag img={info.row.original.icon}>
5182
<styled.span color="ink.text-primary">{info.getValue() as string}</styled.span>
5283
</Flag>
5384
),
@@ -165,10 +196,21 @@ interface LiquidStackingProvider {
165196
provider: string;
166197
estApr: string;
167198
payout: string;
199+
icon: ReactElement;
168200
}
169201
const liquidStackingProviders: LiquidStackingProvider[] = [
170-
{ provider: 'StackingDAO', estApr: '5%', payout: 'stSTX' },
171-
{ provider: 'LISA', estApr: '10%', payout: 'LiSTX' },
202+
{
203+
provider: 'StackingDAO',
204+
estApr: '5%',
205+
payout: 'stSTX',
206+
icon: <ImgFillLoader src="icons/stacking-dao.webp" width="24" fill="black" />,
207+
},
208+
{
209+
provider: 'LISA',
210+
estApr: '10%',
211+
payout: 'LiSTX',
212+
icon: <ImgFillLoader src="icons/lisa.webp" width="24" fill="#FB9DF1" />,
213+
},
172214
];
173215

174216
export function LiquidStackingProviderTable(props: HTMLStyledProps<'div'>) {
@@ -178,7 +220,7 @@ export function LiquidStackingProviderTable(props: HTMLStyledProps<'div'>) {
178220
{
179221
accessorKey: 'provider',
180222
cell: info => (
181-
<Flag img={<DummyIcon />}>
223+
<Flag img={info.row.original.icon}>
182224
<styled.span color="ink.text-primary">{info.getValue() as string}</styled.span>
183225
</Flag>
184226
),
-5.38 KB
Binary file not shown.

apps/web/public/icons/32x32_Lisa.png

-1.33 KB
Binary file not shown.
-437 Bytes
Binary file not shown.
-958 Bytes
Binary file not shown.
-494 Bytes
Binary file not shown.
-644 Bytes
Binary file not shown.

apps/web/public/icons/fastpool.webp

474 Bytes
Binary file not shown.

0 commit comments

Comments
 (0)