Commit b9935be6 authored by tom's avatar tom

project info

parent 0d75bac8
<svg viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg"> <svg viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M5.978 6.156c.56.455.77.42 1.82.35l9.912-.595c.21 0 .035-.21-.035-.245l-1.646-1.19c-.315-.245-.736-.525-1.54-.455l-9.598.7c-.35.035-.42.21-.28.35l1.367 1.085Zm.595 2.31v10.428c0 .56.28.77.91.735L18.375 19c.631-.035.701-.42.701-.875V7.765c0-.454-.175-.7-.56-.664l-11.383.664c-.42.036-.56.246-.56.7Zm10.753.559c.07.315 0 .63-.316.666l-.525.104v7.699c-.456.245-.876.385-1.226.385-.56 0-.701-.175-1.121-.7l-3.433-5.389v5.214l1.086.245s0 .63-.876.63l-2.416.14c-.07-.14 0-.49.245-.56l.63-.174V10.39l-.875-.07c-.07-.315.105-.77.595-.805l2.592-.175 3.573 5.46V9.97l-.911-.104c-.07-.386.21-.666.56-.7l2.418-.141ZM4.086 3.776l9.982-.735c1.226-.105 1.541-.035 2.312.525l3.186 2.24c.526.385.701.49.701.91v12.283c0 .77-.28 1.225-1.26 1.295l-11.593.7c-.736.035-1.087-.07-1.472-.56l-2.347-3.045c-.42-.56-.595-.98-.595-1.47V5c0-.63.28-1.155 1.085-1.225Z" fill="currentColor"/> <path fill-rule="evenodd" clip-rule="evenodd" d="M12.26 17.5H4.027a.47.47 0 0 1-.47-.469V5.312c0-.26.21-.469.47-.469h2.137V2.969c0-.259.21-.469.468-.469h5.89l.015.003.014.003a.449.449 0 0 1 .14.03.463.463 0 0 1 .156.095l3.452 3.31-.002.002a.466.466 0 0 1 .146.337v7.3c0 .87-.708 1.577-1.577 1.577h-1.029v.766c0 .87-.707 1.577-1.577 1.577Zm2.823-11.69L12.99 3.794v1.379a.64.64 0 0 0 .638.639h1.454Zm-2.755-2.648H6.826v11.333h8.316a.64.64 0 0 0 .639-.64V6.474H13.63c-.87 0-1.302-.432-1.302-1.301v-2.01ZM6.164 5.505H4.22v11.333h8.316c.352 0 .639-.563.639-.915v-.766H6.632a.469.469 0 0 1-.468-.469V5.505ZM8.85 8.5a.25.25 0 1 0 0 .5h4.7a.25.25 0 1 0 0-.5h-4.7Zm-.25 1.95a.25.25 0 0 1 .25-.25h4.7a.25.25 0 1 1 0 .5h-4.7a.25.25 0 0 1-.25-.25ZM8.85 12a.25.25 0 1 0 0 .5h4.7a.25.25 0 1 0 0-.5h-4.7Z" fill="currentColor"/>
<path d="M6.164 4.843v.35h.35v-.35h-.35Zm6.373-2.34-.098.336h.003l.095-.336Zm0 0 .099-.336h-.003l-.095.336Zm.014.003.02-.35-.02.35Zm.123.025.12-.33h-.004l-.115.33Zm.017.005.101-.335-.101.335Zm.025.009.145-.319h-.002l-.143.319Zm.13.086.243-.253-.243.252ZM16.3 5.94l.247.248.253-.253-.258-.247-.242.252Zm-.002.002-.247-.248-.252.252.257.248.242-.252Zm-2.46 9.214v-.35h-.35v.35h.35Zm-.846-11.364.242-.252-.593-.572v.824h.35Zm2.092 2.018v.35h.867l-.624-.602-.243.252ZM6.826 3.162v-.35h-.35v.35h.35Zm5.502 0h.35v-.35h-.35v.35ZM6.826 14.495h-.35v.35h.35v-.35Zm8.955-8.022h.35v-.35h-.35v.35ZM4.22 5.505v-.35h-.35v.35h.35Zm1.944 0h.35v-.35h-.35v.35ZM4.22 16.838h-.35v.35h.35v-.35Zm8.955-1.68h.35v-.35h-.35v.35ZM4.027 17.85h8.233v-.7H4.027v.7Zm-.82-.819a.82.82 0 0 0 .82.819v-.7a.12.12 0 0 1-.12-.119h-.7Zm0-11.719v11.719h.7V5.312h-.7Zm.82-.819a.82.82 0 0 0-.82.819h.7a.12.12 0 0 1 .12-.119v-.7Zm2.137 0H4.027v.7h2.137v-.7Zm-.35-1.524v1.874h.7V2.969h-.7Zm.818-.819a.819.819 0 0 0-.818.819h.7c0-.066.053-.119.118-.119v-.7Zm5.89 0h-5.89v.7h5.89v-.7Zm.114.017s-.015-.005-.033-.008a.389.389 0 0 0-.081-.009v.7a.313.313 0 0 1-.065-.007c-.013-.002-.022-.006-.018-.004l.197-.672Zm-.003 0-.191.673.191-.674Zm-.063-.01a.308.308 0 0 1 .053.007l.013.003-.197.672.027.007a.39.39 0 0 0 .066.01l.038-.7Zm.22.043a.8.8 0 0 0-.218-.044l-.041.7a.1.1 0 0 1 .028.005l.231-.66Zm.002 0 .001.001-.237.659c.015.005.029.01.033.01l.203-.67Zm.067.025c-.032-.014-.061-.022-.067-.024l-.203.67h.004-.002a.208.208 0 0 1-.018-.007l.286-.639Zm.23.153a.812.812 0 0 0-.228-.152l-.29.637c.022.01.03.017.033.02l.485-.505Zm3.452 3.31-3.452-3.31-.485.505 3.453 3.311.484-.505Zm.004.502.001-.001-.495-.495-.001.001.495.495Zm.248.09c0-.236-.101-.443-.253-.59l-.485.505a.117.117 0 0 1 .038.085h.7Zm0 7.3v-7.3h-.7v7.3h.7Zm-1.927 1.927a1.929 1.929 0 0 0 1.927-1.927h-.7c0 .677-.551 1.227-1.227 1.227v.7Zm-1.029 0h1.029v-.7h-1.029v.7Zm.35.416v-.766h-.7v.766h.7ZM12.26 17.85a1.929 1.929 0 0 0 1.927-1.927h-.7c0 .676-.55 1.227-1.227 1.227v.7Zm.488-13.805 2.092 2.018.486-.504-2.093-2.018-.486.504Zm.593 1.127v-1.38h-.7v1.38h.7Zm.288.289a.29.29 0 0 1-.288-.29h-.7a.99.99 0 0 0 .988.99v-.7Zm1.454 0h-1.454v.7h1.454v-.7ZM6.826 3.512h5.502v-.7H6.826v.7Zm.35 10.983V3.162h-.7v11.333h.7Zm7.966-.35H6.826v.7h8.316v-.7Zm.289-.29a.29.29 0 0 1-.29.29v.7a.99.99 0 0 0 .99-.99h-.7Zm0-7.382v7.383h.7V6.473h-.7Zm-1.801.35h2.15v-.7h-2.15v.7Zm-1.652-1.651c0 .488.122.918.427 1.224.306.306.737.427 1.225.427v-.7c-.382 0-.602-.095-.73-.222-.127-.127-.222-.348-.222-.73h-.7Zm0-2.01v2.01h.7v-2.01h-.7ZM4.22 5.855h1.944v-.7H4.22v.7Zm.35 10.983V5.505h-.7v11.333h.7Zm7.966-.35H4.22v.7h8.316v-.7Zm.289-.565a.862.862 0 0 1-.134.404c-.099.156-.167.16-.155.16v.7c.364 0 .615-.276.748-.489.143-.229.24-.52.24-.775h-.7Zm0-.766v.766h.7v-.766h-.7Zm-6.193.35h6.543v-.7H6.632v.7Zm-.818-.819c0 .452.365.82.818.82v-.7a.119.119 0 0 1-.118-.12h-.7Zm0-9.183v9.183h.7V5.505h-.7ZM8.95 8.75a.1.1 0 0 1-.1.1v-.7a.6.6 0 0 0-.6.6h.7Zm-.1-.1a.1.1 0 0 1 .1.1h-.7a.6.6 0 0 0 .6.6v-.7Zm4.7 0h-4.7v.7h4.7v-.7Zm-.1.1a.1.1 0 0 1 .1-.1v.7a.6.6 0 0 0 .6-.6h-.7Zm.1.1a.1.1 0 0 1-.1-.1h.7a.6.6 0 0 0-.6-.6v.7Zm-4.7 0h4.7v-.7h-4.7v.7Zm0 1a.6.6 0 0 0-.6.6h.7a.1.1 0 0 1-.1.1v-.7Zm4.7 0h-4.7v.7h4.7v-.7Zm.6.6a.6.6 0 0 0-.6-.6v.7a.1.1 0 0 1-.1-.1h.7Zm-.6.6a.6.6 0 0 0 .6-.6h-.7a.1.1 0 0 1 .1-.1v.7Zm-4.7 0h4.7v-.7h-4.7v.7Zm-.6-.6a.6.6 0 0 0 .6.6v-.7a.1.1 0 0 1 .1.1h-.7Zm.7 1.8a.1.1 0 0 1-.1.1v-.7a.6.6 0 0 0-.6.6h.7Zm-.1-.1a.1.1 0 0 1 .1.1h-.7a.6.6 0 0 0 .6.6v-.7Zm4.7 0h-4.7v.7h4.7v-.7Zm-.1.1a.1.1 0 0 1 .1-.1v.7a.6.6 0 0 0 .6-.6h-.7Zm.1.1a.1.1 0 0 1-.1-.1h.7a.6.6 0 0 0-.6-.6v.7Zm-4.7 0h4.7v-.7h-4.7v.7Z" fill="currentColor"/>
</svg> </svg>
<svg viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M10 9.375a1.25 1.25 0 1 0 0-2.5 1.25 1.25 0 0 0 0 2.5Z" stroke="currentColor" stroke-width="1.4" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M6.25 9.938c-1.188.937-2.125 2.25-2.5 3.812h1.438c.937 0 1.625-.875 1.375-1.75a9.626 9.626 0 0 1-.375-2.688C6.25 5.876 7.813 2.939 10 1.875c2.188 1.063 3.75 4 3.75 7.375 0 .938-.125 1.875-.375 2.688-.25.874.438 1.75 1.375 1.75h1.5c-.375-1.563-1.313-2.938-2.5-3.813M10 13.75v5M8.125 15v2.5M11.875 15v2.5" stroke="currentColor" stroke-width="1.4" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
</svg>
import {
Popover, PopoverTrigger, PopoverContent, PopoverBody,
Modal, ModalContent, ModalCloseButton,
useDisclosure,
} from '@chakra-ui/react';
import React from 'react';
import type { TokenVerifiedInfo } from 'types/api/token';
import useIsMobile from 'lib/hooks/useIsMobile';
import Content from './TokenProjectInfo/Content';
import TriggerButton from './TokenProjectInfo/TriggerButton';
interface Props {
data: TokenVerifiedInfo;
}
const TokenProjectInfo = ({ data }: Props) => {
const isMobile = useIsMobile();
const { isOpen, onToggle, onClose } = useDisclosure();
if (isMobile) {
return (
<>
<TriggerButton isOpen={ isOpen } onClick={ onToggle }/>
<Modal isOpen={ isOpen } onClose={ onClose } size="full">
<ModalContent>
<ModalCloseButton/>
<Content data={ data }/>
</ModalContent>
</Modal>
</>
);
}
return (
<Popover isOpen={ isOpen } onClose={ onClose } placement="bottom-start" isLazy>
<PopoverTrigger>
<TriggerButton isOpen={ isOpen } onClick={ onToggle }/>
</PopoverTrigger>
<PopoverContent w="500px">
<PopoverBody px={ 6 } py={ 5 }>
<Content data={ data }/>
</PopoverBody>
</PopoverContent>
</Popover>
);
};
export default React.memo(TokenProjectInfo);
import { Flex, Text, Box, Grid } from '@chakra-ui/react';
import React from 'react';
import type { TokenVerifiedInfo } from 'types/api/token';
import iconCoinGecko from 'icons/social/coingecko.svg';
import iconCoinMarketCap from 'icons/social/coinmarketcap.svg';
import iconDefiLlama from 'icons/social/defi_llama.svg';
import iconDiscord from 'icons/social/discord_filled.svg';
import iconFacebook from 'icons/social/facebook_filled.svg';
import iconGithub from 'icons/social/github_filled.svg';
import iconLinkedIn from 'icons/social/linkedin_filled.svg';
import iconMedium from 'icons/social/medium_filled.svg';
import iconOpenSea from 'icons/social/opensea_filled.svg';
import iconReddit from 'icons/social/reddit_filled.svg';
import iconSlack from 'icons/social/slack_filled.svg';
import iconTelegram from 'icons/social/telegram_filled.svg';
import iconTwitter from 'icons/social/twitter_filled.svg';
import DocsLink from './DocsLink';
import type { Props as ServiceLinkProps } from './ServiceLink';
import ServiceLink from './ServiceLink';
import SupportLink from './SupportLink';
interface Props {
data: TokenVerifiedInfo;
}
const SOCIAL_LINKS: Array<Omit<ServiceLinkProps, 'href'>> = [
{ field: 'github', icon: iconGithub, title: 'Github' },
{ field: 'twitter', icon: iconTwitter, title: 'Twitter' },
{ field: 'telegram', icon: iconTelegram, title: 'Telegram' },
{ field: 'openSea', icon: iconOpenSea, title: 'OpenSea' },
{ field: 'linkedin', icon: iconLinkedIn, title: 'LinkedIn' },
{ field: 'facebook', icon: iconFacebook, title: 'Facebook' },
{ field: 'discord', icon: iconDiscord, title: 'Discord' },
{ field: 'medium', icon: iconMedium, title: 'Medium' },
{ field: 'slack', icon: iconSlack, title: 'Slack' },
{ field: 'reddit', icon: iconReddit, title: 'Reddit' },
];
const PRICE_TICKERS: Array<Omit<ServiceLinkProps, 'href'>> = [
{ field: 'coinGeckoTicker', icon: iconCoinGecko, title: 'CoinGecko' },
{ field: 'coinMarketCapTicker', icon: iconCoinMarketCap, title: 'CoinMarketCap' },
{ field: 'defiLlamaTicker', icon: iconDefiLlama, title: 'DefiLlama' },
];
const Content = ({ data }: Props) => {
const docs = <DocsLink href={ data.docs }/>;
const support = <SupportLink url={ data.support }/>;
const description = data.projectDescription ? <Text fontSize="sm" mt={ 3 }>{ data.projectDescription }</Text> : null;
const socialLinks = SOCIAL_LINKS
.map((link) => ({ ...link, href: data[link.field] }))
.filter(({ href }) => href);
const priceTickersLinks = PRICE_TICKERS
.map((link) => ({ ...link, href: data[link.field] }))
.filter(({ href }) => href);
return (
<Box fontSize="sm">
{ (description || docs || support) && (
<>
<Text variant="secondary" fontSize="xs">Description and support info</Text>
{ description }
{ (docs || support) && (
<Flex alignItems="center" flexWrap="wrap" columnGap={ 6 } mt={ 3 }>
{ support }
{ docs }
</Flex>
) }
</>
) }
{ socialLinks.length > 0 && (
<>
<Text variant="secondary" fontSize="xs" mt={ 5 }>Links</Text>
<Grid templateColumns={{ base: 'repeat(2, 1fr)', lg: 'repeat(3, 1fr)' }} columnGap={ 4 } rowGap={ 3 } mt={ 3 }>
{ socialLinks.map((link) => <ServiceLink key={ link.field } { ...link }/>) }
</Grid>
</>
) }
{ priceTickersLinks.length > 0 && (
<>
<Text variant="secondary" fontSize="xs" mt={ 5 }>Crypto markets</Text>
<Grid templateColumns={{ base: 'repeat(2, 1fr)', lg: 'repeat(3, 1fr)' }} columnGap={ 4 } rowGap={ 3 } mt={ 3 }>
{ priceTickersLinks.map((link) => <ServiceLink key={ link.field } { ...link }/>) }
</Grid>
</>
) }
</Box>
);
};
export default Content;
import { Icon, Link } from '@chakra-ui/react';
import React from 'react';
import iconDocs from 'icons/docs.svg';
interface Props {
href?: string;
}
const DocsLink = ({ href }: Props) => {
if (!href) {
return null;
}
return (
<Link
href={ href }
target="_blank"
display="inline-flex"
alignItems="center"
columnGap={ 1 }
>
<Icon as={ iconDocs } boxSize={ 6 } color="text_secondary"/>
<span>Documentation</span>
</Link>
);
};
export default DocsLink;
import { Link, Icon } from '@chakra-ui/react';
import React from 'react';
import type { TokenVerifiedInfo } from 'types/api/token';
export interface Props {
field: keyof TokenVerifiedInfo;
icon: React.FunctionComponent<React.SVGAttributes<SVGElement>>;
title: string;
href?: string;
}
const ServiceLink = ({ href, title, icon }: Props) => {
return (
<Link
href={ href }
aria-label={ title }
title={ title }
target="_blank"
display="inline-flex"
alignItems="center"
>
<Icon as={ icon } boxSize={ 5 } mr={ 2 } color="text_secondary"/>
<span>{ title }</span>
</Link>
);
};
export default ServiceLink;
import { Icon, Link } from '@chakra-ui/react';
import React from 'react';
import iconEmail from 'icons/email.svg';
import iconLink from 'icons/link.svg';
interface Props {
url?: string;
}
const SupportLink = ({ url }: Props) => {
if (!url) {
return null;
}
const isEmail = url.includes('@');
const href = isEmail ? `mailto:${ url }` : url;
const icon = isEmail ? iconEmail : iconLink;
return (
<Link
href={ href }
target="_blank"
display="inline-flex"
alignItems="center"
columnGap={ 1 }
>
<Icon as={ icon } boxSize={ 6 } color="text_secondary"/>
<span>{ url }</span>
</Link>
);
};
export default SupportLink;
import { Button, Icon } from '@chakra-ui/react';
import React from 'react';
import arrowIcon from 'icons/arrows/east-mini.svg';
import rocketIcon from 'icons/rocket.svg';
interface Props {
onClick: () => void;
isOpen: boolean;
}
const TriggerButton = ({ isOpen, onClick }: Props, ref: React.ForwardedRef<HTMLButtonElement>) => {
return (
<Button
ref={ ref }
size="sm"
variant="outline"
colorScheme="gray"
onClick={ onClick }
aria-label="Show project info"
fontWeight={ 500 }
px={ 2 }
h="30px"
>
<Icon as={ rocketIcon } boxSize={ 4 } mr={ 1 }/>
<span>Project Info</span>
<Icon as={ arrowIcon } transform={ isOpen ? 'rotate(90deg)' : 'rotate(-90deg)' } transitionDuration="faster" boxSize={ 5 } ml={ 1 }/>
</Button>
);
};
export default React.forwardRef(TriggerButton);
...@@ -7,6 +7,8 @@ import type { TokenVerifiedInfo as TTokenVerifiedInfo } from 'types/api/token'; ...@@ -7,6 +7,8 @@ import type { TokenVerifiedInfo as TTokenVerifiedInfo } from 'types/api/token';
import LinkExternal from 'ui/shared/LinkExternal'; import LinkExternal from 'ui/shared/LinkExternal';
import NetworkExplorers from 'ui/shared/NetworkExplorers'; import NetworkExplorers from 'ui/shared/NetworkExplorers';
import TokenProjectInfo from './TokenProjectInfo';
interface Props { interface Props {
verifiedInfoQuery: UseQueryResult<TTokenVerifiedInfo>; verifiedInfoQuery: UseQueryResult<TTokenVerifiedInfo>;
isVerifiedInfoEnabled: boolean; isVerifiedInfoEnabled: boolean;
...@@ -53,7 +55,7 @@ const TokenVerifiedInfo = ({ verifiedInfoQuery, isVerifiedInfoEnabled, hash }: P ...@@ -53,7 +55,7 @@ const TokenVerifiedInfo = ({ verifiedInfoQuery, isVerifiedInfoEnabled, hash }: P
return ( return (
<> <>
{ websiteLink } { websiteLink }
<Skeleton w="130px" h="30px" borderRadius="base"/> { Boolean(data) && <TokenProjectInfo data={ data }/> }
{ explorers } { explorers }
</> </>
); );
......
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