Header.jsx 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385
  1. import React from 'react';
  2. import {AppBar, Box, Toolbar, IconButton, Typography, Menu, Container, Avatar, Button, Tooltip, MenuItem, Badge} from '@mui/material';
  3. import MenuIcon from '@mui/icons-material/Menu';
  4. import SearchIcon from '@mui/icons-material/Search';
  5. import FavoriteBorderIcon from '@mui/icons-material/FavoriteBorder';
  6. import ShoppingCartIcon from '@mui/icons-material/ShoppingCart';
  7. import ManageSearchIcon from '@mui/icons-material/ManageSearch';
  8. import Link from "react-router-dom/es/Link";
  9. import {useState} from "react";
  10. import '../scss/Header.scss';
  11. import {actionAuthLogout} from "../reducers/AuthReducer";
  12. import {connect} from "react-redux";
  13. import {actionUserRemove} from "../reducers/UserReducer";
  14. import {backURL} from "../actions/PathDB";
  15. import userDefault from "../img/header/userDefault.png"
  16. const pages = ['catalog', 'about us', 'our team', 'faq', 'contact']
  17. const settingsDefaultUserAuth = ['Profile', 'Dashboard', 'Logout']
  18. const Header = ({user={}}) => {
  19. const [anchorElNav, setAnchorElNav] = useState(null);
  20. const [anchorElUser, setAnchorElUser] = useState(null);
  21. const handleOpenNavMenu = (event) => {
  22. setAnchorElNav(event.currentTarget);
  23. };
  24. const handleOpenUserMenu = (event) => {
  25. setAnchorElUser(event.currentTarget);
  26. };
  27. const handleCloseNavMenu = () => {
  28. setAnchorElNav(null);
  29. };
  30. const handleCloseUserMenu = () => {
  31. setAnchorElUser(null);
  32. };
  33. const LogoItem = () => {
  34. return (
  35. <Link
  36. to='/'
  37. className="Header__Logo"
  38. >
  39. ABRAXAS
  40. </Link>
  41. )
  42. }
  43. const LinkItem = ({page, color='white'}) => {
  44. return (
  45. <Button
  46. key={page.toString()}
  47. onClick={handleCloseNavMenu}
  48. sx={{
  49. my: 2,
  50. color: color,
  51. display: 'block'
  52. }}
  53. >
  54. <Link
  55. to={`/${Array.from(page.toLowerCase()).map(i => i === ' ' ? '-' : i).join('')}`}
  56. className="Header__Link"> {page}
  57. </Link>
  58. </Button>
  59. )
  60. }
  61. const IconItems = ({cart={}, wishlist={}, size="large", color='default'}) => {
  62. return (
  63. <>
  64. <Link to='/search'>
  65. <IconButton
  66. key={'search'}
  67. size={size}
  68. aria-label="search"
  69. color={color}
  70. >
  71. <SearchIcon />
  72. </IconButton>
  73. </Link>
  74. <Link to='/my-orders'>
  75. <IconButton
  76. key={'my-orders'}
  77. size={size}
  78. aria-label="my-orders"
  79. color={color}
  80. >
  81. <ManageSearchIcon />
  82. </IconButton>
  83. </Link>
  84. <Link to='/wish-list'>
  85. <IconButton
  86. key={'wish-list'}
  87. size={size}
  88. aria-label="wish-list"
  89. color={color}
  90. >
  91. <Badge
  92. color="success"
  93. badgeContent={+Object.entries(wishlist).length}
  94. anchorOrigin={{
  95. vertical: 'bottom',
  96. horizontal: 'right',
  97. }}
  98. >
  99. <FavoriteBorderIcon />
  100. </Badge>
  101. </IconButton>
  102. </Link>
  103. <Link to='/basket'>
  104. <IconButton
  105. key={'basket'}
  106. size={size}
  107. aria-label="basket"
  108. color={color}
  109. >
  110. <Badge
  111. color="success"
  112. badgeContent={+Object.entries(cart).reduce((a, b) => {
  113. return a + b[1].count
  114. }, 0)}
  115. anchorOrigin={{
  116. vertical: 'bottom',
  117. horizontal: 'right',
  118. }}
  119. >
  120. <ShoppingCartIcon/>
  121. </Badge>
  122. </IconButton>
  123. </Link>
  124. </>
  125. )
  126. }
  127. const CIconItems = connect(state => ({cart: state.cart, wishlist: state.wishlist}))(IconItems)
  128. const ItemAuth = ({link, text}) => {
  129. return (
  130. <Link
  131. style={{
  132. textDecoration: 'none',
  133. color: '#000'
  134. }}
  135. to={`/${link}`}
  136. >
  137. <MenuItem
  138. key={text}
  139. onClick={handleCloseNavMenu}
  140. >
  141. <Typography
  142. textAlign="center"
  143. color='#fff'
  144. >
  145. {text}
  146. </Typography>
  147. </MenuItem>
  148. </Link>
  149. )
  150. }
  151. const UserIcon = ({auth}) => {
  152. return (
  153. Object.entries(auth).length === 0 ?
  154. <Link
  155. style={{textDecoration: 'none'}}
  156. to={'/my-account'}
  157. >
  158. <IconButton sx={{ p: 0 }}>
  159. <Avatar
  160. alt="User default"
  161. src={userDefault}
  162. />
  163. </IconButton>
  164. </Link> :
  165. <>
  166. <Tooltip title="Open settings">
  167. <IconButton onClick={handleOpenUserMenu} sx={{ p: 0 }}>
  168. {!auth.avatar && auth.avatar === null ?
  169. <Avatar
  170. alt="User"
  171. src={userDefault}/>
  172. :
  173. <Avatar
  174. alt="User"
  175. src={user?.avatar?.url && backURL + '/' + user?.avatar?.url}
  176. />
  177. }
  178. </IconButton>
  179. </Tooltip>
  180. <Menu
  181. sx={{ mt: '55px', ml: '90%'}}
  182. id="menu-appbar"
  183. anchorEl={anchorElUser}
  184. anchorOrigin={{
  185. vertical: 'top',
  186. horizontal: 'right',
  187. }}
  188. keepMounted
  189. transformOrigin={{
  190. vertical: 'top',
  191. horizontal: 'right',
  192. }}
  193. open={Boolean(anchorElUser)}
  194. onClose={handleCloseUserMenu}
  195. >
  196. {settingsDefaultUserAuth.map(item => {
  197. if (item === 'Logout') {
  198. return <CButtonLogOut key={'Logout'}/>
  199. }
  200. else if(item === 'Dashboard'){
  201. if (auth.payload?.sub?.acl[2]){
  202. return (
  203. <ItemAuth
  204. link={'admin'}
  205. text={'Dashboard'}
  206. key={'admin'}
  207. />
  208. )
  209. }
  210. }
  211. else if(item !== 'Dashboard') {
  212. return (
  213. <ItemAuth
  214. key={item.toString()}
  215. text={item}
  216. link={Array.from(item.toLowerCase()).map(i => i === ' ' ? '-' : i).join('')}
  217. />
  218. )
  219. }
  220. })}
  221. </Menu>
  222. </>
  223. )
  224. }
  225. const CUserIcon = connect(state => ({auth: state.auth}))(UserIcon)
  226. const ButtonLogOut = ({actionLogOut, actionUserRemove}) => {
  227. return (
  228. <Button
  229. onClick={() => {
  230. actionLogOut();
  231. actionUserRemove();
  232. handleCloseNavMenu();
  233. }}
  234. style={{
  235. textDecoration: 'none',
  236. textTransform: 'capitalize',
  237. fontWeight: '400',
  238. color: '#fff',
  239. textAlign: "center",
  240. width: '100%'
  241. }}
  242. >
  243. Log out
  244. </Button>
  245. )
  246. }
  247. const CButtonLogOut = connect(null, {actionLogOut: actionAuthLogout,
  248. actionUserRemove: actionUserRemove})(ButtonLogOut)
  249. return (
  250. <AppBar
  251. sx={{
  252. padding: '10px 0',
  253. backgroundColor: 'rgb(131,179,175)'
  254. }}
  255. className='Header'
  256. position="fixed"
  257. enableColorOnDark={true}
  258. >
  259. <Container maxWidth="xl">
  260. <Toolbar disableGutters>
  261. <Typography
  262. variant="h6"
  263. noWrap
  264. component="div"
  265. sx={{ mr: 2,
  266. display: {
  267. xs: 'none',
  268. md: 'flex'
  269. }
  270. }}
  271. >
  272. <LogoItem/>
  273. </Typography>
  274. <Box
  275. sx={{
  276. flexGrow: 1,
  277. display: { xs: 'flex', md: 'none' }
  278. }}
  279. >
  280. <IconButton
  281. size="large"
  282. aria-label="account of current user"
  283. aria-controls="menu-appbar"
  284. aria-haspopup="true"
  285. onClick={handleOpenNavMenu}
  286. color="inherit"
  287. >
  288. <MenuIcon />
  289. </IconButton>
  290. <Menu className='Header__Burger'
  291. id="menu-appbar"
  292. anchorEl={anchorElNav}
  293. anchorOrigin={{
  294. vertical: 'bottom',
  295. horizontal: 'left',
  296. }}
  297. keepMounted
  298. transformOrigin={{
  299. vertical: 'top',
  300. horizontal: 'left',
  301. }}
  302. open={Boolean(anchorElNav)}
  303. onClose={handleCloseNavMenu}
  304. sx={{
  305. display: { xs: 'block', md: 'none' },
  306. }}
  307. >
  308. {pages.map((page) => (
  309. <MenuItem
  310. key={page.toString()}
  311. onClick={handleCloseNavMenu}
  312. >
  313. <LinkItem
  314. key={page.toString()}
  315. page={page}
  316. color={'#fff'}
  317. />
  318. </MenuItem>
  319. ))}
  320. <MenuItem onClick={handleCloseNavMenu}>
  321. <CIconItems
  322. size={'large'}
  323. color={'inherit'}
  324. />
  325. </MenuItem>
  326. </Menu>
  327. </Box>
  328. <Typography
  329. variant="h6"
  330. noWrap
  331. component="div"
  332. sx={{
  333. flexGrow: 1,
  334. display: { xs: 'flex', md: 'none' }
  335. }}
  336. >
  337. <LogoItem />
  338. </Typography>
  339. <Box
  340. className='Header__Links'
  341. sx={{
  342. flexGrow: 1,
  343. display: { xs: 'none', md: 'flex' }
  344. }}
  345. >
  346. {pages.map((page) => (
  347. <LinkItem
  348. key={page.toString()}
  349. page={page}
  350. color={'#fff'}
  351. />
  352. ))}
  353. </Box>
  354. <Box
  355. className='Header__Icons'
  356. sx={{
  357. flexGrow: 0,
  358. display: { xs: 'none', md: 'flex' }
  359. }}
  360. >
  361. <CIconItems size={'large'} />
  362. </Box>
  363. <Box sx={{ flexGrow: 0 }}>
  364. <CUserIcon/>
  365. </Box>
  366. </Toolbar>
  367. </Container>
  368. </AppBar>
  369. );
  370. };
  371. const CHeader = connect(state => ({user: state.user}))(Header)
  372. export default CHeader;