Commit 7c24b2e7 authored by tom's avatar tom

profile menu mark-up

parent 1d96aa0b
<svg fill="none" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 30 30">
<path d="M15 25c5.523 0 10-4.477 10-10S20.523 5 15 5 5 9.477 5 15s4.477 10 10 10Z" stroke="currentColor" stroke-width="2" stroke-miterlimit="10" stroke-linejoin="round"/>
<path d="M21.667 22.333a6.666 6.666 0 1 0-13.334 0" stroke="currentColor" stroke-width="2" stroke-miterlimit="10" stroke-linejoin="round"/>
<path d="M15 15.667a4 4 0 1 0 0-8 4 4 0 0 0 0 8Z" stroke="currentColor" stroke-width="2" stroke-miterlimit="10" stroke-linejoin="round"/>
</svg>
\ No newline at end of file
...@@ -6,6 +6,7 @@ import appsIcon from 'icons/apps.svg'; ...@@ -6,6 +6,7 @@ import appsIcon from 'icons/apps.svg';
import blocksIcon from 'icons/block.svg'; import blocksIcon from 'icons/block.svg';
import gearIcon from 'icons/gear.svg'; import gearIcon from 'icons/gear.svg';
import privateTagIcon from 'icons/privattags.svg'; import privateTagIcon from 'icons/privattags.svg';
import profileIcon from 'icons/profile.svg';
import publicTagIcon from 'icons/publictags.svg'; import publicTagIcon from 'icons/publictags.svg';
import tokensIcon from 'icons/token.svg'; import tokensIcon from 'icons/token.svg';
import transactionsIcon from 'icons/transactions.svg'; import transactionsIcon from 'icons/transactions.svg';
...@@ -32,6 +33,8 @@ export default function useNavItems() { ...@@ -32,6 +33,8 @@ export default function useNavItems() {
{ text: 'Custom ABI', pathname: basePath + '/account/custom_abi', icon: abiIcon }, { text: 'Custom ABI', pathname: basePath + '/account/custom_abi', icon: abiIcon },
]; ];
return { mainNavItems, accountNavItems }; const profileItem = { text: 'My account', pathname: basePath + '/auth/profile', icon: profileIcon };
return { mainNavItems, accountNavItems, profileItem };
}, [ basePath ]); }, [ basePath ]);
} }
...@@ -2,7 +2,11 @@ import type { drawerAnatomy as parts } from '@chakra-ui/anatomy'; ...@@ -2,7 +2,11 @@ import type { drawerAnatomy as parts } from '@chakra-ui/anatomy';
import type { SystemStyleFunction, PartsStyleFunction, SystemStyleObject } from '@chakra-ui/theme-tools'; import type { SystemStyleFunction, PartsStyleFunction, SystemStyleObject } from '@chakra-ui/theme-tools';
import { mode } from '@chakra-ui/theme-tools'; import { mode } from '@chakra-ui/theme-tools';
import getDefaultTransitionProps from '../utils/getDefaultTransitionProps';
const transitionProps = getDefaultTransitionProps();
const baseStyleOverlay: SystemStyleObject = { const baseStyleOverlay: SystemStyleObject = {
...transitionProps,
bg: 'blackAlpha.800', bg: 'blackAlpha.800',
zIndex: 'overlay', zIndex: 'overlay',
}; };
...@@ -12,6 +16,7 @@ const baseStyleDialog: SystemStyleFunction = (props) => { ...@@ -12,6 +16,7 @@ const baseStyleDialog: SystemStyleFunction = (props) => {
return { return {
...(isFullHeight && { height: '100vh' }), ...(isFullHeight && { height: '100vh' }),
...transitionProps,
zIndex: 'modal', zIndex: 'modal',
maxH: '100vh', maxH: '100vh',
bg: mode('white', 'gray.900')(props), bg: mode('white', 'gray.900')(props),
......
...@@ -3,11 +3,12 @@ import React from 'react'; ...@@ -3,11 +3,12 @@ import React from 'react';
import useIsMobile from 'lib/hooks/useIsMobile'; import useIsMobile from 'lib/hooks/useIsMobile';
import NetworkLogo from 'ui/blocks/networkMenu/NetworkLogo'; import NetworkLogo from 'ui/blocks/networkMenu/NetworkLogo';
import ProfileMenuDesktop from 'ui/blocks/profileMenu/ProfileMenuDesktop';
import ProfileMenuMobile from 'ui/blocks/profileMenu/ProfileMenuMobile';
import SearchBar from 'ui/blocks/searchBar/SearchBar'; import SearchBar from 'ui/blocks/searchBar/SearchBar';
import Burger from './Burger'; import Burger from './Burger';
import ColorModeToggler from './ColorModeToggler'; import ColorModeToggler from './ColorModeToggler';
import ProfileMenu from './ProfileMenu';
const Header = () => { const Header = () => {
const isMobile = useIsMobile(); const isMobile = useIsMobile();
...@@ -31,7 +32,7 @@ const Header = () => { ...@@ -31,7 +32,7 @@ const Header = () => {
> >
<Burger/> <Burger/>
<NetworkLogo/> <NetworkLogo/>
<ProfileMenu/> <ProfileMenuMobile/>
</Flex> </Flex>
<SearchBar/> <SearchBar/>
</Box> </Box>
...@@ -48,7 +49,7 @@ const Header = () => { ...@@ -48,7 +49,7 @@ const Header = () => {
> >
<SearchBar/> <SearchBar/>
<ColorModeToggler/> <ColorModeToggler/>
<ProfileMenu/> <ProfileMenuDesktop/>
</HStack> </HStack>
); );
}; };
......
import { Center, useColorModeValue, chakra } from '@chakra-ui/react';
import React from 'react';
import Identicon from 'react-identicons';
import useIsMobile from 'lib/hooks/useIsMobile';
const ProfileIcon = chakra(Identicon);
const ProfileMenu = () => {
const isMobile = useIsMobile();
const size = isMobile ? '24px' : '50px';
return (
<Center
flexShrink={ 0 }
padding={ isMobile ? 2 : 0 }
>
{ /* the displayed size is 48px, but we need to generate x2 for retina displays */ }
<ProfileIcon
maxWidth={ size }
maxHeight={ size }
string="randomness"
size={ 100 }
bg={ useColorModeValue('blackAlpha.100', 'white') }
borderRadius="50%"
overflow="hidden"
/>
</Center>
);
};
export default ProfileMenu;
...@@ -9,13 +9,14 @@ import useColors from './useColors'; ...@@ -9,13 +9,14 @@ import useColors from './useColors';
interface Props { interface Props {
isCollapsed?: boolean; isCollapsed?: boolean;
isActive: boolean; isActive?: boolean;
pathname: string; pathname: string;
text: string; text: string;
icon: React.FunctionComponent<React.SVGAttributes<SVGElement>>; icon: React.FunctionComponent<React.SVGAttributes<SVGElement>>;
px?: string | number;
} }
const NavLink = ({ text, pathname, icon, isCollapsed, isActive }: Props) => { const NavLink = ({ text, pathname, icon, isCollapsed, isActive, px }: Props) => {
const colors = useColors(); const colors = useColors();
const isMobile = useIsMobile(); const isMobile = useIsMobile();
const width = (() => { const width = (() => {
...@@ -32,7 +33,7 @@ const NavLink = ({ text, pathname, icon, isCollapsed, isActive }: Props) => { ...@@ -32,7 +33,7 @@ const NavLink = ({ text, pathname, icon, isCollapsed, isActive }: Props) => {
as="li" as="li"
listStyleType="none" listStyleType="none"
w={ width } w={ width }
px={ isCollapsed ? '15px' : 3 } px={ px || (isCollapsed ? '15px' : 3) }
py={ 2.5 } py={ 2.5 }
color={ isActive ? colors.text.active : colors.text.default } color={ isActive ? colors.text.active : colors.text.default }
bgColor={ isActive ? colors.bg.active : colors.bg.default } bgColor={ isActive ? colors.bg.active : colors.bg.default }
......
import { Box, Button, Text, VStack, useColorModeValue } from '@chakra-ui/react';
import { useRouter } from 'next/router';
import React from 'react';
import useNavItems from 'lib/hooks/useNavItems';
import getDefaultTransitionProps from 'theme/utils/getDefaultTransitionProps';
import NavLink from 'ui/blocks/navigation/NavLink';
const ProfileMenuContent = () => {
const { accountNavItems, profileItem } = useNavItems();
const router = useRouter();
const borderColor = useColorModeValue('gray.200', 'whiteAlpha.200');
const primaryTextColor = useColorModeValue('gray.600', 'whiteAlpha.800');
return (
<Box>
<Text
fontSize="sm"
fontWeight={ 500 }
color={ primaryTextColor }
{ ...getDefaultTransitionProps() }
>
Signed in as tgladilina
</Text>
<Text
fontSize="sm"
mb={ 1 }
fontWeight={ 500 }
color="gray.500"
{ ...getDefaultTransitionProps() }
>
tatyana@blockscout.com
</Text>
<NavLink { ...profileItem } isActive={ router.asPath === profileItem.pathname } px="0px"/>
<Box as="nav" mt={ 2 } pt={ 2 } borderTopColor={ borderColor } borderTopWidth="1px" { ...getDefaultTransitionProps() }>
<VStack as="ul" spacing="0" alignItems="flex-start" overflow="hidden">
{ accountNavItems.map((item) => <NavLink key={ item.text } { ...item } px="0px"/>) }
</VStack>
</Box>
<Box mt={ 2 } pt={ 2 } borderTopColor={ borderColor } borderTopWidth="1px" { ...getDefaultTransitionProps() }>
<Button size="sm" width="full" variant="secondary">Sign Out</Button>
</Box>
</Box>
);
};
export default ProfileMenuContent;
import { Popover, PopoverContent, PopoverBody, PopoverTrigger, Button } from '@chakra-ui/react';
import React from 'react';
import ProfileMenuContent from 'ui/blocks/profileMenu/ProfileMenuContent';
import UserAvatar from 'ui/shared/UserAvatar';
const ProfileMenuDesktop = () => {
return (
<Popover openDelay={ 300 } placement="bottom-end" gutter={ 10 } isLazy>
<PopoverTrigger>
<Button variant="unstyled" display="inline-flex" height="auto">
<UserAvatar size={ 50 }/>
</Button>
</PopoverTrigger>
<PopoverContent w="212px">
<PopoverBody padding="24px 16px 16px 16px">
<ProfileMenuContent/>
</PopoverBody>
</PopoverContent>
</Popover>
);
};
export default ProfileMenuDesktop;
import { Flex, Box, Drawer, DrawerOverlay, DrawerContent, DrawerBody, useDisclosure } from '@chakra-ui/react';
import React from 'react';
import ColorModeToggler from 'ui/blocks/header/ColorModeToggler';
import ProfileMenuContent from 'ui/blocks/profileMenu/ProfileMenuContent';
import UserAvatar from 'ui/shared/UserAvatar';
const ProfileMenuMobile = () => {
const { isOpen, onOpen, onClose } = useDisclosure();
return (
<>
<Box padding={ 2 } onClick={ onOpen }>
<UserAvatar size={ 24 }/>
</Box>
<Drawer
isOpen={ isOpen }
placement="right"
onClose={ onClose }
autoFocus={ false }
>
<DrawerOverlay/>
<DrawerContent maxWidth="260px">
<DrawerBody p={ 6 }>
<Flex
justifyContent="space-between"
alignItems="center"
mb={ 6 }
>
<ColorModeToggler/>
<Box onClick={ onClose }>
<UserAvatar size={ 24 }/>
</Box>
</Flex>
<ProfileMenuContent/>
</DrawerBody>
</DrawerContent>
</Drawer>
</>
);
};
export default ProfileMenuMobile;
import { useColorModeValue, chakra } from '@chakra-ui/react';
import React from 'react';
import Identicon from 'react-identicons';
const ProfileIcon = chakra(Identicon);
interface Props {
size: number;
}
const UserAvatar = ({ size }: Props) => {
const sizeString = `${ size }px`;
return (
<ProfileIcon
flexShrink={ 0 }
maxWidth={ sizeString }
maxHeight={ sizeString }
string="randomness"
// the displayed size is doubled for retina displays
size={ size * 2 }
bg={ useColorModeValue('blackAlpha.100', 'white') }
borderRadius="50%"
overflow="hidden"
/>
);
};
export default React.memo(UserAvatar);
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