latest changes
This commit is contained in:
commit
df66275d19
5661
pnpm-lock.yaml
5661
pnpm-lock.yaml
File diff suppressed because it is too large
Load diff
27
public/Login.svg
Normal file
27
public/Login.svg
Normal file
File diff suppressed because one or more lines are too long
After Width: | Height: | Size: 14 MiB |
BIN
public/home-img.png
Normal file
BIN
public/home-img.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 1 MiB |
BIN
public/home.png
Normal file
BIN
public/home.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 120 KiB |
|
@ -3,6 +3,11 @@
|
|||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Gilroy:wght@300;400;500;600;700&display=swap" rel="stylesheet">
|
||||
<link rel="stylesheet" href="../src/index.css">
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="theme-color" content="#000000" />
|
||||
<meta
|
||||
|
|
|
@ -203,13 +203,17 @@ const CustomTable: React.FC<CustomTableProps> = ({
|
|||
handleClose();
|
||||
};
|
||||
|
||||
const filteredRows = rows.filter(
|
||||
(row) =>
|
||||
(row.name &&
|
||||
row.name.toLowerCase().includes(searchQuery.toLowerCase())) ||
|
||||
row.registeredAddress.toLowerCase().includes(searchQuery.toLowerCase()) ||
|
||||
false
|
||||
const filteredRows = rows.filter((row) => {
|
||||
if (!searchQuery.trim()) return true; // Return all rows if searchQuery is empty or whitespace
|
||||
const lowerCaseQuery = searchQuery.toLowerCase().trim();
|
||||
return (
|
||||
(row.name && row.name.toLowerCase().includes(lowerCaseQuery)) ||
|
||||
(row.registeredAddress &&
|
||||
row.registeredAddress.toLowerCase().includes(lowerCaseQuery))
|
||||
);
|
||||
});
|
||||
|
||||
|
||||
|
||||
const indexOfLastRow = currentPage * usersPerPage;
|
||||
const indexOfFirstRow = indexOfLastRow - usersPerPage;
|
||||
|
@ -237,7 +241,6 @@ const CustomTable: React.FC<CustomTableProps> = ({
|
|||
color: "#FFFFFF",
|
||||
fontWeight: 500,
|
||||
fontSize: "18px",
|
||||
fontFamily: "Gilroy",
|
||||
}}
|
||||
>
|
||||
{/* Dynamic title based on the page type */}
|
||||
|
@ -408,7 +411,7 @@ const CustomTable: React.FC<CustomTableProps> = ({
|
|||
key={column.id}
|
||||
sx={{
|
||||
color: "#FFFFFF",
|
||||
fontWeight: "bold",
|
||||
fontWeight: "600",
|
||||
}}
|
||||
>
|
||||
{column.label}
|
||||
|
@ -429,7 +432,7 @@ const CustomTable: React.FC<CustomTableProps> = ({
|
|||
<StyledTableCell
|
||||
key={column.id}
|
||||
sx={{
|
||||
color: "#FFFFFF",
|
||||
color: "#D9D8D8",
|
||||
backgroundColor: "#272727",
|
||||
}}
|
||||
>
|
||||
|
|
|
@ -209,9 +209,9 @@ const EditSlotModal: React.FC<EditSlotModalProps> = ({
|
|||
>
|
||||
{isAvailable ? "Available" : "Not Available"}
|
||||
</Button>
|
||||
<Typography>
|
||||
{/* <Typography>
|
||||
{isAvailable ? "Available" : "Not Available"}
|
||||
</Typography>
|
||||
</Typography> */}
|
||||
</Box>
|
||||
</Box>
|
||||
|
||||
|
|
|
@ -116,9 +116,15 @@ const EditStationModal: React.FC<EditStationModalProps> = ({
|
|||
setSelectedVehicles(editRow.allowedCarIds || []);
|
||||
|
||||
// Set selectedBrands based on the vehicles associated with the station
|
||||
const brands = vehicles
|
||||
.filter((vehicle) => editRow.allowedCarIds.includes(vehicle.id))
|
||||
.map((vehicle) => vehicle.company);
|
||||
const brands = editRow?.allowedCarIds
|
||||
? vehicles
|
||||
.filter((vehicle) =>
|
||||
editRow.allowedCarIds.includes(vehicle.id)
|
||||
)
|
||||
.map((vehicle) => vehicle.company)
|
||||
: [];
|
||||
|
||||
|
||||
|
||||
setSelectedBrands(brands);
|
||||
} else {
|
||||
|
|
|
@ -28,14 +28,13 @@ export default function Header() {
|
|||
<Box
|
||||
sx={{
|
||||
width: "100%",
|
||||
// height: "84px",
|
||||
// backgroundColor: "#1C1C1C",
|
||||
height: "84px",
|
||||
backgroundColor: "#1C1C1C",
|
||||
padding: { xs: "20px 12px", sm: "20px 24px" },
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
justifyContent: "space-between",
|
||||
flexDirection: { xs: "column", sm: "row" },
|
||||
// padding:"0px"
|
||||
}}
|
||||
>
|
||||
<Stack
|
||||
|
|
|
@ -6,163 +6,186 @@ import Typography from "@mui/material/Typography";
|
|||
import { LineChart } from "@mui/x-charts/LineChart";
|
||||
import { FormControl, MenuItem, Select } from "@mui/material";
|
||||
import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
|
||||
import useMediaQuery from "@mui/material/useMediaQuery";
|
||||
|
||||
function AreaGradient({ color, id }: { color: string; id: string }) {
|
||||
|
||||
return (
|
||||
<defs>
|
||||
<linearGradient id={id} x1="50%" y1="0%" x2="50%" y2="100%">
|
||||
<stop offset="0%" stopColor={color} stopOpacity={0.5} />
|
||||
<stop offset="100%" stopColor={color} stopOpacity={0} />
|
||||
</linearGradient>
|
||||
</defs>
|
||||
);
|
||||
return (
|
||||
<defs>
|
||||
<linearGradient id={id} x1="50%" y1="0%" x2="50%" y2="100%">
|
||||
<stop offset="0%" stopColor={color} stopOpacity={0.5} />
|
||||
<stop offset="100%" stopColor={color} stopOpacity={0} />
|
||||
</linearGradient>
|
||||
</defs>
|
||||
);
|
||||
}
|
||||
|
||||
function getDaysInMonth(month: number, year: number) {
|
||||
const date = new Date(year, month, 0);
|
||||
const monthName = date.toLocaleDateString("en-US", {
|
||||
month: "short",
|
||||
});
|
||||
const daysInMonth = date.getDate();
|
||||
const days = [];
|
||||
let i = 1;
|
||||
while (days.length < daysInMonth) {
|
||||
days.push(`${monthName} ${i}`);
|
||||
i += 1;
|
||||
}
|
||||
return days;
|
||||
const date = new Date(year, month, 0);
|
||||
const monthName = date.toLocaleDateString("en-US", {
|
||||
month: "short",
|
||||
});
|
||||
const daysInMonth = date.getDate();
|
||||
const days = [];
|
||||
let i = 1;
|
||||
while (days.length < daysInMonth) {
|
||||
days.push(`${monthName} ${i}`);
|
||||
i += 1;
|
||||
}
|
||||
return days;
|
||||
}
|
||||
|
||||
export default function LineChartCard() {
|
||||
const theme = useTheme();
|
||||
const data = getDaysInMonth(4, 2024);
|
||||
const theme = useTheme();
|
||||
const isXsScreen = useMediaQuery(theme.breakpoints.down("sm"));
|
||||
const isSmScreen = useMediaQuery(theme.breakpoints.between("sm", "md"));
|
||||
|
||||
const data = getDaysInMonth(4, 2024);
|
||||
const colorPalette = [theme.palette.primary.main];
|
||||
const [selectedOption, setSelectedOption] = React.useState("Weekly");
|
||||
|
||||
const colorPalette = [theme.palette.primary.light];
|
||||
const [selectedOption, setSelectedOption] = React.useState("Weekly");
|
||||
|
||||
const handleChange = (event: { target: { value: React.SetStateAction<string>; }; }) => {
|
||||
setSelectedOption(event.target.value);
|
||||
};
|
||||
|
||||
const handleChange = (event: { target: { value: React.SetStateAction<string> } }) => {
|
||||
setSelectedOption(event.target.value);
|
||||
};
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "553px",
|
||||
height: "444px",
|
||||
borderRadius: "16px",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent>
|
||||
<div
|
||||
style={{
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
color: "#F2F2F2",
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
variant="h6"
|
||||
align="left"
|
||||
color="#F2F2F2"
|
||||
sx={{
|
||||
fontFamily: "Gilroy",
|
||||
fontWeight: 500,
|
||||
fontSize: "18px",
|
||||
lineHeight: "24px",
|
||||
}}
|
||||
>
|
||||
Sales Stats
|
||||
</Typography>
|
||||
<FormControl
|
||||
sx={{
|
||||
mt: 2,
|
||||
mb: 2,
|
||||
backgroundColor: "#202020",
|
||||
marginLeft: "auto",
|
||||
marginRight: "16px",
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
// p: 1.5,
|
||||
color: "#F2F2F2",
|
||||
width: "149px",
|
||||
height: "44px",
|
||||
padding: "12px 16px",
|
||||
gap: "8px",
|
||||
}}
|
||||
>
|
||||
<Select
|
||||
value={selectedOption}
|
||||
onChange={handleChange}
|
||||
sx={{
|
||||
//backgroundColor: "#202020",
|
||||
color: "#D9D8D8",
|
||||
".MuiSelect-icon": {
|
||||
color: "#F2F2F2", // Icon color
|
||||
},
|
||||
}}
|
||||
IconComponent={ExpandMoreIcon}
|
||||
>
|
||||
<MenuItem value="Monthly">Monthly</MenuItem>
|
||||
<MenuItem value="Weekly">Weekly</MenuItem>
|
||||
<MenuItem value="Daily">Daily</MenuItem>
|
||||
<MenuItem value="Yearly">Yearly</MenuItem>
|
||||
</Select>
|
||||
</FormControl>
|
||||
</div>
|
||||
// Calculate responsive dimensions
|
||||
const getChartHeight = () => {
|
||||
if (isXsScreen) return 200;
|
||||
if (isSmScreen) return 220;
|
||||
return 250;
|
||||
};
|
||||
|
||||
<LineChart
|
||||
colors={colorPalette}
|
||||
xAxis={[
|
||||
{
|
||||
scaleType: "point",
|
||||
data,
|
||||
tickInterval: (index, i) => (i + 1) % 5 === 0,
|
||||
},
|
||||
]}
|
||||
series={[
|
||||
{
|
||||
id: "direct",
|
||||
label: "Direct",
|
||||
showMark: false,
|
||||
curve: "linear",
|
||||
stack: "total",
|
||||
area: true,
|
||||
stackOrder: "ascending",
|
||||
data: [
|
||||
300, 900, 500, 1200, 1500, 1800, 2400, 2100,
|
||||
2700, 3000, 1800, 3300, 3600, 3900, 4200, 4500,
|
||||
3900, 4800, 5100, 5400, 4500, 5700, 6000, 6300,
|
||||
6600, 6900, 7200, 7500, 7800, 8100,
|
||||
],
|
||||
color: "#FFFFFF",
|
||||
},
|
||||
]}
|
||||
height={250}
|
||||
margin={{ left: 50, right: 20, top: 20, bottom: 20 }}
|
||||
grid={{ horizontal: true }}
|
||||
sx={{
|
||||
"& .MuiAreaElement-series-direct": {
|
||||
fill: "url('#direct')",
|
||||
},
|
||||
}}
|
||||
slotProps={{
|
||||
legend: {
|
||||
hidden: true,
|
||||
},
|
||||
}}
|
||||
>
|
||||
<AreaGradient
|
||||
color={theme.palette.primary.light}
|
||||
id="direct"
|
||||
/>
|
||||
</LineChart>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
const getChartMargin = () => {
|
||||
if (isXsScreen) return { left: 35, right: 10, top: 15, bottom: 15 };
|
||||
if (isSmScreen) return { left: 40, right: 15, top: 18, bottom: 18 };
|
||||
return { left: 50, right: 20, top: 20, bottom: 20 };
|
||||
};
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "100%",
|
||||
height: "auto",
|
||||
minHeight: { xs: "360px", sm: "400px", md: "444px" },
|
||||
borderRadius: "16px",
|
||||
border: "none",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent sx={{ padding: { xs: 2, md: 3 }, "&:last-child": { paddingBottom: { xs: 2, md: 3 } } }}>
|
||||
<div
|
||||
style={{
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
flexDirection: isXsScreen ? "column" : "row",
|
||||
color: "#F2F2F2",
|
||||
marginBottom: isXsScreen ? 16 : 0,
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
variant="h6"
|
||||
align={isXsScreen ? "center" : "left"}
|
||||
color="#F2F2F2"
|
||||
sx={{
|
||||
fontWeight: 500,
|
||||
fontSize: { xs: "16px", sm: "17px", md: "18px" },
|
||||
lineHeight: "24px",
|
||||
marginBottom: isXsScreen ? 2 : 0,
|
||||
width: isXsScreen ? "100%" : "auto",
|
||||
}}
|
||||
>
|
||||
Sales Stats
|
||||
</Typography>
|
||||
<FormControl
|
||||
sx={{
|
||||
mt: isXsScreen ? 0 : 2,
|
||||
mb: isXsScreen ? 0 : 2,
|
||||
backgroundColor: "#202020",
|
||||
marginLeft: isXsScreen ? 0 : "auto",
|
||||
marginRight: isXsScreen ? 0 : "16px",
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
color: "#F2F2F2",
|
||||
width: { xs: "100%", sm: "140px", md: "149px" },
|
||||
height: { xs: "40px", md: "44px" },
|
||||
padding: { xs: "8px 12px", md: "12px 16px" },
|
||||
gap: "8px",
|
||||
}}
|
||||
>
|
||||
<Select
|
||||
value={selectedOption}
|
||||
onChange={handleChange}
|
||||
sx={{
|
||||
fontSize: { xs: "14px", md: "16px" },
|
||||
color: "#D9D8D8",
|
||||
".MuiSelect-icon": {
|
||||
color: "#F2F2F2",
|
||||
},
|
||||
}}
|
||||
IconComponent={ExpandMoreIcon}
|
||||
>
|
||||
<MenuItem value="Monthly">Monthly</MenuItem>
|
||||
<MenuItem value="Weekly">Weekly</MenuItem>
|
||||
<MenuItem value="Daily">Daily</MenuItem>
|
||||
<MenuItem value="Yearly">Yearly</MenuItem>
|
||||
</Select>
|
||||
</FormControl>
|
||||
</div>
|
||||
|
||||
<LineChart
|
||||
colors={colorPalette}
|
||||
xAxis={[
|
||||
{
|
||||
scaleType: "point",
|
||||
data,
|
||||
tickInterval: (index, i) => isXsScreen
|
||||
? (i + 1) % 10 === 0
|
||||
: isSmScreen
|
||||
? (i + 1) % 7 === 0
|
||||
: (i + 1) % 5 === 0,
|
||||
},
|
||||
]}
|
||||
series={[
|
||||
{
|
||||
id: "direct",
|
||||
label: "Direct",
|
||||
showMark: false,
|
||||
curve: "linear",
|
||||
stack: "total",
|
||||
area: true,
|
||||
stackOrder: "ascending",
|
||||
data: [
|
||||
300, 900, 500, 1200, 1500, 1800, 2400, 2100,
|
||||
2700, 3000, 1800, 3300, 3600, 3900, 4200, 4500,
|
||||
3900, 4800, 5100, 5400, 4500, 5700, 6000, 6300,
|
||||
6600, 6900, 7200, 7500, 7800, 8100,
|
||||
],
|
||||
color: "#28ACFF",
|
||||
},
|
||||
]}
|
||||
height={getChartHeight()}
|
||||
margin={getChartMargin()}
|
||||
grid={{ horizontal: true }}
|
||||
sx={{
|
||||
"& .MuiAreaElement-series-direct": {
|
||||
fill: "url('#direct')",
|
||||
},
|
||||
}}
|
||||
slotProps={{
|
||||
legend: {
|
||||
hidden: true,
|
||||
},
|
||||
}}
|
||||
>
|
||||
<AreaGradient
|
||||
color={theme.palette.primary.main}
|
||||
id="direct"
|
||||
/>
|
||||
</LineChart>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
|
@ -1,5 +1,4 @@
|
|||
|
||||
import Grid from "@mui/material/Grid2";
|
||||
import Grid from "@mui/material/Grid";
|
||||
import Box from "@mui/material/Box";
|
||||
import Typography from "@mui/material/Typography";
|
||||
import SessionsChart from "../SessionsChart/sessionChart";
|
||||
|
@ -9,57 +8,43 @@ import RoundedBarChart from "../barChartCard/barChartCard";
|
|||
import LineChartCard from "../LineChartCard/lineChartCard";
|
||||
|
||||
const data: StatCardProps[] = [
|
||||
{
|
||||
title: "Total Charge Stations",
|
||||
value: "86",
|
||||
},
|
||||
{
|
||||
title: "Charging Completed",
|
||||
value: "12",
|
||||
},
|
||||
{
|
||||
title: "Active Users",
|
||||
value: "24",
|
||||
},
|
||||
{
|
||||
title: "Total Energy Consumed",
|
||||
value: "08",
|
||||
},
|
||||
{ title: "Total Charge Stations", value: "86" },
|
||||
{ title: "Charging Completed", value: "12" },
|
||||
{ title: "Active Users", value: "24" },
|
||||
{ title: "Total Energy Consumed", value: "08" },
|
||||
];
|
||||
|
||||
export default function MainGrid() {
|
||||
return (
|
||||
<Box sx={{ width: "100%", maxWidth: { sm: "100%", md: "1700px" } }}>
|
||||
{/* cards */}
|
||||
<Typography component="h2" variant="h6" sx={{ mb: 2 }}>
|
||||
Dashboard
|
||||
</Typography>
|
||||
<Grid
|
||||
container
|
||||
spacing={3}
|
||||
columns={12}
|
||||
|
||||
// sx={{ mb: (theme) => theme.spacing(2) }}
|
||||
>
|
||||
{data.map((card, index) => (
|
||||
<Grid key={index} size={{ xs: 12, sm: 6, lg: 3 }}>
|
||||
<StatCard {...card} />
|
||||
</Grid>
|
||||
))}
|
||||
return (
|
||||
<Box sx={{ width: "100%", maxWidth: "1600px", mx: "auto", px: { xs: 2, sm: 1, md: 0 } }}>
|
||||
{/* Dashboard Header */}
|
||||
<Typography component="h2" variant="h6" sx={{ mb: 2 }}>
|
||||
Dashboard
|
||||
</Typography>
|
||||
|
||||
<Grid size={{ xs: 12, md: 6 }}>
|
||||
<SessionsChart />
|
||||
</Grid>
|
||||
<Grid size={{ xs: 12, md: 6 }}>
|
||||
<ResourcesPieChart />
|
||||
</Grid>
|
||||
<Grid size={{ xs: 12, md: 6 }}>
|
||||
<RoundedBarChart />
|
||||
</Grid>
|
||||
<Grid size={{ xs: 12, md: 6 }}>
|
||||
<LineChartCard />
|
||||
</Grid>
|
||||
</Grid>
|
||||
</Box>
|
||||
);
|
||||
{/* Grid Layout */}
|
||||
<Grid container spacing={3} columns={12}>
|
||||
{/* Statistic Cards */}
|
||||
{data.map((card, index) => (
|
||||
<Grid key={index} item xs={12} sm={6} md={3} lg={3}>
|
||||
<StatCard {...card} />
|
||||
</Grid>
|
||||
))}
|
||||
|
||||
{/* Charts */}
|
||||
<Grid item xs={12} sm={12} md={6} lg={6}>
|
||||
<SessionsChart />
|
||||
</Grid>
|
||||
<Grid item xs={12} sm={12} md={6} lg={6}>
|
||||
<ResourcesPieChart />
|
||||
</Grid>
|
||||
<Grid item xs={12} sm={12} md={6} lg={6}>
|
||||
<RoundedBarChart />
|
||||
</Grid>
|
||||
<Grid item xs={12} sm={12} md={6} lg={6}>
|
||||
<LineChartCard />
|
||||
</Grid>
|
||||
</Grid>
|
||||
</Box>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -35,6 +35,16 @@ export default function MenuContent({ hidden }: PropType) {
|
|||
icon: <ManageAccountsOutlinedIcon />,
|
||||
url: "/panel/admin-list",
|
||||
},
|
||||
userRole === "superadmin" && {
|
||||
text: "Managers",
|
||||
icon: <PeopleOutlinedIcon />,
|
||||
url: "/panel/manager-list",
|
||||
},
|
||||
userRole === "superadmin" && {
|
||||
text: "User",
|
||||
icon: <PeopleOutlinedIcon />,
|
||||
url: "/panel/user-list",
|
||||
},
|
||||
userRole === "superadmin" && {
|
||||
text: "Roles",
|
||||
icon: <AnalyticsOutlinedIcon />,
|
||||
|
|
|
@ -4,111 +4,160 @@ import Card from "@mui/material/Card";
|
|||
import CardContent from "@mui/material/CardContent";
|
||||
import Box from "@mui/material/Box";
|
||||
import Stack from "@mui/material/Stack";
|
||||
import { useTheme } from "@mui/material/styles";
|
||||
import useMediaQuery from "@mui/material/useMediaQuery";
|
||||
|
||||
const colorPalette = [
|
||||
"hsla(202, 69%, 60%, 1)",
|
||||
"hsl(204, 48.60%, 72.50%)",
|
||||
"hsl(214, 56.40%, 30.60%)",
|
||||
"hsl(222, 6.80%, 50.80%)",
|
||||
"hsla(202, 69%, 60%, 1)",
|
||||
"hsl(204, 48.60%, 72.50%)",
|
||||
"hsl(214, 56.40%, 30.60%)",
|
||||
"hsl(222, 6.80%, 50.80%)",
|
||||
];
|
||||
|
||||
const data = [
|
||||
{ title: "Total Resources", value: 50, color: colorPalette[0] },
|
||||
{ title: "Total Stations", value: 20, color: colorPalette[1] },
|
||||
{ title: "Station Manager", value: 15, color: colorPalette[2] },
|
||||
{ title: "Total Booth", value: 15, color: colorPalette[3] },
|
||||
{ title: "Total Resources", value: 50, color: colorPalette[0] },
|
||||
{ title: "Total Stations", value: 20, color: colorPalette[1] },
|
||||
{ title: "Station Manager", value: 15, color: colorPalette[2] },
|
||||
{ title: "Total Booth", value: 15, color: colorPalette[3] },
|
||||
];
|
||||
|
||||
export default function ResourcePieChart() {
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
gap: "12px",
|
||||
flexGrow: 1,
|
||||
width: "553px",
|
||||
height: "324px",
|
||||
padding: "16px",
|
||||
borderRadius: "16px",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent>
|
||||
<Typography
|
||||
component="h2"
|
||||
variant="subtitle2"
|
||||
color="#F2F2F2"
|
||||
width="84px"
|
||||
height="24px"
|
||||
sx={{
|
||||
fontWeight: 500,
|
||||
fontSize: "18px",
|
||||
lineHeight: "24px",
|
||||
color: "#FFFFFF",
|
||||
}}
|
||||
>
|
||||
Resources
|
||||
</Typography>
|
||||
<Box sx={{ display: "flex", alignItems: "center" }}>
|
||||
<PieChart
|
||||
colors={colorPalette}
|
||||
margin={{
|
||||
left: 60,
|
||||
right: 80,
|
||||
top: 80,
|
||||
bottom: 80,
|
||||
}}
|
||||
series={[
|
||||
{
|
||||
data,
|
||||
innerRadius: 50,
|
||||
outerRadius: 100,
|
||||
paddingAngle: 0,
|
||||
highlightScope: {
|
||||
faded: "global",
|
||||
highlighted: "item",
|
||||
},
|
||||
},
|
||||
]}
|
||||
height={300}
|
||||
width={300}
|
||||
slotProps={{
|
||||
legend: { hidden: true },
|
||||
}}
|
||||
></PieChart>
|
||||
const theme = useTheme();
|
||||
const isXsScreen = useMediaQuery(theme.breakpoints.down("sm"));
|
||||
const isSmScreen = useMediaQuery(theme.breakpoints.between("sm", "md"));
|
||||
|
||||
|
||||
<Stack spacing={1}>
|
||||
{data.map((entry, index) => (
|
||||
<Stack
|
||||
key={index}
|
||||
direction="row"
|
||||
spacing={1}
|
||||
alignItems="center"
|
||||
>
|
||||
<Box
|
||||
sx={{
|
||||
width: 16,
|
||||
height: 16,
|
||||
backgroundColor: entry.color,
|
||||
borderRadius: "50%",
|
||||
}}
|
||||
/>
|
||||
<Typography
|
||||
variant="body2"
|
||||
width="100px"
|
||||
height="16px"
|
||||
color="#FFFFFF"
|
||||
>
|
||||
{entry.title}
|
||||
</Typography>
|
||||
</Stack>
|
||||
))}
|
||||
</Stack>
|
||||
</Box>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
const getChartDimensions = () => {
|
||||
if (isXsScreen) {
|
||||
return {
|
||||
height: 240,
|
||||
width: 240,
|
||||
innerRadius: 40,
|
||||
outerRadius: 80,
|
||||
margin: { left: 20, right: 20, top: 40, bottom: 40 }
|
||||
};
|
||||
} else if (isSmScreen) {
|
||||
return {
|
||||
height: 260,
|
||||
width: 260,
|
||||
innerRadius: 50,
|
||||
outerRadius: 90,
|
||||
margin: { left: 40, right: 40, top: 60, bottom: 60 }
|
||||
};
|
||||
} else {
|
||||
return {
|
||||
height: 350,
|
||||
width: 350,
|
||||
innerRadius: 55,
|
||||
outerRadius: 110,
|
||||
margin: { left: 60, right: 80, top: 80, bottom: 80 }
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
const dimensions = getChartDimensions();
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
gap: { xs: "8px", sm: "10px", md: "12px" },
|
||||
flexGrow: 1,
|
||||
width: "100%",
|
||||
height: "auto",
|
||||
minHeight: { xs: "320px", sm: "340px", md: "360px" },
|
||||
padding: { xs: "12px", sm: "14px", md: "16px" },
|
||||
borderRadius: "16px",
|
||||
border: "none",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent sx={{ padding: 0, "&:last-child": { paddingBottom: 0 } }}>
|
||||
<Typography
|
||||
component="h2"
|
||||
variant="subtitle2"
|
||||
color="#F2F2F2"
|
||||
sx={{
|
||||
fontWeight: 500,
|
||||
fontSize: { xs: "16px", sm: "17px", md: "18px" },
|
||||
lineHeight: "24px",
|
||||
color: "#FFFFFF",
|
||||
marginBottom: { xs: 1, sm: 1.5, md: 2 },
|
||||
}}
|
||||
>
|
||||
Resources
|
||||
</Typography>
|
||||
<Box
|
||||
sx={{
|
||||
display: "flex",
|
||||
flexDirection: { xs: "column", sm: "row" },
|
||||
alignItems: "center",
|
||||
justifyContent: "center"
|
||||
}}
|
||||
>
|
||||
<PieChart
|
||||
colors={colorPalette}
|
||||
margin={dimensions.margin}
|
||||
series={[
|
||||
{
|
||||
data,
|
||||
innerRadius: dimensions.innerRadius,
|
||||
outerRadius: dimensions.outerRadius,
|
||||
paddingAngle: 2,
|
||||
cornerRadius: 8,
|
||||
highlightScope: {
|
||||
faded: "global",
|
||||
highlighted: "item",
|
||||
},
|
||||
},
|
||||
]}
|
||||
height={dimensions.height}
|
||||
width={dimensions.width}
|
||||
slotProps={{
|
||||
legend: { hidden: true },
|
||||
}}
|
||||
/>
|
||||
|
||||
<Stack
|
||||
spacing={1}
|
||||
sx={{
|
||||
mt: { xs: 2, sm: 0 },
|
||||
ml: { xs: 0, sm: 2 }
|
||||
}}
|
||||
>
|
||||
{data.map((entry, index) => (
|
||||
<Stack
|
||||
key={index}
|
||||
direction="row"
|
||||
spacing={1}
|
||||
alignItems="center"
|
||||
>
|
||||
<Box
|
||||
sx={{
|
||||
width: { xs: 12, sm: 14, md: 16 },
|
||||
height: { xs: 12, sm: 14, md: 16 },
|
||||
backgroundColor: entry.color,
|
||||
borderRadius: "50%",
|
||||
}}
|
||||
/>
|
||||
<Typography
|
||||
variant="body2"
|
||||
sx={{
|
||||
fontSize: { xs: "12px", sm: "13px", md: "14px" },
|
||||
color: "#FFFFFF",
|
||||
}}
|
||||
>
|
||||
{entry.title}
|
||||
</Typography>
|
||||
</Stack>
|
||||
))}
|
||||
</Stack>
|
||||
</Box>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
|
@ -6,156 +6,146 @@ import Box from "@mui/material/Box";
|
|||
import Select from "@mui/material/Select";
|
||||
import MenuItem from "@mui/material/MenuItem";
|
||||
import FormControl from "@mui/material/FormControl";
|
||||
import InputLabel from "@mui/material/InputLabel";
|
||||
import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
|
||||
import { useTheme } from "@mui/material/styles";
|
||||
|
||||
export default function SessionsChart() {
|
||||
const [selectedStation, setSelectedStation] = React.useState(
|
||||
"Delhi NCR EV Station"
|
||||
);
|
||||
const theme = useTheme();
|
||||
const [selectedStation, setSelectedStation] = React.useState(
|
||||
"Delhi NCR EV Station"
|
||||
);
|
||||
|
||||
const handleChange = (event: { target: { value: React.SetStateAction<string>; }; }) => {
|
||||
setSelectedStation(event.target.value);
|
||||
};
|
||||
const handleChange = (event: { target: { value: React.SetStateAction<string> } }) => {
|
||||
setSelectedStation(event.target.value);
|
||||
};
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "553px",
|
||||
height: "324px",
|
||||
gap: "16px",
|
||||
borderRadius: "16px",
|
||||
padding: "20px",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent>
|
||||
<Typography
|
||||
variant="h6"
|
||||
align="left"
|
||||
color="#F2F2F2"
|
||||
width="132px"
|
||||
height="24px"
|
||||
gap={"12px"}
|
||||
sx={{
|
||||
fontFamily: "Gilroy",
|
||||
fontWeight: 500,
|
||||
fontSize: "18px",
|
||||
lineHeight: "24px",
|
||||
letterSpacing: "0%",
|
||||
color: "#FAFAFA",
|
||||
}}
|
||||
>
|
||||
Charging prices
|
||||
</Typography>
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "100%",
|
||||
height: "auto",
|
||||
minHeight: { xs: "260px", sm: "270px", md: "290px" },
|
||||
gap: "16px",
|
||||
borderRadius: "16px",
|
||||
padding: { xs: "12px", sm: "16px", md: "20px" },
|
||||
border: "none",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent sx={{ padding: 0, "&:last-child": { paddingBottom: 0 } }}>
|
||||
<Typography
|
||||
variant="h6"
|
||||
align="left"
|
||||
color="#F2F2F2"
|
||||
sx={{
|
||||
fontWeight: 500,
|
||||
fontSize: { xs: "16px", sm: "17px", md: "18px" },
|
||||
lineHeight: "24px",
|
||||
letterSpacing: "0%",
|
||||
color: "#FAFAFA",
|
||||
marginBottom: { xs: 1, sm: 1.5, md: 2 },
|
||||
}}
|
||||
>
|
||||
Charging prices
|
||||
</Typography>
|
||||
|
||||
{/* Dropdown button */}
|
||||
<FormControl
|
||||
sx={{
|
||||
mt: 2,
|
||||
mb: 2,
|
||||
width: "100%",
|
||||
// backgroundColor: "#202020",
|
||||
border: "1px solid #454545",
|
||||
borderRadius: "8px",
|
||||
}}
|
||||
>
|
||||
|
||||
<Select
|
||||
value={selectedStation}
|
||||
onChange={handleChange}
|
||||
label="Select Station"
|
||||
sx={{
|
||||
//backgroundColor: "#202020",
|
||||
color: "#D9D8D8",
|
||||
"& .MuiSvgIcon-root": { color: "#F2F2F2" },
|
||||
}}
|
||||
IconComponent={ExpandMoreIcon}
|
||||
>
|
||||
<MenuItem value="Delhi NCR EV Station">
|
||||
Delhi NCR EV Station
|
||||
</MenuItem>
|
||||
<MenuItem value="Mumbai EV Station">
|
||||
Mumbai EV Station
|
||||
</MenuItem>
|
||||
<MenuItem value="Bangalore EV Station">
|
||||
Bangalore EV Station
|
||||
</MenuItem>
|
||||
<MenuItem value="Pune EV Station">
|
||||
Pune EV Station
|
||||
</MenuItem>
|
||||
</Select>
|
||||
</FormControl>
|
||||
{/* Dropdown button */}
|
||||
<FormControl
|
||||
sx={{
|
||||
mt: { xs: 1, sm: 1.5, md: 2 },
|
||||
mb: { xs: 1, sm: 1.5, md: 2 },
|
||||
width: "100%",
|
||||
border: "none",
|
||||
borderRadius: "8px",
|
||||
}}
|
||||
>
|
||||
<Select
|
||||
value={selectedStation}
|
||||
onChange={handleChange}
|
||||
label="Select Station"
|
||||
sx={{
|
||||
color: "#D9D8D8",
|
||||
"& .MuiSvgIcon-root": { color: "#F2F2F2" },
|
||||
fontSize: { xs: "14px", md: "16px" },
|
||||
}}
|
||||
IconComponent={ExpandMoreIcon}
|
||||
>
|
||||
<MenuItem value="Delhi NCR EV Station">Delhi NCR EV Station</MenuItem>
|
||||
<MenuItem value="Mumbai EV Station">Mumbai EV Station</MenuItem>
|
||||
<MenuItem value="Bangalore EV Station">Bangalore EV Station</MenuItem>
|
||||
<MenuItem value="Pune EV Station">Pune EV Station</MenuItem>
|
||||
</Select>
|
||||
</FormControl>
|
||||
|
||||
{/* Grid container for the four boxes */}
|
||||
<Box
|
||||
sx={{
|
||||
display: "grid",
|
||||
gridTemplateColumns: {
|
||||
xs: "1fr",
|
||||
sm: "repeat(2, 1fr)",
|
||||
},
|
||||
gap: { xs: 1, sm: 2 },
|
||||
maxWidth: "750px",
|
||||
width: "100%",
|
||||
mx: "auto",
|
||||
}}
|
||||
>
|
||||
{[1, 2, 3, 4].map((item) => (
|
||||
<Box
|
||||
key={item}
|
||||
sx={{
|
||||
height: "84px",
|
||||
borderRadius: "8px",
|
||||
p: "12px 16px",
|
||||
backgroundColor: "#272727",
|
||||
color: "#D9D8D8",
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
component="h1"
|
||||
variant="body2"
|
||||
width="98px"
|
||||
height="24px"
|
||||
fontWeight={400}
|
||||
fontSize={"14px"}
|
||||
lineHeight={"24px"}
|
||||
gutterBottom
|
||||
>
|
||||
Basic Charging
|
||||
</Typography>
|
||||
<Box display={"flex"} gap={1}>
|
||||
<Typography
|
||||
component="h1"
|
||||
variant="subtitle2"
|
||||
color="#FFFFFF"
|
||||
width="40px"
|
||||
height={"24px"}
|
||||
fontWeight={500}
|
||||
fontSize="18px"
|
||||
lineHeight="24px"
|
||||
gutterBottom
|
||||
>
|
||||
16.83
|
||||
</Typography>
|
||||
|
||||
<Typography
|
||||
width="71px"
|
||||
height="24px"
|
||||
gap="2px"
|
||||
fontWeight={400}
|
||||
fontSize={"14px"}
|
||||
lineHeight={"24px"}
|
||||
>
|
||||
cents/kWh
|
||||
</Typography>
|
||||
</Box>
|
||||
</Box>
|
||||
))}
|
||||
</Box>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
{/* Grid container for the four boxes */}
|
||||
<Box
|
||||
sx={{
|
||||
display: "grid",
|
||||
gridTemplateColumns: {
|
||||
xs: "repeat(1, 1fr)", // 1 column on mobile
|
||||
sm: "repeat(2, 1fr)", // 2 columns on tablets
|
||||
md: "repeat(2, 1fr)", // 2x2 grid on desktop
|
||||
},
|
||||
gap: { xs: 1, sm: 1.5, md: 2 },
|
||||
width: "100%",
|
||||
}}
|
||||
>
|
||||
{[1, 2, 3, 4].map((item) => (
|
||||
<Box
|
||||
key={item}
|
||||
sx={{
|
||||
height: { xs: "105px", sm: "115px", md: "128px" },
|
||||
borderRadius: "8px",
|
||||
p: { xs: "10px", sm: "12px", md: "14px" },
|
||||
backgroundColor: "#272727",
|
||||
color: "#D9D8D8",
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
justifyContent: "center",
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
variant="body2"
|
||||
sx={{
|
||||
fontWeight: 400,
|
||||
fontSize: { xs: "12px", sm: "13px", md: "14px" },
|
||||
lineHeight: { xs: "20px", md: "24px" },
|
||||
marginBottom: "4px",
|
||||
}}
|
||||
gutterBottom
|
||||
>
|
||||
Basic Charging
|
||||
</Typography>
|
||||
<Box display="flex" gap={1} alignItems="center">
|
||||
<Typography
|
||||
variant="subtitle2"
|
||||
color="#FFFFFF"
|
||||
sx={{
|
||||
fontWeight: 500,
|
||||
fontSize: { xs: "16px", sm: "17px", md: "18px" },
|
||||
lineHeight: { xs: "20px", md: "24px" },
|
||||
}}
|
||||
gutterBottom
|
||||
>
|
||||
16.83
|
||||
</Typography>
|
||||
<Typography
|
||||
sx={{
|
||||
fontWeight: 400,
|
||||
fontSize: { xs: "12px", sm: "13px", md: "14px" },
|
||||
lineHeight: { xs: "20px", md: "24px" },
|
||||
}}
|
||||
>
|
||||
cents/kWh
|
||||
</Typography>
|
||||
</Box>
|
||||
</Box>
|
||||
))}
|
||||
</Box>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,59 +1,106 @@
|
|||
|
||||
import Card from "@mui/material/Card";
|
||||
import CardContent from "@mui/material/CardContent";
|
||||
import Typography from "@mui/material/Typography";
|
||||
|
||||
import { useTheme } from "@mui/material/styles";
|
||||
import useMediaQuery from "@mui/material/useMediaQuery";
|
||||
|
||||
export type StatCardProps = {
|
||||
title: string;
|
||||
value: string;
|
||||
title: string;
|
||||
value: string;
|
||||
};
|
||||
|
||||
export default function StatCard({ title, value }: StatCardProps) {
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "264.5px",
|
||||
height: "90px",
|
||||
padding: "16px",
|
||||
borderRadius: "12px",
|
||||
gap: "24px",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent>
|
||||
<Typography
|
||||
component="h2"
|
||||
variant="subtitle2"
|
||||
color="#F2F2F2"
|
||||
width={"118px"}
|
||||
height={"14px"}
|
||||
fontWeight={400}
|
||||
fontSize={"12px"}
|
||||
lineHeight={"14px"}
|
||||
letterSpacing={"0%"}
|
||||
gutterBottom
|
||||
>
|
||||
{title}
|
||||
</Typography>
|
||||
<Typography
|
||||
component="h1"
|
||||
variant="body1"
|
||||
color="#F2F2F2"
|
||||
width={"36px"}
|
||||
height={"36px"}
|
||||
fontSize={"32px"}
|
||||
fontWeight={600}
|
||||
lineHeight={"36px"}
|
||||
letterSpacing={"0%"}
|
||||
gutterBottom
|
||||
>
|
||||
{value}
|
||||
</Typography>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
const theme = useTheme();
|
||||
const isXsScreen = useMediaQuery(theme.breakpoints.only("xs"));
|
||||
const isSmScreen = useMediaQuery(theme.breakpoints.only("sm"));
|
||||
const isMdScreen = useMediaQuery(theme.breakpoints.only("md"));
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "100%",
|
||||
height: "100px",
|
||||
padding: {
|
||||
xs: "12px",
|
||||
sm: "14px",
|
||||
md: "10px"
|
||||
},
|
||||
borderRadius: "12px",
|
||||
border: "none",
|
||||
gap: "24px",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent
|
||||
sx={{
|
||||
padding: {
|
||||
xs: "8px",
|
||||
sm: "12px",
|
||||
md: "16px"
|
||||
},
|
||||
"&:last-child": {
|
||||
paddingBottom: {
|
||||
xs: "8px",
|
||||
sm: "12px",
|
||||
md: "16px"
|
||||
}
|
||||
}
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
component="h2"
|
||||
variant="subtitle2"
|
||||
color="#F2F2F2"
|
||||
sx={{
|
||||
fontWeight: 400,
|
||||
fontSize: {
|
||||
xs: "10px",
|
||||
sm: "11px",
|
||||
md: "12px"
|
||||
},
|
||||
lineHeight: {
|
||||
xs: "12px",
|
||||
sm: "13px",
|
||||
md: "14px"
|
||||
},
|
||||
letterSpacing: "0%",
|
||||
width: "auto",
|
||||
height: "auto",
|
||||
marginBottom: { xs: "6px", sm: "8px", md: "10px" }, // Added more spacing
|
||||
|
||||
}}
|
||||
gutterBottom
|
||||
>
|
||||
{title}
|
||||
</Typography>
|
||||
<Typography
|
||||
component="h1"
|
||||
variant="body1"
|
||||
color="#D9D8D8"
|
||||
sx={{
|
||||
fontWeight: 600,
|
||||
fontSize: {
|
||||
xs: "24px",
|
||||
sm: "28px",
|
||||
md: "32px"
|
||||
},
|
||||
lineHeight: {
|
||||
xs: "28px",
|
||||
sm: "32px",
|
||||
md: "36px"
|
||||
},
|
||||
letterSpacing: "0%",
|
||||
width: "auto",
|
||||
height: "auto",
|
||||
}}
|
||||
gutterBottom
|
||||
>
|
||||
{value}
|
||||
</Typography>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
|
@ -13,6 +13,7 @@ import {
|
|||
import { BarChart } from "@mui/x-charts/BarChart";
|
||||
import { axisClasses } from "@mui/x-charts/ChartsAxis";
|
||||
import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
|
||||
import useMediaQuery from "@mui/material/useMediaQuery";
|
||||
|
||||
// Sample Data
|
||||
const data = [
|
||||
|
@ -24,59 +25,100 @@ const data = [
|
|||
{ name: "Jun", v1: 30 },
|
||||
];
|
||||
|
||||
// Chart Configuration
|
||||
const chartSetting = {
|
||||
yAxis: [
|
||||
{
|
||||
label: "Value",
|
||||
tickFormatter: (value: number) => `${value}`, // Formatting Y-axis ticks
|
||||
},
|
||||
],
|
||||
xAxis: [
|
||||
{
|
||||
dataKey: "name",
|
||||
scaleType: "band" as const,
|
||||
},
|
||||
],
|
||||
width: 500,
|
||||
height: 300,
|
||||
sx: {
|
||||
[`.${axisClasses.left} .${axisClasses.label}`]: {
|
||||
transform: "translate(-20px, 0)",
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export default function RoundedBarChart() {
|
||||
const theme = useTheme();
|
||||
const isXsScreen = useMediaQuery(theme.breakpoints.down("sm"));
|
||||
const isSmScreen = useMediaQuery(theme.breakpoints.between("sm", "md"));
|
||||
const [selectedOption, setSelectedOption] = React.useState("Monthly");
|
||||
|
||||
const handleChange = (event: SelectChangeEvent<string>) => {
|
||||
setSelectedOption(event.target.value);
|
||||
const handleChange = (event: SelectChangeEvent<string>) => {
|
||||
setSelectedOption(event.target.value);
|
||||
};
|
||||
|
||||
// Responsive chart settings
|
||||
const getChartSettings = () => {
|
||||
const baseSettings = {
|
||||
|
||||
yAxis: [
|
||||
{
|
||||
label: isXsScreen ? "" : "Value",
|
||||
tickFormatter: (value: number) => `${value}`,
|
||||
},
|
||||
],
|
||||
xAxis: [
|
||||
{
|
||||
dataKey: "name",
|
||||
scaleType: "band" as const,
|
||||
},
|
||||
],
|
||||
sx: {
|
||||
[`.${axisClasses.left} .${axisClasses.label}`]: {
|
||||
transform: "translate(-10px, 0)",
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
// Screen-specific settings
|
||||
if (isXsScreen) {
|
||||
return {
|
||||
...baseSettings,
|
||||
width: 280,
|
||||
height: 220,
|
||||
};
|
||||
} else if (isSmScreen) {
|
||||
return {
|
||||
...baseSettings,
|
||||
width: 380,
|
||||
height: 260,
|
||||
};
|
||||
} else {
|
||||
return {
|
||||
...baseSettings,
|
||||
width: 500,
|
||||
height: 280,
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
const chartSetting = getChartSettings();
|
||||
|
||||
return (
|
||||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: "553px",
|
||||
height: "444px",
|
||||
width: "100%",
|
||||
height: "auto",
|
||||
minHeight: { xs: "360px", sm: "400px", md: "444px" },
|
||||
borderRadius: "16px",
|
||||
border: "none",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#202020",
|
||||
},
|
||||
}}
|
||||
>
|
||||
<CardContent>
|
||||
<Box display="flex" alignItems="center" color="#F2F2F2">
|
||||
<CardContent
|
||||
sx={{
|
||||
padding: { xs: 2, md: 3 },
|
||||
"&:last-child": { paddingBottom: { xs: 2, md: 3 } },
|
||||
}}
|
||||
>
|
||||
<Box
|
||||
display="flex"
|
||||
alignItems="center"
|
||||
color="#F2F2F2"
|
||||
flexDirection={isXsScreen ? "column" : "row"}
|
||||
sx={{ mb: isXsScreen ? 2 : 0 }}
|
||||
>
|
||||
<Typography
|
||||
variant="h6"
|
||||
color="#F2F2F2"
|
||||
align={isXsScreen ? "center" : "left"}
|
||||
sx={{
|
||||
fontFamily: "Gilroy",
|
||||
fontWeight: 500,
|
||||
fontSize: "18px",
|
||||
fontSize: { xs: "16px", sm: "17px", md: "18px" },
|
||||
lineHeight: "24px",
|
||||
marginBottom: isXsScreen ? 2 : 0,
|
||||
width: isXsScreen ? "100%" : "auto",
|
||||
}}
|
||||
>
|
||||
Charge Stats
|
||||
|
@ -84,13 +126,13 @@ export default function RoundedBarChart() {
|
|||
|
||||
<FormControl
|
||||
sx={{
|
||||
mt: 2,
|
||||
ml: "auto",
|
||||
mt: isXsScreen ? 0 : 2,
|
||||
ml: isXsScreen ? 0 : "auto",
|
||||
backgroundColor: "#202020",
|
||||
color: "#F2F2F2",
|
||||
width: "149px",
|
||||
height: "44px",
|
||||
padding: "12px 16px",
|
||||
width: { xs: "100%", sm: "140px", md: "149px" },
|
||||
height: { xs: "40px", md: "44px" },
|
||||
padding: { xs: "8px 12px", md: "12px 16px" },
|
||||
gap: "8px",
|
||||
}}
|
||||
>
|
||||
|
@ -98,6 +140,7 @@ export default function RoundedBarChart() {
|
|||
value={selectedOption}
|
||||
onChange={handleChange}
|
||||
sx={{
|
||||
fontSize: { xs: "14px", md: "16px" },
|
||||
color: "#D9D8D8",
|
||||
".MuiSelect-icon": {
|
||||
color: "#F2F2F2",
|
||||
|
@ -113,17 +156,28 @@ export default function RoundedBarChart() {
|
|||
</FormControl>
|
||||
</Box>
|
||||
|
||||
<BarChart
|
||||
dataset={data}
|
||||
series={[
|
||||
{
|
||||
dataKey: "v1",
|
||||
label: "Value",
|
||||
color: "skyblue",
|
||||
},
|
||||
]}
|
||||
{...chartSetting}
|
||||
/>
|
||||
<Box
|
||||
sx={{
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
width: "100%",
|
||||
mt: 2,
|
||||
}}
|
||||
>
|
||||
<BarChart
|
||||
borderRadius={0}
|
||||
dataset={data}
|
||||
series={[
|
||||
{
|
||||
dataKey: "v1",
|
||||
color: "#52ACDF",
|
||||
},
|
||||
]}
|
||||
layout="vertical"
|
||||
{...chartSetting}
|
||||
/>
|
||||
</Box>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
|
|
8
src/global.d.ts
vendored
Normal file
8
src/global.d.ts
vendored
Normal file
|
@ -0,0 +1,8 @@
|
|||
declare module "*.css";
|
||||
|
||||
declare module "@mui/styles/defaultTheme" {
|
||||
interface DefaultTheme extends Theme {
|
||||
vars: object;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,14 +1,24 @@
|
|||
body {
|
||||
margin: 0;
|
||||
/* font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',
|
||||
'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
|
||||
sans-serif; */
|
||||
font-family: "Gliroy";
|
||||
font-family: "Gilroy";
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
|
||||
}
|
||||
|
||||
code {
|
||||
font-family: source-code-pro, Menlo, Monaco, Consolas, 'Courier New',
|
||||
monospace;
|
||||
}
|
||||
|
||||
.mui-typography {
|
||||
font-family: "Gilroy", sans-serif !important;
|
||||
background-color: rgb(7, 127, 233);
|
||||
}
|
||||
|
||||
.css-1w8ddxu-MuiBarElement-root {
|
||||
width: 19px !important;
|
||||
border-radius: 50px !important;
|
||||
rx: 8;
|
||||
ry: 8
|
||||
}
|
||||
|
|
|
@ -16,7 +16,7 @@ root.render(
|
|||
position="top-right"
|
||||
richColors
|
||||
closeButton
|
||||
duration={6000}
|
||||
duration={3000}
|
||||
/>
|
||||
</Provider>
|
||||
</React.StrictMode>
|
||||
|
|
|
@ -43,9 +43,10 @@ const DashboardLayout: React.FC<LayoutProps> = ({ customStyles }) => {
|
|||
flexDirection: "column",
|
||||
height: "100vh",
|
||||
flexGrow: 1,
|
||||
backgroundColor: theme.vars
|
||||
? `rgba(${theme.vars.palette.background.defaultChannel} / 1)`
|
||||
: theme.palette.background.default,
|
||||
// backgroundColor: theme.vars
|
||||
// ? `rgba(${theme.vars.palette.background.defaultChannel} / 1)`
|
||||
// : theme.palette.background.default,
|
||||
backgroundColor: theme.palette.background.default,
|
||||
overflow: "auto",
|
||||
...customStyles,
|
||||
mt: { xs: 8, md: 0 },
|
||||
|
|
|
@ -22,6 +22,7 @@ import { Visibility, VisibilityOff } from "@mui/icons-material";
|
|||
import { Card, SignInContainer } from "./styled.css.tsx";
|
||||
import { CustomIconButton } from "../../../components/AddUserModal/styled.css.tsx";
|
||||
import { AppDispatch } from "../../../redux/store/store.ts";
|
||||
|
||||
interface ILoginForm {
|
||||
email: string;
|
||||
password: string;
|
||||
|
@ -34,7 +35,8 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
const {
|
||||
control,
|
||||
handleSubmit,
|
||||
formState: { errors, isValid },trigger
|
||||
formState: { errors, isValid },
|
||||
trigger,
|
||||
} = useForm<ILoginForm>({ mode: "onChange" });
|
||||
const dispatch = useDispatch<AppDispatch>();
|
||||
const router = useNavigate();
|
||||
|
@ -48,15 +50,15 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
};
|
||||
|
||||
const togglePasswordVisibility = (e: React.MouseEvent) => {
|
||||
e.preventDefault(); // Prevent focus loss
|
||||
e.preventDefault();
|
||||
setShowPassword((prev) => !prev);
|
||||
};
|
||||
|
||||
const onSubmit: SubmitHandler<ILoginForm> = async (data: ILoginForm) => {
|
||||
const isValid = await trigger(); // This triggers validation for all fields
|
||||
if (!isValid) {
|
||||
return; // Stop submission if there are errors
|
||||
}
|
||||
const isValid = await trigger();
|
||||
if (!isValid) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const response = await dispatch(loginUser(data)).unwrap();
|
||||
if (response?.data?.token) {
|
||||
|
@ -70,66 +72,90 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
return (
|
||||
<AppTheme {...props}>
|
||||
<SignInContainer direction="column" justifyContent="space-between">
|
||||
<Grid container sx={{ height: "100vh" }}>
|
||||
{/* Image Section */}
|
||||
<Grid container sx={{ minHeight: "100vh" }}>
|
||||
|
||||
<Grid
|
||||
item
|
||||
xs={0}
|
||||
sm={0}
|
||||
md={7}
|
||||
sx={{
|
||||
background: `url('/mainPageLogo.png') center/cover no-repeat`,
|
||||
// height: { xs: "0%", sm: "50%", md: "100%" },
|
||||
background: `url('/Login.svg') center/cover no-repeat`,
|
||||
backgroundSize: "cover",
|
||||
display: { xs: "none", md: "block" }, // Hide the image on xs and sm screens
|
||||
}}
|
||||
/>
|
||||
|
||||
{/* Form Section */}
|
||||
<Grid
|
||||
item
|
||||
xs={12}
|
||||
md={5}
|
||||
width="408px"
|
||||
height="498px"
|
||||
sx={{
|
||||
backgroundColor: "black",
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
flexDirection: "column",
|
||||
padding: { xs: "2rem", md: "3rem", lg: "3rem" },
|
||||
height: "auto",
|
||||
display: { xs: "none", md: "block" },
|
||||
position: "relative",
|
||||
}}
|
||||
>
|
||||
|
||||
<Box
|
||||
sx={{
|
||||
textAlign: "center",
|
||||
marginBottom: "1rem",
|
||||
position: "absolute",
|
||||
top: "50%",
|
||||
left: "50%",
|
||||
transform: "translate(-50%, -50%)",
|
||||
display: { xs: "none", md: "block" },
|
||||
}}
|
||||
>
|
||||
<img
|
||||
src="/evLogo.png"
|
||||
alt="Logo"
|
||||
style={{
|
||||
justifyContent: "center",
|
||||
width: "180px",
|
||||
width: "250px",
|
||||
height: "auto",
|
||||
}}
|
||||
/>
|
||||
</Box>
|
||||
</Grid>
|
||||
|
||||
{/* Form Section */}
|
||||
<Grid
|
||||
item
|
||||
xs={12}
|
||||
md={5}
|
||||
sx={{
|
||||
backgroundColor: "black",
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
flexDirection: "column",
|
||||
padding: { xs: "1.5rem", sm: "2rem", md: "3rem" },
|
||||
position: "relative",
|
||||
}}
|
||||
>
|
||||
|
||||
<Box
|
||||
sx={{
|
||||
display: { xs: "flex", md: "none" },
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
width: "100%",
|
||||
mb: 4,
|
||||
}}
|
||||
>
|
||||
<img
|
||||
src="/evLogo.png"
|
||||
alt="Logo"
|
||||
style={{
|
||||
width: "200px",
|
||||
maxWidth: "100%",
|
||||
height: "auto",
|
||||
}}
|
||||
/>
|
||||
</Box>
|
||||
|
||||
<Typography
|
||||
variant="h3"
|
||||
width={"408px"}
|
||||
height={"46px"}
|
||||
sx={{
|
||||
color: "white",
|
||||
textAlign: "center",
|
||||
fontSize: {
|
||||
xs: "2rem",
|
||||
xs: "1.8rem",
|
||||
sm: "2.2rem",
|
||||
md: "36px",
|
||||
md: "2.5rem",
|
||||
},
|
||||
width: "100%",
|
||||
mb: { xs: 2, md: 3 },
|
||||
mt: { xs: 0, md: 0 },
|
||||
}}
|
||||
>
|
||||
Welcome Back!
|
||||
|
@ -138,11 +164,12 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
<Card
|
||||
variant="outlined"
|
||||
sx={{
|
||||
width: { xs: "100%", sm: "300px", lg: "408px" },
|
||||
height:{lg:"428px"},
|
||||
padding: "24px",
|
||||
width: { xs: "100%", sm: "90%", md: "90%", lg: "408px" },
|
||||
maxWidth: "408px",
|
||||
minHeight: { xs: "auto", md: "428px" },
|
||||
padding: { xs: "16px", sm: "20px", md: "24px" },
|
||||
borderRadius: "9px",
|
||||
border: "1px solidrgb(45, 48, 49)",
|
||||
border: "none",
|
||||
"*:where([data-mui-color-scheme='dark']) &": {
|
||||
backgroundColor: "#1E1E1E",
|
||||
},
|
||||
|
@ -155,7 +182,7 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
sx={{
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
gap: 2,
|
||||
gap: { xs: 1.5, md: 2 },
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
|
@ -164,8 +191,7 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
sx={{
|
||||
textAlign: "center",
|
||||
color: "white",
|
||||
fontFamily: "Gilroy",
|
||||
fontSize: "24px",
|
||||
fontSize: { xs: "20px", md: "24px" },
|
||||
}}
|
||||
>
|
||||
Login
|
||||
|
@ -176,24 +202,24 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
sx={{
|
||||
textAlign: "center",
|
||||
color: "white",
|
||||
fontFamily: "Gilroy",
|
||||
fontSize: "16px",
|
||||
fontSize: { xs: "14px", md: "16px" },
|
||||
mb: 1,
|
||||
}}
|
||||
>
|
||||
Log in with your email and password
|
||||
</Typography>
|
||||
|
||||
{/* -------------------------------- Email Field ----------------- */}
|
||||
{/* Email Field */}
|
||||
<FormControl sx={{ width: "100%" }}>
|
||||
<FormLabel
|
||||
htmlFor="email"
|
||||
sx={{
|
||||
fontSize: {
|
||||
xs: "0.9rem",
|
||||
xs: "0.875rem",
|
||||
sm: "1rem",
|
||||
},
|
||||
color: "white",
|
||||
fontFamily: "Gilroy, sans-serif",
|
||||
mb: 0.5,
|
||||
}}
|
||||
>
|
||||
Email
|
||||
|
@ -232,12 +258,10 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
}
|
||||
InputProps={{
|
||||
sx: {
|
||||
height: "50px",
|
||||
height: { xs: "45px", md: "50px" },
|
||||
alignItems: "center",
|
||||
backgroundColor:
|
||||
"#1E1F1F",
|
||||
fontFamily:
|
||||
"Gilroy, sans-serif",
|
||||
},
|
||||
}}
|
||||
sx={{
|
||||
|
@ -265,7 +289,7 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
"& input": {
|
||||
color: "white",
|
||||
fontSize: {
|
||||
xs: "0.9rem",
|
||||
xs: "0.875rem",
|
||||
sm: "1rem",
|
||||
},
|
||||
fontFamily:
|
||||
|
@ -284,17 +308,18 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
/>
|
||||
</FormControl>
|
||||
|
||||
{/* -------------------------------- Password Field ----------------- */}
|
||||
{/* Password Field */}
|
||||
<FormControl sx={{ width: "100%" }}>
|
||||
<FormLabel
|
||||
htmlFor="password"
|
||||
sx={{
|
||||
fontSize: {
|
||||
xs: "0.9rem",
|
||||
xs: "0.875rem",
|
||||
sm: "1rem",
|
||||
},
|
||||
color: "white",
|
||||
fontFamily: "Gilroy, sans-serif",
|
||||
mb: 0.5,
|
||||
}}
|
||||
>
|
||||
Password
|
||||
|
@ -341,6 +366,9 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
: "primary"
|
||||
}
|
||||
InputProps={{
|
||||
sx: {
|
||||
height: { xs: "45px", md: "50px" },
|
||||
},
|
||||
endAdornment: (
|
||||
<InputAdornment position="end">
|
||||
<CustomIconButton
|
||||
|
@ -383,18 +411,14 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
"& input": {
|
||||
color: "white",
|
||||
fontSize: {
|
||||
xs: "0.9rem",
|
||||
xs: "0.875rem",
|
||||
sm: "1rem",
|
||||
},
|
||||
fontFamily:
|
||||
"Gilroy, sans-serif",
|
||||
},
|
||||
"& .MuiInputBase-input::placeholder":
|
||||
{
|
||||
color: "white",
|
||||
opacity: 1,
|
||||
fontFamily:
|
||||
"Gilroy, sans-serif",
|
||||
},
|
||||
}}
|
||||
/>
|
||||
|
@ -402,13 +426,16 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
/>
|
||||
</FormControl>
|
||||
|
||||
{/* Remember me and Forgot Password */}
|
||||
<Box
|
||||
sx={{
|
||||
display: "flex",
|
||||
justifyContent: "space-between",
|
||||
color: "white",
|
||||
alignItems: "center",
|
||||
flexWrap: "wrap",
|
||||
flexWrap: { xs: "wrap", sm: "nowrap" },
|
||||
gap: 1,
|
||||
mt: 1,
|
||||
}}
|
||||
>
|
||||
<FormControlLabel
|
||||
|
@ -416,10 +443,8 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
<Checkbox
|
||||
value="remember"
|
||||
sx={{
|
||||
width: 20,
|
||||
height: 20,
|
||||
fontFamily:
|
||||
"Gilroy, sans-serif",
|
||||
width: { xs: 16, md: 20 },
|
||||
height: { xs: 16, md: 20 },
|
||||
border: "2px solid #4b5255",
|
||||
borderRadius: "4px",
|
||||
backgroundColor:
|
||||
|
@ -440,7 +465,19 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
}}
|
||||
/>
|
||||
}
|
||||
label="Remember me"
|
||||
label={
|
||||
<Typography
|
||||
sx={{
|
||||
fontSize: {
|
||||
xs: "0.75rem",
|
||||
sm: "0.875rem",
|
||||
md: "1rem"
|
||||
}
|
||||
}}
|
||||
>
|
||||
Remember me
|
||||
</Typography>
|
||||
}
|
||||
/>
|
||||
|
||||
<Link
|
||||
|
@ -450,9 +487,13 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
variant="body2"
|
||||
sx={{
|
||||
alignSelf: "center",
|
||||
fontFamily: "Gilroy, sans-serif",
|
||||
color: "#01579b",
|
||||
textDecoration: "none",
|
||||
textDecoration: "none",
|
||||
fontSize: {
|
||||
xs: "0.75rem",
|
||||
sm: "0.875rem",
|
||||
md: "1rem"
|
||||
},
|
||||
}}
|
||||
>
|
||||
Forgot password?
|
||||
|
@ -462,18 +503,22 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
open={open}
|
||||
handleClose={handleClose}
|
||||
/>
|
||||
|
||||
{/* Login Button */}
|
||||
<Button
|
||||
type="submit"
|
||||
fullWidth
|
||||
disabled={!isValid}
|
||||
sx={{
|
||||
color: "white",
|
||||
fontFamily: "Gilroy, sans-serif",
|
||||
color: "#ffffff !important",
|
||||
fontWeight: 500,
|
||||
backgroundColor: "#52ACDF",
|
||||
"&:hover": {
|
||||
backgroundColor: "#52ACDF",
|
||||
opacity: 0.9,
|
||||
},
|
||||
padding: { xs: "8px 0", md: "10px 0" },
|
||||
mt: { xs: 2, md: 3 },
|
||||
fontSize: { xs: "0.875rem", md: "1rem" },
|
||||
}}
|
||||
>
|
||||
Login
|
||||
|
@ -485,4 +530,4 @@ export default function Login(props: { disableCustomTheme?: boolean }) {
|
|||
</SignInContainer>
|
||||
</AppTheme>
|
||||
);
|
||||
}
|
||||
}
|
|
@ -245,7 +245,7 @@ export default function SignUp(props: { disableCustomTheme?: boolean }) {
|
|||
<FormLabel htmlFor="phone">Phone Number</FormLabel>
|
||||
<MuiPhoneNumber
|
||||
defaultCountry="in"
|
||||
onChange={handlePhoneChange}
|
||||
onChange={(value) => handlePhoneChange(value as string)}
|
||||
value={control._formValues.phone}
|
||||
required
|
||||
error={!!errors.phone}
|
||||
|
|
228
src/pages/LandingPage/index.tsx
Normal file
228
src/pages/LandingPage/index.tsx
Normal file
|
@ -0,0 +1,228 @@
|
|||
import React from "react";
|
||||
import { Box, Button, Container, Grid, Typography } from "@mui/material";
|
||||
import { useNavigate } from "react-router-dom"; // Import useNavigate for navigation
|
||||
import SearchIcon from "@mui/icons-material/Search";
|
||||
|
||||
const LandingPage = () => {
|
||||
const navigate = useNavigate(); // Initialize useNavigate
|
||||
|
||||
const handleLoginClick = () => {
|
||||
navigate("/login"); // Redirect to the login page
|
||||
};
|
||||
|
||||
return (
|
||||
<Box
|
||||
sx={{
|
||||
background: `radial-gradient(circle at top left, rgba(125,121,87,0.992) 10%, rgba(67,92,106,0.8) 40%, rgba(55,47,65,1) 70%),
|
||||
radial-gradient(circle at center, rgba(109, 102, 102, 0.7) 0%, rgba(67,92,106,0.6) 50%, rgba(55,47,65,0.9) 70%),
|
||||
radial-gradient(circle at top right, rgba(61,42,87,1) 30%, rgba(55,47,65,1) 60%, rgba(40,40,40,0.8) 70%)`,
|
||||
color: "white",
|
||||
minHeight: "100vh",
|
||||
fontFamily: "Inter",
|
||||
}}
|
||||
>
|
||||
{/* Navbar */}
|
||||
<Box
|
||||
component="nav"
|
||||
sx={{
|
||||
display: "flex",
|
||||
justifyContent: "space-between",
|
||||
alignItems: "center",
|
||||
py: 2,
|
||||
px: 3,
|
||||
maxWidth: "1200px",
|
||||
mx: "auto",
|
||||
fontFamily: "Inter",
|
||||
}}
|
||||
>
|
||||
<img
|
||||
src="/evLogo.png"
|
||||
alt="DigiEv Logo"
|
||||
style={{ height: "40px" }}
|
||||
/>
|
||||
<Box
|
||||
sx={{
|
||||
display: "flex",
|
||||
alignItems: "center",
|
||||
gap: 2,
|
||||
}}
|
||||
>
|
||||
<SearchIcon
|
||||
sx={{
|
||||
fontSize: "24px",
|
||||
cursor: "pointer",
|
||||
color: "#364056",
|
||||
}}
|
||||
/>
|
||||
<Button
|
||||
type="button" // Changed to "button" to avoid form submission
|
||||
onClick={handleLoginClick} // Trigger navigation on click
|
||||
sx={{
|
||||
backgroundColor: "#52ACDF",
|
||||
color: "white",
|
||||
borderRadius: "8px",
|
||||
width: "117px",
|
||||
fontFamily: "Inter",
|
||||
textTransform: "none",
|
||||
"&:hover": { backgroundColor: "#439BC1" },
|
||||
}}
|
||||
>
|
||||
Login
|
||||
</Button>
|
||||
</Box>
|
||||
</Box>
|
||||
|
||||
{/* Hero Section */}
|
||||
<Container
|
||||
sx={{
|
||||
py: 8,
|
||||
justifyContent: "space-between",
|
||||
fontFamily: "Inter",
|
||||
}}
|
||||
>
|
||||
<Grid
|
||||
container
|
||||
spacing={4}
|
||||
alignItems="center"
|
||||
justifyContent="center"
|
||||
>
|
||||
{/* Text Section */}
|
||||
<Grid
|
||||
item
|
||||
xs={12}
|
||||
md={6}
|
||||
sx={{
|
||||
height: { xs: "auto", md: "400px" },
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
justifyContent: "center",
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
sx={{
|
||||
fontFamily: "Inter",
|
||||
fontWeight: 600,
|
||||
fontSize: "40px",
|
||||
lineHeight: "120%",
|
||||
letterSpacing: "0px",
|
||||
marginBottom: "16px",
|
||||
}}
|
||||
>
|
||||
Empower Your Business With{" "}
|
||||
<Box component="span" sx={{ color: "#52ACDF" }}>
|
||||
Digital Evolution
|
||||
</Box>
|
||||
.
|
||||
</Typography>
|
||||
<Typography
|
||||
variant="body1"
|
||||
sx={{
|
||||
fontFamily: "Inter",
|
||||
color: "#CACACA",
|
||||
marginBottom: "24px",
|
||||
fontWeight: 400,
|
||||
fontSize: "20px",
|
||||
lineHeight: "120%",
|
||||
}}
|
||||
>
|
||||
DigiEv is your one-stop destination for transforming
|
||||
challenges into opportunities through innovative
|
||||
technology, seamless integration, and expert
|
||||
solutions.
|
||||
</Typography>
|
||||
<Button
|
||||
type="submit"
|
||||
sx={{
|
||||
backgroundColor: "#52ACDF",
|
||||
color: "white",
|
||||
borderRadius: "8px",
|
||||
width: "117px",
|
||||
textTransform: "none",
|
||||
fontFamily: "Inter",
|
||||
"&:hover": { backgroundColor: "#439BC1" },
|
||||
}}
|
||||
>
|
||||
Get in Touch
|
||||
</Button>
|
||||
</Grid>
|
||||
|
||||
{/* Image Section */}
|
||||
<Grid
|
||||
item
|
||||
xs={12}
|
||||
md={6}
|
||||
sx={{
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
}}
|
||||
>
|
||||
<img
|
||||
src="/home.png"
|
||||
alt="Dashboard"
|
||||
style={{
|
||||
maxHeight: "100%",
|
||||
maxWidth: "100%",
|
||||
objectFit: "contain",
|
||||
borderRadius: "8px",
|
||||
}}
|
||||
/>
|
||||
</Grid>
|
||||
</Grid>
|
||||
</Container>
|
||||
<Container maxWidth="lg">
|
||||
{" "}
|
||||
<Grid container spacing={4} textAlign="center">
|
||||
{" "}
|
||||
<Grid item xs={12} md={4}>
|
||||
{" "}
|
||||
<Typography
|
||||
variant="h3"
|
||||
fontWeight="bold"
|
||||
color="#1e88e5"
|
||||
>
|
||||
{" "}
|
||||
50+{" "}
|
||||
</Typography>{" "}
|
||||
<Typography variant="body2" color="gray">
|
||||
{" "}
|
||||
Successful Digital Transformations{" "}
|
||||
</Typography>{" "}
|
||||
</Grid>{" "}
|
||||
<Grid item xs={12} md={4}>
|
||||
{" "}
|
||||
<Typography
|
||||
variant="h3"
|
||||
fontWeight="bold"
|
||||
color="#1e88e5"
|
||||
>
|
||||
{" "}
|
||||
100%{" "}
|
||||
</Typography>{" "}
|
||||
<Typography variant="body2" color="gray">
|
||||
{" "}
|
||||
Client Satisfaction{" "}
|
||||
</Typography>{" "}
|
||||
</Grid>{" "}
|
||||
<Grid item xs={12} md={4}>
|
||||
{" "}
|
||||
<Typography
|
||||
variant="h3"
|
||||
fontWeight="bold"
|
||||
color="#1e88e5"
|
||||
>
|
||||
{" "}
|
||||
20+{" "}
|
||||
</Typography>{" "}
|
||||
<Typography variant="body2" color="gray">
|
||||
{" "}
|
||||
Global Partnerships{" "}
|
||||
</Typography>{" "}
|
||||
</Grid>{" "}
|
||||
</Grid>{" "}
|
||||
</Container>
|
||||
</Box>
|
||||
);
|
||||
};
|
||||
|
||||
export default LandingPage;
|
|
@ -118,8 +118,8 @@ export default function StationList() {
|
|||
return {
|
||||
id: station.id,
|
||||
srno: index + 1,
|
||||
name: station.name,
|
||||
registeredAddress: station.registeredAddress,
|
||||
name: station.name || "N/A",
|
||||
registeredAddress: station.registeredAddress || "N/A",
|
||||
totalSlots: station.totalSlots,
|
||||
vehicles: vehicleDisplay, // Add the formatted vehicle display here
|
||||
status:
|
||||
|
|
|
@ -17,7 +17,6 @@ export default function UserList() {
|
|||
const [viewModal, setViewModal] = useState<boolean>(false);
|
||||
const { reset } = useForm();
|
||||
|
||||
|
||||
const dispatch = useDispatch<AppDispatch>();
|
||||
|
||||
const users = useSelector((state: RootState) => state.userReducer.users);
|
||||
|
@ -65,7 +64,6 @@ export default function UserList() {
|
|||
name,
|
||||
email,
|
||||
phone,
|
||||
|
||||
})
|
||||
);
|
||||
await dispatch(userList());
|
||||
|
@ -76,24 +74,21 @@ export default function UserList() {
|
|||
|
||||
const categoryColumns: Column[] = [
|
||||
{ id: "srno", label: "Sr No" },
|
||||
{ id: "name", label: "Name" },
|
||||
{ id: "name", label: "User Name" },
|
||||
{ id: "email", label: "Email" },
|
||||
{ id: "phone", label: "Phone" },
|
||||
|
||||
{ id: "action", label: "Action", align: "center" },
|
||||
];
|
||||
const categoryRows = users?.length
|
||||
? users.map((user, index) => ({
|
||||
id: user.id,
|
||||
srno: index + 1,
|
||||
name: user.name,
|
||||
email: user.email,
|
||||
phone: user.phone || "NA", // Ensures it's a string
|
||||
}))
|
||||
: [];
|
||||
|
||||
|
||||
|
||||
const categoryRows = users?.length
|
||||
? users.map((user, index) => ({
|
||||
id: user.id,
|
||||
srno: index + 1,
|
||||
name: user.name,
|
||||
email: user.email,
|
||||
phone: user.phone || "NA", // Ensures it's a string
|
||||
}))
|
||||
: [];
|
||||
|
||||
return (
|
||||
<>
|
||||
|
|
|
@ -79,6 +79,7 @@ export const createAdmin = createAsyncThunk<
|
|||
>("/create-admin", async (data, { rejectWithValue }) => {
|
||||
try {
|
||||
const response = await http.post("/create-admin", data);
|
||||
toast.success("Admin created successfully");
|
||||
return response.data;
|
||||
} catch (error: any) {
|
||||
return rejectWithValue(
|
||||
|
|
|
@ -63,7 +63,7 @@ export const addManager = createAsyncThunk<
|
|||
toast.success("Manager created successfully");
|
||||
return response.data?.data;
|
||||
} catch (error: any) {
|
||||
toast.error("Error creating manager: " + error.message);
|
||||
toast.error("Error creating manager: " + error.response?.data?.message);
|
||||
return rejectWithValue(
|
||||
error.response?.data?.message || "An error occurred"
|
||||
);
|
||||
|
|
|
@ -9,6 +9,7 @@ import DashboardLayout from "./layouts/DashboardLayout";
|
|||
// Page imports
|
||||
const Login = lazy(() => import("./pages/Auth/Login"));
|
||||
const SignUp = lazy(() => import("./pages/Auth/SignUp"));
|
||||
const LandingPage = lazy(() => import("./pages/LandingPage"));
|
||||
const Dashboard = lazy(() => import("./pages/Dashboard"));
|
||||
const VehicleList = lazy(() => import("./pages/VehicleList"));
|
||||
const AdminList = lazy(() => import("./pages/AdminList"));
|
||||
|
@ -43,7 +44,7 @@ export default function AppRouter() {
|
|||
<Suspense fallback={<LoadingComponent />}>
|
||||
<BaseRoutes>
|
||||
{/* Default Route */}
|
||||
<Route element={<Navigate to="/login" replace />} index />
|
||||
<Route path="" element={<LandingPage /> } />
|
||||
|
||||
{/* Auth Routes */}
|
||||
<Route path="">
|
||||
|
@ -110,7 +111,11 @@ export default function AppRouter() {
|
|||
/>
|
||||
<Route
|
||||
path="external-station-list"
|
||||
element={<ProtectedRoute component={<ExternalStationList />} />}
|
||||
element={
|
||||
<ProtectedRoute
|
||||
component={<ExternalStationList />}
|
||||
/>
|
||||
}
|
||||
/>
|
||||
</Route>
|
||||
|
||||
|
|
|
@ -6,19 +6,12 @@ import { dataDisplayCustomizations } from "./customizations/dataDisplay";
|
|||
import { feedbackCustomizations } from "./customizations/feedback";
|
||||
import { navigationCustomizations } from "./customizations/navigation";
|
||||
import { surfacesCustomizations } from "./customizations/surfaces";
|
||||
import { colorSchemes, typography, shadows, shape } from "./themePrimitives";
|
||||
import { colorSchemes, shadows, shape } from "./themePrimitives";
|
||||
|
||||
|
||||
declare module "@mui/styles/defaultTheme" {
|
||||
interface DefaultTheme extends Theme {
|
||||
vars: object;
|
||||
}
|
||||
}
|
||||
|
||||
interface AppThemeProps {
|
||||
children: React.ReactNode;
|
||||
/**
|
||||
* This is for the docs site. You can ignore it or remove it.
|
||||
*/
|
||||
disableCustomTheme?: boolean;
|
||||
themeComponents?: ThemeOptions["components"];
|
||||
}
|
||||
|
@ -30,21 +23,23 @@ export default function AppTheme(props: AppThemeProps) {
|
|||
? {}
|
||||
: createTheme({
|
||||
palette: {
|
||||
mode: "dark", // Enforcing dark mode across the app
|
||||
mode: "dark",
|
||||
background: {
|
||||
default: "#111111", // Dark background color
|
||||
paper: "#1e1e1e", // Darker background for cards, containers, etc.
|
||||
default: "#111111",
|
||||
paper: "#1e1e1e",
|
||||
},
|
||||
text: {
|
||||
primary: "#ffffff", // White text for readability
|
||||
secondary: "#b0b0b0", // Lighter secondary text
|
||||
primary: "#ffffff",
|
||||
secondary: "#b0b0b0",
|
||||
},
|
||||
},
|
||||
typography: {
|
||||
fontFamily: "Gilroy, sans-serif",
|
||||
},
|
||||
cssVariables: {
|
||||
colorSchemeSelector: "data-mui-color-scheme",
|
||||
cssVarPrefix: "template",
|
||||
},
|
||||
typography,
|
||||
shadows,
|
||||
shape,
|
||||
components: {
|
||||
|
|
|
@ -11,10 +11,22 @@
|
|||
"compilerOptions": {
|
||||
"baseUrl": ".",
|
||||
"jsx": "react-jsx",
|
||||
"types": ["react", "react-dom"],
|
||||
"lib": ["dom", "dom.iterable", "esnext"],
|
||||
"types": [
|
||||
"react",
|
||||
"react-dom"
|
||||
],
|
||||
"lib": [
|
||||
"dom",
|
||||
"dom.iterable",
|
||||
"esnext"
|
||||
],
|
||||
"moduleResolution": "node",
|
||||
"esModuleInterop": true,
|
||||
"resolveJsonModule": true,
|
||||
"paths": {
|
||||
"@/*": ["./src/*"]
|
||||
"@/*": [
|
||||
"./src/*"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue