u
This commit is contained in:
@@ -1,21 +1,24 @@
|
||||
import { PureComponent } from 'react';
|
||||
import Box from '@mui/material/Box';
|
||||
import List from '@mui/material/List';
|
||||
import ListItemButton from '@mui/material/ListItemButton';
|
||||
import ListItemIcon from '@mui/material/ListItemIcon';
|
||||
import ListItemText from '@mui/material/ListItemText';
|
||||
import IconButton from '@mui/material/IconButton';
|
||||
import { Outlet, useLocation, useNavigate } from 'react-router-dom';
|
||||
import UserMenu from './UserMenu';
|
||||
import { NAV_ITEMS, isNavItemActive } from '../nav';
|
||||
import { NAV_ITEMS, SUB_NAV, resolveActiveNav, resolveActiveSub } from '../nav';
|
||||
import { artikelQueryPath } from '../pages/artikel/artikelQuery';
|
||||
import { defaultCategoryPath } from '../pages/artikel/categoryRoute';
|
||||
|
||||
const SIDEBAR_WIDTH = 144;
|
||||
const SUB_NAV_WIDTH = 80;
|
||||
|
||||
export default function AppShell() {
|
||||
const navigate = useNavigate();
|
||||
const { pathname } = useLocation();
|
||||
class AppSidebar extends PureComponent {
|
||||
render() {
|
||||
const { activeNav, navigate } = this.props;
|
||||
|
||||
return (
|
||||
<Box sx={{ display: 'flex', minHeight: '100vh', bgcolor: 'background.default' }}>
|
||||
return (
|
||||
<Box
|
||||
component="nav"
|
||||
sx={(theme) => ({
|
||||
@@ -28,7 +31,7 @@ export default function AppShell() {
|
||||
>
|
||||
<List disablePadding sx={{ flexGrow: 1 }}>
|
||||
{NAV_ITEMS.map(({ path, label, icon: Icon }) => {
|
||||
const active = isNavItemActive(pathname, path);
|
||||
const active = path === activeNav;
|
||||
|
||||
return (
|
||||
<ListItemButton
|
||||
@@ -73,17 +76,113 @@ export default function AppShell() {
|
||||
|
||||
<UserMenu />
|
||||
</Box>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class AppSubNav extends PureComponent {
|
||||
render() {
|
||||
const { activeNav, activeSub, navigate } = this.props;
|
||||
const subNav = activeNav ? SUB_NAV[activeNav] : null;
|
||||
|
||||
if (!subNav?.length) {
|
||||
return (
|
||||
<Box
|
||||
sx={{
|
||||
width: SUB_NAV_WIDTH,
|
||||
flexShrink: 0,
|
||||
}}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<Box
|
||||
component="nav"
|
||||
aria-label="Unternavigation"
|
||||
sx={{
|
||||
width: SUB_NAV_WIDTH,
|
||||
flexShrink: 0,
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
alignItems: 'center',
|
||||
gap: 1,
|
||||
}}
|
||||
>
|
||||
{subNav.map(({ segment, label, icon: Icon }) => {
|
||||
const active = segment === activeSub;
|
||||
|
||||
return (
|
||||
<IconButton
|
||||
key={segment || 'index'}
|
||||
type="button"
|
||||
aria-label={label}
|
||||
aria-current={active ? 'page' : undefined}
|
||||
disableRipple
|
||||
onMouseDown={(e) => e.preventDefault()}
|
||||
onClick={() => {
|
||||
if (!segment && activeNav === '/artikel') {
|
||||
navigate(artikelQueryPath());
|
||||
return;
|
||||
}
|
||||
if (segment === 'kategorien') {
|
||||
navigate(defaultCategoryPath());
|
||||
return;
|
||||
}
|
||||
navigate(segment ? `${activeNav}/${segment}` : activeNav);
|
||||
}}
|
||||
sx={(theme) => ({
|
||||
width: 80,
|
||||
height: 80,
|
||||
borderRadius: '50%',
|
||||
color: active
|
||||
? theme.palette.primary.main
|
||||
: theme.palette.text.secondary,
|
||||
bgcolor: 'transparent',
|
||||
'&:hover': {
|
||||
bgcolor: theme.palette.action.hover,
|
||||
color: theme.palette.primary.main,
|
||||
},
|
||||
})}
|
||||
>
|
||||
<Icon sx={{ fontSize: 40 }} />
|
||||
</IconButton>
|
||||
);
|
||||
})}
|
||||
</Box>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
export default function AppShell() {
|
||||
const navigate = useNavigate();
|
||||
const { pathname } = useLocation();
|
||||
const activeNav = resolveActiveNav(pathname);
|
||||
const activeSub = activeNav ? resolveActiveSub(pathname, activeNav) : null;
|
||||
|
||||
return (
|
||||
<Box sx={{ display: 'flex', minHeight: '100vh', bgcolor: 'background.default' }}>
|
||||
<AppSidebar activeNav={activeNav} navigate={navigate} />
|
||||
<Box
|
||||
component="main"
|
||||
sx={(theme) => ({
|
||||
flexGrow: 1,
|
||||
display: 'flex',
|
||||
gap: 2,
|
||||
py: 4,
|
||||
px: 3,
|
||||
bgcolor: theme.nav.mainBackground,
|
||||
minWidth: 0,
|
||||
})}
|
||||
>
|
||||
<Outlet />
|
||||
<AppSubNav
|
||||
activeNav={activeNav}
|
||||
activeSub={activeSub}
|
||||
navigate={navigate}
|
||||
/>
|
||||
<Box sx={{ flexGrow: 1, minWidth: 0 }}>
|
||||
<Outlet />
|
||||
</Box>
|
||||
</Box>
|
||||
</Box>
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user