Commit 6c0e4529 authored by tom's avatar tom

CutLink for lists

parent eb7637a9
import { Flex, type FlexProps } from '@chakra-ui/react';
import React from 'react';
import type { LinkProps } from 'toolkit/chakra/link';
import { Link } from 'toolkit/chakra/link';
interface Props<T> extends FlexProps {
items: Array<T>;
renderItem: (item: T, index: number) => React.ReactNode;
linkProps?: LinkProps;
cutLength?: number;
}
const CUT_LENGTH = 3;
const CutLinkList = <T,>(props: Props<T>) => {
const { items, renderItem, linkProps, cutLength = CUT_LENGTH, ...rest } = props;
const [ isExpanded, setIsExpanded ] = React.useState(false);
const handleToggle = React.useCallback(() => {
setIsExpanded((flag) => !flag);
}, []);
return (
<Flex flexDir="column" w="100%" { ...rest }>
{ items.slice(0, isExpanded ? undefined : cutLength).map(renderItem) }
{ items.length > cutLength && (
<Link
textStyle="sm"
textDecorationLine="underline"
textDecorationStyle="dashed"
w="fit-content"
onClick={ handleToggle }
{ ...linkProps }
>
{ isExpanded ? 'Hide' : 'Show all' }
</Link>
) }
</Flex>
);
};
export default React.memo(CutLinkList) as typeof CutLinkList;
......@@ -20,7 +20,7 @@ import { currencyUnits } from 'lib/units';
import { Link } from 'toolkit/chakra/link';
import { Skeleton } from 'toolkit/chakra/skeleton';
import { Tooltip } from 'toolkit/chakra/tooltip';
import CutLink from 'toolkit/components/CutLink/CutLink';
import CutLinkDetails from 'toolkit/components/CutLink/CutLinkDetails';
import OptimisticL2TxnBatchDA from 'ui/shared/batch/OptimisticL2TxnBatchDA';
import BlockGasUsed from 'ui/shared/block/BlockGasUsed';
import CopyToClipboard from 'ui/shared/CopyToClipboard';
......@@ -545,7 +545,7 @@ const BlockDetails = ({ query }: Props) => {
) }
{ /* ADDITIONAL INFO */ }
<CutLink loading={ isPlaceholderData } mt={ 6 } gridColumn={{ base: undefined, lg: '1 / 3' }}>
<CutLinkDetails loading={ isPlaceholderData } mt={ 6 } gridColumn={{ base: undefined, lg: '1 / 3' }}>
<GridItem colSpan={{ base: undefined, lg: 2 }} mt={{ base: 1, lg: 4 }}/>
{ rollupFeature.isEnabled && rollupFeature.type === 'zkSync' && data.zksync &&
......@@ -744,7 +744,7 @@ const BlockDetails = ({ query }: Props) => {
) }
</>
) }
</CutLink>
</CutLinkDetails>
</Grid>
);
......
/* eslint-disable react/jsx-no-bind */
/* eslint-disable max-len */
import { Box } from '@chakra-ui/react';
import { Box, Text } from '@chakra-ui/react';
import React from 'react';
import * as addressMock from 'mocks/address/address';
......@@ -10,7 +11,8 @@ import * as ensMock from 'mocks/ens/domain';
import * as poolMock from 'mocks/pools/pool';
import * as txMock from 'mocks/txs/tx';
import { Link } from 'toolkit/chakra/link';
import CutLink from 'toolkit/components/CutLink/CutLink';
import CutLinkDetails from 'toolkit/components/CutLink/CutLinkDetails';
import CutLinkList from 'toolkit/components/CutLink/CutLinkList';
import AddressEntity from 'ui/shared/entities/address/AddressEntity';
import BlobEntity from 'ui/shared/entities/blob/BlobEntity';
import BlockEntity from 'ui/shared/entities/block/BlockEntity';
......@@ -96,15 +98,24 @@ const LinkShowcase = () => {
<SectionSubHeader>Cut link</SectionSubHeader>
<SamplesStack>
<Sample label="Default" flexDirection="column" alignItems="flex-start">
<CutLink id="CutLink_1">
<Sample label="Show details" flexDirection="column" alignItems="flex-start">
<CutLinkDetails id="CutLink_1">
<Box maxW="500px">{ TEXT }</Box>
</CutLink>
</Sample>
<Sample label="Loading" flexDirection="column" alignItems="flex-start">
<CutLink id="CutLink_2" loading>
</CutLinkDetails>
<CutLinkDetails id="CutLink_2" loading>
<Box maxW="500px">{ TEXT }</Box>
</CutLink>
</CutLinkDetails>
</Sample>
<Sample label="Expand all list" flexDirection="row" alignItems="flex-start" flexWrap="nowrap">
<CutLinkList
items={ [ 'foo', 'bar', 'baz', 'qux', 'quux', 'corge', 'grault', 'garply', 'waldo', 'fred', 'plugh', 'xyzzy', 'thud' ] }
renderItem={ (item) => <Text>{ item }</Text> }
/>
<CutLinkList
items={ [ 'foo', 'bar', 'baz', 'qux', 'quux', 'corge', 'grault', 'garply', 'waldo', 'fred', 'plugh', 'xyzzy', 'thud' ] }
renderItem={ (item) => <Text>{ item }</Text> }
linkProps={{ loading: true }}
/>
</Sample>
</SamplesStack>
......
import { Flex } from '@chakra-ui/react';
import React from 'react';
import { Link } from 'toolkit/chakra/link';
import CutLinkList from 'toolkit/components/CutLink/CutLinkList';
import * as DetailsInfoItem from 'ui/shared/DetailsInfoItem';
import AddressEntity from 'ui/shared/entities/address/AddressEntity';
......@@ -9,13 +8,9 @@ interface Props {
items: Array<string>;
}
const CUT_LENGTH = 2;
const TxAllowedPeekers = ({ items }: Props) => {
const [ isExpanded, setIsExpanded ] = React.useState(false);
const handleCutLinkClick = React.useCallback(() => {
setIsExpanded((flag) => !flag);
const renderItem = React.useCallback((item: string) => {
return <AddressEntity key={ item } address={{ hash: item, is_contract: true }}/>;
}, []);
return (
......@@ -26,22 +21,12 @@ const TxAllowedPeekers = ({ items }: Props) => {
Allowed peekers
</DetailsInfoItem.Label>
<DetailsInfoItem.Value>
<Flex flexDir="column" rowGap={ 3 } w="100%">
{ items
.slice(0, isExpanded ? undefined : CUT_LENGTH)
.map((item) => <AddressEntity key={ item } address={{ hash: item, is_contract: true }}/>) }
</Flex>
{ items.length > CUT_LENGTH && (
<Link
display="inline-block"
fontSize="sm"
textDecorationLine="underline"
textDecorationStyle="dashed"
onClick={ handleCutLinkClick }
>
{ isExpanded ? 'Hide' : 'Show all' }
</Link>
) }
<CutLinkList
items={ items }
renderItem={ renderItem }
cutLength={ 2 }
rowGap={ 3 }
/>
</DetailsInfoItem.Value>
</>
);
......
......@@ -29,7 +29,7 @@ import { Badge } from 'toolkit/chakra/badge';
import { Link } from 'toolkit/chakra/link';
import { Skeleton } from 'toolkit/chakra/skeleton';
import { Tooltip } from 'toolkit/chakra/tooltip';
import CutLink from 'toolkit/components/CutLink/CutLink';
import CutLinkDetails from 'toolkit/components/CutLink/CutLinkDetails';
import CopyToClipboard from 'ui/shared/CopyToClipboard';
import CurrencyValue from 'ui/shared/CurrencyValue';
import * as DetailsInfoItem from 'ui/shared/DetailsInfoItem';
......@@ -168,7 +168,7 @@ const TxInfo = ({ data, isLoading, socketStatus }: Props) => {
<DetailsInfoItem.Value>
<TxStatus status={ data.status } errorText={ data.status === 'error' ? data.result : undefined } isLoading={ isLoading }/>
{ data.method && (
<Badge colorScheme={ data.method === 'Multicall' ? 'teal' : 'gray' } loading={ isLoading } truncated ml={ 3 }>
<Badge colorPalette={ data.method === 'Multicall' ? 'teal' : 'gray' } loading={ isLoading } truncated ml={ 3 }>
{ data.method }
</Badge>
) }
......@@ -783,7 +783,7 @@ const TxInfo = ({ data, isLoading, socketStatus }: Props) => {
) }
<TxInfoScrollFees data={ data } isLoading={ isLoading }/>
<CutLink loading={ isLoading } mt={ 6 } gridColumn={{ base: undefined, lg: '1 / 3' }} isExpanded={ isExpanded } onClick={ handleCutLinkClick }>
<CutLinkDetails loading={ isLoading } mt={ 6 } gridColumn={{ base: undefined, lg: '1 / 3' }} isExpanded={ isExpanded } onClick={ handleCutLinkClick }>
<GridItem colSpan={{ base: undefined, lg: 2 }} mt={{ base: 1, lg: 4 }}/>
{ data.arbitrum?.contains_message && data.arbitrum?.message_related_info && (
......@@ -893,7 +893,7 @@ const TxInfo = ({ data, isLoading, socketStatus }: Props) => {
) }
{ data.zksync && <ZkSyncL2TxnBatchHashesInfo data={ data.zksync } isLoading={ isLoading }/> }
</CutLink>
</CutLinkDetails>
</Grid>
);
};
......
import { Flex, Text } from '@chakra-ui/react';
import { Text } from '@chakra-ui/react';
import React from 'react';
import { Link } from 'toolkit/chakra/link';
import CutLinkList from 'toolkit/components/CutLink/CutLinkList';
import NftEntity from 'ui/shared/entities/nft/NftEntity';
interface Props {
......@@ -11,40 +11,23 @@ interface Props {
}
const TxStateTokenIdList = ({ items, tokenAddress, isLoading }: Props) => {
const [ isCut, setIsCut ] = React.useState(true);
const renderItem = React.useCallback((item: typeof items[number], index: number) => {
if (item.total.token_id !== null) {
return <NftEntity key={ index } hash={ tokenAddress } id={ item.total.token_id } isLoading={ isLoading }/>;
}
const handleToggle = React.useCallback(() => {
setIsCut((prev) => !prev);
}, []);
return <Text key={ index } color="text.secondary">N/A</Text>;
}, [ isLoading, tokenAddress ]);
return (
<Flex flexDir="column" rowGap={ 2 }>
{ items.slice(0, isCut ? 3 : items.length).map((item, index) => {
if (item.total.token_id !== null) {
return (
<NftEntity
key={ index }
hash={ tokenAddress }
id={ item.total.token_id }
isLoading={ isLoading }
/>
);
} else {
return <Text key={ index } color="text_secondary">N/A</Text>;
}
}) }
{ items.length > 3 && (
<Link
fontWeight={ 400 }
textDecoration="underline dashed"
_hover={{ textDecoration: 'underline dashed', color: 'link_hovered' }}
onClick={ handleToggle }
pb={{ base: '5px', md: 0 }}
>
View { isCut ? 'more' : 'less' }
</Link>
) }
</Flex>
<CutLinkList
items={ items }
renderItem={ renderItem }
linkProps={{
pb: { base: '5px', md: 0 },
}}
rowGap={ 2 }
/>
);
};
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment