app/src/common/AppHeader.tsx (267 lines of code) (raw):

import React, { useState } from 'react'; import cx from 'classnames'; import { isMobile } from '@epam/uui-core'; import { Anchor, MainMenuCustomElement } from '@epam/uui-components'; import { Burger, BurgerButton, Button, Dropdown, DropdownMenuBody, DropdownMenuButton, FlexSpacer, GlobalMenu, IconContainer, MainMenu, MainMenuButton, MultiSwitch, Text, FlexRow, DropdownMenuHeader, MainMenuDropdown, BurgerGroupHeader, } from '@epam/uui'; import { svc } from '../services'; import { analyticsEvents } from '../analyticsEvents'; import { TMode } from './docs/docsConstants'; import { useAppThemeContext } from '../helpers/appTheme'; import { ReactComponent as LogoIcon } from '../icons/logo.svg'; import { ReactComponent as ThemeIcon } from '../icons/color-pallete.svg'; import { ReactComponent as GitIcon } from '@epam/assets/icons/external_logo/github-fill.svg'; import { ReactComponent as FigmaIcon } from '@epam/assets/icons/external_logo/figma-logo-outline-inverted.svg'; import { ReactComponent as DoneIcon } from '@epam/assets/icons/common/notification-done-18.svg'; import { ReactComponent as CommunicationStarOutlineIcon } from '@epam/assets/icons/communication-star-outline.svg'; import css from './AppHeader.module.scss'; const GIT_LINK = 'https://github.com/epam/UUI'; type ContentDirection = 'rtl' | 'ltr'; export function AppHeader() { const { theme, toggleTheme, themesById } = useAppThemeContext(); const dir = window?.document.dir; const [direction, setDirection] = useState<string>(dir || 'ltr'); const sendEvent = (link: string) => { svc.uuiAnalytics.sendEvent(analyticsEvents.welcome.trusted(link)); }; const changeContentDirection = (value: ContentDirection) => { setDirection(value); window.document.dir = value; }; const renderBurger = () => { const category = svc.uuiRouter.getCurrentLink().query.category; const pathName = svc.uuiRouter.getCurrentLink().pathname; return ( <> <BurgerButton caption="Home" link={ { pathname: '/' } } clickAnalyticsEvent={ () => sendEvent('Welcome') } /> <BurgerButton caption="Docs" link={ { pathname: '/documents', query: { id: 'overview' } } } isLinkActive={ pathName === 'documents' && !category } clickAnalyticsEvent={ () => sendEvent('Documents') } /> <BurgerButton caption="Assets" link={ { pathname: '/documents', query: { id: 'icons', category: 'assets' } } } isLinkActive={ pathName === '/documents' && category === 'assets' } clickAnalyticsEvent={ () => sendEvent('Assets') } /> <BurgerButton caption="Components" link={ { pathname: '/documents', query: { category: 'components', id: 'accordion', mode: TMode.doc, }, } } isLinkActive={ pathName === '/documents' && category === 'components' } clickAnalyticsEvent={ () => sendEvent('Components') } /> <BurgerButton caption="Demo" link={ { pathname: '/demo' } } isLinkActive={ pathName === '/demo' } clickAnalyticsEvent={ () => sendEvent('Demo') } /> <BurgerGroupHeader caption="Figma source" /> <BurgerButton icon={ FigmaIcon } caption="Figma Community" href="https://www.figma.com/community/file/1380452603479283689/epam-uui-v5-7" clickAnalyticsEvent={ () => sendEvent('Figma Community') } target="_blank" /> <BurgerButton icon={ FigmaIcon } caption="EPAM Team (employee only)" href="https://www.figma.com/design/M5Njgc6SQJ3TPUccp5XHQx/UUI-Components?m=auto&t=qiBDEE9slwMV4paI-6" clickAnalyticsEvent={ () => sendEvent('EPAM Team') } target="_blank" /> <BurgerGroupHeader caption="Code source" /> <BurgerButton icon={ GitIcon } caption="Github" href={ GIT_LINK } target="_blank" /> </> ); }; const renderThemeSwitcher = () => { return ( <Dropdown renderBody={ (props) => ( <DropdownMenuBody { ...props } rawProps={ { style: { width: '180px', padding: '6px 0', marginTop: '3px' } } }> { Object.values(themesById).map(({ id, name }) => ( <DropdownMenuButton key={ id } caption={ name } icon={ theme === id && DoneIcon } isActive={ theme === id } iconPosition="right" onClick={ () => toggleTheme(id) } /> )) } </DropdownMenuBody> ) } renderTarget={ (props) => ( <Button { ...props } cx={ css.themeSwitcherButton } icon={ isMobile(768) && ThemeIcon } caption={ !isMobile(768) && themesById[theme]?.name } fill="none" isDropdown={ true } /> ) } placement="bottom-end" key="Theme-switcher" /> ); }; const renderDirectionSwitcher = () => { return ( <FlexRow padding="12" key="RTL-switcher"> <MultiSwitch value={ direction } onValueChange={ changeContentDirection } items={ [{ id: 'ltr', caption: 'LTR' }, { id: 'rtl', caption: 'RTL' }] } /> </FlexRow> ); }; const getMainMenuItems = () => { const category = svc.uuiRouter.getCurrentLink().query.category; const pathName = svc.uuiRouter.getCurrentLink().pathname; return [ { id: 'burger', priority: 100500, collapsedContainer: true, render: () => <Burger renderBurgerContent={ renderBurger } logoUrl="/static/logo.svg" key="burger" />, }, { id: 'logo', priority: 100499, render: () => ( <MainMenuCustomElement key="logo"> <Anchor link={ { pathname: '/' } } onClick={ () => sendEvent('Welcome') }> <IconContainer icon={ LogoIcon } cx={ cx(css.icon, css.logo) } /> </Anchor> </MainMenuCustomElement> ), }, { id: 'documents', priority: 7, render: () => ( <MainMenuButton caption="Docs" link={ { pathname: '/documents', query: { id: 'overview' } } } isLinkActive={ pathName === '/documents' && category !== 'components' && category !== 'assets' } showInBurgerMenu clickAnalyticsEvent={ analyticsEvents.header.link('Documents') } key="documents" /> ), }, { id: 'assets', priority: 0, render: () => ( <MainMenuButton caption="Assets" link={ { pathname: '/documents', query: { id: 'icons', category: 'assets' } } } isLinkActive={ pathName === '/documents' && category === 'assets' } showInBurgerMenu clickAnalyticsEvent={ analyticsEvents.header.link('Assets') } key="assets" /> ), }, { id: 'components', priority: 1, render: () => ( <MainMenuButton caption="Components" link={ { pathname: '/documents', query: { category: 'components', id: 'accordion', mode: 'doc', }, } } isLinkActive={ pathName === '/documents' && category === 'components' } showInBurgerMenu clickAnalyticsEvent={ analyticsEvents.header.link('Components') } key="components" /> ), }, { id: 'demo', priority: 6, render: () => ( <MainMenuButton caption="Demo" link={ { pathname: '/demo' } } isLinkActive={ pathName === '/demo' } showInBurgerMenu clickAnalyticsEvent={ analyticsEvents.header.link('Demo') } key="demo" /> ), }, window.location.host.includes('localhost') && { id: 'Sandbox', priority: 0, render: () => <MainMenuButton caption="Sandbox" link={ { pathname: '/sandbox' } } isLinkActive={ pathName === '/sandbox' } key="sandbox" />, }, { id: 'moreContainer', priority: 7, collapsedContainer: true, render: (item: { id: React.Key; }, hiddenItems: any[]) => { return ( <MainMenuDropdown caption="More" key={ item.id } renderBody={ (props) => { return hiddenItems?.map((i) => { if (!['figma', 'git', 'gitStar', 'direction', 'themeCaption'].includes(i.id)) { return i.render({ ...i, onClose: props.onClose }); } return null; }); } } /> ); }, }, { id: 'flexSpacer', priority: 100500, render: () => <FlexSpacer priority={ 100500 } key="spacer" /> }, { id: 'figma', priority: 5, render: () => ( <Dropdown renderTarget={ (props) => <MainMenuButton rawProps={ { 'aria-label': 'Figma source' } } icon={ FigmaIcon } cx={ cx(css.icon, css.figmaIcon) } { ...props } /> } renderBody={ (props) => ( <DropdownMenuBody { ...props }> <DropdownMenuHeader caption="Open in" /> <DropdownMenuButton caption="Figma Community" href="https://www.figma.com/community/file/1380452603479283689/epam-uui-v5-7" target="_blank" /> <DropdownMenuButton caption="EPAM Team (employee only)" href="https://www.figma.com/design/M5Njgc6SQJ3TPUccp5XHQx/UUI-Components?m=auto&t=qiBDEE9slwMV4paI-6" target="_blank" /> </DropdownMenuBody> ) } key="figma-source" /> ), }, { id: 'git', priority: 4, render: () => <MainMenuButton icon={ GitIcon } href={ GIT_LINK } target="_blank" cx={ cx(css.icon) } key="github-link" rawProps={ { 'aria-label': 'Github repo' } } />, }, { id: 'gitStar', priority: 0, render: () => ( <Anchor tabIndex={ -1 } cx={ css.gitStarContainer } href={ GIT_LINK } target="_blank" onClick={ () => sendEvent(GIT_LINK) } key="gitstar"> <div className={ css.wrapper }> <IconContainer icon={ CommunicationStarOutlineIcon } /> <Text cx={ css.starCaption }>Star on github</Text> </div> </Anchor> ), }, { id: 'themeCaption', priority: 6, render: () => ( <MainMenuButton cx={ css.themeCaption } caption="Theme" showInBurgerMenu key="themeCaption" /> ), }, { id: 'theme', priority: 100498, render: renderThemeSwitcher }, !window.location.host.includes('uui.epam.com') && { id: 'direction', priority: 1, render: renderDirectionSwitcher, }, { id: 'globalMenu', priority: 100500, render: () => <GlobalMenu rawProps={ { 'aria-label': 'Global Menu' } } key="globalMenu" /> }, ].filter((i) => !!i); }; return <MainMenu cx={ css.root } items={ getMainMenuItems() }></MainMenu>; }