feat: styling index page backbone, fishbone, devices & tower
This commit is contained in:
parent
d4ac8fff4e
commit
e62e678fba
|
|
@ -13,6 +13,7 @@
|
||||||
"@fontsource/public-sans": "^5.1.2",
|
"@fontsource/public-sans": "^5.1.2",
|
||||||
"@mui/icons-material": "^6.4.3",
|
"@mui/icons-material": "^6.4.3",
|
||||||
"@mui/material": "^6.4.3",
|
"@mui/material": "^6.4.3",
|
||||||
|
"@tanstack/react-table": "^8.21.2",
|
||||||
"iconsax-react": "^0.0.8",
|
"iconsax-react": "^0.0.8",
|
||||||
"lodash": "^4.17.21",
|
"lodash": "^4.17.21",
|
||||||
"react": "^19.0.0",
|
"react": "^19.0.0",
|
||||||
|
|
@ -1625,6 +1626,37 @@
|
||||||
"tslib": "^2.6.2"
|
"tslib": "^2.6.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@tanstack/react-table": {
|
||||||
|
"version": "8.21.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/@tanstack/react-table/-/react-table-8.21.2.tgz",
|
||||||
|
"integrity": "sha512-11tNlEDTdIhMJba2RBH+ecJ9l1zgS2kjmexDPAraulc8jeNA4xocSNeyzextT0XJyASil4XsCYlJmf5jEWAtYg==",
|
||||||
|
"dependencies": {
|
||||||
|
"@tanstack/table-core": "8.21.2"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"type": "github",
|
||||||
|
"url": "https://github.com/sponsors/tannerlinsley"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": ">=16.8",
|
||||||
|
"react-dom": ">=16.8"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@tanstack/table-core": {
|
||||||
|
"version": "8.21.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/@tanstack/table-core/-/table-core-8.21.2.tgz",
|
||||||
|
"integrity": "sha512-uvXk/U4cBiFMxt+p9/G7yUWI/UbHYbyghLCjlpWZ3mLeIZiUBSKcUnw9UnKkdRz7Z/N4UBuFLWQdJCjUe7HjvA==",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"type": "github",
|
||||||
|
"url": "https://github.com/sponsors/tannerlinsley"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@types/babel__core": {
|
"node_modules/@types/babel__core": {
|
||||||
"version": "7.20.5",
|
"version": "7.20.5",
|
||||||
"resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz",
|
"resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz",
|
||||||
|
|
|
||||||
|
|
@ -15,6 +15,7 @@
|
||||||
"@fontsource/public-sans": "^5.1.2",
|
"@fontsource/public-sans": "^5.1.2",
|
||||||
"@mui/icons-material": "^6.4.3",
|
"@mui/icons-material": "^6.4.3",
|
||||||
"@mui/material": "^6.4.3",
|
"@mui/material": "^6.4.3",
|
||||||
|
"@tanstack/react-table": "^8.21.2",
|
||||||
"iconsax-react": "^0.0.8",
|
"iconsax-react": "^0.0.8",
|
||||||
"lodash": "^4.17.21",
|
"lodash": "^4.17.21",
|
||||||
"react": "^19.0.0",
|
"react": "^19.0.0",
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,176 @@
|
||||||
|
import { forwardRef, ReactNode, ReactPortal, Ref } from 'react';
|
||||||
|
|
||||||
|
// material-ui
|
||||||
|
import { alpha, styled, useTheme } from '@mui/material';
|
||||||
|
import MuiIconButton, { IconButtonProps } from '@mui/material/IconButton';
|
||||||
|
|
||||||
|
// project-imports
|
||||||
|
import getColors from '../utils/getColors';
|
||||||
|
import getShadow from '../utils/getShadow';
|
||||||
|
|
||||||
|
// types
|
||||||
|
import { ButtonVariantProps, ExtendedStyleProps, IconButtonShapeProps } from '../types/extended';
|
||||||
|
|
||||||
|
// ==============================|| ICON BUTTON - COLOR STYLE ||============================== //
|
||||||
|
|
||||||
|
interface IconButtonStyleProps extends ExtendedStyleProps {
|
||||||
|
variant?: ButtonVariantProps;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getColorStyle({ variant, theme, color }: IconButtonStyleProps) {
|
||||||
|
const colors = getColors(theme, color);
|
||||||
|
const { lighter, light, dark, main, contrastText } = colors;
|
||||||
|
|
||||||
|
const buttonShadow = `${color}Button`;
|
||||||
|
const shadows = getShadow(theme, buttonShadow);
|
||||||
|
|
||||||
|
const commonShadow = {
|
||||||
|
'&::after': {
|
||||||
|
boxShadow: `0 0 6px 6px ${alpha(main, 0.9)}`
|
||||||
|
},
|
||||||
|
'&:active::after': {
|
||||||
|
boxShadow: `0 0 0 0 ${alpha(main, 0.9)}`
|
||||||
|
},
|
||||||
|
'&:focus-visible': {
|
||||||
|
outline: `2px solid ${dark}`,
|
||||||
|
outlineOffset: 2
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
console.log(main);
|
||||||
|
|
||||||
|
switch (variant) {
|
||||||
|
case 'contained':
|
||||||
|
return {
|
||||||
|
color: contrastText,
|
||||||
|
backgroundColor: main,
|
||||||
|
'&:hover': {
|
||||||
|
backgroundColor: dark
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
case 'light':
|
||||||
|
return {
|
||||||
|
color: main,
|
||||||
|
backgroundColor: lighter,
|
||||||
|
'&:hover': {
|
||||||
|
backgroundColor: light
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
case 'shadow':
|
||||||
|
return {
|
||||||
|
boxShadow: shadows,
|
||||||
|
color: contrastText,
|
||||||
|
backgroundColor: main,
|
||||||
|
'&:hover': {
|
||||||
|
boxShadow: 'none',
|
||||||
|
backgroundColor: dark
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
case 'outlined':
|
||||||
|
return {
|
||||||
|
'&:hover': {
|
||||||
|
backgroundColor: 'transparent',
|
||||||
|
color: dark,
|
||||||
|
borderColor: dark
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
case 'dashed':
|
||||||
|
return {
|
||||||
|
backgroundColor: lighter,
|
||||||
|
'&:hover': {
|
||||||
|
color: dark,
|
||||||
|
borderColor: dark
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
case 'text':
|
||||||
|
default:
|
||||||
|
return {
|
||||||
|
'&:hover': {
|
||||||
|
color: dark,
|
||||||
|
backgroundColor: lighter
|
||||||
|
},
|
||||||
|
...commonShadow
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// ==============================|| ICON BUTTON - STYLED ||============================== //
|
||||||
|
|
||||||
|
interface StyleProps extends IconButtonStyleProps {
|
||||||
|
shape?: IconButtonShapeProps;
|
||||||
|
}
|
||||||
|
|
||||||
|
const IconButtonStyle = styled(MuiIconButton, { shouldForwardProp: (prop) => prop !== 'variant' && prop !== 'shape' })(
|
||||||
|
({ theme, variant, shape, color }: StyleProps) => ({
|
||||||
|
position: 'relative',
|
||||||
|
'::after': {
|
||||||
|
content: '""',
|
||||||
|
display: 'block',
|
||||||
|
position: 'absolute',
|
||||||
|
left: 0,
|
||||||
|
top: 0,
|
||||||
|
width: '100%',
|
||||||
|
height: '100%',
|
||||||
|
borderRadius: shape === 'rounded' ? '50%' : 8,
|
||||||
|
opacity: 0,
|
||||||
|
transition: 'all 0.5s'
|
||||||
|
},
|
||||||
|
|
||||||
|
':active::after': {
|
||||||
|
position: 'absolute',
|
||||||
|
borderRadius: shape === 'rounded' ? '50%' : 8,
|
||||||
|
left: 0,
|
||||||
|
top: 0,
|
||||||
|
opacity: 1,
|
||||||
|
transition: '0s'
|
||||||
|
},
|
||||||
|
...(shape === 'rounded' && {
|
||||||
|
borderRadius: '50%'
|
||||||
|
}),
|
||||||
|
...(variant === 'outlined' && {
|
||||||
|
border: '1px solid',
|
||||||
|
borderColor: 'inherit'
|
||||||
|
}),
|
||||||
|
...(variant === 'dashed' && {
|
||||||
|
border: '1px dashed',
|
||||||
|
borderColor: 'inherit'
|
||||||
|
}),
|
||||||
|
...(variant !== 'text' && {
|
||||||
|
'&.Mui-disabled': {
|
||||||
|
backgroundColor: theme.palette.secondary[200]
|
||||||
|
}
|
||||||
|
}),
|
||||||
|
...getColorStyle({ variant, theme, color })
|
||||||
|
})
|
||||||
|
);
|
||||||
|
|
||||||
|
// ==============================|| ICON BUTTON - EXTENDED ||============================== //
|
||||||
|
|
||||||
|
export interface Props extends IconButtonProps {
|
||||||
|
shape?: IconButtonShapeProps;
|
||||||
|
variant?: ButtonVariantProps;
|
||||||
|
children: ReactNode;
|
||||||
|
tooltip?: boolean | ReactNode | ReactPortal;
|
||||||
|
}
|
||||||
|
|
||||||
|
function IconButton(
|
||||||
|
{ variant = 'text', shape = 'square', children, color = 'primary', tooltip, ...others }: Props,
|
||||||
|
ref: Ref<HTMLButtonElement>
|
||||||
|
) {
|
||||||
|
const theme = useTheme();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<IconButtonStyle ref={ref} variant={variant} shape={shape} theme={theme} color={color} {...others}>
|
||||||
|
{children}
|
||||||
|
</IconButtonStyle>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
IconButton.displayName = 'IconButton';
|
||||||
|
|
||||||
|
export default forwardRef(IconButton);
|
||||||
|
|
@ -0,0 +1,143 @@
|
||||||
|
import InputAdornment from "@mui/material/InputAdornment";
|
||||||
|
import Paper from "@mui/material/Paper";
|
||||||
|
import Table from "@mui/material/Table";
|
||||||
|
import TableBody from "@mui/material/TableBody";
|
||||||
|
import TableContainer from "@mui/material/TableContainer";
|
||||||
|
import TableCell from "@mui/material/TableCell";
|
||||||
|
import TableHead from "@mui/material/TableHead";
|
||||||
|
import TableRow from "@mui/material/TableRow";
|
||||||
|
import TablePagination from "@mui/material/TablePagination";
|
||||||
|
import TextField from "@mui/material/TextField";
|
||||||
|
import Box from "@mui/material/Box";
|
||||||
|
|
||||||
|
import {
|
||||||
|
flexRender,
|
||||||
|
useReactTable,
|
||||||
|
ColumnDef,
|
||||||
|
getCoreRowModel,
|
||||||
|
getSortedRowModel,
|
||||||
|
getFilteredRowModel,
|
||||||
|
getPaginationRowModel,
|
||||||
|
SortingState,
|
||||||
|
ColumnFiltersState,
|
||||||
|
} from "@tanstack/react-table";
|
||||||
|
import { useState } from "react";
|
||||||
|
import { SearchNormal } from "iconsax-react";
|
||||||
|
|
||||||
|
interface ReactTableProps<T extends object> {
|
||||||
|
columns: ColumnDef<T>[];
|
||||||
|
data: T[];
|
||||||
|
striped?: boolean;
|
||||||
|
title?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
function ComponentReactTable<T extends object>({
|
||||||
|
columns,
|
||||||
|
data,
|
||||||
|
striped,
|
||||||
|
title,
|
||||||
|
}: ReactTableProps<T>) {
|
||||||
|
const [sorting, setSorting] = useState<SortingState>([]);
|
||||||
|
const [columnFilters, setColumnFilters] = useState<ColumnFiltersState>([]);
|
||||||
|
const [globalFilter, setGlobalFilter] = useState("");
|
||||||
|
|
||||||
|
const table = useReactTable({
|
||||||
|
data,
|
||||||
|
columns,
|
||||||
|
state: {
|
||||||
|
sorting,
|
||||||
|
columnFilters,
|
||||||
|
globalFilter,
|
||||||
|
},
|
||||||
|
onSortingChange: setSorting,
|
||||||
|
onColumnFiltersChange: setColumnFilters,
|
||||||
|
onGlobalFilterChange: setGlobalFilter,
|
||||||
|
getCoreRowModel: getCoreRowModel(),
|
||||||
|
getSortedRowModel: getSortedRowModel(),
|
||||||
|
getFilteredRowModel: getFilteredRowModel(),
|
||||||
|
getPaginationRowModel: getPaginationRowModel(),
|
||||||
|
});
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box>
|
||||||
|
<Box justifyContent={"space-between"} display="flex">
|
||||||
|
<Box>
|
||||||
|
|
||||||
|
</Box>
|
||||||
|
<TextField
|
||||||
|
size="small"
|
||||||
|
value={globalFilter ?? ""}
|
||||||
|
onChange={(e) => setGlobalFilter(e.target.value)}
|
||||||
|
placeholder="Search all columns..."
|
||||||
|
sx={{ mb: 2 }}
|
||||||
|
slotProps={{
|
||||||
|
input: {
|
||||||
|
startAdornment: <InputAdornment position="start">
|
||||||
|
<SearchNormal size="20" variant="Linear" color="#808191" />
|
||||||
|
</InputAdornment>,
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
<TableContainer component={Paper}>
|
||||||
|
<Table>
|
||||||
|
<TableHead>
|
||||||
|
{table.getHeaderGroups().map((headerGroup) => (
|
||||||
|
<TableRow key={headerGroup.id}>
|
||||||
|
{headerGroup.headers.map((header) => (
|
||||||
|
<TableCell
|
||||||
|
key={header.id}
|
||||||
|
onClick={header.column.getToggleSortingHandler()}
|
||||||
|
sx={{ cursor: "pointer" }}
|
||||||
|
>
|
||||||
|
{header.isPlaceholder ? null : (
|
||||||
|
<Box sx={{ display: "flex", alignItems: "center" }}>
|
||||||
|
{flexRender(
|
||||||
|
header.column.columnDef.header,
|
||||||
|
header.getContext()
|
||||||
|
)}
|
||||||
|
{{
|
||||||
|
asc: " 🔼",
|
||||||
|
desc: " 🔽",
|
||||||
|
}[header.column.getIsSorted() as string] ?? null}
|
||||||
|
</Box>
|
||||||
|
)}
|
||||||
|
</TableCell>
|
||||||
|
))}
|
||||||
|
</TableRow>
|
||||||
|
))}
|
||||||
|
</TableHead>
|
||||||
|
<TableBody className={striped ? "striped" : undefined}>
|
||||||
|
{table.getRowModel().rows.map((row) => (
|
||||||
|
<TableRow key={row.id}>
|
||||||
|
{row.getVisibleCells().map((cell) => (
|
||||||
|
<TableCell key={cell.id}>
|
||||||
|
{flexRender(cell.column.columnDef.cell, cell.getContext())}
|
||||||
|
</TableCell>
|
||||||
|
))}
|
||||||
|
</TableRow>
|
||||||
|
))}
|
||||||
|
</TableBody>
|
||||||
|
</Table>
|
||||||
|
</TableContainer>
|
||||||
|
<TablePagination
|
||||||
|
component="div"
|
||||||
|
count={table.getFilteredRowModel().rows.length}
|
||||||
|
page={table.getState().pagination.pageIndex}
|
||||||
|
onPageChange={(_, page) => table.setPageIndex(page)}
|
||||||
|
rowsPerPage={table.getState().pagination.pageSize}
|
||||||
|
onRowsPerPageChange={(e) => table.setPageSize(Number(e.target.value))}
|
||||||
|
rowsPerPageOptions={[5, 10, 25, 50]}
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function ReactTable<T extends object>({
|
||||||
|
striped,
|
||||||
|
title,
|
||||||
|
data,
|
||||||
|
columns,
|
||||||
|
}: ReactTableProps<T>) {
|
||||||
|
return <ComponentReactTable {...{ data, columns, title, striped }} />;
|
||||||
|
}
|
||||||
|
|
@ -63,7 +63,7 @@ export default function Header({
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Typography variant="subtitle1" noWrap component="div">
|
<Typography variant="subtitle1" noWrap component="div">
|
||||||
Hi, Admins
|
Hi, Admin
|
||||||
</Typography>
|
</Typography>
|
||||||
</Box>
|
</Box>
|
||||||
<Menu
|
<Menu
|
||||||
|
|
|
||||||
|
|
@ -50,6 +50,11 @@ const MENU = [
|
||||||
link: "/devices",
|
link: "/devices",
|
||||||
icon: Speedometer,
|
icon: Speedometer,
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: "Tower",
|
||||||
|
link: "/towers",
|
||||||
|
icon: Speedometer,
|
||||||
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -8,8 +8,61 @@ import Grid from "@mui/material/Grid2";
|
||||||
import Typography from "@mui/material/Typography";
|
import Typography from "@mui/material/Typography";
|
||||||
import AddIcon from "@mui/icons-material/Add";
|
import AddIcon from "@mui/icons-material/Add";
|
||||||
import { Home } from "@mui/icons-material";
|
import { Home } from "@mui/icons-material";
|
||||||
|
import ReactTable from "../components/ReactTable";
|
||||||
|
import IconButton from "../components/IconButton";
|
||||||
|
import { Edit } from "iconsax-react";
|
||||||
|
import { ColumnDef } from "@tanstack/react-table";
|
||||||
|
|
||||||
|
interface UserData {
|
||||||
|
backbone: string;
|
||||||
|
device_start: string;
|
||||||
|
device_end: string;
|
||||||
|
total_core: string;
|
||||||
|
total_fishbone: string;
|
||||||
|
}
|
||||||
|
|
||||||
export default function Backbone() {
|
export default function Backbone() {
|
||||||
|
const data: UserData[] = [
|
||||||
|
{ backbone: "BB-BDG-SMD", device_start: "DV-CODE-1", device_end: "DV-CODE-2", total_core: "24 Core", total_fishbone: "3" },
|
||||||
|
{ backbone: "BB-BDG-SBG", device_start: "DV-CODE-3", device_end: "DV-CODE-4", total_core: "24 Core", total_fishbone: "5" },
|
||||||
|
];
|
||||||
|
|
||||||
|
// Define columns
|
||||||
|
const columns: ColumnDef<UserData>[] = [
|
||||||
|
{
|
||||||
|
header: "Backbone",
|
||||||
|
accessorKey: "backbone",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device Start",
|
||||||
|
accessorKey: "device_start",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device End",
|
||||||
|
accessorKey: "device_end",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Total Core",
|
||||||
|
accessorKey: "total_core",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Total Fishbone",
|
||||||
|
accessorKey: "total_fishbone",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "",
|
||||||
|
accessorKey: "action",
|
||||||
|
enableSorting: false,
|
||||||
|
cell: () => (
|
||||||
|
<>
|
||||||
|
<IconButton variant="light" color="info">
|
||||||
|
<Edit variant="Bulk" color="currentColor" />
|
||||||
|
</IconButton>
|
||||||
|
</>
|
||||||
|
),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Box component="main">
|
<Box component="main">
|
||||||
<Grid container spacing={2} alignItems={"center"} mb={4}>
|
<Grid container spacing={2} alignItems={"center"} mb={4}>
|
||||||
|
|
@ -33,16 +86,12 @@ export default function Backbone() {
|
||||||
|
|
||||||
<Card sx={{ display: "flex" }}>
|
<Card sx={{ display: "flex" }}>
|
||||||
<CardContent sx={{ flex: "1 0 auto" }}>
|
<CardContent sx={{ flex: "1 0 auto" }}>
|
||||||
<Typography component="div" variant="h5">
|
<ReactTable
|
||||||
Live From Space
|
data={data}
|
||||||
</Typography>
|
columns={columns}
|
||||||
<Typography
|
// striped={true}
|
||||||
variant="subtitle1"
|
title="Users Table"
|
||||||
component="div"
|
/>
|
||||||
sx={{ color: "text.secondary" }}
|
|
||||||
>
|
|
||||||
Mac Miller
|
|
||||||
</Typography>
|
|
||||||
</CardContent>
|
</CardContent>
|
||||||
</Card>
|
</Card>
|
||||||
</Box>
|
</Box>
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,111 @@
|
||||||
|
import Box from "@mui/material/Box";
|
||||||
|
import Breadcrumbs from "@mui/material/Breadcrumbs";
|
||||||
|
import Button from "@mui/material/Button";
|
||||||
|
import Card from "@mui/material/Card";
|
||||||
|
import CardContent from "@mui/material/CardContent";
|
||||||
|
import Link from "@mui/material/Link";
|
||||||
|
import Grid from "@mui/material/Grid2";
|
||||||
|
import Typography from "@mui/material/Typography";
|
||||||
|
import AddIcon from "@mui/icons-material/Add";
|
||||||
|
import { Home } from "@mui/icons-material";
|
||||||
|
import ReactTable from "../components/ReactTable";
|
||||||
|
import { ColumnDef } from "@tanstack/react-table";
|
||||||
|
import IconButton from "../components/IconButton";
|
||||||
|
import { Edit } from "iconsax-react";
|
||||||
|
|
||||||
|
interface UserData {
|
||||||
|
device_code: string;
|
||||||
|
device_type: string;
|
||||||
|
address: string;
|
||||||
|
port_amount: string;
|
||||||
|
status: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function Devices() {
|
||||||
|
const data: UserData[] = [
|
||||||
|
{ device_code: 'DV-CODE-1', device_type: "OTB", address: "Jl. Contoh 1", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-2', device_type: "OTB", address: "Jl. Contoh 2", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-3', device_type: "OTB", address: "Jl. Contoh 3", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-4', device_type: "OTB", address: "Jl. Contoh 4", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-5', device_type: "OTB", address: "Jl. Contoh 5", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-6', device_type: "OTB", address: "Jl. Contoh 6", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-7', device_type: "OTB", address: "Jl. Contoh 7", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-8', device_type: "OTB", address: "Jl. Contoh 8", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-9', device_type: "OTB", address: "Jl. Contoh 9", port_amount: '16', status: "Active" },
|
||||||
|
{ device_code: 'DV-CODE-10', device_type: "OTB", address: "Jl. Contoh 10", port_amount: '16', status: "Active" },
|
||||||
|
];
|
||||||
|
|
||||||
|
// Define columns
|
||||||
|
const columns: ColumnDef<UserData>[] = [
|
||||||
|
{
|
||||||
|
header: "Device Code",
|
||||||
|
accessorKey: "device_code",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device Type",
|
||||||
|
accessorKey: "device_type",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Address",
|
||||||
|
accessorKey: "address",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Total Port",
|
||||||
|
accessorKey: "port_amount",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Status",
|
||||||
|
accessorKey: "status",
|
||||||
|
cell: ({ row }) => (
|
||||||
|
<Typography color={row.original.status === "Active" ? "success.main" : "error.main"}>
|
||||||
|
{row.original.status}
|
||||||
|
</Typography>
|
||||||
|
)
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: '',
|
||||||
|
accessorKey: "action",
|
||||||
|
enableSorting: false,
|
||||||
|
cell: () => (
|
||||||
|
<>
|
||||||
|
<IconButton variant="light" color="info" >
|
||||||
|
<Edit variant="Bulk" color="currentColor" />
|
||||||
|
</IconButton>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box component="main">
|
||||||
|
<Grid container spacing={2} alignItems={"center"} mb={4}>
|
||||||
|
<Grid size="grow">
|
||||||
|
<Typography variant="h3">Devices</Typography>
|
||||||
|
</Grid>
|
||||||
|
<Grid size="auto">
|
||||||
|
<Button variant="contained" startIcon={<AddIcon color="inherit" />}>
|
||||||
|
Add New
|
||||||
|
</Button>
|
||||||
|
</Grid>
|
||||||
|
<Grid size={12}>
|
||||||
|
<Breadcrumbs aria-label="breadcrumb">
|
||||||
|
<Link underline="hover" color="inherit" href="/dashboard">
|
||||||
|
<Home />
|
||||||
|
</Link>
|
||||||
|
<Typography sx={{ color: "text.primary" }}>Devices</Typography>
|
||||||
|
</Breadcrumbs>
|
||||||
|
</Grid>
|
||||||
|
</Grid>
|
||||||
|
|
||||||
|
<Card sx={{ display: "flex" }}>
|
||||||
|
<CardContent sx={{ flex: "1 0 auto" }}>
|
||||||
|
<ReactTable
|
||||||
|
data={data}
|
||||||
|
columns={columns}
|
||||||
|
// striped={true}
|
||||||
|
/>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,93 @@
|
||||||
|
import Box from "@mui/material/Box";
|
||||||
|
import Breadcrumbs from "@mui/material/Breadcrumbs";
|
||||||
|
import Button from "@mui/material/Button";
|
||||||
|
import Card from "@mui/material/Card";
|
||||||
|
import CardContent from "@mui/material/CardContent";
|
||||||
|
import Link from "@mui/material/Link";
|
||||||
|
import Grid from "@mui/material/Grid2";
|
||||||
|
import Typography from "@mui/material/Typography";
|
||||||
|
import AddIcon from "@mui/icons-material/Add";
|
||||||
|
import { Home } from "@mui/icons-material";
|
||||||
|
import ReactTable from "../components/ReactTable";
|
||||||
|
import { ColumnDef } from "@tanstack/react-table";
|
||||||
|
import IconButton from "../components/IconButton";
|
||||||
|
import { Edit } from "iconsax-react";
|
||||||
|
|
||||||
|
interface UserData {
|
||||||
|
backbone: string;
|
||||||
|
device_start: string;
|
||||||
|
device_end: string;
|
||||||
|
total_core: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function Fishbone() {
|
||||||
|
const data: UserData[] = [
|
||||||
|
{ backbone: 'BB-BDG-SMD', device_start: "DV-CODE-1", device_end: "DV-CODE-2", total_core: '24 Core', },
|
||||||
|
{ backbone: 'BB-BDG-SBG', device_start: "DV-CODE-3", device_end: "DV-CODE-4", total_core: '24 Core', },
|
||||||
|
];
|
||||||
|
|
||||||
|
// Define columns
|
||||||
|
const columns: ColumnDef<UserData>[] = [
|
||||||
|
{
|
||||||
|
header: "Backbone",
|
||||||
|
accessorKey: "backbone",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device Start",
|
||||||
|
accessorKey: "device_start",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device End",
|
||||||
|
accessorKey: "device_end",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Total Core",
|
||||||
|
accessorKey: "total_core",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: '',
|
||||||
|
accessorKey: "action",
|
||||||
|
enableSorting: false,
|
||||||
|
cell: () => (
|
||||||
|
<>
|
||||||
|
<IconButton variant="light" color="info" >
|
||||||
|
<Edit variant="Bulk" color="currentColor" />
|
||||||
|
</IconButton>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box component="main">
|
||||||
|
<Grid container spacing={2} alignItems={"center"} mb={4}>
|
||||||
|
<Grid size="grow">
|
||||||
|
<Typography variant="h3">Fishbone</Typography>
|
||||||
|
</Grid>
|
||||||
|
<Grid size="auto">
|
||||||
|
<Button variant="contained" startIcon={<AddIcon color="inherit" />}>
|
||||||
|
Add New
|
||||||
|
</Button>
|
||||||
|
</Grid>
|
||||||
|
<Grid size={12}>
|
||||||
|
<Breadcrumbs aria-label="breadcrumb">
|
||||||
|
<Link underline="hover" color="inherit" href="/dashboard">
|
||||||
|
<Home />
|
||||||
|
</Link>
|
||||||
|
<Typography sx={{ color: "text.primary" }}>Fishbone</Typography>
|
||||||
|
</Breadcrumbs>
|
||||||
|
</Grid>
|
||||||
|
</Grid>
|
||||||
|
|
||||||
|
<Card sx={{ display: "flex" }}>
|
||||||
|
<CardContent sx={{ flex: "1 0 auto" }}>
|
||||||
|
<ReactTable
|
||||||
|
data={data}
|
||||||
|
columns={columns}
|
||||||
|
// striped={true}
|
||||||
|
/>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,96 @@
|
||||||
|
import Box from "@mui/material/Box";
|
||||||
|
import Breadcrumbs from "@mui/material/Breadcrumbs";
|
||||||
|
import Button from "@mui/material/Button";
|
||||||
|
import Card from "@mui/material/Card";
|
||||||
|
import CardContent from "@mui/material/CardContent";
|
||||||
|
import Link from "@mui/material/Link";
|
||||||
|
import Grid from "@mui/material/Grid2";
|
||||||
|
import Typography from "@mui/material/Typography";
|
||||||
|
import AddIcon from "@mui/icons-material/Add";
|
||||||
|
import { Home } from "@mui/icons-material";
|
||||||
|
import ReactTable from "../components/ReactTable";
|
||||||
|
import { ColumnDef } from "@tanstack/react-table";
|
||||||
|
import IconButton from "../components/IconButton";
|
||||||
|
import { Edit } from "iconsax-react";
|
||||||
|
|
||||||
|
interface UserData {
|
||||||
|
tower_code: string;
|
||||||
|
device: string;
|
||||||
|
address: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function Towers() {
|
||||||
|
const data: UserData[] = [
|
||||||
|
{ tower_code: 'TW-CODE-1', device: "DV-CODE-1", address: "Jl. Contoh 1" },
|
||||||
|
{ tower_code: 'TW-CODE-2', device: "DV-CODE-2", address: "Jl. Contoh 2" },
|
||||||
|
{ tower_code: 'TW-CODE-3', device: "", address: "Jl. Contoh 3" },
|
||||||
|
{ tower_code: 'TW-CODE-4', device: "", address: "Jl. Contoh 4" },
|
||||||
|
{ tower_code: 'TW-CODE-5', device: "DV-CODE-5", address: "Jl. Contoh 5" },
|
||||||
|
{ tower_code: 'TW-CODE-6', device: "", address: "Jl. Contoh 6" },
|
||||||
|
{ tower_code: 'TW-CODE-7', device: "", address: "Jl. Contoh 7" },
|
||||||
|
{ tower_code: 'TW-CODE-8', device: "DV-CODE-8", address: "Jl. Contoh 8" },
|
||||||
|
{ tower_code: 'TW-CODE-9', device: "", address: "Jl. Contoh 9" },
|
||||||
|
{ tower_code: 'TW-CODE-10', device: "DV-CODE-10", address: "Jl. Contoh 10" },
|
||||||
|
];
|
||||||
|
|
||||||
|
// Define columns
|
||||||
|
const columns: ColumnDef<UserData>[] = [
|
||||||
|
{
|
||||||
|
header: "Tower Code",
|
||||||
|
accessorKey: "tower_code",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Device",
|
||||||
|
accessorKey: "device",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: "Address",
|
||||||
|
accessorKey: "address",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
header: '',
|
||||||
|
accessorKey: "action",
|
||||||
|
enableSorting: false,
|
||||||
|
cell: () => (
|
||||||
|
<>
|
||||||
|
<IconButton variant="light" color="info" >
|
||||||
|
<Edit variant="Bulk" color="currentColor" />
|
||||||
|
</IconButton>
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box component="main">
|
||||||
|
<Grid container spacing={2} alignItems={"center"} mb={4}>
|
||||||
|
<Grid size="grow">
|
||||||
|
<Typography variant="h3">Towers</Typography>
|
||||||
|
</Grid>
|
||||||
|
<Grid size="auto">
|
||||||
|
<Button variant="contained" startIcon={<AddIcon color="inherit" />}>
|
||||||
|
Add New
|
||||||
|
</Button>
|
||||||
|
</Grid>
|
||||||
|
<Grid size={12}>
|
||||||
|
<Breadcrumbs aria-label="breadcrumb">
|
||||||
|
<Link underline="hover" color="inherit" href="/dashboard">
|
||||||
|
<Home />
|
||||||
|
</Link>
|
||||||
|
<Typography sx={{ color: "text.primary" }}>Towers</Typography>
|
||||||
|
</Breadcrumbs>
|
||||||
|
</Grid>
|
||||||
|
</Grid>
|
||||||
|
|
||||||
|
<Card sx={{ display: "flex" }}>
|
||||||
|
<CardContent sx={{ flex: "1 0 auto" }}>
|
||||||
|
<ReactTable
|
||||||
|
data={data}
|
||||||
|
columns={columns}
|
||||||
|
// striped={true}
|
||||||
|
/>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -5,6 +5,9 @@ import Login from "../pages/auth/Login";
|
||||||
import Dashboard from "../pages/Dashboard";
|
import Dashboard from "../pages/Dashboard";
|
||||||
import DashboardLayout from "../layouts/DashboardLayout";
|
import DashboardLayout from "../layouts/DashboardLayout";
|
||||||
import Backbone from "../pages/Backbone";
|
import Backbone from "../pages/Backbone";
|
||||||
|
import Devices from "../pages/Devices";
|
||||||
|
import Fishbone from "../pages/Fishbone";
|
||||||
|
import Towers from "../pages/Towers";
|
||||||
|
|
||||||
export default function Routes() {
|
export default function Routes() {
|
||||||
return (
|
return (
|
||||||
|
|
@ -14,6 +17,9 @@ export default function Routes() {
|
||||||
<Route element={<DashboardLayout />}>
|
<Route element={<DashboardLayout />}>
|
||||||
<Route path="/dashboard" element={<Dashboard />} />
|
<Route path="/dashboard" element={<Dashboard />} />
|
||||||
<Route path="/backbone" element={<Backbone />} />
|
<Route path="/backbone" element={<Backbone />} />
|
||||||
|
<Route path="/fishbone" element={<Fishbone />} />
|
||||||
|
<Route path="/devices" element={<Devices />} />
|
||||||
|
<Route path="/towers" element={<Towers />} />
|
||||||
</Route>
|
</Route>
|
||||||
{/* Auth routes */}
|
{/* Auth routes */}
|
||||||
<Route element={<AuthLayout />}>
|
<Route element={<AuthLayout />}>
|
||||||
|
|
|
||||||
|
|
@ -48,8 +48,8 @@ const Palette = (mode: ThemeMode) => {
|
||||||
900: "#4e5161",
|
900: "#4e5161",
|
||||||
},
|
},
|
||||||
error: {
|
error: {
|
||||||
lighter: "#fef3f2",
|
lighter: "#ffe3e1",
|
||||||
light: "#ffe3e1",
|
light: "#ffccc8",
|
||||||
main: "#f44334",
|
main: "#f44334",
|
||||||
dark: "#e22f20",
|
dark: "#e22f20",
|
||||||
darker: "#be2417",
|
darker: "#be2417",
|
||||||
|
|
@ -65,8 +65,8 @@ const Palette = (mode: ThemeMode) => {
|
||||||
'900': '#82221a',
|
'900': '#82221a',
|
||||||
},
|
},
|
||||||
warning: {
|
warning: {
|
||||||
lighter: "#fffbec",
|
lighter: "#fff6d3",
|
||||||
light: "#ffd96d",
|
light: "#ffeaa5",
|
||||||
main: "#fb8c00",
|
main: "#fb8c00",
|
||||||
dark: "#cc6902",
|
dark: "#cc6902",
|
||||||
darker: "#a1500b",
|
darker: "#a1500b",
|
||||||
|
|
@ -82,7 +82,7 @@ const Palette = (mode: ThemeMode) => {
|
||||||
'900': '#82430c'
|
'900': '#82430c'
|
||||||
},
|
},
|
||||||
info: {
|
info: {
|
||||||
lighter: "#ecfdff",
|
lighter: "#d0f6fd",
|
||||||
light: "#a7edfa",
|
light: "#a7edfa",
|
||||||
main: "#16c0e8",
|
main: "#16c0e8",
|
||||||
dark: "#106c8e",
|
dark: "#106c8e",
|
||||||
|
|
@ -99,8 +99,8 @@ const Palette = (mode: ThemeMode) => {
|
||||||
'900': '#174962',
|
'900': '#174962',
|
||||||
},
|
},
|
||||||
success: {
|
success: {
|
||||||
lighter: "#f3faf3",
|
lighter: "#e3f5e3",
|
||||||
light: "#e3f5e3",
|
light: "#c8eac9",
|
||||||
main: "#4caf50",
|
main: "#4caf50",
|
||||||
dark: "#358438",
|
dark: "#358438",
|
||||||
darker: "#2d6830",
|
darker: "#2d6830",
|
||||||
|
|
@ -136,7 +136,7 @@ const Palette = (mode: ThemeMode) => {
|
||||||
divider: mode === ThemeMode.DARK ? alpha(paletteColor.secondary.darker!, 0.05) : alpha(paletteColor.secondary.light!, 0.65),
|
divider: mode === ThemeMode.DARK ? alpha(paletteColor.secondary.darker!, 0.05) : alpha(paletteColor.secondary.light!, 0.65),
|
||||||
background: {
|
background: {
|
||||||
paper: mode === ThemeMode.DARK ? paletteColor.secondary[100] : '#fff',
|
paper: mode === ThemeMode.DARK ? paletteColor.secondary[100] : '#fff',
|
||||||
default: mode !== ThemeMode.DARK ? '#fff' : paletteColor.secondary.lighter
|
default: mode !== ThemeMode.DARK ? '#fff' : paletteColor.secondary[900]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue