├── jsconfig.json ├── next.config.js ├── postcss.config.js ├── src ├── app │ ├── favicon.ico │ ├── page.js │ ├── globals.css │ ├── layout.js │ ├── charts │ │ └── page.js │ ├── reports │ │ └── page.js │ ├── tasks │ │ └── page.js │ ├── kanban │ │ └── page.js │ └── dashboard │ │ └── page.js ├── theme-provider │ └── index.js ├── components │ ├── card │ │ └── index.js │ ├── charts │ │ ├── chart-layout.js │ │ └── chart-card.js │ ├── widget │ │ └── index.js │ ├── common-layout │ │ └── index.js │ ├── kanban │ │ └── index.js │ ├── header │ │ └── index.js │ ├── sidebar │ │ └── index.js │ └── modal │ │ └── index.js ├── utils │ ├── index.js │ └── chart-data.js └── context │ └── index.js ├── .gitignore ├── public ├── vercel.svg └── next.svg ├── package.json ├── README.md └── tailwind.config.js /jsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "paths": { 4 | "@/*": ["./src/*"] 5 | } 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /next.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('next').NextConfig} */ 2 | const nextConfig = {} 3 | 4 | module.exports = nextConfig 5 | -------------------------------------------------------------------------------- /postcss.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | plugins: { 3 | tailwindcss: {}, 4 | autoprefixer: {}, 5 | }, 6 | } 7 | -------------------------------------------------------------------------------- /src/app/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/sangammukherjee/react-next-admin-dashboard-2023/HEAD/src/app/favicon.ico -------------------------------------------------------------------------------- /src/app/page.js: -------------------------------------------------------------------------------- 1 | import Image from 'next/image' 2 | 3 | export default function Home() { 4 | return ( 5 |
6 | Dashboard page 7 |
8 | ) 9 | } 10 | -------------------------------------------------------------------------------- /src/theme-provider/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { ThemeProvider } from "next-themes"; 4 | import * as React from "react"; 5 | 6 | export default function NextThemeProvider({ children }) { 7 | return ( 8 | 9 | {children} 10 | 11 | ); 12 | } 13 | -------------------------------------------------------------------------------- /src/components/card/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | export default function Card({ children, addtionalStyles }) { 4 | return ( 5 |
8 | {children} 9 |
10 | ); 11 | } 12 | -------------------------------------------------------------------------------- /src/app/globals.css: -------------------------------------------------------------------------------- 1 | @tailwind base; 2 | @tailwind components; 3 | @tailwind utilities; 4 | 5 | :root { 6 | --foreground-rgb: 0, 0, 0; 7 | --background-start-rgb: 214, 219, 220; 8 | --background-end-rgb: 255, 255, 255; 9 | } 10 | 11 | @media (prefers-color-scheme: dark) { 12 | :root { 13 | --foreground-rgb: 255, 255, 255; 14 | --background-start-rgb: 0, 0, 0; 15 | --background-end-rgb: 0, 0, 0; 16 | } 17 | } 18 | 19 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # next.js 12 | /.next/ 13 | /out/ 14 | 15 | # production 16 | /build 17 | 18 | # misc 19 | .DS_Store 20 | *.pem 21 | 22 | # debug 23 | npm-debug.log* 24 | yarn-debug.log* 25 | yarn-error.log* 26 | 27 | # local env files 28 | .env*.local 29 | 30 | # vercel 31 | .vercel 32 | 33 | # typescript 34 | *.tsbuildinfo 35 | next-env.d.ts 36 | -------------------------------------------------------------------------------- /public/vercel.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/components/charts/chart-layout.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { useEffect, useState } from "react"; 4 | import Chart from "react-apexcharts"; 5 | 6 | export default function ChartLayout({ chartData, chartOptions, type }) { 7 | const [updateChartData, setUpdateChartData] = useState([]); 8 | const [updateChartOptions, setUpdateChartOptions] = useState({}); 9 | 10 | useEffect(() => { 11 | setUpdateChartOptions(chartOptions); 12 | setUpdateChartData(chartData); 13 | }, []); 14 | 15 | return ( 16 | 23 | ); 24 | } 25 | -------------------------------------------------------------------------------- /src/app/layout.js: -------------------------------------------------------------------------------- 1 | import { Inter } from "next/font/google"; 2 | import "./globals.css"; 3 | import GlobalState from "@/context"; 4 | import NextThemeProvider from "@/theme-provider"; 5 | import CommonLayout from "@/components/common-layout"; 6 | 7 | const inter = Inter({ subsets: ["latin"] }); 8 | 9 | export const metadata = { 10 | title: "Create Next App", 11 | description: "Generated by create next app", 12 | }; 13 | 14 | export default function RootLayout({ children }) { 15 | return ( 16 | 17 | 18 | 19 | 20 | {children} 21 | 22 | 23 | 24 | 25 | ); 26 | } 27 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "11.admin-dashboard", 3 | "version": "0.1.0", 4 | "private": true, 5 | "scripts": { 6 | "dev": "next dev", 7 | "build": "next build", 8 | "start": "next start", 9 | "lint": "next lint" 10 | }, 11 | "dependencies": { 12 | "@dnd-kit/core": "^6.0.8", 13 | "@emotion/react": "^11.11.1", 14 | "@emotion/styled": "^11.11.0", 15 | "@mui/material": "^5.14.14", 16 | "@mui/x-data-grid": "^6.16.2", 17 | "next": "13.5.6", 18 | "next-themes": "^0.2.1", 19 | "react": "^18", 20 | "react-apexcharts": "^1.4.1", 21 | "react-dom": "^18", 22 | "react-icons": "^4.11.0", 23 | "tailwindcss-rtl": "^0.9.0" 24 | }, 25 | "devDependencies": { 26 | "autoprefixer": "^10", 27 | "postcss": "^8", 28 | "tailwindcss": "^3" 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/utils/index.js: -------------------------------------------------------------------------------- 1 | import { 2 | MdHome, 3 | MdOutlineShoppingCart, 4 | MdTask, 5 | MdStackedBarChart, 6 | MdViewKanban, 7 | } from "react-icons/md"; 8 | 9 | export const routes = [ 10 | { 11 | name: "Dashboard", 12 | layout: "/dashboard", 13 | icon: , 14 | }, 15 | 16 | { 17 | name: "Reports", 18 | layout: "/reports", 19 | icon: , 20 | }, 21 | { 22 | name: "Tasks", 23 | layout: "/tasks", 24 | icon: , 25 | }, 26 | { 27 | name: "Kanban", 28 | layout: "/kanban", 29 | icon: , 30 | }, 31 | { 32 | name: "Charts", 33 | layout: "/charts", 34 | icon: , 35 | }, 36 | ]; 37 | -------------------------------------------------------------------------------- /src/components/widget/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import Card from "../card"; 4 | 5 | export default function Widget({ icon, title, subtitle }) { 6 | return ( 7 | 12 |
13 |
14 | {icon} 15 |
16 |
17 |
18 |

{title}

19 |

20 | {subtitle} 21 |

22 |
23 |
24 | ); 25 | } 26 | -------------------------------------------------------------------------------- /src/components/common-layout/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { usePathname } from "next/navigation"; 4 | import Header from "../header"; 5 | import Sidebar from "../sidebar"; 6 | import Dashboard from "@/app/dashboard/page"; 7 | 8 | export default function CommonLayout({ children }) { 9 | const pathName = usePathname(); 10 | 11 | return ( 12 |
13 | 14 |
15 |
16 |
17 |
18 |
19 | {pathName === "/" ? : children} 20 |
21 |
22 |
23 |
24 |
25 | ); 26 | } 27 | -------------------------------------------------------------------------------- /src/components/charts/chart-card.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import Card from "../card"; 4 | import { MdBarChart } from "react-icons/md"; 5 | import ChartLayout from "./chart-layout"; 6 | 7 | export default function ChartCard({ type, title, chartData, chartOptions }) { 8 | return ( 9 | 14 |
15 |

16 | {title} 17 |

18 | 21 |
22 |
26 |
27 | 32 |
33 |
34 |
35 | ); 36 | } 37 | -------------------------------------------------------------------------------- /public/next.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app). 2 | 3 | ## Getting Started 4 | 5 | First, run the development server: 6 | 7 | ```bash 8 | npm run dev 9 | # or 10 | yarn dev 11 | # or 12 | pnpm dev 13 | # or 14 | bun dev 15 | ``` 16 | 17 | Open [http://localhost:3000](http://localhost:3000) with your browser to see the result. 18 | 19 | You can start editing the page by modifying `app/page.js`. The page auto-updates as you edit the file. 20 | 21 | This project uses [`next/font`](https://nextjs.org/docs/basic-features/font-optimization) to automatically optimize and load Inter, a custom Google Font. 22 | 23 | ## Learn More 24 | 25 | To learn more about Next.js, take a look at the following resources: 26 | 27 | - [Next.js Documentation](https://nextjs.org/docs) - learn about Next.js features and API. 28 | - [Learn Next.js](https://nextjs.org/learn) - an interactive Next.js tutorial. 29 | 30 | You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js/) - your feedback and contributions are welcome! 31 | 32 | ## Deploy on Vercel 33 | 34 | The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js. 35 | 36 | Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details. 37 | -------------------------------------------------------------------------------- /src/components/kanban/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { useDraggable, useDroppable } from "@dnd-kit/core"; 4 | import { CSS } from "@dnd-kit/utilities"; 5 | 6 | function KanbanItem({ item, index, parent }) { 7 | const { attributes, listeners, setNodeRef, transform } = useDraggable({ 8 | id: item.title, 9 | data: { 10 | title: item.title, 11 | index, 12 | parent, 13 | }, 14 | }); 15 | 16 | const setStyle = { 17 | transform: CSS.Translate.toString(transform), 18 | }; 19 | 20 | return ( 21 |
28 |

{item.title}

29 |
30 | ); 31 | } 32 | 33 | export default function KanbanCard({ title, tasks }) { 34 | const { setNodeRef } = useDroppable({ 35 | id: title, 36 | }); 37 | 38 | return ( 39 |
40 |

{title}

41 |
42 | {tasks && tasks.length > 0 43 | ? tasks.map((task, index) => ( 44 | 45 | )) 46 | : null} 47 |
48 |
49 | ); 50 | } 51 | -------------------------------------------------------------------------------- /src/components/header/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | import { GlobalContext } from "@/context"; 3 | import { useTheme } from "next-themes"; 4 | import { usePathname } from "next/navigation"; 5 | import { useContext } from "react"; 6 | import { FiAlignJustify } from "react-icons/fi"; 7 | import { RiSunFill, RiMoonFill } from "react-icons/ri"; 8 | 9 | export default function Header() { 10 | const { theme, setTheme } = useTheme(); 11 | const { setOpenSidebar, openSidebar } = useContext(GlobalContext); 12 | const pathName = usePathname(); 13 | 14 | return ( 15 | 40 | ); 41 | } 42 | -------------------------------------------------------------------------------- /src/components/sidebar/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { GlobalContext } from "@/context"; 4 | import { routes } from "@/utils"; 5 | import Link from "next/link"; 6 | import { useContext } from "react"; 7 | import { HiX } from "react-icons/hi"; 8 | 9 | export default function Sidebar() { 10 | const { openSidebar, setOpenSidebar } = useContext(GlobalContext); 11 | 12 | return ( 13 |
18 | setOpenSidebar(false)} 20 | className="absolute right-4 top-4 block cursor-pointer xl:hidden" 21 | > 22 | 23 | 24 |
25 |
26 | ADMIN DASHBOARD 27 |
28 |
29 |
    30 | {routes.map((routeItem, index) => ( 31 | 32 |
    33 |
  • 34 | 35 | {routeItem.icon} 36 | 37 |

    38 | {routeItem.name} 39 |

    40 |
  • 41 |
    42 | 43 | ))} 44 |
45 |
46 | ); 47 | } 48 | -------------------------------------------------------------------------------- /src/app/charts/page.js: -------------------------------------------------------------------------------- 1 | 'use client' 2 | 3 | import ChartCard from "@/components/charts/chart-card"; 4 | import { 5 | areaChartData, 6 | areaChartDataOptions, 7 | barChartDataCategoryOne, 8 | barChartDataCategoryTwo, 9 | barChartOptionsCategoryOne, 10 | barChartOptionsCategoryTwo, 11 | lineChartData, 12 | lineChartOptions, 13 | mixedChartData, 14 | mixedChartDataOptions, 15 | pieChartData, 16 | pieChartOptions, 17 | } from "@/utils/chart-data"; 18 | 19 | export default function Charts() { 20 | return ( 21 |
22 |
23 | 29 | 35 |
36 |
37 | 43 | 49 |
50 |
51 | 57 | 63 |
64 |
65 | ); 66 | } 67 | -------------------------------------------------------------------------------- /src/context/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { createContext, useEffect, useState } from "react"; 4 | 5 | export const GlobalContext = createContext(null); 6 | 7 | export const initialReportFormData = { 8 | name: "", 9 | visitors: 0, 10 | sales: 0, 11 | revenue: 0, 12 | task: "", 13 | }; 14 | 15 | export default function GlobalState({ children }) { 16 | const [openSidebar, setOpenSidebar] = useState(false); 17 | const [allTasks, setAllTasks] = useState([]); 18 | const [unassignedItems, setUnassignedItems] = useState([]); 19 | const [todoItems, setTodoItems] = useState([]); 20 | const [inprogressItems, setInprogressItems] = useState([]); 21 | const [doneItems, setDoneItems] = useState([]); 22 | const [newTask, setNewTask] = useState(""); 23 | const [reportFormData, setReportFormData] = useState(initialReportFormData); 24 | const [allReportsData, setAllReportsData] = useState([]); 25 | 26 | useEffect(() => { 27 | setAllTasks(JSON.parse(localStorage.getItem("allTasks")) || []); 28 | setUnassignedItems( 29 | JSON.parse(localStorage.getItem("unassignedItems")) || [] 30 | ); 31 | setDoneItems(JSON.parse(localStorage.getItem("doneItems")) || []); 32 | setInprogressItems( 33 | JSON.parse(localStorage.getItem("inprogressItems")) || [] 34 | ); 35 | setTodoItems(JSON.parse(localStorage.getItem("todoItems")) || []); 36 | setAllReportsData(JSON.parse(localStorage.getItem("allReportsData")) || []); 37 | }, []); 38 | 39 | return ( 40 | 62 | {children} 63 | 64 | ); 65 | } 66 | -------------------------------------------------------------------------------- /src/app/reports/page.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import Card from "@/components/card"; 4 | import CommonModal from "@/components/modal"; 5 | import { GlobalContext } from "@/context"; 6 | import { useContext } from "react"; 7 | 8 | export default function Reports() { 9 | const { allReportsData } = useContext(GlobalContext); 10 | 11 | const columns = ["name", "visitors", "sales", "revenue", "task"]; 12 | 13 | return ( 14 |
15 | 16 |
17 |
18 | Report Analytics 19 |
20 | 21 |
22 |
23 |
24 |
25 |
26 | 27 | 28 | 29 | {columns.map((col) => ( 30 | 33 | ))} 34 | 35 | 36 | 37 | {allReportsData && allReportsData.length 38 | ? allReportsData.map((dataItem) => ( 39 | 40 | 43 | 46 | 49 | 52 | 55 | 56 | )) 57 | : null} 58 | 59 |
31 | {col} 32 |
41 | {dataItem.name} 42 | 44 | {dataItem.visitors} 45 | 47 | {dataItem.sales} 48 | 50 | {dataItem.revenue} 51 | 53 | {dataItem.task} 54 |
60 |
61 |
62 |
63 |
64 |
65 |
66 | ); 67 | } 68 | -------------------------------------------------------------------------------- /tailwind.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('tailwindcss').Config} */ 2 | module.exports = { 3 | darkMode: "class", 4 | mode: "jit", 5 | content: [ 6 | "./app/**/*.{js,ts,jsx,tsx,mdx}", 7 | "./components/**/*.{js,ts,jsx,tsx,mdx}", 8 | "./src/**/*.{js,ts,jsx,tsx,mdx}", 9 | ], 10 | theme: { 11 | extend: { 12 | fontFamily: { 13 | poppins: ["Poppins", "sans-serif"], 14 | dm: ["DM Sans", "sans-serif"], 15 | }, 16 | boxShadow: { 17 | "3xl": "14px 17px 40px 4px", 18 | inset: "inset 0px 18px 22px", 19 | darkinset: "0px 4px 4px inset", 20 | }, 21 | backgroundImage: { 22 | customBg: "linear-gradient(to bottom, #FFC46B, #FF9B05)", 23 | }, 24 | }, 25 | screens: { 26 | sm: "576px", 27 | "sm-max": { max: "576px" }, 28 | md: "768px", 29 | "md-max": { max: "768px" }, 30 | lg: "992px", 31 | "lg-max": { max: "992px" }, 32 | xl: "1200px", 33 | "xl-max": { max: "1200px" }, 34 | "2xl": "1320px", 35 | "2xl-max": { max: "1320px" }, 36 | "3xl": "1600px", 37 | "3xl-max": { max: "1600px" }, 38 | "4xl": "1850px", 39 | "4xl-max": { max: "1850px" }, 40 | }, 41 | colors: { 42 | white: "#ffffff", 43 | lightPrimary: "#F4F7FE", 44 | blueSecondary: "#4318FF", 45 | brandLinear: "#868CFF", 46 | gray: { 47 | 50: "#F5F6FA", 48 | 100: "#EEF0F6", 49 | 200: "#DADEEC", 50 | 300: "#C9D0E3", 51 | 400: "#B0BBD5", 52 | 500: "#B5BED9", 53 | 600: "#A3AED0", 54 | 700: "#707eae", 55 | 800: "#2D396B", 56 | 900: "#1B2559", 57 | }, 58 | navy: { 59 | 50: "#d0dcfb", 60 | 100: "#aac0fe", 61 | 200: "#a3b9f8", 62 | 300: "#728fea", 63 | 400: "#3652ba", 64 | 500: "#1b3bbb", 65 | 600: "#24388a", 66 | 700: "#1B254B", 67 | 800: "#111c44", 68 | 900: "#0b1437", 69 | }, 70 | yellow: { 71 | 50: "#fefce8", 72 | 100: "#fef9c3", 73 | 200: "#fef08a", 74 | 300: "#fde047", 75 | 400: "#fbcf33", 76 | 500: "#eab308", 77 | 600: "#ca8a04", 78 | 700: "#a16207", 79 | 800: "#854d0e", 80 | 900: "#713f12", 81 | }, 82 | blue: { 83 | 50: "#eff6ff", 84 | 100: "#dbeafe", 85 | 200: "#bfdbfe", 86 | 300: "#93c5fd", 87 | 400: "#60a5fa", 88 | 500: "#3b82f6", 89 | 600: "#2152ff", 90 | 700: "#1d4ed8", 91 | 800: "#344e86", 92 | 900: "#00007d", 93 | }, 94 | background: { 95 | 100: "rgb(244 247 254)", 96 | 900: "#070f2e", 97 | }, 98 | brand: { 99 | 500: "#422AFB", 100 | }, 101 | shadow: { 102 | 100: "var(--shadow-100)", 103 | 500: "rgba(112, 144, 176, 0.08)", 104 | }, 105 | }, 106 | }, 107 | plugins: [require("tailwindcss-rtl")], 108 | }; 109 | -------------------------------------------------------------------------------- /src/app/tasks/page.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import Card from "@/components/card"; 4 | import { MdCheckCircle } from "react-icons/md"; 5 | import { FiPlus } from "react-icons/fi"; 6 | import { useContext } from "react"; 7 | import { GlobalContext } from "@/context"; 8 | 9 | export default function Tasks() { 10 | const { 11 | allTasks, 12 | setAllTasks, 13 | newTask, 14 | setNewTask, 15 | unassignedItems, 16 | setUnassignedItems, 17 | } = useContext(GlobalContext); 18 | 19 | function handleAddNewTask(getCurrentTask) { 20 | setAllTasks([...allTasks, { title: getCurrentTask }]); 21 | setUnassignedItems([...unassignedItems, { title: getCurrentTask }]); 22 | localStorage.setItem( 23 | "allTasks", 24 | JSON.stringify([...allTasks, { title: getCurrentTask }]) 25 | ); 26 | localStorage.setItem( 27 | "unassignedItems", 28 | JSON.stringify([...unassignedItems, { title: getCurrentTask }]) 29 | ); 30 | } 31 | 32 | console.log(allTasks); 33 | 34 | return ( 35 |
36 | 37 |
38 |
39 |
40 | 41 |
42 |

43 | Tasks 44 |

45 |
46 |
47 |
48 | setNewTask(e.target.value)} 53 | placeholder="Add New Task..." 54 | className="pl-3 block h-full w-full rounded-full bg-lightPrimary text-sm font-medium text-navy-700 outline-none placeholder:!text-gray-400 dark:bg-navy-900 dark:text-white dark:placeholder:!text-white sm:w-fit" 55 | /> 56 |
57 | { 59 | setNewTask(""); 60 | handleAddNewTask(newTask); 61 | }} 62 | className="h-6 w-6 cursor-pointer text-gray-400 dark:text-white" 63 | /> 64 |
65 |
66 |
67 | {allTasks && allTasks.length 68 | ? allTasks.map((task, index) => ( 69 |
73 |
74 |

75 | {task.title} 76 |

77 |
78 |
79 | )) 80 | : null} 81 |
82 |
83 |
84 | ); 85 | } 86 | -------------------------------------------------------------------------------- /src/app/kanban/page.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import KanbanCard from "@/components/kanban"; 4 | import { GlobalContext } from "@/context"; 5 | import { DndContext, rectIntersection } from "@dnd-kit/core"; 6 | import { useContext } from "react"; 7 | 8 | export default function Kanban() { 9 | const { 10 | unassignedItems, 11 | setUnassignedItems, 12 | todoItems, 13 | setTodoItems, 14 | inprogressItems, 15 | setInprogressItems, 16 | doneItems, 17 | setDoneItems, 18 | } = useContext(GlobalContext); 19 | 20 | return ( 21 | { 24 | const container = e.over?.id; 25 | const title = e.active.data.current?.title ?? ""; 26 | const index = e.active.data.current?.index ?? 0; 27 | const parent = e.active.data.current?.parent ?? "ToDo"; 28 | console.log(e.active.data.current, container); 29 | 30 | if (container === "ToDo") { 31 | setTodoItems([...todoItems, { title }]); 32 | localStorage.setItem('todoItems', JSON.stringify([...todoItems, { title }])) 33 | } else if (container === "Done") { 34 | setDoneItems([...doneItems, { title }]); 35 | localStorage.setItem('doneItems', JSON.stringify([...doneItems, { title }])) 36 | } else if (container === "Unassigned") { 37 | setUnassignedItems([...unassignedItems, { title }]); 38 | localStorage.setItem('unassignedItems', JSON.stringify([...unassignedItems, { title }])) 39 | } else { 40 | setInprogressItems([...inprogressItems, { title }]); 41 | localStorage.setItem('inprogressItems', JSON.stringify([...inprogressItems, { title }])) 42 | } 43 | 44 | if (parent === "ToDo") { 45 | setTodoItems([ 46 | ...todoItems.slice(0, index), 47 | ...todoItems.slice(index + 1), 48 | ]); 49 | localStorage.setItem('todoItems', JSON.stringify([ 50 | ...todoItems.slice(0, index), 51 | ...todoItems.slice(index + 1), 52 | ])) 53 | } else if (parent === "Done") { 54 | setDoneItems([ 55 | ...doneItems.slice(0, index), 56 | ...doneItems.slice(index + 1), 57 | ]); 58 | localStorage.setItem('doneItems', JSON.stringify([ 59 | ...doneItems.slice(0, index), 60 | ...doneItems.slice(index + 1), 61 | ])) 62 | } else if (parent === "Unassigned") { 63 | setUnassignedItems([ 64 | ...unassignedItems.slice(0, index), 65 | ...unassignedItems.slice(index + 1), 66 | ]); 67 | localStorage.setItem('unassignedItems', JSON.stringify([ 68 | ...unassignedItems.slice(0, index), 69 | ...unassignedItems.slice(index + 1), 70 | ])) 71 | } else { 72 | setInprogressItems([ 73 | ...inprogressItems.slice(0, index), 74 | ...inprogressItems.slice(index + 1), 75 | ]); 76 | localStorage.setItem('inprogressItems', JSON.stringify([ 77 | ...inprogressItems.slice(0, index), 78 | ...inprogressItems.slice(index + 1), 79 | ])) 80 | } 81 | }} 82 | > 83 |
84 | 85 | 86 | 87 | 88 |
89 |
90 | ); 91 | } 92 | -------------------------------------------------------------------------------- /src/app/dashboard/page.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { MdReport, MdTask } from "react-icons/md"; 4 | import { BiMoneyWithdraw } from "react-icons/bi"; 5 | import { BsFillPersonCheckFill } from "react-icons/bs"; 6 | import { FaMoneyBillWave } from "react-icons/fa"; 7 | import { LuFolderKanban } from "react-icons/lu"; 8 | import Widget from "@/components/widget"; 9 | import ChartCard from "@/components/charts/chart-card"; 10 | import { 11 | areaChartData, 12 | areaChartDataOptions, 13 | barChartDataCategoryOne, 14 | barChartDataCategoryTwo, 15 | barChartOptionsCategoryOne, 16 | barChartOptionsCategoryTwo, 17 | lineChartData, 18 | lineChartOptions, 19 | mixedChartData, 20 | mixedChartDataOptions, 21 | pieChartData, 22 | pieChartOptions, 23 | } from "@/utils/chart-data"; 24 | import Reports from "../reports/page"; 25 | import Tasks from "../tasks/page"; 26 | import Kanban from "../kanban/page"; 27 | import { useContext } from "react"; 28 | import { GlobalContext } from "@/context"; 29 | 30 | export default function Dashboard() { 31 | const { allReportsData, allTasks } = useContext(GlobalContext); 32 | 33 | const widgetData = [ 34 | { 35 | title: "Reports", 36 | subtitle: (allReportsData && allReportsData.length) || 0, 37 | icon: , 38 | }, 39 | { 40 | title: "Tasks", 41 | subtitle: (allTasks && allTasks.length) || 0, 42 | icon: , 43 | }, 44 | { 45 | title: "Sales", 46 | subtitle: 47 | allReportsData && allReportsData.length 48 | ? allReportsData.reduce( 49 | (curr, item) => curr + parseInt(item.sales), 50 | 0 51 | ) 52 | : 0, 53 | icon: , 54 | }, 55 | { 56 | title: "Visitors", 57 | subtitle: 58 | allReportsData && allReportsData.length 59 | ? allReportsData.reduce( 60 | (curr, item) => curr + parseInt(item.visitors), 61 | 0 62 | ) 63 | : 0, 64 | icon: , 65 | }, 66 | { 67 | title: "Revenue", 68 | subtitle: 69 | allReportsData && allReportsData.length 70 | ? allReportsData.reduce( 71 | (curr, item) => curr + parseInt(item.revenue), 72 | 0 73 | ) 74 | : 0, 75 | icon: , 76 | }, 77 | { 78 | title: "Board", 79 | subtitle: "4", 80 | icon: , 81 | }, 82 | ]; 83 | 84 | return ( 85 |
86 |
87 | {widgetData.map((widgetItem) => ( 88 | 93 | ))} 94 |
95 |
96 | 102 | 108 | 114 |
115 |
116 | 122 | 128 | 134 |
135 |
136 | 137 |
138 |
139 | 140 |
141 |
142 | 143 |
144 |
145 | ); 146 | } 147 | -------------------------------------------------------------------------------- /src/components/modal/index.js: -------------------------------------------------------------------------------- 1 | "use client"; 2 | 3 | import { GlobalContext, initialReportFormData } from "@/context"; 4 | import { Dialog, DialogActions, DialogContent } from "@mui/material"; 5 | import { useContext, useState } from "react"; 6 | import { FiPlus } from "react-icons/fi"; 7 | 8 | export default function CommonModal() { 9 | const [openModal, setOpenModal] = useState(false); 10 | const { 11 | allTasks, 12 | reportFormData, 13 | allReportsData, 14 | setAllReportsData, 15 | setReportFormData, 16 | } = useContext(GlobalContext); 17 | 18 | const formControls = [ 19 | { 20 | name: "name", 21 | type: "text", 22 | placeholder: "Enter report name", 23 | component: "input", 24 | options: [], 25 | }, 26 | { 27 | name: "visitors", 28 | type: "number", 29 | placeholder: "Enter visitors count", 30 | component: "input", 31 | options: [], 32 | }, 33 | { 34 | name: "sales", 35 | type: "number", 36 | placeholder: "Enter number of sales", 37 | component: "input", 38 | options: [], 39 | }, 40 | { 41 | name: "revenue", 42 | type: "number", 43 | placeholder: "Enter revenue", 44 | component: "input", 45 | options: [], 46 | }, 47 | { 48 | name: "task", 49 | type: "", 50 | placeholder: "Select task", 51 | component: "select", 52 | options: 53 | allTasks && allTasks.length 54 | ? allTasks.map((item) => ({ 55 | label: item.title, 56 | value: item.title, 57 | })) 58 | : [], 59 | }, 60 | ]; 61 | 62 | function handleAddNewReport() { 63 | let cpyAllReportsData = [...allReportsData]; 64 | cpyAllReportsData.push({ 65 | id: allReportsData.length + 1, 66 | ...reportFormData, 67 | }); 68 | 69 | setAllReportsData(cpyAllReportsData); 70 | setReportFormData(initialReportFormData); 71 | setOpenModal(false); 72 | localStorage.setItem("allReportsData", JSON.stringify(cpyAllReportsData)); 73 | } 74 | 75 | console.log(allReportsData); 76 | 77 | return ( 78 |
79 | setOpenModal(true)} 81 | className="h-6 w-6 cursor-pointer text-gray-400 dark:text-white" 82 | /> 83 | setOpenModal(false)}> 84 | 85 |
86 | {formControls.map((control) => 87 | control.component === "input" ? ( 88 |
89 | 93 | setReportFormData({ 94 | ...reportFormData, 95 | [control.name]: e.target.value, 96 | }) 97 | } 98 | placeholder={control.placeholder} 99 | type={control.type} 100 | className="pl-3 block h-full w-full rounded-full bg-lightPrimary text-sm font-medium text-navy-700 outline-none placeholder:!text-gray-400 dark:!bg-navy-900 dark:text-white dark:placeholder:!!text-white" 101 | /> 102 |
103 | ) : ( 104 |
105 | 131 |
132 | ) 133 | )} 134 |
135 |
136 | 137 | 143 | 144 |
145 |
146 | ); 147 | } 148 | -------------------------------------------------------------------------------- /src/utils/chart-data.js: -------------------------------------------------------------------------------- 1 | export const barChartDataCategoryOne = [ 2 | { 3 | name: "Bar Chart", 4 | data: [20, 30, 40, 20, 45, 50, 30], 5 | }, 6 | ]; 7 | 8 | export const barChartOptionsCategoryOne = { 9 | chart: { 10 | toolbar: { 11 | show: false, 12 | }, 13 | }, 14 | tooltip: { 15 | style: { 16 | fontSize: "12px", 17 | fontFamily: undefined, 18 | backgroundColor: "#000000", 19 | }, 20 | onDatasetHover: { 21 | style: { 22 | fontSize: "12px", 23 | fontFamily: undefined, 24 | }, 25 | }, 26 | theme: "dark", 27 | }, 28 | xaxis: { 29 | categories: ["00", "04", "08", "12", "14", "16", "18"], 30 | show: false, 31 | labels: { 32 | show: true, 33 | style: { 34 | colors: "#A3AED0", 35 | fontSize: "14px", 36 | fontWeight: "500", 37 | }, 38 | }, 39 | axisBorder: { 40 | show: false, 41 | }, 42 | axisTicks: { 43 | show: false, 44 | }, 45 | }, 46 | yaxis: { 47 | show: false, 48 | color: "black", 49 | labels: { 50 | show: true, 51 | style: { 52 | colors: "#CBD5E0", 53 | fontSize: "14px", 54 | }, 55 | }, 56 | }, 57 | grid: { 58 | show: false, 59 | strokeDashArray: 5, 60 | yaxis: { 61 | lines: { 62 | show: true, 63 | }, 64 | }, 65 | xaxis: { 66 | lines: { 67 | show: false, 68 | }, 69 | }, 70 | }, 71 | fill: { 72 | type: "gradient", 73 | gradient: { 74 | type: "vertical", 75 | shadeIntensity: 1, 76 | opacityFrom: 0.7, 77 | opacityTo: 0.9, 78 | colorStops: [ 79 | [ 80 | { 81 | offset: 0, 82 | color: "#FF9B05", 83 | opacity: 1, 84 | }, 85 | { 86 | offset: 100, 87 | color: "#FFC46B", 88 | 89 | opacity: 0.8, 90 | }, 91 | ], 92 | ], 93 | }, 94 | }, 95 | dataLabels: { 96 | enabled: false, 97 | }, 98 | plotOptions: { 99 | bar: { 100 | borderRadius: 10, 101 | columnWidth: "40px", 102 | }, 103 | }, 104 | }; 105 | 106 | export const pieChartOptions = { 107 | labels: ["One", "Two", "Three"], 108 | colors: ["#FF9B05", "#FFC46B", "#EFF4FB"], 109 | chart: { 110 | width: "50px", 111 | }, 112 | states: { 113 | hover: { 114 | filter: { 115 | type: "none", 116 | }, 117 | }, 118 | }, 119 | legend: { 120 | show: false, 121 | }, 122 | dataLabels: { 123 | enabled: false, 124 | }, 125 | hover: { mode: null }, 126 | plotOptions: { 127 | donut: { 128 | expandOnClick: false, 129 | donut: { 130 | labels: { 131 | show: false, 132 | }, 133 | }, 134 | }, 135 | }, 136 | fill: { 137 | colors: ["#FF9B05", "#FFC46B", "#EFF4FB"], 138 | }, 139 | tooltip: { 140 | enabled: true, 141 | theme: "dark", 142 | style: { 143 | fontSize: "12px", 144 | fontFamily: undefined, 145 | backgroundColor: "#000000", 146 | }, 147 | }, 148 | }; 149 | 150 | export const pieChartData = [63, 25, 12]; 151 | 152 | export const barChartDataCategoryTwo = [ 153 | { 154 | name: "PRODUCT A", 155 | data: [400, 370, 330, 390, 320, 350, 360, 320, 380], 156 | color: "#FF9B05", 157 | }, 158 | { 159 | name: "PRODUCT B", 160 | data: [400, 370, 330, 390, 320, 350, 360, 320, 380], 161 | color: "#FFC46B", 162 | }, 163 | { 164 | name: "PRODUCT C", 165 | data: [400, 370, 330, 390, 320, 350, 360, 320, 380], 166 | color: "#EFF4FB", 167 | }, 168 | ]; 169 | 170 | export const barChartOptionsCategoryTwo = { 171 | chart: { 172 | stacked: true, 173 | toolbar: { 174 | show: false, 175 | }, 176 | }, 177 | // colors:['#ff3322','#faf'] 178 | tooltip: { 179 | style: { 180 | fontSize: "12px", 181 | fontFamily: undefined, 182 | backgroundColor: "#000000", 183 | }, 184 | theme: "dark", 185 | onDatasetHover: { 186 | style: { 187 | fontSize: "12px", 188 | fontFamily: undefined, 189 | }, 190 | }, 191 | }, 192 | xaxis: { 193 | categories: ["17", "18", "19", "20", "21", "22", "23", "24", "25"], 194 | show: false, 195 | labels: { 196 | show: true, 197 | style: { 198 | colors: "#A3AED0", 199 | fontSize: "14px", 200 | fontWeight: "500", 201 | }, 202 | }, 203 | axisBorder: { 204 | show: false, 205 | }, 206 | axisTicks: { 207 | show: false, 208 | }, 209 | }, 210 | yaxis: { 211 | show: false, 212 | color: "black", 213 | labels: { 214 | show: false, 215 | style: { 216 | colors: "#A3AED0", 217 | fontSize: "14px", 218 | fontWeight: "500", 219 | }, 220 | }, 221 | }, 222 | 223 | grid: { 224 | borderColor: "rgba(163, 174, 208, 0.3)", 225 | show: true, 226 | yaxis: { 227 | lines: { 228 | show: false, 229 | opacity: 0.5, 230 | }, 231 | }, 232 | row: { 233 | opacity: 0.5, 234 | }, 235 | xaxis: { 236 | lines: { 237 | show: false, 238 | }, 239 | }, 240 | }, 241 | fill: { 242 | type: "solid", 243 | colors: ["#5E37FF", "#6AD2FF", "#E1E9F8"], 244 | }, 245 | legend: { 246 | show: false, 247 | }, 248 | colors: ["#5E37FF", "#6AD2FF", "#E1E9F8"], 249 | dataLabels: { 250 | enabled: false, 251 | }, 252 | plotOptions: { 253 | bar: { 254 | borderRadius: 10, 255 | columnWidth: "20px", 256 | }, 257 | }, 258 | }; 259 | 260 | export const lineChartData = [ 261 | { 262 | name: "Profit", 263 | data: [30, 40, 24, 46, 20, 46], 264 | color: "#FF9B05", 265 | }, 266 | { 267 | name: "Revenue", 268 | data: [50, 64, 48, 66, 49, 68], 269 | color: "#FFC46B", 270 | }, 271 | ]; 272 | 273 | export const lineChartOptions = { 274 | legend: { 275 | show: false, 276 | }, 277 | 278 | theme: { 279 | mode: "light", 280 | }, 281 | chart: { 282 | type: "line", 283 | 284 | toolbar: { 285 | show: false, 286 | }, 287 | }, 288 | 289 | dataLabels: { 290 | enabled: false, 291 | }, 292 | stroke: { 293 | curve: "smooth", 294 | }, 295 | 296 | tooltip: { 297 | style: { 298 | fontSize: "12px", 299 | fontFamily: undefined, 300 | backgroundColor: "#000000", 301 | }, 302 | theme: "dark", 303 | x: { 304 | format: "dd/MM/yy HH:mm", 305 | }, 306 | }, 307 | grid: { 308 | show: false, 309 | }, 310 | xaxis: { 311 | axisBorder: { 312 | show: false, 313 | }, 314 | axisTicks: { 315 | show: false, 316 | }, 317 | labels: { 318 | style: { 319 | colors: "#A3AED0", 320 | fontSize: "12px", 321 | fontWeight: "500", 322 | }, 323 | }, 324 | type: "text", 325 | range: undefined, 326 | categories: ["SEP", "OCT", "NOV", "DEC", "JAN", "FEB"], 327 | }, 328 | 329 | yaxis: { 330 | show: false, 331 | }, 332 | }; 333 | 334 | export const areaChartData = [ 335 | { 336 | name: "series1", 337 | data: [31, 40, 28, 51, 42, 109], 338 | color: "#FFC46B", 339 | }, 340 | { 341 | name: "series2", 342 | data: [11, 32, 45, 32, 34, 52], 343 | color: "#FF9B05", 344 | }, 345 | ]; 346 | 347 | export const areaChartDataOptions = { 348 | legend: { 349 | show: false, 350 | }, 351 | 352 | theme: { 353 | mode: "light", 354 | }, 355 | chart: { 356 | type: "line", 357 | 358 | toolbar: { 359 | show: false, 360 | }, 361 | }, 362 | 363 | dataLabels: { 364 | enabled: false, 365 | }, 366 | stroke: { 367 | curve: "smooth", 368 | }, 369 | 370 | tooltip: { 371 | style: { 372 | fontSize: "12px", 373 | fontFamily: undefined, 374 | backgroundColor: "#000000", 375 | }, 376 | theme: "dark", 377 | x: { 378 | format: "dd/MM/yy HH:mm", 379 | }, 380 | }, 381 | grid: { 382 | show: false, 383 | }, 384 | xaxis: { 385 | axisBorder: { 386 | show: false, 387 | }, 388 | axisTicks: { 389 | show: false, 390 | }, 391 | labels: { 392 | style: { 393 | colors: "#A3AED0", 394 | fontSize: "12px", 395 | fontWeight: "500", 396 | }, 397 | }, 398 | type: "text", 399 | range: undefined, 400 | categories: ["SEP", "OCT", "NOV", "DEC", "JAN", "FEB"], 401 | }, 402 | 403 | yaxis: { 404 | show: false, 405 | }, 406 | }; 407 | 408 | export const mixedChartData = [ 409 | { 410 | name: "TEAM A", 411 | type: "column", 412 | data: [23, 11, 22, 27, 13, 22], 413 | color: "#FF9B05", 414 | }, 415 | { 416 | name: "TEAM B", 417 | type: "area", 418 | data: [44, 55, 41, 67, 22, 43], 419 | color: "#EFF4FB", 420 | }, 421 | { 422 | name: "TEAM C", 423 | type: "line", 424 | data: [30, 25, 36, 30, 45, 35], 425 | color: "#FFC46B", 426 | }, 427 | ]; 428 | 429 | export const mixedChartDataOptions = { 430 | legend: { 431 | show: false, 432 | }, 433 | 434 | theme: { 435 | mode: "light", 436 | }, 437 | chart: { 438 | type: "line", 439 | 440 | toolbar: { 441 | show: false, 442 | }, 443 | }, 444 | 445 | dataLabels: { 446 | enabled: false, 447 | }, 448 | stroke: { 449 | curve: "smooth", 450 | }, 451 | 452 | tooltip: { 453 | style: { 454 | fontSize: "12px", 455 | fontFamily: undefined, 456 | backgroundColor: "#000000", 457 | }, 458 | theme: "dark", 459 | x: { 460 | format: "dd/MM/yy HH:mm", 461 | }, 462 | }, 463 | grid: { 464 | show: false, 465 | }, 466 | xaxis: { 467 | axisBorder: { 468 | show: false, 469 | }, 470 | axisTicks: { 471 | show: false, 472 | }, 473 | labels: { 474 | style: { 475 | colors: "#A3AED0", 476 | fontSize: "12px", 477 | fontWeight: "500", 478 | }, 479 | }, 480 | type: "text", 481 | range: undefined, 482 | categories: ["SEP", "OCT", "NOV", "DEC", "JAN", "FEB"], 483 | }, 484 | 485 | yaxis: { 486 | show: false, 487 | }, 488 | }; 489 | --------------------------------------------------------------------------------