124 lines
4.0 KiB
JavaScript
124 lines
4.0 KiB
JavaScript
import React from "react";
|
|
import { Link, NavLink, useLocation, useNavigate } from "react-router-dom";
|
|
import menuData from "../../data/menuData.json";
|
|
import { getCachedProfileData } from "../../slices/apiDataManager";
|
|
import { useSidBarMenu } from "../../hooks/useProfile";
|
|
import { MenuItemSkeleton } from "./MenuItemSkeleton";
|
|
|
|
const Sidebar = () => {
|
|
const navigate = useNavigate();
|
|
const { data, isError, isLoading, isFetched, error } = useSidBarMenu();
|
|
return (
|
|
<aside
|
|
id="layout-menu"
|
|
className="layout-menu menu-vertical menu bg-menu-theme "
|
|
>
|
|
<div className="app-brand" style={{ paddingLeft: "30px" }}>
|
|
<Link to="/dashboard" className="app-brand-link">
|
|
{/* <span className="app-brand-logo rounded-circle app-brand-logo-border">
|
|
<img
|
|
className="app-brand-logo-sidebar"
|
|
src="/img/brand/marco.png"
|
|
alt="logo"
|
|
aria-label="logo image"
|
|
style={{ margin: "5px", paddingRight: "5px" }}
|
|
/>
|
|
</span> */}
|
|
|
|
<a
|
|
href="/"
|
|
className="app-brand-link fw-bold navbar-brand text-green fs-6"
|
|
>
|
|
<span className="app-brand-logo demo">
|
|
<img src="/img/brand/marco.png" width="50" />
|
|
</span>
|
|
<span className="text-blue">OnField</span>
|
|
<span>Work</span>
|
|
<span className="text-dark">.com</span>
|
|
</a>
|
|
</Link>
|
|
|
|
<a className="layout-menu-toggle menu-link text-large ms-auto">
|
|
<i className="bx bx-chevron-left bx-sm d-flex align-items-center justify-content-center"></i>
|
|
</a>
|
|
</div>
|
|
|
|
<div className="menu-inner-shadow"></div>
|
|
|
|
<ul className="menu-inner py-1">
|
|
{isError && (
|
|
<div className="text-center text-small">{error.message}</div>
|
|
)}
|
|
{isLoading && (
|
|
<>
|
|
{[...Array(7)].map((_, idx) => (
|
|
<MenuItemSkeleton
|
|
key={idx}
|
|
hasSubmenu={idx % 2 === 1}
|
|
submenuCount={Math.floor(Math.random() * 3) + 2}
|
|
/>
|
|
))}
|
|
</>
|
|
)}
|
|
{data &&
|
|
data?.data.map((section) => (
|
|
<React.Fragment
|
|
key={section.id || section.header || section.items[0]?.id}
|
|
>
|
|
{/* {section.header && (
|
|
<li className="menu-header small text-uppercase">
|
|
<span className="menu-header-text">{section.header}</span>
|
|
</li>
|
|
)} */}
|
|
{section.items.map((item) => (
|
|
<MenuItem key={item.id || item.link} {...item} />
|
|
))}
|
|
</React.Fragment>
|
|
))}
|
|
</ul>
|
|
</aside>
|
|
);
|
|
};
|
|
|
|
const MenuItem = (item) => {
|
|
const location = useLocation();
|
|
const isActive = location.pathname === item.link;
|
|
const hasSubmenu = Array.isArray(item.submenu) && item.submenu.length > 0;
|
|
const isSubmenuActive =
|
|
hasSubmenu && item.submenu.some((sub) => location.pathname === sub.link);
|
|
|
|
return (
|
|
<li
|
|
className={`menu-item ${isActive || isSubmenuActive ? "active" : ""} ${
|
|
hasSubmenu && isSubmenuActive ? "open" : ""
|
|
}`}
|
|
>
|
|
<NavLink
|
|
aria-label={`Navigate to ${item.text} ${!item.available ? "Pro" : ""}`}
|
|
to={item.link}
|
|
className={`menu-link ${hasSubmenu ? "menu-toggle" : ""}`}
|
|
target={item.link?.includes("http") ? "_blank" : undefined}
|
|
>
|
|
{item.icon && <i className={`menu-icon tf-icons ${item.icon}`}></i>}
|
|
<div>{item.name}</div>
|
|
{item.available === false && (
|
|
<div className="badge bg-label-primary fs-tiny rounded-pill ms-auto">
|
|
Pro
|
|
</div>
|
|
)}
|
|
</NavLink>
|
|
|
|
{/* Only render submenu if exists */}
|
|
{hasSubmenu && (
|
|
<ul className="menu-sub">
|
|
{item.submenu.map((sub) => (
|
|
<MenuItem key={sub.id || sub.link} {...sub} />
|
|
))}
|
|
</ul>
|
|
)}
|
|
</li>
|
|
);
|
|
};
|
|
|
|
export default Sidebar;
|