Completed Change to ReactJS
This commit is contained in:
128
frontend/src/components/Navbar.jsx
Normal file
128
frontend/src/components/Navbar.jsx
Normal file
@@ -0,0 +1,128 @@
|
||||
import { useAuth, useSignInUp } from '@hooks/useAuth'
|
||||
import { Avatar, Badge, Box, Divider, Flex, Menu, NavLink } from '@mantine/core'
|
||||
import { notifications } from '@mantine/notifications'
|
||||
import { NAV_ITEM } from '@routes/nav-route'
|
||||
import { PathConstants } from '@routes/routes'
|
||||
import {
|
||||
IconAt,
|
||||
IconCircleXFilled,
|
||||
IconLogout,
|
||||
IconUserCircle,
|
||||
} from '@tabler/icons-react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import { NavLink as Link } from 'react-router-dom'
|
||||
|
||||
function NavLinkWithChildren(item) {
|
||||
const Icon = item.icon
|
||||
|
||||
return (
|
||||
<NavLink label={item.text} leftSection={<Icon size={15} />}>
|
||||
{item.children.map((child) => {
|
||||
if (!child.show) return
|
||||
if (child.children) {
|
||||
return <NavLinkWithChildren key={child.pathName} {...child} />
|
||||
} else {
|
||||
return (
|
||||
<NavLink
|
||||
key={child.pathName}
|
||||
leftSection={<Icon size={15} />}
|
||||
label={child.text}
|
||||
component={Link}
|
||||
to={child.pathName}
|
||||
/>
|
||||
)
|
||||
}
|
||||
})}
|
||||
</NavLink>
|
||||
)
|
||||
}
|
||||
|
||||
export default function Navbar() {
|
||||
const { auth, setAuth } = useAuth()
|
||||
const { t } = useTranslation()
|
||||
const { onLogout } = useSignInUp(setAuth)
|
||||
|
||||
const logOut = async () => {
|
||||
try {
|
||||
await onLogout()
|
||||
} catch (error) {
|
||||
notifications.show({
|
||||
color: 'red.5',
|
||||
icon: <IconCircleXFilled />,
|
||||
withCloseButton: true,
|
||||
title: t('message_logout_fail'),
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Box hiddenFrom="md">
|
||||
<Flex p="lg">
|
||||
<Menu trigger="hover" position="bottom-start" width={150}>
|
||||
<Menu.Target>
|
||||
<Avatar
|
||||
size="30"
|
||||
variant="filled"
|
||||
name={auth.userInfo?.name}
|
||||
color="red.4"
|
||||
style={{ cursor: 'pointer' }}
|
||||
/>
|
||||
</Menu.Target>
|
||||
<Menu.Dropdown>
|
||||
<Menu.Label>
|
||||
<Badge
|
||||
leftSection={<IconAt size={12} />}
|
||||
size="sm"
|
||||
color="yellow.8"
|
||||
>
|
||||
{auth.userInfo?.name}
|
||||
</Badge>
|
||||
</Menu.Label>
|
||||
<Menu.Divider />
|
||||
<Menu.Item
|
||||
leftSection={<IconUserCircle size={15} />}
|
||||
component={Link}
|
||||
to={PathConstants.PROFILE}
|
||||
>
|
||||
{t('ui_profile')}
|
||||
</Menu.Item>
|
||||
<Menu.Item
|
||||
leftSection={<IconLogout size={15} />}
|
||||
fw="500"
|
||||
onClick={logOut}
|
||||
>
|
||||
{t('ui_logout')}
|
||||
</Menu.Item>
|
||||
</Menu.Dropdown>
|
||||
</Menu>
|
||||
</Flex>
|
||||
<Divider />
|
||||
</Box>
|
||||
<Box>
|
||||
{NAV_ITEM(t, auth?.userInfo?.isAdmin).map((item) => {
|
||||
if (!item.show) return null
|
||||
const Icon = item.icon
|
||||
|
||||
if (item.children) {
|
||||
return <NavLinkWithChildren key={item.pathName} {...item} />
|
||||
} else {
|
||||
return (
|
||||
<NavLink
|
||||
key={item.pathName}
|
||||
leftSection={<Icon size={15} />}
|
||||
label={item.text}
|
||||
component={Link}
|
||||
to={item.pathName}
|
||||
className={({ isActive, isPending }) =>
|
||||
isPending ? 'pending' : isActive ? 'active' : ''
|
||||
}
|
||||
color="red.8"
|
||||
/>
|
||||
)
|
||||
}
|
||||
})}
|
||||
</Box>
|
||||
</>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user