first update

This commit is contained in:
sebvtl728
2025-01-02 13:39:40 +01:00
parent 32dc34afcf
commit 27d4a1e6a0
26 changed files with 7611 additions and 0 deletions
+365
View File
@@ -0,0 +1,365 @@
import React, { useState } from "react";
import {
AppBar,
Toolbar,
Typography,
Button,
Box,
Drawer,
List,
ListItem,
ListItemText,
TextField,
IconButton,
Divider,
Menu,
MenuItem,
CircularProgress,
} from "@mui/material";
import { Link, useLocation, useNavigate } from "react-router-dom";
import MenuIcon from "@mui/icons-material/Menu";
import SearchIcon from "@mui/icons-material/Search";
import HomeIcon from "@mui/icons-material/Home";
import ArticleIcon from "@mui/icons-material/Article";
import InfoIcon from "@mui/icons-material/Info";
import ContactMailIcon from "@mui/icons-material/ContactMail";
import WorkIcon from "@mui/icons-material/Work";
const Header = () => {
const [drawerOpen, setDrawerOpen] = useState(false);
const [searchQuery, setSearchQuery] = useState("");
const [isSearching, setIsSearching] = useState(false);
const [anchorEl, setAnchorEl] = useState(null); // Pour gérer le menu Services
const location = useLocation();
const navigate = useNavigate();
const toggleDrawer = (open) => (event) => {
if (
event.type === "keydown" &&
(event.key === "Tab" || event.key === "Shift")
) {
return;
}
setDrawerOpen(open);
};
const handleSearch = () => {
if (searchQuery.trim()) {
setIsSearching(true);
setTimeout(() => {
navigate(`/search?query=${encodeURIComponent(searchQuery.trim())}`);
setIsSearching(false);
}, 500);
}
};
const handleMenuOpen = (event) => {
setAnchorEl(event.currentTarget);
};
const handleMenuClose = () => {
setAnchorEl(null);
};
const commonButtonStyles = {
transition: "color 0.3s",
position: "relative",
"&:hover": { color: "#00bcd4" },
"&:after": {
content: '""',
position: "absolute",
width: "0",
height: "2px",
bottom: 0,
left: 0,
backgroundColor: "#00bcd4",
transition: "width 0.3s",
},
"&:hover:after": {
width: "100%",
},
};
return (
<AppBar
position="static"
color="transparent"
elevation={0}
sx={{
background: "linear-gradient(to right, #0e467f, #00bcd4)",
color: "white",
transition: "all 0.3s ease",
}}
>
<Toolbar>
{/* Mobile menu icon */}
<IconButton
edge="start"
color="inherit"
aria-label="menu"
onClick={toggleDrawer(true)}
sx={{ display: { xs: "block", md: "none" } }}
>
<MenuIcon />
</IconButton>
{/* Logo as Home Link */}
<Typography
variant="h6"
component={Link}
to="/"
sx={{
flexGrow: 1,
textAlign: { xs: "center", md: "left" },
fontWeight: "bold",
textDecoration: "none",
color: "white",
"&:hover": {
color: "#00bcd4",
},
}}
>
Mon Site React
</Typography>
{/* Navigation Links */}
<Box sx={{ display: { xs: "none", md: "flex" }, gap: 2 }}>
<Button
component={Link}
to="/posts"
color="inherit"
sx={{
fontWeight: location.pathname === "/posts" ? "bold" : "normal",
textDecoration:
location.pathname === "/posts" ? "underline" : "none",
...commonButtonStyles,
}}
>
Articles
</Button>
{/* Services Dropdown */}
<Button
color="inherit"
aria-controls="services-menu"
aria-haspopup="true"
onClick={handleMenuOpen}
sx={{
fontWeight: location.pathname.includes("/services")
? "bold"
: "normal",
textDecoration: location.pathname.includes("/services")
? "underline"
: "none",
...commonButtonStyles,
}}
>
Services
</Button>
<Menu
id="services-menu"
anchorEl={anchorEl}
open={Boolean(anchorEl)}
onClose={handleMenuClose}
MenuListProps={{
"aria-labelledby": "services-button",
}}
>
<MenuItem
component={Link}
to="/services/formation-web"
onClick={handleMenuClose}
>
<WorkIcon sx={{ marginRight: 1 }} />
Formation Web
</MenuItem>
<MenuItem
component={Link}
to="/services/formation-ia"
onClick={handleMenuClose}
>
<WorkIcon sx={{ marginRight: 1 }} />
Formation IA
</MenuItem>
<MenuItem
component={Link}
to="/services/formation-video"
onClick={handleMenuClose}
>
<WorkIcon sx={{ marginRight: 1 }} />
Formation Video
</MenuItem>
</Menu>
<Button
component={Link}
to="/about"
color="inherit"
sx={{
fontWeight: location.pathname === "/about" ? "bold" : "normal",
textDecoration:
location.pathname === "/about" ? "underline" : "none",
...commonButtonStyles,
}}
>
À propos
</Button>
<Button
component={Link}
to="/contact"
color="inherit"
sx={{
fontWeight: location.pathname === "/contact" ? "bold" : "normal",
textDecoration:
location.pathname === "/contact" ? "underline" : "none",
...commonButtonStyles,
}}
>
Contact
</Button>
</Box>
{/* Search Field */}
<Box
component="form"
onSubmit={(e) => {
e.preventDefault();
handleSearch();
}}
sx={{
display: { xs: "none", md: "flex" },
alignItems: "center",
gap: 1,
}}
>
<label
htmlFor="search-input"
style={{ position: "absolute", left: "-9999px" }}
>
Rechercher sur le site
</label>
<TextField
id="search-input"
variant="outlined"
size="small"
placeholder="Rechercher..."
value={searchQuery}
onChange={(e) => setSearchQuery(e.target.value)}
sx={{
backgroundColor: "rgba(255, 255, 255, 0.9)",
borderRadius: 1,
"& .MuiOutlinedInput-root": {
"& fieldset": {
borderColor: "white",
},
"&:hover fieldset": {
borderColor: "#00bcd4",
},
"&.Mui-focused fieldset": {
borderColor: "#00bcd4",
},
},
}}
/>
<IconButton type="submit" color="inherit" aria-label="Rechercher">
{isSearching ? (
<CircularProgress size={20} color="inherit" />
) : (
<SearchIcon />
)}
</IconButton>
</Box>
{/* Drawer for mobile */}
<Drawer anchor="left" open={drawerOpen} onClose={toggleDrawer(false)}>
<Box
sx={{
width: 250,
backgroundColor: "#f5f5f5",
height: "100%",
padding: 2,
}}
role="presentation"
onClick={toggleDrawer(false)}
onKeyDown={toggleDrawer(false)}
>
<Typography
variant="h6"
sx={{ textAlign: "center", marginBottom: 2 }}
>
Menu
</Typography>
<Divider />
<List>
<ListItem
button
component={Link}
to="/"
selected={location.pathname === "/"}
>
<HomeIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Accueil" />
</ListItem>
<ListItem
button
component={Link}
to="/posts"
selected={location.pathname === "/posts"}
>
<ArticleIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Articles" />
</ListItem>
<ListItem
button
component={Link}
to="/services/formation-web"
selected={location.pathname.includes("/services/formation-web")}
>
<WorkIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Formation Web" />
</ListItem>
<ListItem
button
component={Link}
to="/services/formation-ia"
selected={location.pathname.includes("/services/formation-ia")}
>
<WorkIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Formation IA" />
</ListItem>
<ListItem
button
component={Link}
to="/services/formation-video"
selected={location.pathname.includes("/services/formation-video")}
>
<WorkIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Formation Video" />
</ListItem>
<ListItem
button
component={Link}
to="/about"
selected={location.pathname === "/about"}
>
<InfoIcon sx={{ marginRight: 1 }} />
<ListItemText primary="À propos" />
</ListItem>
<ListItem
button
component={Link}
to="/contact"
selected={location.pathname === "/contact"}
>
<ContactMailIcon sx={{ marginRight: 1 }} />
<ListItemText primary="Contact" />
</ListItem>
</List>
</Box>
</Drawer>
</Toolbar>
</AppBar>
);
};
export default Header;