MatxVerticalNav.jsx
1 import { Fragment } from "react"; 2 import { NavLink } from "react-router-dom"; 3 import { Box, ButtonBase, Icon, styled } from "@mui/material"; 4 5 import useSettings from "app/hooks/useSettings"; 6 import { Paragraph, Span } from "../Typography"; 7 import MatxVerticalNavExpansionPanel from "./MatxVerticalNavExpansionPanel"; 8 9 const ListLabel = styled(Paragraph)(({ theme, mode }) => ({ 10 fontSize: "12px", 11 marginTop: "20px", 12 marginLeft: "15px", 13 marginBottom: "10px", 14 textTransform: "uppercase", 15 display: mode === "compact" && "none", 16 color: theme.palette.text.secondary 17 })); 18 19 const ExtAndIntCommon = { 20 display: "flex", 21 overflow: "hidden", 22 borderRadius: "4px", 23 height: 44, 24 whiteSpace: "pre", 25 marginBottom: "8px", 26 textDecoration: "none", 27 justifyContent: "space-between", 28 transition: "all 150ms ease-in", 29 "&:hover": { background: "rgba(255, 255, 255, 0.08)" }, 30 "&.compactNavItem": { 31 overflow: "hidden", 32 justifyContent: "center !important" 33 }, 34 "& .icon": { 35 fontSize: "18px", 36 paddingLeft: "16px", 37 paddingRight: "16px", 38 verticalAlign: "middle" 39 } 40 }; 41 const ExternalLink = styled("a")(({ theme }) => ({ 42 ...ExtAndIntCommon, 43 color: theme.palette.text.primary 44 })); 45 46 const InternalLink = styled(Box)(({ theme }) => ({ 47 "& a": { 48 ...ExtAndIntCommon, 49 color: theme.palette.text.primary 50 }, 51 "& .navItemActive": { 52 backgroundColor: "rgba(255, 255, 255, 0.16)" 53 } 54 })); 55 56 const StyledText = styled(Span)(({ mode }) => ({ 57 fontSize: "0.875rem", 58 paddingLeft: "0.8rem", 59 display: mode === "compact" && "none" 60 })); 61 62 const BulletIcon = styled("div")(({ theme }) => ({ 63 padding: "2px", 64 marginLeft: "24px", 65 marginRight: "8px", 66 overflow: "hidden", 67 borderRadius: "300px", 68 background: theme.palette.text.primary 69 })); 70 71 const BadgeValue = styled("div")(() => ({ 72 padding: "1px 8px", 73 overflow: "hidden", 74 borderRadius: "300px" 75 })); 76 77 export default function MatxVerticalNav({ items }) { 78 const { settings } = useSettings(); 79 const { mode } = settings.layout1Settings.leftSidebar; 80 81 const renderLevels = (data) => { 82 return data.map((item, index) => { 83 if (item.type === "label") 84 return ( 85 <ListLabel key={index} mode={mode} className="sidenavHoverShow"> 86 {item.label} 87 </ListLabel> 88 ); 89 90 if (item.children) { 91 return ( 92 <MatxVerticalNavExpansionPanel mode={mode} item={item} key={index}> 93 {renderLevels(item.children)} 94 </MatxVerticalNavExpansionPanel> 95 ); 96 } else if (item.type === "extLink") { 97 return ( 98 <ExternalLink 99 key={index} 100 href={item.path} 101 className={`${mode === "compact" && "compactNavItem"}`} 102 rel="noopener noreferrer" 103 target="_blank"> 104 <ButtonBase key={item.name} name="child" sx={{ width: "100%" }}> 105 {(() => { 106 if (item.icon) { 107 return <Icon className="icon">{item.icon}</Icon>; 108 } else { 109 return <span className="item-icon icon-text">{item.iconText}</span>; 110 } 111 })()} 112 <StyledText mode={mode} className="sidenavHoverShow"> 113 {item.name} 114 </StyledText> 115 <Box mx="auto"></Box> 116 {item.badge && <BadgeValue>{item.badge.value}</BadgeValue>} 117 </ButtonBase> 118 </ExternalLink> 119 ); 120 } else { 121 return ( 122 <InternalLink key={index}> 123 <NavLink 124 to={item.path} 125 className={({ isActive }) => 126 isActive 127 ? `navItemActive ${mode === "compact" && "compactNavItem"}` 128 : `${mode === "compact" && "compactNavItem"}` 129 }> 130 <ButtonBase key={item.name} name="child" sx={{ width: "100%" }}> 131 {item?.icon ? ( 132 <Icon className="icon" sx={{ width: 36 }}> 133 {item.icon} 134 </Icon> 135 ) : ( 136 <Fragment> 137 <BulletIcon 138 className={`nav-bullet`} 139 sx={{ display: mode === "compact" && "none" }} 140 /> 141 <Box 142 className="nav-bullet-text" 143 sx={{ 144 ml: "20px", 145 fontSize: "11px", 146 display: mode !== "compact" && "none" 147 }}> 148 {item.iconText} 149 </Box> 150 </Fragment> 151 )} 152 <StyledText mode={mode} className="sidenavHoverShow"> 153 {item.name} 154 </StyledText> 155 156 <Box mx="auto" /> 157 158 {item.badge && ( 159 <BadgeValue className="sidenavHoverShow">{item.badge.value}</BadgeValue> 160 )} 161 </ButtonBase> 162 </NavLink> 163 </InternalLink> 164 ); 165 } 166 }); 167 }; 168 169 return <div className="navigation">{renderLevels(items)}</div>; 170 }