import * as React from 'react';
import {
Box,
Drawer,
AppBar,
Toolbar,
List,
Typography,
Divider,
ListItem,
ListItemButton,
ListItemIcon,
ListItemText,
CssBaseline,
Button,
IconButton,
Tooltip,
useMediaQuery,
useTheme,
} from '@mui/material';
import TableViewIcon from '@mui/icons-material/TableView';
import DashboardIcon from '@mui/icons-material/Dashboard';
import LogoutIcon from '@mui/icons-material/Logout';
import MenuIcon from '@mui/icons-material/Menu';
import ChevronLeftIcon from '@mui/icons-material/ChevronLeft';
import ChevronRightIcon from '@mui/icons-material/ChevronRight';
import { ResourceConfig } from '../types/config';
import { useLocation, useNavigate } from 'react-router-dom';
const drawerWidth = 240;
const collapsedWidth = 64;
interface AdminLayoutProps {
children: React.ReactNode;
onSelectResource: (resourceName: string | null) => void;
onLogout: () => void;
username?: string;
resources: ResourceConfig[];
}
export default function AdminLayout({
children,
onSelectResource,
onLogout,
username,
resources,
}: AdminLayoutProps) {
const theme = useTheme();
const isMobile = useMediaQuery(theme.breakpoints.down('md'));
const location = useLocation();
const navigate = useNavigate();
const [isCollapsed, setIsCollapsed] = React.useState(false);
const [mobileOpen, setMobileOpen] = React.useState(false);
const activeResourceName = location.pathname.split('/')[1] || null;
// AUTO-TOGGLE LOGIC
React.useEffect(() => {
if (isMobile) {
setIsCollapsed(false); // Mobile drawer is never "mini"
setMobileOpen(false); // Close on navigation
} else {
if (location.pathname === '/' || location.pathname === '') {
setIsCollapsed(false);
} else {
setIsCollapsed(true);
}
}
}, [location.pathname, isMobile]);
const currentWidth = isMobile ? drawerWidth : (isCollapsed ? collapsedWidth : drawerWidth);
const handleDrawerToggle = () => {
setMobileOpen(!mobileOpen);
};
const handleSidebarToggle = () => {
setIsCollapsed(!isCollapsed);
};
const drawerContent = (
{!isMobile && (
<>
{isCollapsed ? : }
>
)}
{isMobile && }
navigate('/')}
sx={{
minHeight: 48,
justifyContent: (isCollapsed && !isMobile) ? 'center' : 'initial',
px: 2.5,
}}
>
{(!isCollapsed || isMobile) && }
{resources.map((res) => (
onSelectResource(res.name)}
sx={{
minHeight: 48,
justifyContent: (isCollapsed && !isMobile) ? 'center' : 'initial',
px: 2.5,
}}
>
{(!isCollapsed || isMobile) && }
))}
);
return (
theme.zIndex.drawer + 1,
backdropFilter: 'blur(8px)',
backgroundColor: 'rgba(255, 255, 255, 0.8)',
color: 'text.primary',
boxShadow: 'none',
borderBottom: '1px solid',
borderColor: 'divider',
}}
>
{isMobile && (
)}
Admin Panel
{isMobile ? (
{drawerContent}
) : (
theme.transitions.create('width', {
easing: theme.transitions.easing.sharp,
duration: theme.transitions.duration.enteringScreen,
}),
[`& .MuiDrawer-paper`]: {
width: currentWidth,
boxSizing: 'border-box',
overflowX: 'hidden',
transition: (theme) => theme.transitions.create('width', {
easing: theme.transitions.easing.sharp,
duration: theme.transitions.duration.enteringScreen,
}),
},
}}
open
>
{drawerContent}
)}
theme.transitions.create(['margin', 'width'], {
easing: theme.transitions.easing.sharp,
duration: theme.transitions.duration.enteringScreen,
}),
}}
>
{children}
);
}