From 751ce8e6d64500f22018e9ed5708c97e8a5308f3 Mon Sep 17 00:00:00 2001 From: Charles Bachmeier Date: Fri, 26 Aug 2022 04:39:58 -0700 Subject: [PATCH] feat: Mobile Nav (#4501) * working and cleaned up mobile nav * delete old files * fix wallet position * update searchbar breakpoint * update full screen search * delete old comments * cleanup eslint * Update MenuDropdown.tsx * Update SearchBar.tsx Co-authored-by: Charlie --- src/components/NavBar/ChainSwitcher.tsx | 2 +- src/components/NavBar/MenuDropdown.css.ts | 2 +- src/components/NavBar/MenuDropdown.tsx | 12 +- src/components/NavBar/MobileSidebar.css.ts | 121 ---------- src/components/NavBar/MobileSidebar.tsx | 249 --------------------- src/components/NavBar/NavDropdown.css.ts | 37 ++- src/components/NavBar/NavDropdown.tsx | 47 +--- src/components/NavBar/NavIcon.css.ts | 1 - src/components/NavBar/NavIcon.tsx | 8 +- src/components/NavBar/Navbar.css.ts | 42 +--- src/components/NavBar/Navbar.tsx | 132 +++++------ src/components/NavBar/SearchBar.css.ts | 2 +- src/components/NavBar/SearchBar.tsx | 24 +- src/components/WalletDropdown/index.tsx | 13 +- src/components/Web3Status/index.tsx | 11 +- 15 files changed, 151 insertions(+), 552 deletions(-) delete mode 100644 src/components/NavBar/MobileSidebar.css.ts delete mode 100644 src/components/NavBar/MobileSidebar.tsx diff --git a/src/components/NavBar/ChainSwitcher.tsx b/src/components/NavBar/ChainSwitcher.tsx index 47483aec81..554ce262b0 100644 --- a/src/components/NavBar/ChainSwitcher.tsx +++ b/src/components/NavBar/ChainSwitcher.tsx @@ -79,7 +79,7 @@ export const ChainSwitcher = ({ leftAlign }: ChainSwitcherProps) => { const isSupported = !!info const dropdown = ( - + {NETWORK_SELECTOR_CHAINS.map((chainId: SupportedChainId) => ( { {isOpen && ( - + {nftFlag === NftVariant.Enabled && ( @@ -154,7 +154,13 @@ export const MenuDropdown = () => { - + Help center ↗ Documentation ↗ { {(isDevelopmentEnv() || isStagingEnv()) && ( {`Feature Flags`} )} - + diff --git a/src/components/NavBar/MobileSidebar.css.ts b/src/components/NavBar/MobileSidebar.css.ts deleted file mode 100644 index ea9d97a736..0000000000 --- a/src/components/NavBar/MobileSidebar.css.ts +++ /dev/null @@ -1,121 +0,0 @@ -import { style } from '@vanilla-extract/css' -import { subhead } from 'nft/css/common.css' - -import { sprinkles } from '../../nft/css/sprinkles.css' - -export const sidebar = style([ - sprinkles({ - display: 'flex', - position: 'fixed', - background: 'white', - height: 'full', - top: '0', - left: '0', - right: '0', - bottom: '0', - paddingBottom: '16', - justifyContent: 'space-between', - }), - { - zIndex: 20, - }, -]) - -export const icon = style([ - sprinkles({ - width: '32', - height: '32', - }), -]) - -export const iconContainer = style([ - sprinkles({ - position: 'relative', - display: 'flex', - flexDirection: 'column', - color: 'darkGray', - background: 'none', - border: 'none', - justifyContent: 'flex-end', - textAlign: 'center', - cursor: 'pointer', - padding: '6', - }), -]) - -export const linkRow = style([ - subhead, - sprinkles({ - color: 'blackBlue', - width: 'full', - paddingLeft: '16', - paddingY: '12', - cursor: 'pointer', - }), - { - lineHeight: '24px', - textDecoration: 'none', - }, -]) - -export const activeLinkRow = style([ - linkRow, - sprinkles({ - background: 'lightGrayButton', - }), -]) - -export const separator = style([ - sprinkles({ - height: '0', - borderStyle: 'solid', - borderColor: 'medGray', - borderWidth: '1px', - marginY: '8', - marginX: '16', - }), -]) - -export const extraLinkRow = style([ - subhead, - sprinkles({ - width: 'full', - color: 'blackBlue', - paddingY: '12', - paddingLeft: '16', - cursor: 'pointer', - }), - { - lineHeight: '24px', - textDecoration: 'none', - }, -]) - -export const bottomExternalLinks = style([ - sprinkles({ - gap: '4', - paddingX: '4', - width: 'max', - flexWrap: 'wrap', - }), -]) - -export const bottomJointExternalLinksContainer = style([ - sprinkles({ - paddingX: '8', - paddingY: '4', - color: 'darkGray', - fontWeight: 'medium', - fontSize: '12', - }), - { - lineHeight: '20px', - }, -]) - -export const IconRow = style([ - sprinkles({ - gap: '12', - width: 'max', - }), -]) diff --git a/src/components/NavBar/MobileSidebar.tsx b/src/components/NavBar/MobileSidebar.tsx deleted file mode 100644 index c46627e277..0000000000 --- a/src/components/NavBar/MobileSidebar.tsx +++ /dev/null @@ -1,249 +0,0 @@ -import FeatureFlagModal from 'components/FeatureFlagModal/FeatureFlagModal' -import { PrivacyPolicyModal } from 'components/PrivacyPolicy' -import { NftVariant, useNftFlag } from 'featureFlags/flags/nft' -import { Box } from 'nft/components/Box' -import { Portal } from 'nft/components/common/Portal' -import { Column, Row } from 'nft/components/Flex' -import { - BarChartIconMobile, - BulletIcon, - CloseIcon, - DiscordIconMenuMobile, - GithubIconMenuMobile, - GovernanceIconMobile, - HamburgerIcon, - ThinTagIconMobile, - TwitterIconMenuMobile, -} from 'nft/components/icons' -import { themeVars } from 'nft/css/sprinkles.css' -import { ReactNode, useReducer } from 'react' -import { NavLink, NavLinkProps, useLocation } from 'react-router-dom' -import { useToggleModal, useTogglePrivacyPolicy } from 'state/application/hooks' -import { ApplicationModal } from 'state/application/reducer' -import { isDevelopmentEnv, isStagingEnv } from 'utils/env' - -import * as styles from './MobileSidebar.css' -import { NavIcon } from './NavIcon' - -interface NavLinkRowProps { - href: string - id?: NavLinkProps['id'] - isActive?: boolean - close: () => void - children: ReactNode -} - -const NavLinkRow = ({ href, id, isActive, close, children }: NavLinkRowProps) => { - return ( - - {children} - - ) -} - -const ExtraLinkRow = ({ - to, - href, - close, - children, -}: { - to?: NavLinkProps['to'] - href?: string - close: () => void - children: ReactNode -}) => { - return ( - <> - {to ? ( - - - {children} - - - ) : ( - - {children} - - )} - - ) -} - -const BottomExternalLink = ({ - href, - onClick, - children, -}: { - href?: string - onClick?: () => void - children: ReactNode -}) => { - return ( - - {children} - - ) -} - -const Icon = ({ href, children }: { href?: string; children: ReactNode }) => { - return ( - <> - - {children} - - - ) -} - -const IconRow = ({ children }: { children: ReactNode }) => { - return {children} -} - -const Seperator = () => { - return -} - -export const MobileSideBar = () => { - const [isOpen, toggleOpen] = useReducer((s) => !s, false) - const togglePrivacyPolicy = useTogglePrivacyPolicy() - const openFeatureFlagsModal = useToggleModal(ApplicationModal.FEATURE_FLAGS) - const { pathname } = useLocation() - const nftFlag = useNftFlag() - const isPoolActive = - pathname.startsWith('/pool') || - pathname.startsWith('/add') || - pathname.startsWith('/remove') || - pathname.startsWith('/increase') || - pathname.startsWith('/find') - - return ( - <> - - - - {isOpen && ( - - - - - - - - - - - Swap - - - Tokens - - {nftFlag === NftVariant.Enabled && ( - - NFTs - - )} - - Pool - - - - - {nftFlag === NftVariant.Enabled && ( - - - - - Sell NFTs - - )} - - - - - Vote in governance - - - - - - View token analytics ↗ - - - - - - - - Help center ↗ - - - - Documentation ↗ - - - { - toggleOpen() - togglePrivacyPolicy() - }} - > - {`Legal & Privacy`} - - - {(isDevelopmentEnv() || isStagingEnv()) && ( - <> - - {`Feature Flags`} - - )} - - - - - - - - - - - - - - - - - - )} - - - - ) -} diff --git a/src/components/NavBar/NavDropdown.css.ts b/src/components/NavBar/NavDropdown.css.ts index 4b84b26485..9b368cbb65 100644 --- a/src/components/NavBar/NavDropdown.css.ts +++ b/src/components/NavBar/NavDropdown.css.ts @@ -1,25 +1,40 @@ import { style } from '@vanilla-extract/css' -import { breakpoints, sprinkles } from '../../nft/css/sprinkles.css' +import { sprinkles } from '../../nft/css/sprinkles.css' -export const NavDropdown = style([ +const baseNavDropdown = style([ sprinkles({ - position: { sm: 'fixed', md: 'absolute' }, background: 'lightGray', - borderRadius: '12', borderStyle: 'solid', borderColor: 'medGray', borderWidth: '1px', - bottom: { sm: '56', md: 'unset' }, + paddingBottom: '8', + paddingTop: '8', }), { boxShadow: '0px 4px 12px 0px #00000026', zIndex: 10, - '@media': { - [`screen and (max-width: ${breakpoints.sm}px)`]: { - borderBottomLeftRadius: '0', - borderBottomRightRadius: '0', - }, - }, }, ]) + +export const NavDropdown = style([ + baseNavDropdown, + sprinkles({ + position: 'absolute', + borderRadius: '12', + }), + {}, +]) + +export const mobileNavDropdown = style([ + baseNavDropdown, + sprinkles({ + position: 'fixed', + borderTopRightRadius: '12', + borderTopLeftRadius: '12', + top: 'unset', + bottom: '56', + left: '0', + right: '0', + }), +]) diff --git a/src/components/NavBar/NavDropdown.tsx b/src/components/NavBar/NavDropdown.tsx index ff4139ce58..d0241c745e 100644 --- a/src/components/NavBar/NavDropdown.tsx +++ b/src/components/NavBar/NavDropdown.tsx @@ -1,45 +1,12 @@ -import { Box } from 'nft/components/Box' +import { Box, BoxProps } from 'nft/components/Box' import { useIsMobile } from 'nft/hooks' -import { ReactNode } from 'react' +import { ForwardedRef, forwardRef } from 'react' import * as styles from './NavDropdown.css' -interface NavDropdownProps { - top: number - right?: number - leftAligned?: boolean - horizontalPadding?: boolean - centerHorizontally?: boolean - paddingBottom?: number - paddingTop?: number - children: ReactNode -} - -export const NavDropdown = ({ - top, - centerHorizontally, - leftAligned, - horizontalPadding, - paddingBottom, - paddingTop, - children, -}: NavDropdownProps) => { +export const NavDropdown = forwardRef((props: BoxProps, ref: ForwardedRef) => { const isMobile = useIsMobile() - return ( - - {children} - - ) -} + return +}) + +NavDropdown.displayName = 'NavDropdown' diff --git a/src/components/NavBar/NavIcon.css.ts b/src/components/NavBar/NavIcon.css.ts index 01c61e2c1e..ba22337b0f 100644 --- a/src/components/NavBar/NavIcon.css.ts +++ b/src/components/NavBar/NavIcon.css.ts @@ -7,7 +7,6 @@ export const navIcon = style([ position: 'relative', display: 'flex', flexDirection: 'column', - color: 'blackBlue', border: 'none', justifyContent: 'center', textAlign: 'center', diff --git a/src/components/NavBar/NavIcon.tsx b/src/components/NavBar/NavIcon.tsx index 69e767357f..0df34b3acc 100644 --- a/src/components/NavBar/NavIcon.tsx +++ b/src/components/NavBar/NavIcon.tsx @@ -11,7 +11,13 @@ interface NavIconProps { export const NavIcon = ({ children, isActive, onClick }: NavIconProps) => { return ( - + {children} ) diff --git a/src/components/NavBar/Navbar.css.ts b/src/components/NavBar/Navbar.css.ts index 5f074b851c..a11eba0ed1 100644 --- a/src/components/NavBar/Navbar.css.ts +++ b/src/components/NavBar/Navbar.css.ts @@ -38,15 +38,6 @@ export const baseContainer = style([ }), ]) -export const baseMobileContainer = style([ - sprinkles({ - display: 'flex', - width: 'full', - alignItems: 'center', - marginY: '2', - }), -]) - export const baseSideContainer = style([ baseContainer, sprinkles({ @@ -64,19 +55,13 @@ export const leftSideContainer = style([ }), ]) -export const leftSideMobileContainer = style([ - baseMobileContainer, - sprinkles({ - justifyContent: 'flex-start', - }), -]) - export const middleContainer = style([ baseContainer, sprinkles({ flex: '1', flexShrink: '1', justifyContent: 'center', + display: { sm: 'none', lg: 'flex' }, }), ]) @@ -95,6 +80,7 @@ const baseMenuItem = style([ marginY: '4', borderRadius: '12', transition: '250', + height: 'min', }), { lineHeight: '24px', @@ -112,13 +98,6 @@ export const menuItem = style([ }), ]) -export const rightSideMobileContainer = style([ - baseMobileContainer, - sprinkles({ - justifyContent: 'flex-end', - }), -]) - export const activeMenuItem = style([ baseMenuItem, sprinkles({ @@ -127,16 +106,17 @@ export const activeMenuItem = style([ }), ]) -export const mobileWalletContainer = style([ +export const mobileBottomBar = style([ sprinkles({ position: 'fixed', - display: 'flex', + display: { sm: 'flex', xxl: 'none' }, bottom: '0', - right: '1/2', - marginY: '0', - marginX: 'auto', + right: '0', + left: '0', + justifyContent: 'space-between', + paddingY: '4', + paddingX: '8', + height: '56', + background: 'lightGray', }), - { - transform: 'translate(50%,-50%)', - }, ]) diff --git a/src/components/NavBar/Navbar.tsx b/src/components/NavBar/Navbar.tsx index eafa4d61f8..21ee3e0613 100644 --- a/src/components/NavBar/Navbar.tsx +++ b/src/components/NavBar/Navbar.tsx @@ -1,16 +1,13 @@ import Web3Status from 'components/Web3Status' import { NftVariant, useNftFlag } from 'featureFlags/flags/nft' -import { useWindowSize } from 'hooks/useWindowSize' import { ReactNode } from 'react' import { NavLink, NavLinkProps, useLocation } from 'react-router-dom' import { Box } from '../../nft/components/Box' import { Row } from '../../nft/components/Flex' -import { UniIcon, UniIconMobile } from '../../nft/components/icons' -import { breakpoints } from '../../nft/css/sprinkles.css' +import { UniIcon } from '../../nft/components/icons' import { ChainSwitcher } from './ChainSwitcher' import { MenuDropdown } from './MenuDropdown' -import { MobileSideBar } from './MobileSidebar' import * as styles from './Navbar.css' import { SearchBar } from './SearchBar' @@ -34,46 +31,10 @@ const MenuItem = ({ href, id, isActive, children }: MenuItemProps) => { ) } -const MobileNavbar = () => { - return ( - <> - - - - - - ) -} - -const Navbar = () => { - const { width: windowWidth } = useWindowSize() +const PageTabs = () => { const { pathname } = useLocation() const nftFlag = useNftFlag() - if (windowWidth && windowWidth <= breakpoints.xl) { - return - } - const isPoolActive = pathname.startsWith('/pool') || pathname.startsWith('/add') || @@ -82,41 +43,66 @@ const Navbar = () => { pathname.startsWith('/find') return ( - + ) } diff --git a/src/components/NavBar/SearchBar.css.ts b/src/components/NavBar/SearchBar.css.ts index 51861c2495..eb23bec9b6 100644 --- a/src/components/NavBar/SearchBar.css.ts +++ b/src/components/NavBar/SearchBar.css.ts @@ -15,7 +15,7 @@ const baseSearchStyle = style([ }), { '@media': { - [`screen and (min-width: ${breakpoints.sm}px)`]: { + [`screen and (min-width: ${breakpoints.md}px)`]: { width: DESKTOP_NAVBAR_WIDTH, }, }, diff --git a/src/components/NavBar/SearchBar.tsx b/src/components/NavBar/SearchBar.tsx index 73278a9412..89f39670de 100644 --- a/src/components/NavBar/SearchBar.tsx +++ b/src/components/NavBar/SearchBar.tsx @@ -2,14 +2,12 @@ import clsx from 'clsx' import { NftVariant, useNftFlag } from 'featureFlags/flags/nft' import useDebounce from 'hooks/useDebounce' import { useOnClickOutside } from 'hooks/useOnClickOutside' -import { useWindowSize } from 'hooks/useWindowSize' import { organizeSearchResults } from 'lib/utils/searchBar' import { Box } from 'nft/components/Box' import { Column, Row } from 'nft/components/Flex' import { Overlay } from 'nft/components/modals/Overlay' import { magicalGradientOnHover, subheadSmall } from 'nft/css/common.css' -import { breakpoints } from 'nft/css/sprinkles.css' -import { useSearchHistory } from 'nft/hooks' +import { useIsMobile, useSearchHistory } from 'nft/hooks' import { fetchSearchCollections, fetchTrendingCollections } from 'nft/queries' import { fetchSearchTokens } from 'nft/queries/genie/SearchTokensFetcher' import { fetchTrendingTokens } from 'nft/queries/genie/TrendingTokensFetcher' @@ -267,8 +265,8 @@ export const SearchBar = () => { const debouncedSearchValue = useDebounce(searchValue, 300) const searchRef = useRef(null) const { pathname } = useLocation() - const { width: windowWidth } = useWindowSize() const phase1Flag = useNftFlag() + const isMobile = useIsMobile() useOnClickOutside(searchRef, () => { isOpen && toggleOpen() @@ -318,15 +316,13 @@ export const SearchBar = () => { setSearchValue('') }, [pathname]) - const isMobile = useMemo(() => windowWidth && windowWidth <= breakpoints.sm, [windowWidth]) - return ( <> @@ -335,16 +331,16 @@ export const SearchBar = () => { borderRadius={isOpen ? undefined : '12'} borderTopRightRadius={isOpen && !isMobile ? '12' : undefined} borderTopLeftRadius={isOpen && !isMobile ? '12' : undefined} - display={{ sm: isOpen ? 'flex' : 'none', md: 'flex' }} + display={{ sm: isOpen ? 'flex' : 'none', lg: 'flex' }} justifyContent={isOpen || phase1Flag === NftVariant.Enabled ? 'flex-start' : 'center'} onFocus={() => !isOpen && toggleOpen()} onClick={() => !isOpen && toggleOpen()} gap="12" > - + - + { value={searchValue} /> - + diff --git a/src/components/WalletDropdown/index.tsx b/src/components/WalletDropdown/index.tsx index dfa6a0cd9b..002aa57707 100644 --- a/src/components/WalletDropdown/index.tsx +++ b/src/components/WalletDropdown/index.tsx @@ -20,6 +20,10 @@ const WalletWrapper = styled.div` border: ${({ theme }) => `1px solid ${theme.backgroundOutline}`}; box-shadow: ${({ theme }) => theme.deepShadow}; padding: 16px 0; + + @media only screen and (max-width: ${({ theme }) => `${theme.breakpoint.sm}px`}) { + width: 100%; + } ` export enum MenuState { @@ -33,11 +37,12 @@ const WalletDropdownWrapper = styled.div` top: 65px; right: 20px; - @media only screen and (max-width: ${({ theme }) => `${theme.breakpoint.xl}px`}) { + @media only screen and (max-width: ${({ theme }) => `${theme.breakpoint.sm}px`}) { top: unset; - right: 50%; - bottom: 45px; - transform: translateX(50%); + left: 0; + right: 0; + bottom: 56px; + z-index: 1; } ` diff --git a/src/components/Web3Status/index.tsx b/src/components/Web3Status/index.tsx index 5d0bac8d1e..e71e463564 100644 --- a/src/components/Web3Status/index.tsx +++ b/src/components/Web3Status/index.tsx @@ -6,6 +6,8 @@ import { TraceEvent } from 'components/AmplitudeAnalytics/TraceEvent' import WalletDropdown from 'components/WalletDropdown' import { getConnection } from 'connection/utils' import { NavBarVariant, useNavBarFlag } from 'featureFlags/flags/navBar' +import { Portal } from 'nft/components/common/Portal' +import { useIsMobile } from 'nft/hooks' import { getIsValidSwapQuote } from 'pages/Swap' import { darken } from 'polished' import { useMemo, useRef } from 'react' @@ -285,6 +287,7 @@ export default function Web3Status() { const ref = useRef(null) const closeModal = useCloseModal(ApplicationModal.WALLET_DROPDOWN) const isOpen = useIsOpen() + const isMobile = useIsMobile() useOnClickOutside(ref, isOpen ? closeModal : undefined) @@ -300,7 +303,13 @@ export default function Web3Status() { - + {isMobile ? ( + + + + ) : ( + + )} ) }